dawarich/app/services/visits/smart_detect.rb
2025-03-05 20:04:26 +01:00

44 lines
1.3 KiB
Ruby

# frozen_string_literal: true
module Visits
# Coordinates the process of detecting and creating visits from tracked points
class SmartDetect
MINIMUM_VISIT_DURATION = 5.minutes
MAXIMUM_VISIT_GAP = 30.minutes
MINIMUM_POINTS_FOR_VISIT = 3
SIGNIFICANT_PLACE_VISITS = 2 # Number of visits to consider a place significant
SIGNIFICANT_MOVEMENT_THRESHOLD = 50 # meters
attr_reader :user, :start_at, :end_at, :points
def initialize(user, start_at:, end_at:)
@user = user
@start_at = start_at.to_i
@end_at = end_at.to_i
@points = user.tracked_points.not_visited
.order(timestamp: :asc)
.where(timestamp: start_at..end_at)
end
def call
return [] if points.empty?
potential_visits = Visits::Detector.new(points).detect_potential_visits
merged_visits = Visits::Merger.new(points).merge_visits(potential_visits)
grouped_visits = group_nearby_visits(merged_visits).flatten
Visits::Creator.new(user).create_visits(grouped_visits)
end
private
def group_nearby_visits(visits)
visits.group_by do |visit|
[
(visit[:center_lat] * 1000).round / 1000.0,
(visit[:center_lon] * 1000).round / 1000.0
]
end.values
end
end
end