Modèles de données
Les principales formes d’objets renvoyées par l’API. Les horodatages sont en millisecondes epoch, sauf mention contraire.
interface Marker { id: string; latitude: number; longitude: number; title: string; description?: string; // Markdown color: string; // hex, e.g. "#3B82F6" markerIconId?: string; // reference into the room icon registry markerIconSize?: number; // per-marker size override (px) tags?: string[]; createdBy: string; createdAt: number; eventDate?: number; // for the timeline imageKey?: string; // storage key — fetch via .../markers/image?key=… thumbnailKey?: string; imageBlob?: string; // legacy inline image, superseded by imageKey thumbnailBlob?: string; // legacy embeddedMediaUrl?: string; // YouTube / Vimeo / external mediaSize?: 'sm' | 'md' | 'lg'; // embedded-media popup width (default 'md') imageMetadata?: ImageMetadata; // EXIF read from the attached photo — read-only}
interface ImageMetadata { gpsSource: boolean; // true when the marker sits where the photo was taken cameraMake?: string; cameraModel?: string; dateTaken?: number; // epoch ms altitude?: number; orientation?: number;}imageMetadata est déduit lorsqu’une photo est jointe dans l’application — une photo géolocalisée
déplace le repère vers sa position GPS et renseigne gpsSource. Ce champ n’est pas modifiable via
l’API, et remplacer imageKey/thumbnailKey l’efface, afin qu’une nouvelle photo n’hérite jamais de la
provenance de la précédente.
Les points de terminaison de repère unique (GET/PATCH /api/rooms/:roomId/markers/:markerId) omettent
createdByEmail et les champs de blob en ligne (imageBlob, thumbnailBlob, iconBlob) dans leurs
réponses ; le point de terminaison de liste renvoie la forme stockée telle quelle.
PolygonLayer
Section intitulée « PolygonLayer »interface PolygonLayer { id: string; name: string; description?: string; geometryType?: string; // "Polygon" | "MultiPolygon" | "LineString" | ... color: string; opacity: number; // 0–1 strokeWeight: number; // px visible: boolean; totalFeatureCount?: number; createdBy: string; createdAt: number; eventDate?: number; bbox?: [number, number, number, number]; // [minLon, minLat, maxLon, maxLat]}RasterLayer
Section intitulée « RasterLayer »interface RasterLayer { id: string; name: string; description?: string; fileSize: number; // original TIFF size, bytes bounds: [number, number, number, number]; minZoom: number; maxZoom: number; opacity: number; // 0–1 visible: boolean; createdAt: number; eventDate?: number; processingStatus?: 'pending' | 'processing' | 'complete' | 'error'; // display (see the Raster Layers reference) colormap?: string; vmin?: number; vmax?: number; band?: number; // 0 = natural color / all bands renderMode?: 'tiles' | 'image_overlay' | 'rgb'; rgbBands?: [number, number, number]; // 1-based [R, G, B]}MarkerIcon
Section intitulée « MarkerIcon »interface MarkerIcon { id: string; name: string; iconBlob: string; // image data (base64) category?: string; size: number; // display height in px (default 27) createdAt: number;}Room et RoomMember
Section intitulée « Room et RoomMember »interface Room { roomId: string; createdBy: string; // owner's user ID createdAt: number; markerCount: number; commitCount: number; lastActivity?: number; isPublic?: boolean;}
interface RoomMember { userId: string; email: string; name?: string; role: 'owner' | 'editor' | 'viewer'; addedBy: string; addedAt: number;}
