Donnerstag, 7. Juli 2011

Rails Migrations mit Oracle Enhanced Adapter

Da Oracle für verschiedene numerische Datentypen nur den Datentyp NUMBER kennt, kann dies zu Problemen führen, wenn eine Rails-Applikation auf eine bereits bestehende Datenbank zurückgreift. Wird eine neue Tabelle mit Hilfe von Migrations angelegt, werden die Datentypen wie folgt zugewiesen:
 :boolean => number(1)  
 :integer => number(38)  
 :float => number  
 :decimal => decimal  

Sind Integer-Werte in der bestehenden Datenbank mit NUMBER ohne Grössenangabe definiert, werden diese in der Rails-Applikation standardmässig als BigDecimal behandelt. Dies kann sich fehlerhaft auf die Applikation auswirken (Darstellungsprobleme, Vergleichsabfragen etc.).

Um das Problem zu lösen, können verschiedene Ansätze gewählt werden:

Wenn möglich, sollte der Datentyp auf der Datenbank angepasst werden (z.B. NUMBER(12)).
Mit der Option
 emulate_integers_by_column_name  
kann eingestellt werden, dass alle Datenbankfelder, welche auf ID enden, in der Applikation als Fixnum behandelt werden. Dazu kann die Datei config/initializers/oracle_enhanced.rb angelegt und mit folgendem Code abgefüllt werden:
 ActiveRecord::ConnectionAdapters::OracleEnhancedAdapter.emulate_dates_by_column_name = true  

Um die Einstellungen global zu ändern, kann die Methode is_integer_column aus der Klasse OracleEnhancedAdapter überschrieben werden.

Müssen nur spezifische Attribute angepasst werden, können für diese im Model die Getter-Methode überschrieben werden.
 def attr   
  self[:attr].to_i if self[:attr].kinf_of? Numeric   
  self[:attr]  
 end  

Keine Kommentare:

Kommentar veröffentlichen