Class: AverageMonthlyTemperature
- Inherits:
-
ApplicationRecord
- Object
- ActiveRecord::Base
- ApplicationRecord
- AverageMonthlyTemperature
- Includes:
- Models::Auditable
- Defined in:
- app/models/average_monthly_temperature.rb
Overview
== Schema Information
Table name: average_monthly_temperatures
Database name: primary
id :integer not null, primary key
average_annual_temperature :float
average_temperatures :float is an Array
lat :float
lng :float
postal_code :string(255)
temperature_variations :float is an Array
created_at :datetime not null
updated_at :datetime not null
Indexes
index_average_monthly_temperatures_on_average_annual_temperatur (average_annual_temperature)
index_average_monthly_temperatures_on_left_three_postal_code ("left"((postal_code)::text, 3))
index_average_monthly_temperatures_on_postal_code (postal_code)
Constant Summary
Constants included from Models::Auditable
Models::Auditable::ALWAYS_IGNORED
Constants included from Models::Schedulable
Models::Schedulable::SIMPLE_FORM_OPTIONS
Instance Attribute Summary collapse
- #average_annual_temperature ⇒ Float readonly
- #average_temperatures ⇒ Float readonly
- #lat ⇒ Float readonly
- #lng ⇒ Float readonly
- #postal_code ⇒ String(255) readonly
- #temperature_variations ⇒ Float readonly
Class Method Summary collapse
- .get_forecast_for(latitude, longitude, datetime) ⇒ void
- .get_from_postal_code(code) ⇒ void
- .get_monthly_temperature_data_for_lat_lng(lat, lng) ⇒ void
- .get_monthly_temperature_data_for_postal_code(postal_code) ⇒ void
Methods included from Models::Auditable
#all_skipped_columns, #audit_reference_data, #creator, #should_not_save_version, #stamp_record, #updater
Methods inherited from ApplicationRecord
ransackable_associations, ransackable_attributes, ransackable_scopes, ransortable_attributes, #to_relation
Methods included from Models::Schedulable
Methods included from Models::AfterCommittable
Methods included from Models::EventPublishable
Instance Attribute Details
#average_annual_temperature ⇒ Float (readonly)
38 |
# File 'app/models/average_monthly_temperature.rb', line 38 validates :average_annual_temperature, presence: true |
#average_temperatures ⇒ Float (readonly)
34 |
# File 'app/models/average_monthly_temperature.rb', line 34 validates :average_temperatures, presence: true |
#lat ⇒ Float (readonly)
30 |
# File 'app/models/average_monthly_temperature.rb', line 30 validates :lat, presence: true |
#lng ⇒ Float (readonly)
32 |
# File 'app/models/average_monthly_temperature.rb', line 32 validates :lng, presence: true |
#postal_code ⇒ String(255) (readonly)
Validations (if => proc { |o| o.postal_code.to_s.strip[0..2].to_i.positive? } ):
- Zip_code_format
Validations (if => proc { |o| o.postal_code.to_s.strip[0..2].to_i.zero? } ):
- Postal_code_format
28 |
# File 'app/models/average_monthly_temperature.rb', line 28 validates :postal_code, presence: true |
#temperature_variations ⇒ Float (readonly)
36 |
# File 'app/models/average_monthly_temperature.rb', line 36 validates :temperature_variations, presence: true |
Class Method Details
.get_forecast_for(latitude, longitude, datetime) ⇒ void
130 131 132 133 |
# File 'app/models/average_monthly_temperature.rb', line 130 def self.get_forecast_for(latitude, longitude, datetime) Rails.logger.debug { "AverageMonthlyTemperature.get_forecast_for(#{latitude}, #{longitude}, #{datetime})" } Weather::VisualCrossingClient.new.get_forecast_for(latitude, longitude, datetime) end |
.get_from_postal_code(code) ⇒ void
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 |
# File 'app/models/average_monthly_temperature.rb', line 46 def self.get_from_postal_code(code) postal_code = if code.to_s.strip[0..2].to_i.positive? # We want US 5 numbered ZIP code code.to_s.strip.delete(' ').delete('-')[0..4] else # We want Canadian 6 letter/number postal code code.to_s.strip.delete(' ').delete('-')[0..5] end res = AverageMonthlyTemperature.where(postal_code: postal_code).first unless res temp_data = AverageMonthlyTemperature.get_monthly_temperature_data_for_postal_code(postal_code) if temp_data res = AverageMonthlyTemperature.create(postal_code: postal_code, average_temperatures: temp_data['average_temperatures'], temperature_variations: temp_data['temperature_variations'], lat: temp_data['latitude'], lng: temp_data['longitude'], average_annual_temperature: temp_data['average_annual_temperature'] || temp_data['average_temperatures'].average.round(2)) else res = nil end end if res&.valid? { average_temperatures: res.average_temperatures, temperature_variations: res.temperature_variations, average_annual_temperature: res.average_annual_temperature, status: :ok } else { status: :error, message: res&.errors&.&.join(', ') || "Can't find temperature data for postal code: #{postal_code}" } end end |
.get_monthly_temperature_data_for_lat_lng(lat, lng) ⇒ void
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 |
# File 'app/models/average_monthly_temperature.rb', line 93 def self.get_monthly_temperature_data_for_lat_lng(lat, lng) res = {} res['average_temperatures'] = [] res['temperature_variations'] = [] # here we round to 0 decimal places which gives us ~90 miles resolution, ok for temperature variation, but improves caching latitude = lat.round longitude = lng.round res['latitude'] = latitude res['longitude'] = longitude Rails.cache.fetch("monthly_temperature_data_for_lat_lng:#{[latitude, longitude].inspect}", expires_in: 3.months) do 12.times do |i| month = i + 1 t = Time.zone.local(Time.zone.now.year + 5, month, 1) # puts "calculate_heat_loss, t: #{t}" forecast = AverageMonthlyTemperature.get_forecast_for(latitude, longitude, t) if forecast['temp'] res['average_temperatures'] << forecast['temp'] res['temperature_variations'] << (forecast['tempmax'] - forecast['tempmin']) else res['error'] = 'Forecast could not be determined for this location!' raise StandardError, res['error'] break end end res['average_annual_temperature'] = res['average_temperatures'].average.round(2) res end end |
.get_monthly_temperature_data_for_postal_code(postal_code) ⇒ void
76 77 78 79 80 81 82 83 84 85 |
# File 'app/models/average_monthly_temperature.rb', line 76 def self.get_monthly_temperature_data_for_postal_code(postal_code) res, lat, lng = nil begin lat, lng = Address.geocode_address_string("#{postal_code}, North America") res = AverageMonthlyTemperature.get_monthly_temperature_data_for_lat_lng(lat, lng) if lat && lng rescue StandardError => e ErrorReporting.warning(e, { postal_code: postal_code, lat: lat, lng: lng }) end res end |