fix: update JSONB handling for ahoy events

- Change query conditions in City model to use the
  `properties::jsonb` syntax for compatibility.
- Update WeatherArt model's event counting to reflect
  the same JSONB handling for consistency across models.

These changes ensure that the queries correctly access the
JSONB fields in the database, which enhances robustness
when handling different database adapters like Postgres
or SQLite. This fixes potential issues with ahoy events
not being counted accurately due to incorrect property access.
This commit is contained in:
songtianlun 2025-01-27 01:05:16 +08:00
parent f918a42619
commit 6eca78da8d
2 changed files with 8 additions and 9 deletions

View File

@ -20,7 +20,6 @@ class City < ApplicationRecord
scope :by_country, ->(country_id) { where(country_id: country_id) }
scope :active, -> { where(active: true) }
scope :by_popularity, -> {
if ActiveRecord::Base.connection.adapter_name.downcase == "sqlite"
joins("LEFT JOIN ahoy_events ON json_extract(ahoy_events.properties, '$.city_id') = cities.id
@ -29,8 +28,8 @@ class City < ApplicationRecord
.select("cities.*, COUNT(ahoy_events.id) as visit_count")
.order("visit_count DESC")
else
joins("LEFT JOIN ahoy_events ON (ahoy_events.properties->>'city_id')::integer = cities.id
AND ahoy_events.properties->>'event_type' = 'city_view'")
joins("LEFT JOIN ahoy_events ON (ahoy_events.properties::jsonb->>'city_id')::integer = cities.id
AND ahoy_events.properties::jsonb->>'event_type' = 'city_view'")
.group("cities.id")
.select("cities.*, COUNT(ahoy_events.id) as visit_count")
.order("visit_count DESC")
@ -47,8 +46,8 @@ class City < ApplicationRecord
.order("visit_count ASC, cities.name ASC")
else
active
.joins("LEFT JOIN ahoy_events ON (ahoy_events.properties->>'city_id')::integer = cities.id
AND ahoy_events.properties->>'event_type' = 'city_view'")
.joins("LEFT JOIN ahoy_events ON (ahoy_events.properties::jsonb->>'city_id')::integer = cities.id
AND ahoy_events.properties::jsonb->>'event_type' = 'city_view'")
.group("cities.id")
.select("cities.*, COUNT(ahoy_events.id) as visit_count")
.order("visit_count ASC, cities.name ASC")
@ -108,7 +107,7 @@ class City < ApplicationRecord
if ActiveRecord::Base.connection.adapter_name.downcase == "sqlite"
Ahoy::Event.where("json_extract(properties, '$.event_type') = 'city_view' AND json_extract(properties, '$.city_id') = ?", self.id).count
else
Ahoy::Event.where("properties->>'event_type' = 'city_view' AND (properties->>'city_id')::integer = ?", self.id).count
Ahoy::Event.where("properties::jsonb->>'event_type' = 'city_view' AND (properties::jsonb->>'city_id')::integer = ?", self.id).count
end
end
end

View File

@ -19,8 +19,8 @@ class WeatherArt < ApplicationRecord
.select("weather_arts.*, COUNT(ahoy_events.id) as visit_count")
.order("visit_count DESC")
else
joins("LEFT JOIN ahoy_events ON (ahoy_events.properties->>'weather_art_id')::integer = weather_arts.id
AND ahoy_events.properties->>'event_type' = 'weather_art_view'")
joins("LEFT JOIN ahoy_events ON (ahoy_events.properties::jsonb->>'weather_art_id')::integer = weather_arts.id
AND ahoy_events.properties::jsonb->>'event_type' = 'weather_art_view'")
.group("weather_arts.id")
.select("weather_arts.*, COUNT(ahoy_events.id) as visit_count")
.order("visit_count DESC")
@ -47,7 +47,7 @@ class WeatherArt < ApplicationRecord
if ActiveRecord::Base.connection.adapter_name.downcase == "sqlite"
Ahoy::Event.where("json_extract(properties, '$.event_type') = 'weather_art_view' AND json_extract(properties, '$.weather_art_id') = ?", self.id).count
else
Ahoy::Event.where("properties->>'event_type' = 'weather_art_view' AND (properties->>'weather_art_id')::integer = ?", self.id).count
Ahoy::Event.where("properties::jsonb->>'event_type' = 'weather_art_view' AND (properties::jsonb->>'weather_art_id')::integer = ?", self.id).count
end
end
end