mirror of
https://github.com/bilawalsidhu/gods-eye-view.git
synced 2026-11-05 10:53:59 +00:00
fix(tools): identify historical camera fallback imagery (#1118)
The CCTV frame proxy marks a Street View fallback with X-CCTV-Source, but the portable source dropped the header and get_cctv_snapshot always reported a current view credited to the camera's agency. The source now keeps the recognised provenance, and the tool labels Street View frames as historical Google imagery, refuses synthetic placeholders, and reports unknown provenance without claiming a current view.
This commit is contained in:
1 parent
79176667b0
commit
2fd1b4323c
7 files changed
+256
-10
No files matched your search
@@ -3,6 +3,12 @@ import {
|
||||
FRAME_ENDPOINT,
|
||||
MEDIA_ENDPOINT,
|
||||
} from './sourcePolicy.js';
|
||||
const FRAME_SOURCE_KINDS = new Set([
|
||||
'upstream-image',
|
||||
'hls-pull',
|
||||
'streetview',
|
||||
'synthetic',
|
||||
]);
|
||||
function safeNumber(value, fallback = NaN) {
|
||||
const n = Number(value);
|
||||
return Number.isFinite(n) ? n : fallback;
|
||||
@@ -51,7 +57,7 @@ export function createCctvSource({
|
||||
},
|
||||
getFrameUrl: frameUrlFor,
|
||||
getMediaUrl: mediaUrlFor,
|
||||
/** Read one current frame through the registered frame endpoint. */
|
||||
/** Read a registered frame and its provenance, including fallback frames. */
|
||||
async getFrame(camera, { signal } = {}) {
|
||||
signal?.throwIfAborted();
|
||||
const response = await fetchImpl(frameUrlFor(camera), {
|
||||
@@ -62,7 +68,12 @@ export function createCctvSource({
|
||||
const bytes = new Uint8Array(await response.arrayBuffer());
|
||||
signal?.throwIfAborted();
|
||||
const type = response.headers.get('content-type') || '';
|
||||
return { contentType: type.split(';')[0].trim().toLowerCase(), bytes };
|
||||
const sourceKind = response.headers.get('x-cctv-source');
|
||||
return {
|
||||
contentType: type.split(';')[0].trim().toLowerCase(),
|
||||
bytes,
|
||||
sourceKind: FRAME_SOURCE_KINDS.has(sourceKind) ? sourceKind : null,
|
||||
};
|
||||
},
|
||||
};
|
||||
}
|
||||
@@ -173,3 +173,26 @@ test('frames are read through the registered frame endpoint', async () => {
|
||||
});
|
||||
await assert.rejects(failing.getFrame(camera), /Camera frame HTTP 502/);
|
||||
});
|
||||
|
||||
test('frame provenance admits the proxy kinds and leaves missing or unknown headers unknown', async () => {
|
||||
for (const kind of [
|
||||
'upstream-image',
|
||||
'hls-pull',
|
||||
'streetview',
|
||||
'synthetic',
|
||||
'other',
|
||||
null,
|
||||
]) {
|
||||
const source = createCctvSource({
|
||||
fetchImpl: async () =>
|
||||
new Response(new Uint8Array([1]), {
|
||||
headers: {
|
||||
'Content-Type': 'image/png',
|
||||
...(kind ? { 'X-CCTV-Source': kind } : {}),
|
||||
},
|
||||
}),
|
||||
});
|
||||
const frame = await source.getFrame(camera);
|
||||
assert.equal(frame.sourceKind, kind === 'other' ? null : kind);
|
||||
}
|
||||
});
|
||||
Reference in new issue
Block a user