Install Fleet Apps (primary agnostic installer)
One command stands up the entire new-architecture analytics stack and is the primary installation path for it. It also owns the live ORS/VROOM routing engine build (Phase C): the engine is provisioned natively by default, so this skill is fully self-contained. Pass --no-engine to skip the heavy engine build.
This skill owns all of its artifacts (relocated here), so the stack installs and runs without any other skill. The analytics layer (dashboards, Cortex Analyst, agents) works with no engine; live routing verbs require the ORS engine, which the installer builds and provisions by default (skip with --no-engine).
Scope: vehicle/industry-AGNOSTIC only
This installer is mode-agnostic by construction. VEHICLE_TYPE is a data dimension carried by the selected dataset - never a schema, view, semantic view, agent tool, or UI surface. The R6 fleet_sa_app/app/packs/BUSINESS_PROBLEM_TAXONOMY.md (status: locked) is the authoritative contract.
| Layer |
INSTALLED (agnostic) |
EXCLUDED (industry-vertical) |
| Packs |
unified_fleet, fleet_ops, dwell, route_deviation, route_optimization, catchment, starter |
marketplace, backload, dhl_ntbo |
| UI views |
Fleet/Asset Status, Asset Map, Demand Density (H3), Trip Inspection, Operator Performance, Top Origins, Dwell & Congestion, Route Deviation, Asset Utilization, VRP, Catchment |
Freight Marketplace, Backload Matching, DHL pages |
| Agents |
SV_FLEET_OPS, SV_DWELL_ANALYTICS, SV_ROUTE_DEVIATION, SV_ASSET_VELOCITY, SV_CATCHMENT + neutral routing verbs |
SV_DELIVERIES, SV_BACKLOAD_MATCHING, SV_DHL_BACKLOAD |
| Seed data |
SYNTHETIC_DATASETS.UNIFIED.* / NEUTRAL.*, FLEET_INTELLIGENCE.CORE, DWELL/DEVIATION/ROUTE_OPT CONFIG, CATCHMENT base tables |
freight offers/partners, DHL tables |
The installer always installs the complete agnostic set - there is no per-use-case selection prompt.
Agent Playground demo tools are dynamic. The TOOL_CATCHMENT,
TOOL_DELIVERY_OPTIMIZATION, and TOOL_NETWORK_OPTIMIZATION procs source live,
region-scoped Overture POIs (FLEET_INTELLIGENCE.CATCHMENT.POIS /
REGIONAL_ADDRESSES, BOUNDARY-constrained + routable-filtered) and read the
active region from CATCHMENT.CONFIG - no static demo seed is required. Step 4.6
uploads the region-neutral agent-demos.json scenario config to the ORS stage
(engine-present only; skip with SKIP_DEMO=1).
Execution Rules
- All relative paths are relative to this skill's directory (
.cortex/skills/install-fleet-apps/).
- Replace
<connection> with the active Snowflake CLI connection. Find it via snow connection list (or read ~/.snowflake/connections.toml) and verify with snow sql -q "SELECT CURRENT_ACCOUNT()" -c <connection>.
- The installer is idempotent: re-running detects existing objects and reuses them. Use per-layer
SKIP_* env vars only to shorten re-runs.
- Every object created carries the
oss-install-fleet-apps COMMENT tag; every session sets the query_tag (see references/conventions.md).
- After a run, always emit a friction log to
logs/ per the repo AGENTS.md.
Prerequisites
- Container runtime (Podman or Docker) running; Node.js >= 20 + npm; Python 3; Snowflake CLI (
snow).
- The engine build (on by default) auto-detects docker first (a default 2 GB podman machine OOMs the ORS image build). Force a runtime with
CONTAINER_CMD=docker|podman.
- Install crane (
brew install crane) for reliable SPCS image pushes - docker push to the SPCS registry intermittently hangs on the final manifest commit; build_push prefers crane when present (docker runtime). Disable with USE_CRANE_PUSH=0.
export SNOWFLAKE_CLI_NO_UPDATE_CHECK=true.
- An active connection whose role can create databases, schemas, services, compute pools, image repositories, external access integrations, roles, and agents (see
## Required Privileges).
- Repository cloned; the four Carto/Overture Marketplace shares are optional (basemap egress is via the CARTO EAI).
One-command install
bash .cortex/skills/install-fleet-apps/scripts/install_fleet_apps.sh --connection <connection>
The orchestrator runs these layers in order (detect-and-reuse-else-create throughout):
- Preflight - tools, connection, account.
- Infra - image repository, compute pool, CARTO EAI (+ network rule), spec stage. Reuses
OPENROUTESERVICE_APP equivalents if present; otherwise creates skill-owned objects. See references/infra.sql.
- Data - probes the agnostic source tables; reuses existing rows, else loads
scripts/seed_data.sql. See references/seed-data.md.
3.5. SAP mock landscape - always lands a tiny, static MOCK_SAP (EAM/SD: EQUI/IFLOT/LIKP/LIPS) + MOCK_TELEMATICS (GPS) example so the sap-fleet-connector demo (introspection/discovery) has data in an account with no real SAP. Runs .cortex/skills/sap-fleet-connector/scripts/mock_sap_seed.sql (pure static INSERTs - NOT a Data Studio generator), raw tables only (does NOT bind FLEET_APP to SAP), idempotent, best-effort (a WARN never aborts). Not gated by SKIP_DATA.
- Analytic layer - authors the agnostic
FLEET_INTELLIGENCE.* objects the packs read but do not build themselves: DWELL_ANALYSIS.CONFIG, ROUTE_DEVIATION CONFIG + projection views + TRIP_DEVIATION_ANALYSIS (a plain VIEW, no DT refresh), the ROUTE_OPTIMIZATION.CONFIG cost-column safety-net, and the Overture-sourced CATCHMENT tables (POIS/CITIES_BY_STATE/REGIONAL_ADDRESSES with real address/city/state/postcode - the installer acquires the two Overture Marketplace listings idempotently). Runs scripts/analytic_layer.sql, best-effort (a catchment failure never aborts the install); gate off with SKIP_ANALYTIC=1.
- Data contract -
python3 fleet_sa_app/app/packs/_lib/install.py --regenerate -c <connection> builds the 7 agnostic FLEET_APP.* packs; --probe confirms each resolves.
5.5. Semantic views - fleet_sa_app/app/semantic_views.sql creates FLEET_INTELLIGENCE.SEMANTIC + the 5 Cortex Analyst SVs the consumer agent binds to (SV_FLEET_OPS, SV_ROUTE_DEVIATION, SV_CATCHMENT, SV_DWELL_ANALYTICS, SV_ASSET_VELOCITY). DWELL/ASSET_VELOCITY are rebound onto the pack-built FLEET_APP.* views; the rest bind the analytic-layer objects. Runs after packs + analytic layer, before roles/agents (so the role grant and the agent's Cortex Analyst tools resolve). Best-effort; gate off with SKIP_SEMANTIC=1.
- Synapse tools - per-account materialize + deploy of the
user/ops/admin bundles (ROUTING_MCP, FLEET_OPS_MCP, FLEET_ADMIN_MCP). See references/synapse-bundles.md.
- Roles - applies
fleet_sa_app/app/role_binding.sql (agnostic grants only).
- Agents -
CREATE OR REPLACE AGENT FLEET_AGENT (consumer) + FLEET_OPS_AGENT (ops) from the trimmed specs.
- Apps -
scripts/deploy_fleet_sa_app.sh and scripts/deploy_fleet_admin_app.sh; prints both endpoint URLs.
- Routing engine + tool substrate - probes
ROUTING_PLATFORM.CONTRACT.ROUTING_STATUS() / SHOW SERVICES IN DATABASE OPENROUTESERVICE_APP; binds verbs LIVE if the engine is present. If absent (and not --no-engine), builds + provisions it natively via scripts/provision_engine.sh; with --no-engine the verbs install inert. Then applies the engine-agnostic routing contract (routing_platform/setup.sql) and the 9 FLEET_INTELLIGENCE.ROUTING_TOOLS.TOOL_* procedures (from routing-agent/references/deploy-agent.sql) that the synapse routing verbs wrap - without this substrate every FLEET_AGENT routing request fails ("routing service experiencing issues") even with a healthy engine. The installer asserts all 9 TOOL_* procs exist and warns loudly if any are missing. See references/routing-engine.md.
Final output (every run)
At the end of every run the orchestrator prints, and writes into the friction log, a consolidated report with three sections:
- URLs - the resolved public SA app (consumer/analytics) and Admin app (build console) endpoints. Endpoints are polled with a short retry loop because SPCS ingress takes ~1-3 min to go public after service RESUME; if one is still provisioning the report shows the exact
SHOW ENDPOINTS command to fetch it manually.
- Summary - steps OK vs total, routing-substrate status, SAP-mock status, and the friction-log path (plus a loud line if the routing substrate is degraded).
- Next steps - open each app (Snowflake OAuth; a fresh endpoint returns HTTP 302 to login), smoke-test live routing in the SA app agent, and how to re-check endpoints/services.
Live routing engine (default; skip with --no-engine)
Live routing verbs (directions, isochrones, matrix, VRP optimization, find_poi, catchment) require the ORS/VROOM engine. The analytics stack installs and runs without it; by default the installer builds + provisions the engine in the same run. To skip the heavy engine build (routing verbs install inert):
bash .cortex/skills/install-fleet-apps/scripts/install_fleet_apps.sh --connection <connection> --no-engine
The engine build is HEAVY (builds 4 SPCS images + a region routing graph, tens of minutes) but runs by default and is skipped automatically when an engine is already present. provision_engine.sh ensures the OPENROUTESERVICE_APP.CORE infra, builds + pushes the 4 engine images (references/build-images.md), stages the map/config + service specs, loads SQL modules 01-08/15, and lets module 03 bootstrap the default region. The engine keeps the OPENROUTESERVICE_APP.CORE namespace behind the ROUTING_PLATFORM.CONTRACT seam, and preserves the AUTO_SUSPEND_SECS, REBUILD_GRAPHS reuse, and per-region VROOM invariants (see references/available-functions.md, references/snowflake-scripting-guidelines.md, references/snowflake-sql-gotchas.md, references/troubleshooting.md).
Configuration
| Parameter |
Default |
Purpose |
--connection |
(required) |
Snow CLI connection name |
--no-engine |
(unset; engine on) |
Skip the heavy ORS engine build (verbs install inert). Env equivalents: NO_ENGINE=1 or PROVISION_ENGINE=0. --with-engine is accepted as a no-op (engine is the default). |
IMAGE_REPO_SQL_NAME |
resolved (reuse OPENROUTESERVICE_APP.core.image_repository else FLEET_INTELLIGENCE.CORE.IMAGE_REPOSITORY) |
SPCS image repo |
COMPUTE_POOL |
resolved (OPENROUTESERVICE_APP_COMPUTE_POOL else FLEET_APPS_COMPUTE_POOL) |
SPCS compute pool |
CARTO_EAI |
resolved (ORS_CARTO_EAI else FLEET_APP_CARTO_EAI) |
basemap tile egress |
SPEC_STAGE |
resolved |
service-spec stage |
REGION |
SanFrancisco |
seed-data region when seeding is required |
SKIP_INFRA / SKIP_DATA / SKIP_ANALYTIC / SKIP_PACKS / SKIP_SEMANTIC / SKIP_TOOLS / SKIP_ROLES / SKIP_AGENTS / SKIP_APPS / SKIP_ROUTING |
0 |
shorten idempotent re-runs |
Required Privileges
| Privilege |
Scope |
Why |
| CREATE DATABASE / SCHEMA |
account |
FLEET_INTELLIGENCE, FLEET_APP, STARTER_APP, ROUTING_PLATFORM if absent |
| CREATE COMPUTE POOL |
account |
app compute pool when self-provisioned |
| CREATE IMAGE REPOSITORY |
schema |
push app images when self-provisioned |
| CREATE INTEGRATION |
account |
CARTO external access integration when self-provisioned |
| CREATE SERVICE |
schema |
FLEET_SA_APP, FLEET_ADMIN_APP |
| CREATE ROLE + MANAGE GRANTS |
account |
FLEET_APP_USER/OPS/ADMIN, FLEET_APP_DYNAMIC_READER |
| CREATE AGENT, CREATE MCP SERVER |
schema |
consumer/ops agents + synapse bundles |
| SNOWFLAKE.CORTEX_USER |
database role |
Cortex Analyst / agent calls |
ACCOUNTADMIN satisfies all of the above but is not required if the above are granted to a custom role.
Cost Guardrails (optional)
Cost controls that ship enabled by default: dynamic tables use DOWNSTREAM/hourly lags, non-essential tasks are created suspended, the RESCUE_PENDING_PROVISIONS_TASK self-gates, the core SPCS pool is MIN_NODES=1 (scales to 5), the gateway idle-suspends after 1h, Time Travel is 0 on all accelerator databases, and AUTO_HIBERNATE_TASK enters cost-safe mode after 4h idle (toggle in the admin Service Manager). COST_SAFE_MODE() / RESUME_FLEET() give a one-click manual control, and docs/guides/cost-safe-teardown.sql is a paste-in runbook for a live account.
For a HARD ceiling + spend alerting, apply the optional references/cost-guardrails.sql: a RESOURCE MONITOR on the ROUTING_ANALYTICS warehouse plus a SNOWFLAKE.CORE.BUDGET covering the compute pools + warehouse. This is opt-in and NOT run by the installer because it needs ACCOUNTADMIN (or a role granted CREATE RESOURCE MONITOR ON ACCOUNT and CREATE SNOWFLAKE.CORE.BUDGET) plus a deployment-specific credit budget. Edit the two placeholders (MONTHLY_CREDIT_QUOTA, BUDGET_NOTIFY_EMAIL) and run it as such a role.
The admin app's Observability page also shows a "Daily consumption (last 3 weeks)" chart (accelerator credits per day: ROUTING_ANALYTICS + the routing/app SPCS pools) read from SNOWFLAKE.ACCOUNT_USAGE. The admin app's service-owner role needs the narrow SNOWFLAKE.USAGE_VIEWER database role for this - the same references/cost-guardrails.sql includes that grant (step 3). Until granted, the widget renders a "grant required" notice with the exact statement instead of the chart.
Cleanup
ALTER SESSION SET query_tag = '{"origin":"sf_sit-is-fleet","name":"oss-install-fleet-apps","version":{"major":1,"minor":0},"attributes":{"is_quickstart":1,"source":"sql"}}';
DROP SERVICE IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_SA_APP;
DROP SERVICE IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_ADMIN_APP;
DROP AGENT IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_AGENT;
DROP AGENT IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_OPS_AGENT;
DROP DATABASE IF EXISTS FLEET_APP;
DROP DATABASE IF EXISTS STARTER_APP;
-- SAP mock landscape (demo example landed by step 3.5):
DROP DATABASE IF EXISTS MOCK_SAP;
DROP DATABASE IF EXISTS MOCK_TELEMATICS;
-- Self-provisioned infra (only if this skill created them):
DROP EXTERNAL ACCESS INTEGRATION IF EXISTS FLEET_APP_CARTO_EAI;
DROP COMPUTE POOL IF EXISTS FLEET_APPS_COMPUTE_POOL;
-- FLEET_INTELLIGENCE / SYNTHETIC_DATASETS / ROUTING_PLATFORM are shared with the
-- routing engine; drop only on a full teardown.
Use the routing-solution-cleanup skill to auto-discover all tagged objects via COMMENT tracking.
Object ownership (analytic layer)
The agnostic FLEET_INTELLIGENCE.* analytic objects the packs read are owned by skill SQL and authored in the data + analytic steps, in this order:
scripts/seed_data.sql - ensures ROUTING_ANALYTICS, the engine-namespace stubs the loader needs (OPENROUTESERVICE_APP.CORE + REGION_CATALOG), and the ROUTE_OPTIMIZATION base tables, then runs the canonical loader (UNIFIED.* + DIM_DATASETS).
scripts/vehicle_profile_catalog.sql - DIM_VEHICLE_PROFILE / DIM_VEHICLE_DWELL_SLA + the DIM_FLEET asset-column stamp.
scripts/projection_views.sql - the dataset-scoped SYNTHETIC_DATASETS.UNIFIED.V_*_CURRENT views.
scripts/analytic_layer.sql (step 3.5) - DWELL_ANALYSIS.CONFIG, ROUTE_DEVIATION CONFIG + projection views + TRIP_DEVIATION_ANALYSIS (a plain VIEW), the ROUTE_OPTIMIZATION.CONFIG cost-column safety-net, and the Overture-sourced CATCHMENT tables.
These skill SQL files are the single source of truth for a fresh install. The new admin app's fleet_admin_app/ui/src/server/lib/init.ts is a secondary, idempotent runtime owner that overlaps only on the V_*_CURRENT projection views (kept consistent with projection_views.sql by design); its legacy DWELL asset-velocity views are gated on DWELL_ANALYSIS.DT_DWELL_ENRICHED (absent on the agnostic install → skipped) and its MARKETPLACE/BACKLOAD creations reference purged tables → best-effort skip, so init.ts never clobbers the agnostic analytic layer. The legacy build-routing-solution Vite control app (which had its own init.ts) has been removed from the repo.
References
references/conventions.md - query_tag + COMMENT tracking literals.
references/infra.sql - detect-and-reuse-else-create infra provisioning.
references/seed-data.md - agnostic seed-data probe + load path.
references/synapse-bundles.md - per-account materialize + deploy.
references/routing-engine.md - engine detection + native provisioning (default; skip with --no-engine).
references/build-images.md - build + push the 4 ORS/VROOM engine images.
references/available-functions.md - engine SQL functions, profiles, service limits, matrix builders.
references/snowflake-scripting-guidelines.md - SQL Scripting rules for the engine modules.
references/snowflake-sql-gotchas.md - engine SQL constraints (GET_SERVICE_STATUS, RESULT_SCAN, etc.).
references/troubleshooting.md - engine image build / registry / service troubleshooting.
references/cost-guardrails.sql - OPTIONAL privileged resource monitor + budget (see Cost Guardrails).
fleet_sa_app/app/packs/BUSINESS_PROBLEM_TAXONOMY.md - the locked agnostic contract.
1---2name: install-fleet-apps3description: Primary one-command installer for the synapse-based, vehicle/industry-AGNOSTIC fleet analytics architecture on Snowflake: the FLEET_SA_APP consumer app, the FLEET_ADMIN_APP build console, the three role-scoped synapse MCP tool bundles, the neutral FLEET_APP data contract, roles, Cortex agents, and (by default) the live ORS/VROOM routing engine. Use when: install the fleet apps, deploy FLEET_SA_APP and FLEET_ADMIN_APP, set up the agnostic fleet analytics solution, install the synapse fleet stack, provision the routing engine. Self-owning and idempotent: detects-and-reuses-else-creates SPCS infra, seed data, and the ORS engine; pass --no-engine to skip the heavy engine build. Do NOT use for: changing routing maps/profiles (use routing-customization) or the legacy per-vehicle demo skills (fleet-intelligence-car, route-deviation, etc.). Triggers: install fleet apps, install-fleet-apps, deploy fleet sa app, deploy fleet admin app, install synapse fleet stack, set up agnostic fleet solution, provision routing engin4---56# Install Fleet Apps (primary agnostic installer)78One command stands up the entire new-architecture analytics stack and is the **primary** installation path for it. It also **owns the live ORS/VROOM routing engine build** (Phase C): the engine is provisioned natively **by default**, so this skill is fully self-contained. Pass `--no-engine` to skip the heavy engine build.910This skill **owns** all of its artifacts (relocated here), so the stack installs and runs without any other skill. The analytics layer (dashboards, Cortex Analyst, agents) works with no engine; live routing verbs require the ORS engine, which the installer builds and provisions by default (skip with `--no-engine`).1112## Scope: vehicle/industry-AGNOSTIC only1314This installer is mode-agnostic by construction. `VEHICLE_TYPE` is a data dimension carried by the selected dataset - never a schema, view, semantic view, agent tool, or UI surface. The R6 `fleet_sa_app/app/packs/BUSINESS_PROBLEM_TAXONOMY.md` (status: locked) is the authoritative contract.1516| Layer | INSTALLED (agnostic) | EXCLUDED (industry-vertical) |17|---|---|---|18| Packs | `unified_fleet`, `fleet_ops`, `dwell`, `route_deviation`, `route_optimization`, `catchment`, `starter` | `marketplace`, `backload`, `dhl_ntbo` |19| UI views | Fleet/Asset Status, Asset Map, Demand Density (H3), Trip Inspection, Operator Performance, Top Origins, Dwell & Congestion, Route Deviation, Asset Utilization, VRP, Catchment | Freight Marketplace, Backload Matching, DHL pages |20| Agents | `SV_FLEET_OPS`, `SV_DWELL_ANALYTICS`, `SV_ROUTE_DEVIATION`, `SV_ASSET_VELOCITY`, `SV_CATCHMENT` + neutral routing verbs | `SV_DELIVERIES`, `SV_BACKLOAD_MATCHING`, `SV_DHL_BACKLOAD` |21| Seed data | `SYNTHETIC_DATASETS.UNIFIED.*` / `NEUTRAL.*`, `FLEET_INTELLIGENCE.CORE`, DWELL/DEVIATION/ROUTE_OPT CONFIG, `CATCHMENT` base tables | freight offers/partners, DHL tables |2223The installer always installs the **complete** agnostic set - there is no per-use-case selection prompt.2425> **Agent Playground demo tools are dynamic.** The `TOOL_CATCHMENT`,26> `TOOL_DELIVERY_OPTIMIZATION`, and `TOOL_NETWORK_OPTIMIZATION` procs source live,27> region-scoped Overture POIs (`FLEET_INTELLIGENCE.CATCHMENT.POIS` /28> `REGIONAL_ADDRESSES`, BOUNDARY-constrained + routable-filtered) and read the29> active region from `CATCHMENT.CONFIG` - no static demo seed is required. Step 4.630> uploads the region-neutral `agent-demos.json` scenario config to the ORS stage31> (engine-present only; skip with `SKIP_DEMO=1`).3233## Execution Rules34351. All relative paths are relative to this skill's directory (`.cortex/skills/install-fleet-apps/`).362. Replace `<connection>` with the active Snowflake CLI connection. Find it via `snow connection list` (or read `~/.snowflake/connections.toml`) and verify with `snow sql -q "SELECT CURRENT_ACCOUNT()" -c <connection>`.373. The installer is **idempotent**: re-running detects existing objects and reuses them. Use per-layer `SKIP_*` env vars only to shorten re-runs.384. Every object created carries the `oss-install-fleet-apps` COMMENT tag; every session sets the `query_tag` (see `references/conventions.md`).395. After a run, always emit a friction log to `logs/` per the repo `AGENTS.md`.4041## Prerequisites4243- Container runtime (Podman or Docker) running; Node.js >= 20 + npm; Python 3; Snowflake CLI (`snow`).44 - The engine build (on by default) auto-detects **docker first** (a default 2 GB podman machine OOMs the ORS image build). Force a runtime with `CONTAINER_CMD=docker|podman`.45 - Install **crane** (`brew install crane`) for reliable SPCS image pushes - `docker push` to the SPCS registry intermittently hangs on the final manifest commit; `build_push` prefers crane when present (docker runtime). Disable with `USE_CRANE_PUSH=0`.46- `export SNOWFLAKE_CLI_NO_UPDATE_CHECK=true`.47- An active connection whose role can create databases, schemas, services, compute pools, image repositories, external access integrations, roles, and agents (see `## Required Privileges`).48- Repository cloned; the four Carto/Overture Marketplace shares are optional (basemap egress is via the CARTO EAI).4950## One-command install5152```bash53bash .cortex/skills/install-fleet-apps/scripts/install_fleet_apps.sh --connection <connection>54```5556The orchestrator runs these layers in order (detect-and-reuse-else-create throughout):57581. **Preflight** - tools, connection, account.592. **Infra** - image repository, compute pool, CARTO EAI (+ network rule), spec stage. Reuses `OPENROUTESERVICE_APP` equivalents if present; otherwise creates skill-owned objects. See `references/infra.sql`.603. **Data** - probes the agnostic source tables; reuses existing rows, else loads `scripts/seed_data.sql`. See `references/seed-data.md`.613.5. **SAP mock landscape** - always lands a tiny, static `MOCK_SAP` (EAM/SD: EQUI/IFLOT/LIKP/LIPS) + `MOCK_TELEMATICS` (GPS) example so the `sap-fleet-connector` demo (introspection/discovery) has data in an account with no real SAP. Runs `.cortex/skills/sap-fleet-connector/scripts/mock_sap_seed.sql` (pure static INSERTs - NOT a Data Studio generator), raw tables only (does NOT bind `FLEET_APP` to SAP), idempotent, best-effort (a WARN never aborts). Not gated by `SKIP_DATA`.624. **Analytic layer** - authors the agnostic `FLEET_INTELLIGENCE.*` objects the packs read but do not build themselves: `DWELL_ANALYSIS.CONFIG`, `ROUTE_DEVIATION` CONFIG + projection views + `TRIP_DEVIATION_ANALYSIS` (a plain VIEW, no DT refresh), the `ROUTE_OPTIMIZATION.CONFIG` cost-column safety-net, and the Overture-sourced `CATCHMENT` tables (`POIS`/`CITIES_BY_STATE`/`REGIONAL_ADDRESSES` with real address/city/state/postcode - the installer acquires the two Overture Marketplace listings idempotently). Runs `scripts/analytic_layer.sql`, best-effort (a catchment failure never aborts the install); gate off with `SKIP_ANALYTIC=1`.635. **Data contract** - `python3 fleet_sa_app/app/packs/_lib/install.py --regenerate -c <connection>` builds the 7 agnostic `FLEET_APP.*` packs; `--probe` confirms each resolves.645.5. **Semantic views** - `fleet_sa_app/app/semantic_views.sql` creates `FLEET_INTELLIGENCE.SEMANTIC` + the 5 Cortex Analyst SVs the consumer agent binds to (`SV_FLEET_OPS`, `SV_ROUTE_DEVIATION`, `SV_CATCHMENT`, `SV_DWELL_ANALYTICS`, `SV_ASSET_VELOCITY`). DWELL/ASSET_VELOCITY are rebound onto the pack-built `FLEET_APP.*` views; the rest bind the analytic-layer objects. Runs after packs + analytic layer, before roles/agents (so the role grant and the agent's Cortex Analyst tools resolve). Best-effort; gate off with `SKIP_SEMANTIC=1`.656. **Synapse tools** - per-account materialize + deploy of the `user`/`ops`/`admin` bundles (`ROUTING_MCP`, `FLEET_OPS_MCP`, `FLEET_ADMIN_MCP`). See `references/synapse-bundles.md`.667. **Roles** - applies `fleet_sa_app/app/role_binding.sql` (agnostic grants only).678. **Agents** - `CREATE OR REPLACE AGENT FLEET_AGENT` (consumer) + `FLEET_OPS_AGENT` (ops) from the trimmed specs.689. **Apps** - `scripts/deploy_fleet_sa_app.sh` and `scripts/deploy_fleet_admin_app.sh`; prints both endpoint URLs.6910. **Routing engine + tool substrate** - probes `ROUTING_PLATFORM.CONTRACT.ROUTING_STATUS()` / `SHOW SERVICES IN DATABASE OPENROUTESERVICE_APP`; binds verbs LIVE if the engine is present. If absent (and not `--no-engine`), builds + provisions it natively via `scripts/provision_engine.sh`; with `--no-engine` the verbs install inert. Then applies the engine-agnostic routing contract (`routing_platform/setup.sql`) and the 9 `FLEET_INTELLIGENCE.ROUTING_TOOLS.TOOL_*` procedures (from `routing-agent/references/deploy-agent.sql`) that the synapse routing verbs wrap - without this substrate every `FLEET_AGENT` routing request fails ("routing service experiencing issues") even with a healthy engine. The installer asserts all 9 `TOOL_*` procs exist and warns loudly if any are missing. See `references/routing-engine.md`.7071## Final output (every run)7273At the end of every run the orchestrator prints, and writes into the friction log, a consolidated report with three sections:7475- **URLs** - the resolved public SA app (consumer/analytics) and Admin app (build console) endpoints. Endpoints are polled with a short retry loop because SPCS ingress takes ~1-3 min to go public after service RESUME; if one is still provisioning the report shows the exact `SHOW ENDPOINTS` command to fetch it manually.76- **Summary** - steps OK vs total, routing-substrate status, SAP-mock status, and the friction-log path (plus a loud line if the routing substrate is degraded).77- **Next steps** - open each app (Snowflake OAuth; a fresh endpoint returns HTTP 302 to login), smoke-test live routing in the SA app agent, and how to re-check endpoints/services.7879## Live routing engine (default; skip with `--no-engine`)8081Live routing verbs (directions, isochrones, matrix, VRP optimization, find_poi, catchment) require the ORS/VROOM engine. The analytics stack installs and runs without it; by default the installer builds + provisions the engine in the same run. To skip the heavy engine build (routing verbs install inert):8283```bash84bash .cortex/skills/install-fleet-apps/scripts/install_fleet_apps.sh --connection <connection> --no-engine85```8687The engine build is HEAVY (builds 4 SPCS images + a region routing graph, tens of minutes) but runs by default and is skipped automatically when an engine is already present. `provision_engine.sh` ensures the `OPENROUTESERVICE_APP.CORE` infra, builds + pushes the 4 engine images (`references/build-images.md`), stages the map/config + service specs, loads SQL modules `01-08`/`15`, and lets module `03` bootstrap the default region. The engine keeps the `OPENROUTESERVICE_APP.CORE` namespace behind the `ROUTING_PLATFORM.CONTRACT` seam, and preserves the AUTO_SUSPEND_SECS, REBUILD_GRAPHS reuse, and per-region VROOM invariants (see `references/available-functions.md`, `references/snowflake-scripting-guidelines.md`, `references/snowflake-sql-gotchas.md`, `references/troubleshooting.md`).8889## Configuration9091| Parameter | Default | Purpose |92|---|---|---|93| `--connection` | (required) | Snow CLI connection name |94| `--no-engine` | (unset; engine on) | Skip the heavy ORS engine build (verbs install inert). Env equivalents: `NO_ENGINE=1` or `PROVISION_ENGINE=0`. `--with-engine` is accepted as a no-op (engine is the default). |95| `IMAGE_REPO_SQL_NAME` | resolved (reuse `OPENROUTESERVICE_APP.core.image_repository` else `FLEET_INTELLIGENCE.CORE.IMAGE_REPOSITORY`) | SPCS image repo |96| `COMPUTE_POOL` | resolved (`OPENROUTESERVICE_APP_COMPUTE_POOL` else `FLEET_APPS_COMPUTE_POOL`) | SPCS compute pool |97| `CARTO_EAI` | resolved (`ORS_CARTO_EAI` else `FLEET_APP_CARTO_EAI`) | basemap tile egress |98| `SPEC_STAGE` | resolved | service-spec stage |99| `REGION` | `SanFrancisco` | seed-data region when seeding is required |100| `SKIP_INFRA` / `SKIP_DATA` / `SKIP_ANALYTIC` / `SKIP_PACKS` / `SKIP_SEMANTIC` / `SKIP_TOOLS` / `SKIP_ROLES` / `SKIP_AGENTS` / `SKIP_APPS` / `SKIP_ROUTING` | `0` | shorten idempotent re-runs |101102## Required Privileges103104| Privilege | Scope | Why |105|---|---|---|106| CREATE DATABASE / SCHEMA | account | `FLEET_INTELLIGENCE`, `FLEET_APP`, `STARTER_APP`, `ROUTING_PLATFORM` if absent |107| CREATE COMPUTE POOL | account | app compute pool when self-provisioned |108| CREATE IMAGE REPOSITORY | schema | push app images when self-provisioned |109| CREATE INTEGRATION | account | CARTO external access integration when self-provisioned |110| CREATE SERVICE | schema | `FLEET_SA_APP`, `FLEET_ADMIN_APP` |111| CREATE ROLE + MANAGE GRANTS | account | `FLEET_APP_USER/OPS/ADMIN`, `FLEET_APP_DYNAMIC_READER` |112| CREATE AGENT, CREATE MCP SERVER | schema | consumer/ops agents + synapse bundles |113| SNOWFLAKE.CORTEX_USER | database role | Cortex Analyst / agent calls |114115ACCOUNTADMIN satisfies all of the above but is not required if the above are granted to a custom role.116117## Cost Guardrails (optional)118119Cost controls that ship enabled by default: dynamic tables use `DOWNSTREAM`/hourly lags, non-essential tasks are created suspended, the `RESCUE_PENDING_PROVISIONS_TASK` self-gates, the core SPCS pool is `MIN_NODES=1` (scales to 5), the gateway idle-suspends after 1h, Time Travel is `0` on all accelerator databases, and `AUTO_HIBERNATE_TASK` enters cost-safe mode after 4h idle (toggle in the admin Service Manager). `COST_SAFE_MODE()` / `RESUME_FLEET()` give a one-click manual control, and `docs/guides/cost-safe-teardown.sql` is a paste-in runbook for a live account.120121For a HARD ceiling + spend alerting, apply the optional `references/cost-guardrails.sql`: a `RESOURCE MONITOR` on the `ROUTING_ANALYTICS` warehouse plus a `SNOWFLAKE.CORE.BUDGET` covering the compute pools + warehouse. This is opt-in and NOT run by the installer because it needs ACCOUNTADMIN (or a role granted `CREATE RESOURCE MONITOR ON ACCOUNT` and `CREATE SNOWFLAKE.CORE.BUDGET`) plus a deployment-specific credit budget. Edit the two placeholders (`MONTHLY_CREDIT_QUOTA`, `BUDGET_NOTIFY_EMAIL`) and run it as such a role.122123The admin app's Observability page also shows a "Daily consumption (last 3 weeks)" chart (accelerator credits per day: `ROUTING_ANALYTICS` + the routing/app SPCS pools) read from `SNOWFLAKE.ACCOUNT_USAGE`. The admin app's service-owner role needs the narrow `SNOWFLAKE.USAGE_VIEWER` database role for this - the same `references/cost-guardrails.sql` includes that grant (step 3). Until granted, the widget renders a "grant required" notice with the exact statement instead of the chart.124125## Cleanup126127```sql128ALTER SESSION SET query_tag = '{"origin":"sf_sit-is-fleet","name":"oss-install-fleet-apps","version":{"major":1,"minor":0},"attributes":{"is_quickstart":1,"source":"sql"}}';129130DROP SERVICE IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_SA_APP;131DROP SERVICE IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_ADMIN_APP;132DROP AGENT IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_AGENT;133DROP AGENT IF EXISTS FLEET_INTELLIGENCE.SYNAPSE_USER.FLEET_OPS_AGENT;134DROP DATABASE IF EXISTS FLEET_APP;135DROP DATABASE IF EXISTS STARTER_APP;136-- SAP mock landscape (demo example landed by step 3.5):137DROP DATABASE IF EXISTS MOCK_SAP;138DROP DATABASE IF EXISTS MOCK_TELEMATICS;139-- Self-provisioned infra (only if this skill created them):140DROP EXTERNAL ACCESS INTEGRATION IF EXISTS FLEET_APP_CARTO_EAI;141DROP COMPUTE POOL IF EXISTS FLEET_APPS_COMPUTE_POOL;142-- FLEET_INTELLIGENCE / SYNTHETIC_DATASETS / ROUTING_PLATFORM are shared with the143-- routing engine; drop only on a full teardown.144```145146> Use the `routing-solution-cleanup` skill to auto-discover all tagged objects via COMMENT tracking.147148## Object ownership (analytic layer)149150The agnostic `FLEET_INTELLIGENCE.*` analytic objects the packs read are owned by skill SQL and authored in the data + analytic steps, in this order:151152- `scripts/seed_data.sql` - ensures `ROUTING_ANALYTICS`, the engine-namespace stubs the loader needs (`OPENROUTESERVICE_APP.CORE` + `REGION_CATALOG`), and the `ROUTE_OPTIMIZATION` base tables, then runs the canonical loader (`UNIFIED.*` + `DIM_DATASETS`).153- `scripts/vehicle_profile_catalog.sql` - `DIM_VEHICLE_PROFILE` / `DIM_VEHICLE_DWELL_SLA` + the `DIM_FLEET` asset-column stamp.154- `scripts/projection_views.sql` - the dataset-scoped `SYNTHETIC_DATASETS.UNIFIED.V_*_CURRENT` views.155- `scripts/analytic_layer.sql` (step 3.5) - `DWELL_ANALYSIS.CONFIG`, `ROUTE_DEVIATION` CONFIG + projection views + `TRIP_DEVIATION_ANALYSIS` (a plain VIEW), the `ROUTE_OPTIMIZATION.CONFIG` cost-column safety-net, and the Overture-sourced `CATCHMENT` tables.156157These skill SQL files are the single source of truth for a fresh install. The new admin app's `fleet_admin_app/ui/src/server/lib/init.ts` is a secondary, idempotent runtime owner that overlaps only on the `V_*_CURRENT` projection views (kept consistent with `projection_views.sql` by design); its legacy DWELL asset-velocity views are gated on `DWELL_ANALYSIS.DT_DWELL_ENRICHED` (absent on the agnostic install → skipped) and its `MARKETPLACE`/`BACKLOAD` creations reference purged tables → best-effort skip, so init.ts never clobbers the agnostic analytic layer. The legacy `build-routing-solution` Vite control app (which had its own `init.ts`) has been removed from the repo.158159## References160161- `references/conventions.md` - query_tag + COMMENT tracking literals.162- `references/infra.sql` - detect-and-reuse-else-create infra provisioning.163- `references/seed-data.md` - agnostic seed-data probe + load path.164- `references/synapse-bundles.md` - per-account materialize + deploy.165- `references/routing-engine.md` - engine detection + native provisioning (default; skip with `--no-engine`).166- `references/build-images.md` - build + push the 4 ORS/VROOM engine images.167- `references/available-functions.md` - engine SQL functions, profiles, service limits, matrix builders.168- `references/snowflake-scripting-guidelines.md` - SQL Scripting rules for the engine modules.169- `references/snowflake-sql-gotchas.md` - engine SQL constraints (GET_SERVICE_STATUS, RESULT_SCAN, etc.).170- `references/troubleshooting.md` - engine image build / registry / service troubleshooting.171- `references/cost-guardrails.sql` - OPTIONAL privileged resource monitor + budget (see Cost Guardrails).172- `fleet_sa_app/app/packs/BUSINESS_PROBLEM_TAXONOMY.md` - the locked agnostic contract.