Conversation
Add GeoInfo::set_response_headers() to set x-geo-* headers on responses and wire it into the centralized response middleware in main.rs. When geo data is unavailable, sets x-geo-info-available: false. Remove unused get_dma_code() function. Add unit tests for the new method. Resolves #280
…e geo header logic into a new helper function.
There was a problem hiding this comment.
Nice work centralizing the response headers — the finalize_response helper is a solid pattern and the dead get_dma_code cleanup is welcome. Two things to address before merging:
1. Gate x-geo-metro-code on has_metro_code()
In crates/common/src/geo.rs, set_response_headers always emits x-geo-metro-code (line 95), so when Fastly has no DMA data it sends x-geo-metro-code: 0. This is ambiguous — consumers can't distinguish "metro code is actually 0" from "no metro data available."
There's already a has_metro_code() helper (line 81) built for this. Consider gating the header the same way region is handled:
// current (line 95)
response.set_header(HEADER_X_GEO_METRO_CODE, self.metro_code.to_string());
// suggested
if self.has_metro_code() {
response.set_header(HEADER_X_GEO_METRO_CODE, self.metro_code.to_string());
}The existing test should also be updated — add a case where metro_code is 0 and assert the header is absent, similar to the set_response_headers_omits_region_when_none test.
2. Header precedence in finalize_response
In crates/fastly/src/main.rs, finalize_response (lines 150-167) writes headers in this order:
- Geo headers (
x-geo-*) - Version/staging (
x-ts-version,x-ts-env) settings.response_headers(operator-configured)
Since set_header overwrites, an operator who configures x-geo-city or x-ts-version in their settings would silently replace the real values. If this is intentional (operators should be able to override), a short comment in the code documenting the precedence would be enough. If it's not intentional, the operator headers should be written first, or the managed header keys should be skipped when iterating settings.response_headers.
Summary
GeoInfo::set_response_headers()to setx-geo-*headers on outgoing responses, enabling publishers to access Fastly geolocation data (city, country, continent, coordinates, metro code, region) from every Trusted Server response.main.rsso all routes receive geo headers. When geo data is unavailable (e.g., local dev), setsx-geo-info-available: false.get_dma_code()function that was dead code (no callers) and duplicatedGeoInfo::from_request()logic.Changes
crates/common/src/geo.rsset_response_headers()method toGeoInfo; remove deadget_dma_code()function; add 5 unit testscrates/fastly/src/main.rsGeoInfobefore routing; set geo headers on every response in response middlewareCloses
Closes #280
Test plan
cargo test --workspacecargo clippy --all-targets --all-features -- -D warningscargo fmt --all -- --checkcd crates/js/lib && npx vitest run(pre-existingERR_REQUIRE_ESMfailure on main — unrelated)cd crates/js/lib && npm run formatcd docs && npm run formatcargo build --bin trusted-server-fastly --release --target wasm32-wasip1fastly compute serveChecklist
unwrap()in production code — useexpect("should ...")tracingmacros (notprintln!)