Commit graph

8 commits

Author SHA1 Message Date
david kiania
8e119e2328 feat: tickets.inc_open_sla view + lowercase legacy region
- Add tickets.inc_open_sla: open tickets with derived SLA (hours_open, sla_state
  vs 48h; clock = created_at_service or first_seen_at fallback) + team/cluster/geog
  for dispatch. (One-time legacy region->lowercase backfill applied to live data.)

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 00:03:55 +03:00
david kiania
e54e2b7c56 feat: drop constant service_type column (migration 07)
service_type is always 'inc' (cardinality 1) — zero info, redundant in an INC-only
table. Drop the generated column; stays in raw for audit.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-15 23:54:43 +03:00
david kiania
b86c0b2d13 feat: mttr -> minutes; drop constant alarm/auto flags (migration 06)
mttr generated column is now integer minutes (source raw.mttr is decimal hours),
analytics-friendly. Drop is_alarm/is_auto_created/is_auto_closed generated columns
— all constant `false` in tickets.inc since alarms are filtered at ingest (still
present in raw for audit; loader still filters on raw->>'is_alarm'). is_actionable
kept.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-15 23:51:28 +03:00
david kiania
565cd592a0 feat: add geography column + GiST index for routing (migration 05)
geom is geometry(Point,4326) (planar degrees); add geog = geom::geography (STORED
generated) + GiST index so ST_Distance/ST_DWithin/KNN work in real metres for
nearest-vehicle and radius queries.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-15 23:33:45 +03:00
david kiania
b323e8a1ac feat: populate inc latitude/longitude from geocoded geom (migration 04)
Feed coords are always empty; redefine the latitude/longitude generated columns to
COALESCE(feed, ST_Y/ST_X(geom)) so they carry the resolved/geocoded position for
every geocoded ticket (precision indicated by geo_source). STORED, recomputes when
geom changes.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-15 23:26:39 +03:00
david kiania
073db9b5b8 feat: unpack tickets.inc.raw into typed generated columns (migration 03)
Add STORED generated columns derived from raw (text/numeric/bool/double + EAT
timestamptz via an IMMUTABLE tickets.eat_ts() wrapper). Computed for all existing
rows and auto-populated on every future ingest — raw stays the source of truth,
no loader change. Indexes on status/cluster/team/closed_at/is_actionable for the
SLA/team/closure queries.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-15 23:08:31 +03:00
david kiania
df054c92be feat: INC hourly-CSV ingestion (newest-file, ETag dedup, clean + archive)
Rework import_tickets.py from the retired JSON `latest.json` model to the new
hourly full-snapshot CSV export. Strictly INC (CRQ out of scope).

- Ingest the newest automations/inc/<EAT-timestamp>.csv; skip-if-unchanged by
  comparing S3 ETag to tickets.import_meta.metadata.source_etag.
- Upsert on ticket_id (PK; no dups, never delete -> closure history accrues).
  No truncate. On success, move processed files to automations/inc/processed/.
- Clean at ingest: drop is_alarm=true + the "EXPORT STOPPED..." sentinel; drop
  week_*, source_s3_*/source_snapshot_id, department/source_type; lowercase
  region, uppercase raw_status; keep service_type + bucket.
- Force path-style S3 addressing; --inc-csv for local dev; --from-bucket for cron.
- Add migrations/02 (import_meta + freshness); refresh README/.env.example/docs.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-15 19:33:16 +03:00
david kiania
4631cc6382 feat: fleettickets — INC/CRQ ticket ingestion, geocoding + read-schema
Standalone module extracted from the tracksolid repo (was migrations 21-23 +
tools/import_tickets.py). Owns the `tickets` schema in the shared tracksolid_db.

- migrations/01_tickets_schema.sql: consolidated final-state schema (tickets.inc/
  crq raw-jsonb-first, geo_clusters + geo_locations gazetteers, geom trigger,
  reporting.fn_tickets_for_map)
- import_tickets.py: rustfs bucket ingest + cluster/location geocoding
  (LocationIQ/OpenCage, viewbox-bounded + cluster-distance guard)
- run_migrations.py, shared.py (self-contained), pyproject, .env.example, README

The DB stays in tracksolid_db; dashboard_api keeps serving /webhook/tickets; the
Tickets map stays a FleetOps tab.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-11 20:13:50 +03:00