Class: VORuby::ActiveVotable::ActiveVotable
- Inherits:
-
ActiveRecord::Base
- Object
- ActiveRecord::Base
- VORuby::ActiveVotable::ActiveVotable
- Defined in:
- lib/voruby/active_votable/active_votable.rb
Overview
ActiveVotable is a simple, but hopefully useful, database-backed VOTable parser. It uses LibXML’s SAX parser to extract the fields and data of a VOTable and loads those fields into a database table. This allows all the power of a full database manager + ActiveRecord to be used in searching and manipulating the VOTable. It assumes that the VOTable has one resource with one table and that the table is encoded as text and binary.
ActiveVotable.establish_connection(
:adapter => 'postgresql'
:database => 'votables'
:host => 'localhost'
:username => 'dbuser'
:password => 'dbpassword')
ActiveVotable.build('test/active_votable/test.vot') do |vot|
records = vot.find(:all, :conditions => ['survey LIKE ?', 'Deep Lens Survey'], :order => 'id')
records = vot.page(10)
vot.foreach_page do |page_num, records|
puts "Page #{page_num}:"
records.each do |rec|
puts rec.inspect
end
end
Constant Summary collapse
- DATATYPE_CONVERSIONS =
{ 'boolean' => :boolean, 'bit' => :integer, 'unsignedByte' => :integer, 'short' => :integer, 'int' => :integer, 'long' => :integer, 'char' => :string, 'unicodeChar' => :string, 'float' => :float, 'double' => :float, 'floatComplex' => :string, 'doubleComplex' => :string }
- @@end_of_cell =
true
- @@arow =
[]
- @@ordered_columns =
[]
- @@items_per_page =
20
- @@actions =
{ :on_start_element => { 'FIELD' => Proc.new { |name, attrs| field_name = ActiveVotable.columnize(attrs['name'] || attrs['ID'] || "unknown_column_#{rand(1000000)}") field_name = 'record_id' if field_name == 'id' field_type = ActiveVotable.column_type(attrs['datatype'] || 'char', attrs['arraysize']) @@ordered_columns << {:name => field_name, :type => field_type} ActiveRecord::Schema.define do add_column(ActiveVotable.table_name(), field_name, field_type) end }, 'TD' => Proc.new{ |name, attrs| @@end_of_cell = false } }, :on_end_element => { 'TR' => Proc.new { |name| row_def = {:resource_num => 1, :table_num => 1} @@ordered_columns.each_index do |i| row_def[@@ordered_columns[i][:name]] = cast(@@arow[i], @@ordered_columns[i][:type]) end ActiveVotable.create(row_def) @@arow = [] }, 'TD' => Proc.new { |name| @@end_of_cell = true } }, :on_characters => Proc.new { |chars| @@arow << chars if !@@end_of_cell }, :on_cdata_block => Proc.new{ |cdata| @@arow << cdata if !@@end_of_cell # not sure if this is safe } }
Class Method Summary collapse
-
.build(src, tbl_name = nil, &block) ⇒ Object
Parse a VOTable into a database table.
-
.cast(value, type) ⇒ Object
Given one of the types specified in ActiveRecord::ConnectionAdapters::TableDefinition.column casts a string into a corresponding value.
-
.column_type(datatype, arraysize) ⇒ Object
Converts a VOTable datatype into a corresponding database column type.
-
.columnize(name) ⇒ Object
Converts a VOTable name or ID into a (hopefully) valid database column name.
-
.create_basic_schema ⇒ Object
All parsed VOTables will have a standard set of columns which are created by this method.
-
.drop ⇒ Object
Erase the table out of the database.
-
.establish_connection(config) ⇒ Object
Establish a connection to the database.
-
.find(*args) ⇒ Object
Works exactly as ActiveRecord.find() except that an additional option–:page–may be passed in.
-
.foreach_page(&block) ⇒ Object
Iterate through each page in the VOTable.
-
.foreach_record(&block) ⇒ Object
Iterate through each record in the votable.
-
.items_per_page ⇒ Object
Get the number of records per page.
-
.items_per_page=(num) ⇒ Object
Set the number of records per page for use in paging results.
-
.page(page = 1) ⇒ Object
Retrieve the specified page.
-
.parse ⇒ Object
Parse the VOTable.
-
.parser ⇒ Object
Get the XML parser in use.
-
.parser=(parser) ⇒ Object
Set the XML parser to use.
-
.src ⇒ Object
Get the file name of the source VOTable.
-
.src=(src) ⇒ Object
Set the file name of the source VOTable.
Class Method Details
.build(src, tbl_name = nil, &block) ⇒ Object
Parse a VOTable into a database table. If no table is specified, one will be created with the signature ‘votable_timestamp_randomnumber’. If the optional block is provided, ActiveVotable.drop() will be called automatically.
- src:
-
The name of the VOTable file.
- tbl_name:
-
The name of the database table to dump the VOTable into.
154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 |
# File 'lib/voruby/active_votable/active_votable.rb', line 154 def self.build(src, tbl_name=nil, &block) if block build(src, tbl_name) block.call(self) drop() else ActiveVotable.src = src ActiveVotable.parser = VOTableExtractor.new(src, @@actions) set_table_name(tbl_name || "votable_#{Time.now.to_i}_#{rand(1000000)}") create_basic_schema() parse() return self end end |
.cast(value, type) ⇒ Object
Given one of the types specified in ActiveRecord::ConnectionAdapters::TableDefinition.column casts a string into a corresponding value.
253 254 255 256 257 258 259 260 261 262 |
# File 'lib/voruby/active_votable/active_votable.rb', line 253 def self.cast(value, type) case type when :integer then value.to_i when :float then value.to_f when :string then value when :boolean (value != 'false' and value != '0') ? true: false else value end end |
.column_type(datatype, arraysize) ⇒ Object
Converts a VOTable datatype into a corresponding database column type. Typically you’ll never use this directly.
243 244 245 246 247 248 249 |
# File 'lib/voruby/active_votable/active_votable.rb', line 243 def self.column_type(datatype, arraysize) if arraysize :string else DATATYPE_CONVERSIONS[datatype] || :string end end |
.columnize(name) ⇒ Object
Converts a VOTable name or ID into a (hopefully) valid database column name. Typically you’ll never use this directly.
233 234 235 236 237 238 |
# File 'lib/voruby/active_votable/active_votable.rb', line 233 def self.columnize(name) name = name.downcase name['-'] = '_' if name =~ /-/ name[/\W+/] = '_' if name =~ /\W+/ name end |
.create_basic_schema ⇒ Object
All parsed VOTables will have a standard set of columns which are created by this method. Typically you’ll never use this directly.
212 213 214 215 216 217 218 219 220 221 |
# File 'lib/voruby/active_votable/active_votable.rb', line 212 def self.create_basic_schema ActiveRecord::Schema.define do create_table ActiveVotable::table_name(), :primary_key => 'id' do |t| t.column :resource_num, :integer, :null => false, :default => 1 t.column :table_num, :integer, :null => false, :default => 1 end add_index ActiveVotable::table_name(), [:resource_num, :table_num] end end |
.drop ⇒ Object
Erase the table out of the database.
224 225 226 227 228 |
# File 'lib/voruby/active_votable/active_votable.rb', line 224 def self.drop ActiveRecord::Schema.define do drop_table ActiveVotable::table_name end end |
.establish_connection(config) ⇒ Object
Establish a connection to the database. See ActiveRecord::Base.establish_connection() for further details.
266 267 268 |
# File 'lib/voruby/active_votable/active_votable.rb', line 266 def self.establish_connection(config) self.superclass.establish_connection(config) end |
.find(*args) ⇒ Object
Works exactly as ActiveRecord.find() except that an additional option–:page–may be passed in. In that case :limit and :offset are ignored.
273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 |
# File 'lib/voruby/active_votable/active_votable.rb', line 273 def self.find(*args) = (args) if .has_key?(:page) [:limit] = items_per_page() [:offset] = items_per_page() * ([:page] - 1) .delete(:page) end () set_readonly_option!() case args.first when :first then find_initial() when :all then find_every() else find_from_ids(args, ) end end |
.foreach_page(&block) ⇒ Object
Iterate through each page in the VOTable. The block receives the page number and the list of records.
301 302 303 304 305 306 307 |
# File 'lib/voruby/active_votable/active_votable.rb', line 301 def self.foreach_page(&block) num_pages = (count().to_f / items_per_page().to_f).ceil() (1..num_pages).each do |page_num| block.call(page_num, page(page_num)) end end |
.foreach_record(&block) ⇒ Object
Iterate through each record in the votable.
310 311 312 313 314 |
# File 'lib/voruby/active_votable/active_votable.rb', line 310 def self.foreach_record(&block) find(:all, :order => 'id').each do |record| block.call(record) end end |
.items_per_page ⇒ Object
Get the number of records per page.
199 200 201 |
# File 'lib/voruby/active_votable/active_votable.rb', line 199 def self.items_per_page @@items_per_page end |
.items_per_page=(num) ⇒ Object
Set the number of records per page for use in paging results.
194 195 196 |
# File 'lib/voruby/active_votable/active_votable.rb', line 194 def self.items_per_page=(num) @@items_per_page = num end |
.page(page = 1) ⇒ Object
Retrieve the specified page. Applies to all rows in the VOTable.
294 295 296 |
# File 'lib/voruby/active_votable/active_votable.rb', line 294 def self.page(page=1) find(:all, :order => 'id', :page => page) end |
.parse ⇒ Object
Parse the VOTable. Called automatically when you used ActiveVotable.build(). Typically you’ll never use this directly.
205 206 207 |
# File 'lib/voruby/active_votable/active_votable.rb', line 205 def self.parse parser().parse() end |
.parser ⇒ Object
Get the XML parser in use.
189 190 191 |
# File 'lib/voruby/active_votable/active_votable.rb', line 189 def self.parser @@parser end |
.parser=(parser) ⇒ Object
Set the XML parser to use. Must of type VOTableExtractor. Typically you’ll never use this directly.
184 185 186 |
# File 'lib/voruby/active_votable/active_votable.rb', line 184 def self.parser=(parser) @@parser = parser end |
.src ⇒ Object
Get the file name of the source VOTable.
178 179 180 |
# File 'lib/voruby/active_votable/active_votable.rb', line 178 def self.src @@src end |
.src=(src) ⇒ Object
Set the file name of the source VOTable.
173 174 175 |
# File 'lib/voruby/active_votable/active_votable.rb', line 173 def self.src=(src) @@src = src end |