UNKNOWN_READING = { :total_kwh_consumed_high => nil, :total_kwh_consumed_low => nil, :total_kwh_produced_high => nil, :total_kwh_produced_low => nil, :total_m3_gas_consumed => nil} class Reading < ActiveRecord::Base # Round up with 1 (default) decimals def round_up(number, decimals = 1) factor = 10 ** decimals (number * factor).ceil / factor.to_f end def eql_reading?(reading) self.total_kwh_consumed_high == reading.total_kwh_consumed_high && self.total_kwh_consumed_low == reading.total_kwh_consumed_low && self.total_kwh_produced_high == reading.total_kwh_produced_high && self.total_kwh_produced_low == reading.total_kwh_produced_low && round_up(self.current_kw_consumed) == round_up(reading.current_kw_consumed) && round_up(self.current_kw_produced) == round_up(reading.current_kw_produced) && self.total_m3_gas_consumed == reading.total_m3_gas_consumed && self.high_tarif == reading.high_tarif end # reduce precision to 1 digit behind comma def total_kwh_consumed_high=(kwh) write_attribute(:total_kwh_consumed_high,kwh.round(1)) end # reduce precision to 1 digit behind comma def total_kwh_consumed_low=(kwh) write_attribute(:total_kwh_consumed_low,kwh.round(1)) end # reduce precision to 1 digit behind comma def total_kwh_produced_high=(kwh) write_attribute(:total_kwh_produced_high,kwh.round(1)) end # reduce precision to 1 digit behind comma def total_kwh_produced_low=(kwh) write_attribute(:total_kwh_produced_low,kwh.round(1)) end # calculate difference with another reading # return a hash with differences (self - reading) def diff(reading) if reading { :total_kwh_consumed_high => (self.total_kwh_consumed_high - reading.total_kwh_consumed_high).round(1), :total_kwh_consumed_low => (self.total_kwh_consumed_low - reading.total_kwh_consumed_low).round(1), :total_kwh_produced_high => (self.total_kwh_produced_high - reading.total_kwh_produced_high).round(1), :total_kwh_produced_low => (self.total_kwh_produced_low - reading.total_kwh_produced_low).round(1), :total_m3_gas_consumed => (self.total_m3_gas_consumed - reading.total_m3_gas_consumed).round(3) } else { :total_kwh_consumed_high => self.total_kwh_consumed_high, :total_kwh_consumed_low => self.total_kwh_consumed_low, :total_kwh_produced_high => self.total_kwh_produced_high, :total_kwh_produced_low => self.total_kwh_produced_low, :total_m3_gas_consumed => self.total_m3_gas_consumed } end end # # Class methods # class << self # return readings from beginning of 'from' until end of 'to' def days(from, to) Reading.where("created_at > :begin AND created_at < :end", { :begin => from.to_date.beginning_of_day, :end => to.to_date.end_of_day}) end def day(date) Reading.where("created_at > :begin AND created_at < :end", { :begin => date.to_date.beginning_of_day, :end => date.to_date.end_of_day}) end def in_month(date) hour_start = date.beginning_of_month.beginning_of_day hour_end = date.end_of_month.end_of_day # can't get cost for the future hour_end = Time.now if hour_end > Time.now Reading.where("created_at > :begin AND created_at < :end", { :begin => hour_start, :end => hour_end}) end def max_charge_kwh=(kwh) @@max_charge_kwh = kwh end def max_charge_kwh @@max_charge_kwh end # do not make distinction between high and low consumption/production def consumed_and_produced_for_diff(d) usage_kwh = (d[:total_kwh_consumed_high].nil? || d[:total_kwh_consumed_low].nil?) ? nil : d[:total_kwh_consumed_high] + d[:total_kwh_consumed_low] return_kwh = (d[:total_kwh_produced_high].nil? || d[:total_kwh_produced_low].nil?) ? nil : d[:total_kwh_produced_high] + d[:total_kwh_produced_low] return usage_kwh, return_kwh end # calculate net_consumption (= consumption-production) def net_consumed_high_and_low_for_diff(d) net_consumed_high = (d[:total_kwh_consumed_high].nil? || d[:total_kwh_produced_high].nil?) ? nil : d[:total_kwh_consumed_high]-d[:total_kwh_produced_high] net_consumed_low = (d[:total_kwh_consumed_low].nil? || d[:total_kwh_produced_low].nil?) ? nil : d[:total_kwh_consumed_low]-d[:total_kwh_produced_low] return net_consumed_high, net_consumed_low end def diff_on(date) readings_on = day(date) first = readings_on.first last = readings_on.last if last last.diff(first) else { :total_kwh_consumed_high => 0, :total_kwh_consumed_low => 0, :total_kwh_produced_high => 0, :total_kwh_produced_low => 0, :total_m3_gas_consumed => 0 } end end def diff_between(from_date, to_date) readings_on_days = days(from_date, to_date) first = readings_on_days.first last = readings_on_days.last if last last.diff(first) else { :total_kwh_consumed_high => 0, :total_kwh_consumed_low => 0, :total_kwh_produced_high => 0, :total_kwh_produced_low => 0, :total_m3_gas_consumed => 0 } end end def diff_in_month(date) hour_start = date.beginning_of_month.beginning_of_day hour_end = date.end_of_month.end_of_day # can't get cost for the future hour_end = Time.now if hour_end > Time.now readings_in_month = Reading.where("created_at > :begin AND created_at < :end", { :begin => hour_start, :end => hour_end}) last = readings_in_month.last if last last.diff(readings_in_month.first) else { :total_kwh_consumed_high => 0, :total_kwh_consumed_low => 0, :total_kwh_produced_high => 0, :total_kwh_produced_low => 0, :total_m3_gas_consumed => 0 } end end end end