From 58daf45b604f46e30a2b8e0c8d65603e93782356 Mon Sep 17 00:00:00 2001 From: Graham McIntire Date: Tue, 16 Jun 2026 10:47:34 -0500 Subject: [PATCH] fix oban pro worker warnings --- lib/towerops/snmp/neighbor_cleanup_worker.ex | 6 +++--- lib/towerops/workers/agent_latency_evaluator.ex | 4 ++-- lib/towerops/workers/agent_release_webhook_worker.ex | 4 ++-- lib/towerops/workers/ai_network_insight_worker.ex | 4 ++-- lib/towerops/workers/alert_digest_worker.ex | 6 +++--- lib/towerops/workers/alert_notification_worker.ex | 8 ++++---- lib/towerops/workers/backup_summary_worker.ex | 6 +++--- lib/towerops/workers/backup_timeout_worker.ex | 6 +++--- lib/towerops/workers/billing_sync_worker.ex | 4 ++-- lib/towerops/workers/capacity_insight_worker.ex | 4 ++-- lib/towerops/workers/check_executor_worker.ex | 4 ++-- lib/towerops/workers/check_worker.ex | 4 ++-- lib/towerops/workers/cloud_latency_probe_worker.ex | 4 ++-- lib/towerops/workers/cloudflare_ban_worker.ex | 4 ++-- lib/towerops/workers/cn_maestro_sync_worker.ex | 6 +++--- lib/towerops/workers/coverage_worker.ex | 4 ++-- lib/towerops/workers/data_retention_worker.ex | 4 ++-- lib/towerops/workers/device_health_insight_worker.ex | 4 ++-- lib/towerops/workers/device_monitor_worker.ex | 6 +++--- lib/towerops/workers/device_poller_worker.ex | 6 +++--- lib/towerops/workers/discovery_worker.ex | 6 +++--- lib/towerops/workers/escalation_check_worker.ex | 4 ++-- lib/towerops/workers/expired_ban_cleanup_worker.ex | 4 ++-- .../workers/firmware_version_fetcher_worker.ex | 6 +++--- lib/towerops/workers/gaiia_insight_worker.ex | 4 ++-- lib/towerops/workers/gaiia_sync_worker.ex | 6 +++--- lib/towerops/workers/gaiia_webhook_worker.ex | 4 ++-- lib/towerops/workers/insight_expiry_worker.ex | 4 ++-- lib/towerops/workers/insight_llm_enrichment_worker.ex | 4 ++-- lib/towerops/workers/job_health_check_worker.ex | 6 +++--- lib/towerops/workers/lidar_catalog_sync_worker.ex | 4 ++-- lib/towerops/workers/login_history_cleanup_worker.ex | 6 +++--- lib/towerops/workers/mikrotik_backup_worker.ex | 6 +++--- lib/towerops/workers/mikrotik_webhook_worker.ex | 4 ++-- lib/towerops/workers/ms_buildings_import_worker.ex | 4 ++-- lib/towerops/workers/netbox_sync_worker.ex | 6 +++--- lib/towerops/workers/pagerduty_webhook_worker.ex | 4 ++-- lib/towerops/workers/preseem_baseline_worker.ex | 4 ++-- lib/towerops/workers/preseem_sync_worker.ex | 6 +++--- lib/towerops/workers/recommendations_run_worker.ex | 4 ++-- lib/towerops/workers/report_worker.ex | 6 +++--- lib/towerops/workers/session_cleanup_worker.ex | 6 +++--- lib/towerops/workers/sonar_sync_worker.ex | 6 +++--- lib/towerops/workers/splynx_sync_worker.ex | 6 +++--- lib/towerops/workers/stale_agent_worker.ex | 4 ++-- .../workers/stale_violation_cleanup_worker.ex | 4 ++-- lib/towerops/workers/stripe_webhook_worker.ex | 4 ++-- lib/towerops/workers/system_insight_worker.ex | 4 ++-- lib/towerops/workers/uisp_sync_worker.ex | 6 +++--- lib/towerops/workers/visp_sync_worker.ex | 6 +++--- lib/towerops/workers/weather_sync_worker.ex | 4 ++-- lib/towerops/workers/welcome_email_worker.ex | 4 ++-- lib/towerops/workers/wireless_insight_worker.ex | 4 ++-- lib/towerops_web/live/org/integrations_live.ex | 2 -- lib/towerops_web/live/org/settings_live.ex | 11 ----------- 55 files changed, 129 insertions(+), 142 deletions(-) diff --git a/lib/towerops/snmp/neighbor_cleanup_worker.ex b/lib/towerops/snmp/neighbor_cleanup_worker.ex index 516abd01..218c8bef 100644 --- a/lib/towerops/snmp/neighbor_cleanup_worker.ex +++ b/lib/towerops/snmp/neighbor_cleanup_worker.ex @@ -19,9 +19,9 @@ defmodule Towerops.Snmp.NeighborCleanupWorker do # Consider neighbors stale if not seen in 24 hours @stale_threshold_hours 24 - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok + def process(%Oban.Job{}) do cleanup_stale_records() cleanup_stale_topology_links() :ok diff --git a/lib/towerops/workers/agent_latency_evaluator.ex b/lib/towerops/workers/agent_latency_evaluator.ex index 96c76489..6ed41c9e 100644 --- a/lib/towerops/workers/agent_latency_evaluator.ex +++ b/lib/towerops/workers/agent_latency_evaluator.ex @@ -29,8 +29,8 @@ defmodule Towerops.Workers.AgentLatencyEvaluator do # Look back 48 hours to cover multiple 8-hour probe cycles @hours_ago 48 - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do start_time = System.monotonic_time(:millisecond) candidates = diff --git a/lib/towerops/workers/agent_release_webhook_worker.ex b/lib/towerops/workers/agent_release_webhook_worker.ex index 8ef18c23..75d2b24c 100644 --- a/lib/towerops/workers/agent_release_webhook_worker.ex +++ b/lib/towerops/workers/agent_release_webhook_worker.ex @@ -10,8 +10,8 @@ defmodule Towerops.Workers.AgentReleaseWebhookWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do case Agents.broadcast_mass_update() do {:ok, result} -> Logger.info("Agent mass update: #{result.notified} notified, #{result.skipped} skipped") diff --git a/lib/towerops/workers/ai_network_insight_worker.ex b/lib/towerops/workers/ai_network_insight_worker.ex index 45a82341..028b95e1 100644 --- a/lib/towerops/workers/ai_network_insight_worker.ex +++ b/lib/towerops/workers/ai_network_insight_worker.ex @@ -30,8 +30,8 @@ defmodule Towerops.Workers.AiNetworkInsightWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do org_ids = Organization |> select([o], o.id) diff --git a/lib/towerops/workers/alert_digest_worker.ex b/lib/towerops/workers/alert_digest_worker.ex index ba4c01d8..d5ffa82e 100644 --- a/lib/towerops/workers/alert_digest_worker.ex +++ b/lib/towerops/workers/alert_digest_worker.ex @@ -18,8 +18,8 @@ defmodule Towerops.Workers.AlertDigestWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: %{"user_id" => "__cron__"}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"user_id" => "__cron__"}}) do # Cron mode: find all pending digests and enqueue delivery pending = @@ -48,7 +48,7 @@ defmodule Towerops.Workers.AlertDigestWorker do :ok end - def perform(%Oban.Job{args: %{"user_id" => user_id}}) when user_id != "__cron__" do + def process(%Oban.Job{args: %{"user_id" => user_id}}) when user_id != "__cron__" do case NotificationRateLimiter.get_pending_digest(user_id) do nil -> :ok diff --git a/lib/towerops/workers/alert_notification_worker.ex b/lib/towerops/workers/alert_notification_worker.ex index 92824551..057d02cd 100644 --- a/lib/towerops/workers/alert_notification_worker.ex +++ b/lib/towerops/workers/alert_notification_worker.ex @@ -19,8 +19,8 @@ defmodule Towerops.Workers.AlertNotificationWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: %{"action" => "trigger", "alert_id" => alert_id}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"action" => "trigger", "alert_id" => alert_id}}) do with {:ok, alert} <- fetch_alert(alert_id), {:ok, device} <- fetch_device(alert.device_id) do handle_trigger_notification(alert, device, alert_id) @@ -35,7 +35,7 @@ defmodule Towerops.Workers.AlertNotificationWorker do end end - def perform(%Oban.Job{args: %{"action" => "acknowledge", "alert_id" => alert_id}}) do + def process(%Oban.Job{args: %{"action" => "acknowledge", "alert_id" => alert_id}}) do case fetch_alert(alert_id) do {:ok, alert} -> routing = alert_routing_for_alert(alert) @@ -54,7 +54,7 @@ defmodule Towerops.Workers.AlertNotificationWorker do end end - def perform(%Oban.Job{args: %{"action" => "resolve", "alert_id" => alert_id}}) do + def process(%Oban.Job{args: %{"action" => "resolve", "alert_id" => alert_id}}) do case fetch_alert(alert_id) do {:ok, alert} -> routing = alert_routing_for_alert(alert) diff --git a/lib/towerops/workers/backup_summary_worker.ex b/lib/towerops/workers/backup_summary_worker.ex index f9b17993..16aba68b 100644 --- a/lib/towerops/workers/backup_summary_worker.ex +++ b/lib/towerops/workers/backup_summary_worker.ex @@ -12,9 +12,9 @@ defmodule Towerops.Workers.BackupSummaryWorker do require Logger - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok + def process(%Oban.Job{}) do yesterday = DateTime.add(DateTime.utc_now(), -24 * 60 * 60, :second) summary = BackupRequests.summary_since(yesterday) diff --git a/lib/towerops/workers/backup_timeout_worker.ex b/lib/towerops/workers/backup_timeout_worker.ex index 15824601..ec29a5bd 100644 --- a/lib/towerops/workers/backup_timeout_worker.ex +++ b/lib/towerops/workers/backup_timeout_worker.ex @@ -15,9 +15,9 @@ defmodule Towerops.Workers.BackupTimeoutWorker do @timeout_minutes 5 - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok + def process(%Oban.Job{}) do cutoff = DateTime.add(DateTime.utc_now(), -@timeout_minutes * 60, :second) timeout_count = BackupRequests.mark_timed_out_requests(cutoff) diff --git a/lib/towerops/workers/billing_sync_worker.ex b/lib/towerops/workers/billing_sync_worker.ex index c3d8b690..78391f3d 100644 --- a/lib/towerops/workers/billing_sync_worker.ex +++ b/lib/towerops/workers/billing_sync_worker.ex @@ -12,8 +12,8 @@ defmodule Towerops.Workers.BillingSyncWorker do require Logger - @impl Oban.Worker - def perform(_job) do + @impl Oban.Pro.Worker + def process(_job) do Logger.info("Starting daily billing sync") # Get all organizations with active paid subscriptions diff --git a/lib/towerops/workers/capacity_insight_worker.ex b/lib/towerops/workers/capacity_insight_worker.ex index 78e301ae..2d0fcc2b 100644 --- a/lib/towerops/workers/capacity_insight_worker.ex +++ b/lib/towerops/workers/capacity_insight_worker.ex @@ -26,8 +26,8 @@ defmodule Towerops.Workers.CapacityInsightWorker do @warning_threshold 75 @resolve_threshold 70 - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do # Use streaming to avoid loading all org IDs into memory Repo.transaction(fn -> Organization diff --git a/lib/towerops/workers/check_executor_worker.ex b/lib/towerops/workers/check_executor_worker.ex index 4a3d94ad..a9e0c9f0 100644 --- a/lib/towerops/workers/check_executor_worker.ex +++ b/lib/towerops/workers/check_executor_worker.ex @@ -50,8 +50,8 @@ defmodule Towerops.Workers.CheckExecutorWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: %{"check_id" => check_id}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"check_id" => check_id}}) do case Monitoring.get_check(check_id) do nil -> Logger.debug("Check #{check_id} deleted, skipping execution") diff --git a/lib/towerops/workers/check_worker.ex b/lib/towerops/workers/check_worker.ex index d9e1a169..99c0d98b 100644 --- a/lib/towerops/workers/check_worker.ex +++ b/lib/towerops/workers/check_worker.ex @@ -24,8 +24,8 @@ defmodule Towerops.Workers.CheckWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: %{"check_id" => check_id}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"check_id" => check_id}}) do case Monitoring.get_check(check_id) do nil -> Logger.debug("Check #{check_id} no longer exists, skipping and not rescheduling") diff --git a/lib/towerops/workers/cloud_latency_probe_worker.ex b/lib/towerops/workers/cloud_latency_probe_worker.ex index 874edb5c..1caba5cb 100644 --- a/lib/towerops/workers/cloud_latency_probe_worker.ex +++ b/lib/towerops/workers/cloud_latency_probe_worker.ex @@ -15,8 +15,8 @@ defmodule Towerops.Workers.CloudLatencyProbeWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do cloud_pollers = Agents.list_online_cloud_pollers() devices = Agents.list_cloud_polled_devices() diff --git a/lib/towerops/workers/cloudflare_ban_worker.ex b/lib/towerops/workers/cloudflare_ban_worker.ex index a116df11..f9868c51 100644 --- a/lib/towerops/workers/cloudflare_ban_worker.ex +++ b/lib/towerops/workers/cloudflare_ban_worker.ex @@ -12,8 +12,8 @@ defmodule Towerops.Workers.CloudflareBanWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: %{"ip_address" => ip_address}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"ip_address" => ip_address}}) do case CloudflareClient.block_ip(ip_address) do {:ok, _response} -> Logger.info("Successfully pushed permanent ban to Cloudflare: #{ip_address}") diff --git a/lib/towerops/workers/cn_maestro_sync_worker.ex b/lib/towerops/workers/cn_maestro_sync_worker.ex index 4d4f10cb..43f3cbcb 100644 --- a/lib/towerops/workers/cn_maestro_sync_worker.ex +++ b/lib/towerops/workers/cn_maestro_sync_worker.ex @@ -15,8 +15,8 @@ defmodule Towerops.Workers.CnMaestroSyncWorker do @window_seconds 300 - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations("cn_maestro") now = DateTime.utc_now() @@ -48,7 +48,7 @@ defmodule Towerops.Workers.CnMaestroSyncWorker do :ok end - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/coverage_worker.ex b/lib/towerops/workers/coverage_worker.ex index eb124bcb..e9eeb9b6 100644 --- a/lib/towerops/workers/coverage_worker.ex +++ b/lib/towerops/workers/coverage_worker.ex @@ -56,8 +56,8 @@ defmodule Towerops.Workers.CoverageWorker do @sm_height_tiers_m [1.83, 3.05, 4.57, 6.10, 9.14, 12.19] @default_tier_m 3.05 - @impl Oban.Worker - def perform(%Oban.Job{args: %{"coverage_id" => coverage_id, "organization_id" => organization_id}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"coverage_id" => coverage_id, "organization_id" => organization_id}}) do case Repo.get(Coverage, coverage_id) do nil -> Logger.warning("CoverageWorker: coverage #{coverage_id} not found, skipping") diff --git a/lib/towerops/workers/data_retention_worker.ex b/lib/towerops/workers/data_retention_worker.ex index d094293f..0f25545c 100644 --- a/lib/towerops/workers/data_retention_worker.ex +++ b/lib/towerops/workers/data_retention_worker.ex @@ -23,8 +23,8 @@ defmodule Towerops.Workers.DataRetentionWorker do require Logger - @impl Oban.Worker - def perform(_job) do + @impl Oban.Pro.Worker + def process(_job) do retention_groups = fetch_retention_groups() results = diff --git a/lib/towerops/workers/device_health_insight_worker.ex b/lib/towerops/workers/device_health_insight_worker.ex index 04d584cf..93f1d6fc 100644 --- a/lib/towerops/workers/device_health_insight_worker.ex +++ b/lib/towerops/workers/device_health_insight_worker.ex @@ -15,8 +15,8 @@ defmodule Towerops.Workers.DeviceHealthInsightWorker do @poll_gap_hours 24 - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do devices = list_stale_monitored_devices() Enum.each(devices, &generate_poll_gap_insight/1) diff --git a/lib/towerops/workers/device_monitor_worker.ex b/lib/towerops/workers/device_monitor_worker.ex index aea87fd3..705a7a6b 100644 --- a/lib/towerops/workers/device_monitor_worker.ex +++ b/lib/towerops/workers/device_monitor_worker.ex @@ -37,9 +37,9 @@ defmodule Towerops.Workers.DeviceMonitorWorker do @monitor_interval 30 - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok - def perform(%Oban.Job{args: %{"device_id" => device_id}}) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok + def process(%Oban.Job{args: %{"device_id" => device_id}}) do case Devices.get_device(device_id) do nil -> Logger.debug("Device #{device_id} no longer exists, skipping monitor and not rescheduling") diff --git a/lib/towerops/workers/device_poller_worker.ex b/lib/towerops/workers/device_poller_worker.ex index fa22c2b5..1f55f7f2 100644 --- a/lib/towerops/workers/device_poller_worker.ex +++ b/lib/towerops/workers/device_poller_worker.ex @@ -46,9 +46,9 @@ defmodule Towerops.Workers.DevicePollerWorker do @default_poll_interval 60 - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok - def perform(%Oban.Job{args: %{"device_id" => device_id}} = job) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok + def process(%Oban.Job{args: %{"device_id" => device_id}} = job) do _ = Events.broadcast_job_event(job, :started) start_time = System.monotonic_time(:second) diff --git a/lib/towerops/workers/discovery_worker.ex b/lib/towerops/workers/discovery_worker.ex index dc919e1c..47033a09 100644 --- a/lib/towerops/workers/discovery_worker.ex +++ b/lib/towerops/workers/discovery_worker.ex @@ -38,9 +38,9 @@ defmodule Towerops.Workers.DiscoveryWorker do # Consider agents online if they checked in within last 10 minutes @agent_online_threshold_minutes 10 - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok | :discard | {:error, term()} - def perform(%Oban.Job{args: %{"device_id" => device_id}} = job) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok | :discard | {:error, term()} + def process(%Oban.Job{args: %{"device_id" => device_id}} = job) do _ = Events.broadcast_job_event(job, :started) start_time = System.monotonic_time(:second) diff --git a/lib/towerops/workers/escalation_check_worker.ex b/lib/towerops/workers/escalation_check_worker.ex index eeed8016..43179593 100644 --- a/lib/towerops/workers/escalation_check_worker.ex +++ b/lib/towerops/workers/escalation_check_worker.ex @@ -10,8 +10,8 @@ defmodule Towerops.Workers.EscalationCheckWorker do alias Towerops.OnCall.Escalation - @impl Oban.Worker - def perform(%Oban.Job{args: %{"incident_id" => incident_id}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"incident_id" => incident_id}}) do _ = Escalation.check_and_escalate(incident_id) :ok end diff --git a/lib/towerops/workers/expired_ban_cleanup_worker.ex b/lib/towerops/workers/expired_ban_cleanup_worker.ex index ef358fbf..eff9adab 100644 --- a/lib/towerops/workers/expired_ban_cleanup_worker.ex +++ b/lib/towerops/workers/expired_ban_cleanup_worker.ex @@ -10,8 +10,8 @@ defmodule Towerops.Workers.ExpiredBanCleanupWorker do alias Towerops.Security.BruteForce - @impl Oban.Worker - def perform(_job) do + @impl Oban.Pro.Worker + def process(_job) do BruteForce.delete_expired_bans() :ok end diff --git a/lib/towerops/workers/firmware_version_fetcher_worker.ex b/lib/towerops/workers/firmware_version_fetcher_worker.ex index fcd2a855..5fbe96ea 100644 --- a/lib/towerops/workers/firmware_version_fetcher_worker.ex +++ b/lib/towerops/workers/firmware_version_fetcher_worker.ex @@ -22,9 +22,9 @@ defmodule Towerops.Workers.FirmwareVersionFetcherWorker do @rss_url "https://cdn.mikrotik.com/routeros/latest-stable.rss" @changelog_url "https://mikrotik.com/download/changelogs" - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok | {:error, term()} - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok | {:error, term()} + def process(%Oban.Job{}) do Logger.info("Fetching MikroTik RouterOS firmware version from RSS feed") with {:ok, rss_body} <- fetch_rss_feed(), diff --git a/lib/towerops/workers/gaiia_insight_worker.ex b/lib/towerops/workers/gaiia_insight_worker.ex index f37849a5..f9d1d076 100644 --- a/lib/towerops/workers/gaiia_insight_worker.ex +++ b/lib/towerops/workers/gaiia_insight_worker.ex @@ -18,8 +18,8 @@ defmodule Towerops.Workers.GaiiaInsightWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do integrations = Integrations.list_enabled_integrations("gaiia") Enum.each(integrations, fn integration -> diff --git a/lib/towerops/workers/gaiia_sync_worker.ex b/lib/towerops/workers/gaiia_sync_worker.ex index fcb63845..7c040d20 100644 --- a/lib/towerops/workers/gaiia_sync_worker.ex +++ b/lib/towerops/workers/gaiia_sync_worker.ex @@ -25,8 +25,8 @@ defmodule Towerops.Workers.GaiiaSyncWorker do @window_seconds 600 # Cron dispatcher: enqueues staggered individual sync jobs. - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations(@provider) eligible = Enum.filter(integrations, &due_for_sync?/1) @@ -54,7 +54,7 @@ defmodule Towerops.Workers.GaiiaSyncWorker do end # Individual sync: loads integration by ID and syncs. - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/gaiia_webhook_worker.ex b/lib/towerops/workers/gaiia_webhook_worker.ex index 3601ba99..9257e305 100644 --- a/lib/towerops/workers/gaiia_webhook_worker.ex +++ b/lib/towerops/workers/gaiia_webhook_worker.ex @@ -8,8 +8,8 @@ defmodule Towerops.Workers.GaiiaWebhookWorker do alias Towerops.Gaiia.Webhooks - @impl Oban.Worker - def perform(%Oban.Job{args: %{"organization_id" => org_id, "event" => event, "payload" => payload}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"organization_id" => org_id, "event" => event, "payload" => payload}}) do Webhooks.process_event(org_id, event, payload) :ok end diff --git a/lib/towerops/workers/insight_expiry_worker.ex b/lib/towerops/workers/insight_expiry_worker.ex index 8eca7ccd..1c54ce91 100644 --- a/lib/towerops/workers/insight_expiry_worker.ex +++ b/lib/towerops/workers/insight_expiry_worker.ex @@ -27,8 +27,8 @@ defmodule Towerops.Workers.InsightExpiryWorker do @default_max_age_days 7 - @impl Oban.Worker - def perform(%Oban.Job{} = _job) do + @impl Oban.Pro.Worker + def process(%Oban.Job{} = _job) do cutoff = DateTime.add(DateTime.utc_now(), -max_age_days() * 86_400, :second) {count, _} = diff --git a/lib/towerops/workers/insight_llm_enrichment_worker.ex b/lib/towerops/workers/insight_llm_enrichment_worker.ex index 37c00007..8a318c6d 100644 --- a/lib/towerops/workers/insight_llm_enrichment_worker.ex +++ b/lib/towerops/workers/insight_llm_enrichment_worker.ex @@ -19,8 +19,8 @@ defmodule Towerops.Workers.InsightLlmEnrichmentWorker do @batch_size 25 - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do [limit: @batch_size] |> Insights.list_unenriched_insights() |> Enum.each(&enrich_one/1) diff --git a/lib/towerops/workers/job_health_check_worker.ex b/lib/towerops/workers/job_health_check_worker.ex index 68a5a11b..58a52a86 100644 --- a/lib/towerops/workers/job_health_check_worker.ex +++ b/lib/towerops/workers/job_health_check_worker.ex @@ -24,9 +24,9 @@ defmodule Towerops.Workers.JobHealthCheckWorker do require Logger - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok + def process(%Oban.Job{}) do check_recoveries = recover_missing_check_executor_jobs() if check_recoveries > 0 do diff --git a/lib/towerops/workers/lidar_catalog_sync_worker.ex b/lib/towerops/workers/lidar_catalog_sync_worker.ex index 3ec69052..5ffe7881 100644 --- a/lib/towerops/workers/lidar_catalog_sync_worker.ex +++ b/lib/towerops/workers/lidar_catalog_sync_worker.ex @@ -13,8 +13,8 @@ defmodule Towerops.Workers.LidarCatalogSyncWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do case run_sync() do {:ok, summary} -> Logger.info( diff --git a/lib/towerops/workers/login_history_cleanup_worker.ex b/lib/towerops/workers/login_history_cleanup_worker.ex index 55b9158f..b4aeb58b 100644 --- a/lib/towerops/workers/login_history_cleanup_worker.ex +++ b/lib/towerops/workers/login_history_cleanup_worker.ex @@ -15,9 +15,9 @@ defmodule Towerops.Workers.LoginHistoryCleanupWorker do alias Towerops.Accounts.LoginAttempt alias Towerops.Repo - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: {:ok, %{deleted: non_neg_integer(), anonymized_deleted: non_neg_integer()}} - def perform(_job) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: {:ok, %{deleted: non_neg_integer(), anonymized_deleted: non_neg_integer()}} + def process(_job) do # Delete login attempts older than retention period (365 days) retention_days = Application.get_env(:towerops, :login_history_retention_days, 365) cutoff = DateTime.add(DateTime.utc_now(), -retention_days, :day) diff --git a/lib/towerops/workers/mikrotik_backup_worker.ex b/lib/towerops/workers/mikrotik_backup_worker.ex index eb93c65a..6df2eeb5 100644 --- a/lib/towerops/workers/mikrotik_backup_worker.ex +++ b/lib/towerops/workers/mikrotik_backup_worker.ex @@ -19,9 +19,9 @@ defmodule Towerops.Workers.MikrotikBackupWorker do require Logger - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: :ok | {:error, String.t()} - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: :ok | {:error, String.t()} + def process(%Oban.Job{}) do Logger.info("Starting MikroTik configuration backup job") devices = list_backup_eligible_devices() diff --git a/lib/towerops/workers/mikrotik_webhook_worker.ex b/lib/towerops/workers/mikrotik_webhook_worker.ex index 0085b187..75278892 100644 --- a/lib/towerops/workers/mikrotik_webhook_worker.ex +++ b/lib/towerops/workers/mikrotik_webhook_worker.ex @@ -23,8 +23,8 @@ defmodule Towerops.Workers.MikrotikWebhookWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: args}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) do organization_id = Map.fetch!(args, "organization_id") source = Map.fetch!(args, "source") event_type = Map.fetch!(args, "event_type") diff --git a/lib/towerops/workers/ms_buildings_import_worker.ex b/lib/towerops/workers/ms_buildings_import_worker.ex index e23e676d..dc845ff7 100644 --- a/lib/towerops/workers/ms_buildings_import_worker.ex +++ b/lib/towerops/workers/ms_buildings_import_worker.ex @@ -31,8 +31,8 @@ defmodule Towerops.Workers.MsBuildingsImportWorker do @batch_size 500 - @impl Oban.Worker - def perform(%Oban.Job{args: %{"path" => path} = args}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"path" => path} = args}) do source = Map.get(args, "source", "ms_global_ml") if File.exists?(path) do diff --git a/lib/towerops/workers/netbox_sync_worker.ex b/lib/towerops/workers/netbox_sync_worker.ex index e60324ee..51c12994 100644 --- a/lib/towerops/workers/netbox_sync_worker.ex +++ b/lib/towerops/workers/netbox_sync_worker.ex @@ -25,8 +25,8 @@ defmodule Towerops.Workers.NetBoxSyncWorker do @window_seconds 600 # Cron dispatcher: enqueues staggered individual sync jobs. - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations(@provider) eligible = Enum.filter(integrations, &due_for_sync?/1) @@ -54,7 +54,7 @@ defmodule Towerops.Workers.NetBoxSyncWorker do end # Individual sync: loads integration by ID and syncs. - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/pagerduty_webhook_worker.ex b/lib/towerops/workers/pagerduty_webhook_worker.ex index cb16947a..68de396c 100644 --- a/lib/towerops/workers/pagerduty_webhook_worker.ex +++ b/lib/towerops/workers/pagerduty_webhook_worker.ex @@ -10,8 +10,8 @@ defmodule Towerops.Workers.PagerdutyWebhookWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: %{"event_type" => event_type, "data" => data, "organization_id" => org_id}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"event_type" => event_type, "data" => data, "organization_id" => org_id}}) do case event_type do "incident.resolved" -> resolve_from_pagerduty(data, org_id) diff --git a/lib/towerops/workers/preseem_baseline_worker.ex b/lib/towerops/workers/preseem_baseline_worker.ex index 19eb1690..1493ad79 100644 --- a/lib/towerops/workers/preseem_baseline_worker.ex +++ b/lib/towerops/workers/preseem_baseline_worker.ex @@ -12,8 +12,8 @@ defmodule Towerops.Workers.PreseemBaselineWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do integrations = Integrations.list_enabled_integrations("preseem") Enum.each(integrations, fn integration -> diff --git a/lib/towerops/workers/preseem_sync_worker.ex b/lib/towerops/workers/preseem_sync_worker.ex index bcb178b8..65d7cb11 100644 --- a/lib/towerops/workers/preseem_sync_worker.ex +++ b/lib/towerops/workers/preseem_sync_worker.ex @@ -22,8 +22,8 @@ defmodule Towerops.Workers.PreseemSyncWorker do @window_seconds 600 # Cron dispatcher: enqueues staggered individual sync jobs - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations("preseem") eligible = Enum.filter(integrations, &should_sync?/1) @@ -51,7 +51,7 @@ defmodule Towerops.Workers.PreseemSyncWorker do end # Individual sync: loads integration by ID and syncs - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/recommendations_run_worker.ex b/lib/towerops/workers/recommendations_run_worker.ex index 92cb56af..8405d7a2 100644 --- a/lib/towerops/workers/recommendations_run_worker.ex +++ b/lib/towerops/workers/recommendations_run_worker.ex @@ -40,8 +40,8 @@ defmodule Towerops.Workers.RecommendationsRunWorker do OpticalRxLow ] - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do Enum.each(list_organization_ids(), &run_rules_for_org/1) :ok end diff --git a/lib/towerops/workers/report_worker.ex b/lib/towerops/workers/report_worker.ex index 8e53f6b0..37cf7f99 100644 --- a/lib/towerops/workers/report_worker.ex +++ b/lib/towerops/workers/report_worker.ex @@ -13,8 +13,8 @@ defmodule Towerops.Workers.ReportWorker do require Logger # Cron dispatcher: find due reports and enqueue individual jobs - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do reports = Reports.Report |> Towerops.Repo.all() @@ -42,7 +42,7 @@ defmodule Towerops.Workers.ReportWorker do end # Individual report: generate and deliver - def perform(%Oban.Job{args: %{"report_id" => id}}) do + def process(%Oban.Job{args: %{"report_id" => id}}) do case Reports.get_report(id) do {:ok, report} -> run_report(report) diff --git a/lib/towerops/workers/session_cleanup_worker.ex b/lib/towerops/workers/session_cleanup_worker.ex index 5b610973..0c53c541 100644 --- a/lib/towerops/workers/session_cleanup_worker.ex +++ b/lib/towerops/workers/session_cleanup_worker.ex @@ -9,9 +9,9 @@ defmodule Towerops.Workers.SessionCleanupWorker do alias Towerops.Accounts - @impl Oban.Worker - @spec perform(Oban.Job.t()) :: {:ok, %{sessions_deleted: non_neg_integer()}} - def perform(_job) do + @impl Oban.Pro.Worker + @spec process(Oban.Job.t()) :: {:ok, %{sessions_deleted: non_neg_integer()}} + def process(_job) do count = Accounts.delete_expired_browser_sessions() {:ok, %{sessions_deleted: count}} end diff --git a/lib/towerops/workers/sonar_sync_worker.ex b/lib/towerops/workers/sonar_sync_worker.ex index e57b53d7..e02935c0 100644 --- a/lib/towerops/workers/sonar_sync_worker.ex +++ b/lib/towerops/workers/sonar_sync_worker.ex @@ -25,8 +25,8 @@ defmodule Towerops.Workers.SonarSyncWorker do @window_seconds 300 # Cron dispatcher: enqueues staggered individual sync jobs. - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations(@provider) eligible = Enum.filter(integrations, &due_for_sync?/1) @@ -54,7 +54,7 @@ defmodule Towerops.Workers.SonarSyncWorker do end # Individual sync: loads integration by ID and syncs. - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/splynx_sync_worker.ex b/lib/towerops/workers/splynx_sync_worker.ex index aafe7b89..9af243b7 100644 --- a/lib/towerops/workers/splynx_sync_worker.ex +++ b/lib/towerops/workers/splynx_sync_worker.ex @@ -25,8 +25,8 @@ defmodule Towerops.Workers.SplynxSyncWorker do @window_seconds 300 # Cron dispatcher: enqueues staggered individual sync jobs. - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations(@provider) eligible = Enum.filter(integrations, &due_for_sync?/1) @@ -54,7 +54,7 @@ defmodule Towerops.Workers.SplynxSyncWorker do end # Individual sync: loads integration by ID and syncs. - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/stale_agent_worker.ex b/lib/towerops/workers/stale_agent_worker.ex index 13bd2dc2..b4a659ab 100644 --- a/lib/towerops/workers/stale_agent_worker.ex +++ b/lib/towerops/workers/stale_agent_worker.ex @@ -27,8 +27,8 @@ defmodule Towerops.Workers.StaleAgentWorker do # Consider agents "newly stale" if not seen in 10-15 minutes (for warning logs) @newly_stale_threshold_minutes 15 - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do stale_agents = find_stale_agents() _ = diff --git a/lib/towerops/workers/stale_violation_cleanup_worker.ex b/lib/towerops/workers/stale_violation_cleanup_worker.ex index 2da02b27..960aa4a5 100644 --- a/lib/towerops/workers/stale_violation_cleanup_worker.ex +++ b/lib/towerops/workers/stale_violation_cleanup_worker.ex @@ -10,8 +10,8 @@ defmodule Towerops.Workers.StaleViolationCleanupWorker do alias Towerops.Security.BruteForce - @impl Oban.Worker - def perform(_job) do + @impl Oban.Pro.Worker + def process(_job) do BruteForce.delete_stale_violations() :ok end diff --git a/lib/towerops/workers/stripe_webhook_worker.ex b/lib/towerops/workers/stripe_webhook_worker.ex index 5c19c5cb..342b904a 100644 --- a/lib/towerops/workers/stripe_webhook_worker.ex +++ b/lib/towerops/workers/stripe_webhook_worker.ex @@ -10,8 +10,8 @@ defmodule Towerops.Workers.StripeWebhookWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{args: %{"event" => event}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"event" => event}}) do case WebhookProcessor.process(event) do :ok -> :ok diff --git a/lib/towerops/workers/system_insight_worker.ex b/lib/towerops/workers/system_insight_worker.ex index 2f57fd8a..e51ab77c 100644 --- a/lib/towerops/workers/system_insight_worker.ex +++ b/lib/towerops/workers/system_insight_worker.ex @@ -20,8 +20,8 @@ defmodule Towerops.Workers.SystemInsightWorker do @stale_threshold_minutes 10 - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do # Use streaming to avoid loading all org IDs into memory Repo.transaction(fn -> Organization diff --git a/lib/towerops/workers/uisp_sync_worker.ex b/lib/towerops/workers/uisp_sync_worker.ex index 94f967cd..f0e6a0a1 100644 --- a/lib/towerops/workers/uisp_sync_worker.ex +++ b/lib/towerops/workers/uisp_sync_worker.ex @@ -22,8 +22,8 @@ defmodule Towerops.Workers.UispSyncWorker do @window_seconds 300 # Cron dispatcher: enqueues staggered individual sync jobs - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations("uisp") eligible = Enum.filter(integrations, &should_sync?/1) @@ -51,7 +51,7 @@ defmodule Towerops.Workers.UispSyncWorker do end # Individual sync: loads integration by ID and syncs - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/visp_sync_worker.ex b/lib/towerops/workers/visp_sync_worker.ex index 8edadd2c..e11c0ee8 100644 --- a/lib/towerops/workers/visp_sync_worker.ex +++ b/lib/towerops/workers/visp_sync_worker.ex @@ -25,8 +25,8 @@ defmodule Towerops.Workers.VispSyncWorker do @window_seconds 300 # Cron dispatcher: enqueues staggered individual sync jobs. - @impl Oban.Worker - def perform(%Oban.Job{args: args}) when args == %{} do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: args}) when args == %{} do integrations = Integrations.list_enabled_integrations(@provider) eligible = Enum.filter(integrations, &due_for_sync?/1) @@ -54,7 +54,7 @@ defmodule Towerops.Workers.VispSyncWorker do end # Individual sync: loads integration by ID and syncs. - def perform(%Oban.Job{args: %{"integration_id" => id}}) do + def process(%Oban.Job{args: %{"integration_id" => id}}) do case Integrations.get_integration_by_id(id) do {:ok, integration} -> sync_integration(integration) diff --git a/lib/towerops/workers/weather_sync_worker.ex b/lib/towerops/workers/weather_sync_worker.ex index 00229a8f..16540f2a 100644 --- a/lib/towerops/workers/weather_sync_worker.ex +++ b/lib/towerops/workers/weather_sync_worker.ex @@ -16,8 +16,8 @@ defmodule Towerops.Workers.WeatherSyncWorker do require Logger - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do api_key = Application.get_env(:towerops, :openweathermap_api_key) if is_nil(api_key) or api_key == "" do diff --git a/lib/towerops/workers/welcome_email_worker.ex b/lib/towerops/workers/welcome_email_worker.ex index 9aafa0cc..4a06fd4b 100644 --- a/lib/towerops/workers/welcome_email_worker.ex +++ b/lib/towerops/workers/welcome_email_worker.ex @@ -13,8 +13,8 @@ defmodule Towerops.Workers.WelcomeEmailWorker do @delay_minutes 3 - @impl Oban.Worker - def perform(%Oban.Job{args: %{"user_id" => user_id}}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{args: %{"user_id" => user_id}}) do case Accounts.get_user(user_id) do nil -> Logger.warning("Welcome email skipped: user #{user_id} not found") diff --git a/lib/towerops/workers/wireless_insight_worker.ex b/lib/towerops/workers/wireless_insight_worker.ex index 693c4afc..b6bca97f 100644 --- a/lib/towerops/workers/wireless_insight_worker.ex +++ b/lib/towerops/workers/wireless_insight_worker.ex @@ -35,8 +35,8 @@ defmodule Towerops.Workers.WirelessInsightWorker do @ap_critical_threshold 75 @ap_recovery_threshold 40 - @impl Oban.Worker - def perform(%Oban.Job{}) do + @impl Oban.Pro.Worker + def process(%Oban.Job{}) do # Use streaming to avoid loading all org IDs into memory Repo.transaction(fn -> Organization diff --git a/lib/towerops_web/live/org/integrations_live.ex b/lib/towerops_web/live/org/integrations_live.ex index 6ba684ff..4730817e 100644 --- a/lib/towerops_web/live/org/integrations_live.ex +++ b/lib/towerops_web/live/org/integrations_live.ex @@ -105,8 +105,6 @@ defmodule ToweropsWeb.Org.IntegrationsLive do } ] - @providers Enum.flat_map(@provider_categories, & &1.providers) - @impl true def mount(_params, _session, socket) do organization = socket.assigns.current_scope.organization diff --git a/lib/towerops_web/live/org/settings_live.ex b/lib/towerops_web/live/org/settings_live.ex index 1d8460f2..6141d938 100644 --- a/lib/towerops_web/live/org/settings_live.ex +++ b/lib/towerops_web/live/org/settings_live.ex @@ -18,8 +18,6 @@ defmodule ToweropsWeb.Org.SettingsLive do require Logger - @billing_provider_ids ~w(gaiia sonar splynx visp) - @impl true def mount(_params, _session, socket) do organization = socket.assigns.current_scope.organization @@ -560,15 +558,6 @@ defmodule ToweropsWeb.Org.SettingsLive do |> Map.new(fn integration -> {integration.provider, integration} end) end - defp active_billing_provider(integrations) do - Enum.find_value(@billing_provider_ids, fn id -> - case Map.get(integrations, id) do - %{enabled: true} -> id - _ -> nil - end - end) - end - defp get_current_integration(socket) do provider = socket.assigns.configuring