-
Notifications
You must be signed in to change notification settings - Fork 6
feat: Gtfs change tracker 1634 #1737
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Changes from 16 commits
Commits
Show all changes
23 commits
Select commit
Hold shift + click to select a range
f442d41
Preliminary code.
jcpitre fdafd7b
Read pre-extracted GTFS files from GCS instead of downloading the dat…
jcpitre 2d5a130
Added terraform config
jcpitre 03969b0
Mounted buckets on file system in terraform
jcpitre 806dc29
Mount GCS bucket on gtfs_change_tracker via terraform_data workaround
jcpitre 4489e24
Allowed ALL ingress
jcpitre 5b1177f
Change ids to stable_ids
jcpitre 55b9942
Use stable IDs in payload and return plain UUIDs from _resolve_datasets
jcpitre dcdf833
Idempotency check, memory limiting, and retry suppression
jcpitre ffe92d2
Added dry_run and allow_overwrite payload parameters.
jcpitre 8e35bd6
Flipped allow_overwrite to disallow_overwrite
jcpitre 8d8f164
Added README.md
jcpitre efc538e
Merge branch 'main' into gtfs_change_tracker-1634
jcpitre c0320e6
Corrected some tests
jcpitre c9ccd42
Gated the call to the change tracker based on the presence in the gtf…
jcpitre 9f2b47e
Adjusted the memory allocation
jcpitre 6ecedd0
Made sure the base dataset is from the right feed.
jcpitre fcec71a
Remove CHANGELOG_DB_WRITE_ENABLED flag (covered by dry_run)
jcpitre a2254ec
Made the uploaded report public
jcpitre 8420941
improve error logging, add payload to error response, and fix upsert …
jcpitre a1fa432
Changed the name to gtfs-datasets-comparer
jcpitre 358f6ad
Changed the folder name to gtfs-datasets-comparer
jcpitre b3f06be
Merge branch 'main' into gtfs_change_tracker-1634
jcpitre File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,82 @@ | ||
| # GTFS Change Tracker | ||
|
|
||
| This function computes a structured diff between two consecutive GTFS datasets and stores the resulting changelog in GCS and the database. | ||
|
|
||
| The function reads pre-extracted GTFS files from a GCS-mounted bucket (uploaded by `batch_process_dataset`), runs the diff engine, uploads the changelog JSON to GCS, and upserts a row in `gtfs_dataset_changelog`. | ||
|
|
||
| ## Usage | ||
|
|
||
| The function receives the following request: | ||
| ``` | ||
| { | ||
| "feed_stable_id": str, – stable_id of the GTFS feed | ||
| "base_dataset_stable_id": str, – stable_id of the base (older) dataset | ||
| "new_dataset_stable_id": str, – stable_id of the new (recent) dataset | ||
| "disallow_overwrite": bool (optional), – skip if changelog already exists (default: false) | ||
| "dry_run": bool (optional) – compute diff but skip GCS upload and DB write (default: false) | ||
| } | ||
| ``` | ||
|
|
||
| Example: | ||
| ```json | ||
| { | ||
| "feed_stable_id": "mdb-2142", | ||
| "base_dataset_stable_id": "mdb-2142-202502251658", | ||
| "new_dataset_stable_id": "mdb-2142-202507081652" | ||
| } | ||
| ``` | ||
|
|
||
| Example curl call: | ||
| ```bash | ||
| curl -X POST https://<function-url> \ | ||
| -H "Authorization: Bearer $(gcloud auth print-identity-token)" \ | ||
| -H "Content-Type: application/json" \ | ||
| -d '{ | ||
| "feed_stable_id": "mdb-2142", | ||
| "base_dataset_stable_id": "mdb-2142-202502251658", | ||
| "new_dataset_stable_id": "mdb-2142-202507081652" | ||
| }' | ||
| ``` | ||
|
|
||
| ### `disallow_overwrite` | ||
| By default the function will overwrite an existing changelog for the same dataset pair. Set `disallow_overwrite: true` to skip execution if a changelog already exists in GCS. | ||
|
|
||
| ### `dry_run` | ||
| When `dry_run: true`, the diff is computed and a summary is returned in the response, but nothing is written to GCS or the database. Useful for validating that the extracted files are present and the diff engine runs correctly. | ||
|
|
||
| ## Response | ||
|
|
||
| Success: | ||
| ```json | ||
| { | ||
| "status": "success", | ||
| "message": "Changelog generated successfully.", | ||
| "changelog_url": "https://storage.googleapis.com/<bucket>/<feed>/<dataset>/..." | ||
| } | ||
| ``` | ||
|
|
||
| Dry run: | ||
| ```json | ||
| { | ||
| "status": "success", | ||
| "message": "Dry run completed. Diff computed but not persisted.", | ||
| "summary": { | ||
| "total_changes": 42, | ||
| "files_added_count": 0, | ||
| "files_deleted_count": 0, | ||
| "files_modified_count": 3, | ||
| ... | ||
| } | ||
| } | ||
| ``` | ||
|
|
||
| The function always returns HTTP 200, including on errors. Errors are reported in the response body under `"status": "error"`. This prevents GCP from retrying failures where re-running with the same parameters would produce the same result. | ||
|
|
||
| ## GCP environment variables | ||
|
|
||
| - `DATASETS_BUCKET_NAME`: The GCS bucket where datasets are stored (required). Must include the environment suffix, e.g. `mobilitydata-datasets-dev`. | ||
| - `DATASETS_BUCKET_MOUNT`: Mount path for the GCS bucket (default: `/mobilitydata-datasets`). | ||
| - `GTFS_DIFF_DUCKDB_TMPDIR`: Mount path for the in-memory tmpfs used by the diff engine (default: `/tmp/in-memory`). Used by `limit_gcp_memory` to compute the available process memory and set `RLIMIT_AS`, preventing silent OOM kills. | ||
| - `MEMORY_MARGIN_MB`: Safety margin in MiB subtracted from the memory limit before setting `RLIMIT_AS` (default: `200`). | ||
| - `CHANGELOG_DB_WRITE_ENABLED`: Set to `true` to enable writing changelog records to the database (default: `false`). | ||
| - `LOGGING_LEVEL`: Log level (default: `INFO`). | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,31 @@ | ||
| { | ||
| "name": "gtfs-change-tracker", | ||
| "description": "Tracks changes between two GTFS datasets and stores a structured changelog in GCS and the database", | ||
| "entry_point": "gtfs_change_tracker", | ||
| "timeout": 540, | ||
| "memory": "8Gi", | ||
| "trigger_http": true, | ||
| "include_folders": ["helpers"], | ||
| "include_api_folders": ["database_gen", "database", "common"], | ||
| "environment_variables": [ | ||
| { | ||
| "key": "DATASETS_BUCKET_NAME" | ||
| }, | ||
| { | ||
| "key": "LOGGING_LEVEL" | ||
| }, | ||
| { | ||
| "key": "GTFS_DIFF_DUCKDB_TMPDIR" | ||
| } | ||
| ], | ||
| "secret_environment_variables": [ | ||
| { | ||
| "key": "FEEDS_DATABASE_URL" | ||
| } | ||
| ], | ||
| "ingress_settings": "ALLOW_ALL", | ||
| "max_instance_request_concurrency": 1, | ||
| "max_instance_count": 10, | ||
| "min_instance_count": 0, | ||
| "available_cpu": 2 | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,22 @@ | ||
| # Common packages | ||
| functions-framework==3.* | ||
| google-cloud-logging | ||
| psycopg2-binary==2.9.6 | ||
| urllib3~=2.6.3 | ||
| attrs~=23.1.0 | ||
| certifi~=2025.8.3 | ||
|
|
||
| # SQL Alchemy and Geo Alchemy | ||
| SQLAlchemy==2.0.23 | ||
| geoalchemy2==0.14.7 | ||
|
|
||
| # Google specific packages for this function | ||
| flask | ||
| google-cloud-storage | ||
| google-cloud-tasks | ||
|
|
||
| # GTFS diff engine | ||
| gtfs-diff-engine==0.1.0 | ||
|
|
||
| # Configuration | ||
| python-dotenv==1.2.2 |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,2 @@ | ||
| pytest~=7.4.3 | ||
| requests-mock |
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.