Class: ObservationMatrixRow
- Inherits:
-
ApplicationRecord
- Object
- ActiveRecord::Base
- ApplicationRecord
- ObservationMatrixRow
- Includes:
- Housekeeping, Shared::Citations, Shared::Identifiers, Shared::IsData, Shared::Notes, Shared::Tags
- Defined in:
- app/models/observation_matrix_row.rb
Overview
A ObservationMatrixRow is a row in an Observation matrix representing an Otu or a CollectionObject
Defined Under Namespace
Classes: Autocomplete
Instance Attribute Summary collapse
-
#cached_observation_matrix_row_item_id ⇒ Integer
If the column item is derived from a ::Single::<FOO> subclass, the id of that instance.
-
#collection_object_id ⇒ Integer?
Id of the collecton_object or nil.
-
#name ⇒ String?
TEMPORARY value.
-
#observation_matrix_id ⇒ Integer
Id of the matrix the row is in.
-
#otu_id ⇒ Integer?
Id of the OTU or nil.
-
#position ⇒ Integer
From acts as list.
-
#reference_count ⇒ Integer
Indicates the total number of times this row is referened via some row_item.
-
#row_object_global_id ⇒ Object
! if row_object changes (it never should, just create/destroy) this memoization is bad.
Class Method Summary collapse
-
.sort(array) ⇒ Object
True incrementally sort the supplied ids.
Instance Method Summary collapse
- #current_otu ⇒ Object
- #current_taxon_name ⇒ Object
-
#next_row ⇒ Object
TODO: belong in helpers.
- #observation_matrix_columns ⇒ Object
-
#observations ⇒ Scope
All the observations in this row, ordered (but not gathered).
- #otu_and_collection_object_blank ⇒ Object private
- #otu_and_collection_object_given ⇒ Object private
- #previous_row ⇒ Object
- #row_object ⇒ Object
- #row_object_class_name ⇒ Object
- #set_reference_count ⇒ Object
Methods included from Shared::IsData
#errors_excepting, #full_error_messages_excepting, #identical, #is_community?, #is_destroyable?, #is_editable?, #is_in_use?, #is_in_users_projects?, #metamorphosize, #similar
Methods included from Shared::Notes
#concatenated_notes_string, #reject_notes
Methods included from Shared::Tags
#reject_tags, #tag_with, #tagged?, #tagged_with?
Methods included from Shared::Identifiers
#identified?, #next_by_identifier, #previous_by_identifier, #reject_identifiers
Methods included from Shared::Citations
#cited?, #mark_citations_for_destruction, #nomenclature_date, #origin_citation_source_id, #reject_citations, #requires_citation?, #sources_by_topic_id
Methods included from Housekeeping
#has_polymorphic_relationship?
Methods inherited from ApplicationRecord
Instance Attribute Details
#cached_observation_matrix_row_item_id ⇒ Integer
Returns if the column item is derived from a ::Single::<FOO> subclass, the id of that instance.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'app/models/observation_matrix_row.rb', line 29 class ObservationMatrixRow < ApplicationRecord include Housekeeping include Shared::Citations include Shared::Identifiers include Shared::Tags include Shared::Notes include Shared::IsData acts_as_list scope: [:observation_matrix_id, :project_id] belongs_to :otu, inverse_of: :observation_matrix_rows belongs_to :collection_object, inverse_of: :observation_matrix_rows belongs_to :observation_matrix, inverse_of: :observation_matrix_rows attr_accessor :row_object_global_id #list of rows with otu_ids in format '1|3|5' scope :with_otu_ids, -> (otu_ids) { where('(observation_matrix_rows.otu_id IN (?))', otu_ids.to_s.split('|').map(&:to_i)).order(:position) } def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end after_initialize :set_reference_count validates_presence_of :observation_matrix validate :otu_and_collection_object_blank validate :otu_and_collection_object_given validates_uniqueness_of :otu_id, scope: [:observation_matrix_id], if: -> {!otu_id.nil?} validates_uniqueness_of :collection_object_id, scope: [:observation_matrix_id], if: -> {!collection_object_id.nil?} # @param array [Array] # @return true # incrementally sort the supplied ids def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end def set_reference_count self.reference_count ||= 0 end def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end # ! if row_object changes (it never should, just create/destroy) this memoization is bad def row_object_global_id @row_object_global_id ||= row_object.to_global_id.to_s @row_object_global_id end def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end # TODO: belong in helpers def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end # @return [Scope] # all the observations in this row, ordered (but not gathered) def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end private def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end end |
#collection_object_id ⇒ Integer?
Returns id of the collecton_object or nil.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'app/models/observation_matrix_row.rb', line 29 class ObservationMatrixRow < ApplicationRecord include Housekeeping include Shared::Citations include Shared::Identifiers include Shared::Tags include Shared::Notes include Shared::IsData acts_as_list scope: [:observation_matrix_id, :project_id] belongs_to :otu, inverse_of: :observation_matrix_rows belongs_to :collection_object, inverse_of: :observation_matrix_rows belongs_to :observation_matrix, inverse_of: :observation_matrix_rows attr_accessor :row_object_global_id #list of rows with otu_ids in format '1|3|5' scope :with_otu_ids, -> (otu_ids) { where('(observation_matrix_rows.otu_id IN (?))', otu_ids.to_s.split('|').map(&:to_i)).order(:position) } def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end after_initialize :set_reference_count validates_presence_of :observation_matrix validate :otu_and_collection_object_blank validate :otu_and_collection_object_given validates_uniqueness_of :otu_id, scope: [:observation_matrix_id], if: -> {!otu_id.nil?} validates_uniqueness_of :collection_object_id, scope: [:observation_matrix_id], if: -> {!collection_object_id.nil?} # @param array [Array] # @return true # incrementally sort the supplied ids def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end def set_reference_count self.reference_count ||= 0 end def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end # ! if row_object changes (it never should, just create/destroy) this memoization is bad def row_object_global_id @row_object_global_id ||= row_object.to_global_id.to_s @row_object_global_id end def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end # TODO: belong in helpers def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end # @return [Scope] # all the observations in this row, ordered (but not gathered) def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end private def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end end |
#name ⇒ String?
Returns TEMPORARY value. Allows for a temporary generated/custom name for the row, useful for example when generating labels for phylogenetic trees. This value is NOT persisted and NOT intended for provenance purposes, it is strictly utilitarian. Consider using custom OTUs to track provenance.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'app/models/observation_matrix_row.rb', line 29 class ObservationMatrixRow < ApplicationRecord include Housekeeping include Shared::Citations include Shared::Identifiers include Shared::Tags include Shared::Notes include Shared::IsData acts_as_list scope: [:observation_matrix_id, :project_id] belongs_to :otu, inverse_of: :observation_matrix_rows belongs_to :collection_object, inverse_of: :observation_matrix_rows belongs_to :observation_matrix, inverse_of: :observation_matrix_rows attr_accessor :row_object_global_id #list of rows with otu_ids in format '1|3|5' scope :with_otu_ids, -> (otu_ids) { where('(observation_matrix_rows.otu_id IN (?))', otu_ids.to_s.split('|').map(&:to_i)).order(:position) } def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end after_initialize :set_reference_count validates_presence_of :observation_matrix validate :otu_and_collection_object_blank validate :otu_and_collection_object_given validates_uniqueness_of :otu_id, scope: [:observation_matrix_id], if: -> {!otu_id.nil?} validates_uniqueness_of :collection_object_id, scope: [:observation_matrix_id], if: -> {!collection_object_id.nil?} # @param array [Array] # @return true # incrementally sort the supplied ids def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end def set_reference_count self.reference_count ||= 0 end def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end # ! if row_object changes (it never should, just create/destroy) this memoization is bad def row_object_global_id @row_object_global_id ||= row_object.to_global_id.to_s @row_object_global_id end def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end # TODO: belong in helpers def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end # @return [Scope] # all the observations in this row, ordered (but not gathered) def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end private def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end end |
#observation_matrix_id ⇒ Integer
Returns id of the matrix the row is in.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'app/models/observation_matrix_row.rb', line 29 class ObservationMatrixRow < ApplicationRecord include Housekeeping include Shared::Citations include Shared::Identifiers include Shared::Tags include Shared::Notes include Shared::IsData acts_as_list scope: [:observation_matrix_id, :project_id] belongs_to :otu, inverse_of: :observation_matrix_rows belongs_to :collection_object, inverse_of: :observation_matrix_rows belongs_to :observation_matrix, inverse_of: :observation_matrix_rows attr_accessor :row_object_global_id #list of rows with otu_ids in format '1|3|5' scope :with_otu_ids, -> (otu_ids) { where('(observation_matrix_rows.otu_id IN (?))', otu_ids.to_s.split('|').map(&:to_i)).order(:position) } def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end after_initialize :set_reference_count validates_presence_of :observation_matrix validate :otu_and_collection_object_blank validate :otu_and_collection_object_given validates_uniqueness_of :otu_id, scope: [:observation_matrix_id], if: -> {!otu_id.nil?} validates_uniqueness_of :collection_object_id, scope: [:observation_matrix_id], if: -> {!collection_object_id.nil?} # @param array [Array] # @return true # incrementally sort the supplied ids def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end def set_reference_count self.reference_count ||= 0 end def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end # ! if row_object changes (it never should, just create/destroy) this memoization is bad def row_object_global_id @row_object_global_id ||= row_object.to_global_id.to_s @row_object_global_id end def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end # TODO: belong in helpers def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end # @return [Scope] # all the observations in this row, ordered (but not gathered) def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end private def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end end |
#otu_id ⇒ Integer?
Returns id of the OTU or nil.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'app/models/observation_matrix_row.rb', line 29 class ObservationMatrixRow < ApplicationRecord include Housekeeping include Shared::Citations include Shared::Identifiers include Shared::Tags include Shared::Notes include Shared::IsData acts_as_list scope: [:observation_matrix_id, :project_id] belongs_to :otu, inverse_of: :observation_matrix_rows belongs_to :collection_object, inverse_of: :observation_matrix_rows belongs_to :observation_matrix, inverse_of: :observation_matrix_rows attr_accessor :row_object_global_id #list of rows with otu_ids in format '1|3|5' scope :with_otu_ids, -> (otu_ids) { where('(observation_matrix_rows.otu_id IN (?))', otu_ids.to_s.split('|').map(&:to_i)).order(:position) } def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end after_initialize :set_reference_count validates_presence_of :observation_matrix validate :otu_and_collection_object_blank validate :otu_and_collection_object_given validates_uniqueness_of :otu_id, scope: [:observation_matrix_id], if: -> {!otu_id.nil?} validates_uniqueness_of :collection_object_id, scope: [:observation_matrix_id], if: -> {!collection_object_id.nil?} # @param array [Array] # @return true # incrementally sort the supplied ids def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end def set_reference_count self.reference_count ||= 0 end def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end # ! if row_object changes (it never should, just create/destroy) this memoization is bad def row_object_global_id @row_object_global_id ||= row_object.to_global_id.to_s @row_object_global_id end def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end # TODO: belong in helpers def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end # @return [Scope] # all the observations in this row, ordered (but not gathered) def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end private def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end end |
#position ⇒ Integer
Returns from acts as list.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'app/models/observation_matrix_row.rb', line 29 class ObservationMatrixRow < ApplicationRecord include Housekeeping include Shared::Citations include Shared::Identifiers include Shared::Tags include Shared::Notes include Shared::IsData acts_as_list scope: [:observation_matrix_id, :project_id] belongs_to :otu, inverse_of: :observation_matrix_rows belongs_to :collection_object, inverse_of: :observation_matrix_rows belongs_to :observation_matrix, inverse_of: :observation_matrix_rows attr_accessor :row_object_global_id #list of rows with otu_ids in format '1|3|5' scope :with_otu_ids, -> (otu_ids) { where('(observation_matrix_rows.otu_id IN (?))', otu_ids.to_s.split('|').map(&:to_i)).order(:position) } def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end after_initialize :set_reference_count validates_presence_of :observation_matrix validate :otu_and_collection_object_blank validate :otu_and_collection_object_given validates_uniqueness_of :otu_id, scope: [:observation_matrix_id], if: -> {!otu_id.nil?} validates_uniqueness_of :collection_object_id, scope: [:observation_matrix_id], if: -> {!collection_object_id.nil?} # @param array [Array] # @return true # incrementally sort the supplied ids def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end def set_reference_count self.reference_count ||= 0 end def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end # ! if row_object changes (it never should, just create/destroy) this memoization is bad def row_object_global_id @row_object_global_id ||= row_object.to_global_id.to_s @row_object_global_id end def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end # TODO: belong in helpers def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end # @return [Scope] # all the observations in this row, ordered (but not gathered) def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end private def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end end |
#reference_count ⇒ Integer
Indicates the total number of times this row is referened via some row_item
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'app/models/observation_matrix_row.rb', line 29 class ObservationMatrixRow < ApplicationRecord include Housekeeping include Shared::Citations include Shared::Identifiers include Shared::Tags include Shared::Notes include Shared::IsData acts_as_list scope: [:observation_matrix_id, :project_id] belongs_to :otu, inverse_of: :observation_matrix_rows belongs_to :collection_object, inverse_of: :observation_matrix_rows belongs_to :observation_matrix, inverse_of: :observation_matrix_rows attr_accessor :row_object_global_id #list of rows with otu_ids in format '1|3|5' scope :with_otu_ids, -> (otu_ids) { where('(observation_matrix_rows.otu_id IN (?))', otu_ids.to_s.split('|').map(&:to_i)).order(:position) } def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end after_initialize :set_reference_count validates_presence_of :observation_matrix validate :otu_and_collection_object_blank validate :otu_and_collection_object_given validates_uniqueness_of :otu_id, scope: [:observation_matrix_id], if: -> {!otu_id.nil?} validates_uniqueness_of :collection_object_id, scope: [:observation_matrix_id], if: -> {!collection_object_id.nil?} # @param array [Array] # @return true # incrementally sort the supplied ids def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end def set_reference_count self.reference_count ||= 0 end def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end # ! if row_object changes (it never should, just create/destroy) this memoization is bad def row_object_global_id @row_object_global_id ||= row_object.to_global_id.to_s @row_object_global_id end def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end # TODO: belong in helpers def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end # @return [Scope] # all the observations in this row, ordered (but not gathered) def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end private def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end end |
#row_object_global_id ⇒ Object
! if row_object changes (it never should, just create/destroy) this memoization is bad
87 88 89 |
# File 'app/models/observation_matrix_row.rb', line 87 def row_object_global_id @row_object_global_id end |
Class Method Details
.sort(array) ⇒ Object
Returns true incrementally sort the supplied ids.
64 65 66 67 68 69 |
# File 'app/models/observation_matrix_row.rb', line 64 def self.sort(array) array.each_with_index do |id, index| ObservationMatrixRow.where(id: id).update_all(position: index + 1) end true end |
Instance Method Details
#current_otu ⇒ Object
107 108 109 110 111 112 113 114 |
# File 'app/models/observation_matrix_row.rb', line 107 def current_otu case row_object_class_name when 'Otu' row_object when 'CollectionObject' row_object.current_otu end end |
#current_taxon_name ⇒ Object
98 99 100 101 102 103 104 105 |
# File 'app/models/observation_matrix_row.rb', line 98 def current_taxon_name case row_object_class_name when 'Otu' row_object.taxon_name when 'CollectionObject' row_object.current_taxon_name end end |
#next_row ⇒ Object
TODO: belong in helpers
117 118 119 |
# File 'app/models/observation_matrix_row.rb', line 117 def next_row observation_matrix.observation_matrix_rows.where("position > ?", position).order(:position).first end |
#observation_matrix_columns ⇒ Object
48 49 50 |
# File 'app/models/observation_matrix_row.rb', line 48 def observation_matrix_columns ObservationMatrixColumn.where(observation_matrix_id: observation_matrix_id) end |
#observations ⇒ Scope
Returns all the observations in this row, ordered (but not gathered).
127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 |
# File 'app/models/observation_matrix_row.rb', line 127 def observations t = Observation.arel_table a = t.alias b = t.project(a[Arel.star]).from(a) c = ObservationMatrixColumn.arel_table d = Descriptor.arel_table f = d.project(d[Arel.star]).from(d) # Descriptors in the matrix f = f.join(c, Arel::Nodes::InnerJoin) .on( d[:id].eq(c[:descriptor_id]). and( c[:observation_matrix_id].eq(observation_matrix_id) ) ).order(c[:position]).as('a1') # TODO: when polymorphic this whole method will collapse and # not require this fork x = nil case row_object_class_name when 'Otu' x = a[:otu_id].eq(otu_id) when 'CollectionObject' x = a[:collection_object_id].eq(collection_object_id) else raise end # Observations from those descriptros b = b.join(f, Arel::Nodes::InnerJoin) .on( a[:descriptor_id].eq(f[:id]). and(x) ).as('a2') ::Observation.joins(Arel::Nodes::InnerJoin.new(b, Arel::Nodes::On.new(b['id'].eq(t['id'])))) end |
#otu_and_collection_object_blank ⇒ Object (private)
169 170 171 172 173 |
# File 'app/models/observation_matrix_row.rb', line 169 def otu_and_collection_object_blank if otu_id.nil? && collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object!') end end |
#otu_and_collection_object_given ⇒ Object (private)
175 176 177 178 179 |
# File 'app/models/observation_matrix_row.rb', line 175 def otu_and_collection_object_given if !otu_id.nil? && !collection_object_id.nil? errors.add(:base, 'Specify otu OR collection object, not both!') end end |
#previous_row ⇒ Object
121 122 123 |
# File 'app/models/observation_matrix_row.rb', line 121 def previous_row observation_matrix.observation_matrix_rows.where("position < ?", position).order('position DESC').first end |
#row_object ⇒ Object
75 76 77 78 79 80 81 82 83 84 |
# File 'app/models/observation_matrix_row.rb', line 75 def row_object # exit as quickly as possible if o = otu return o end if c = collection_object return c end nil end |
#row_object_class_name ⇒ Object
92 93 94 95 96 |
# File 'app/models/observation_matrix_row.rb', line 92 def row_object_class_name return 'Otu' if otu_id return 'CollectionObject' if collection_object_id raise end |
#set_reference_count ⇒ Object
71 72 73 |
# File 'app/models/observation_matrix_row.rb', line 71 def set_reference_count self.reference_count ||= 0 end |