@inspectorhub/field-ui 0.3.0 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -24,7 +24,7 @@ The root entry exports:
24
24
 
25
25
  | Group | Exports |
26
26
  |---|---|
27
- | The editor | `FieldEditor` (props: `{ data: EditorData }`) |
27
+ | The editor | `FieldEditor` (props: `{ data: EditorData; readOnly?: boolean }`) |
28
28
  | Host contract | `FieldDataSourceProvider`, `useFieldDataSource`, `useFieldCommand`, `useFieldEnsureHuman`, `useFieldSlots`, `isIgnored`, `setFieldLocale`, `bindFieldLocaleSource`, and the TypeScript types of the contract (`FieldDataSource`, `FieldHostSlots`, `FieldUrls`, `FieldResources`, `EditorData`, `SessionInfo`, and so on) |
29
29
  | Finding keys | `findingKey`, `findingsForUnit`, `isMetaKey` (the same functions the server uses to address a result) |
30
30
  | Photo decoding | `DecodeImageError`, `isDecodeImageError` (matches by error name, so it works across two copies of the package), and the types `DecodeImage`, `DecodeImageOptions`, `DecodedImage` (see `media` below) |
@@ -46,6 +46,13 @@ setFieldLocale(session.locale); // and keep it in step with the host's own local
46
46
  </FieldDataSourceProvider>
47
47
  ```
48
48
 
49
+ Pass `readOnly` to show an inspection for reading only. Nothing in a read-only editor can write: the results document is
50
+ never handed to a write helper, every write on the data source (commands, uploads, the media store, the resource writes)
51
+ is refused with "This inspection is read-only.", and the controls that write (rating row, notes input, add-photo tile,
52
+ publish, sign, finish, structure and template editing, settings, units, cost items, batch and Speed mode) are not
53
+ rendered. Navigation, the section and item lists, the rating as an indicator, notes as text, photos and their viewer, the
54
+ preview and updates from other people keep working. Without `readOnly` nothing changes.
55
+
49
56
  What the host has to provide:
50
57
 
51
58
  - A `FieldDataSource` (next section). `editorData` is what its `load()` returns.
@@ -131,6 +138,10 @@ signatures):
131
138
  neutral notice and counts the batch as saved, not failed.
132
139
  - `urls`: `FieldUrls`, the address builders for photos, reports, presence and
133
140
  in-app paths.
141
+ `photo()` is synchronous; a host that can only produce an address later (a photo it fetches and caches) provides the
142
+ optional `subscribe(listener)` and calls the listener whenever any photo address may have changed. The editor then asks
143
+ `photo()` again and its thumbnails, viewer and previews show the new address. Calls may be batched; `subscribe` returns
144
+ the unsubscribe function. Absent, nothing changes.
134
145
  - `resources`: `FieldResources`, optional capabilities (preferences, canned
135
146
  comments, cost items, repair items, media pool, settings sheet, AI assist,
136
147
  publish readiness, template search, version history, video). A member the
@@ -524,6 +524,12 @@ interface TagLibraryEntry {
524
524
  name: string;
525
525
  color: string;
526
526
  }
527
+ /** The tags on each checklist item of one inspection, keyed by the item's id (the editor's chips). */
528
+ type ItemTagMap = Record<string, Array<{
529
+ id: string;
530
+ name: string;
531
+ color?: string;
532
+ }>>;
527
533
  /** The loader returns `{ id, name, color }` rows. */
528
534
  interface DefectCategory {
529
535
  id: string;
@@ -1364,6 +1370,13 @@ interface CollabConnector {
1364
1370
  }
1365
1371
  interface FieldUrls {
1366
1372
  photo(inspectionId: string, key: string): string;
1373
+ /**
1374
+ * Optional. `photo()` is synchronous, so a host that can only produce an address later (a photo it fetches and
1375
+ * caches, a signed address it renews) calls the listener whenever any photo address may have changed; the editor then
1376
+ * asks `photo()` again and its thumbnails, viewer and previews show the new address. Calls may be batched. Returns
1377
+ * the unsubscribe function. Absent: addresses are read when the editor renders, as before.
1378
+ */
1379
+ subscribe?(listener: () => void): () => void;
1367
1380
  reportPreview(tenantSlug: string, inspectionId: string): string | null;
1368
1381
  reportPdf(inspectionId: string): string | null;
1369
1382
  /**
@@ -1431,6 +1444,20 @@ interface FieldResources {
1431
1444
  id?: string;
1432
1445
  }>>;
1433
1446
  };
1447
+ /**
1448
+ * The tags on each checklist item of one inspection (the web host serves it from
1449
+ * `/resources/inspection-item-tags`). `list` never rejects: `null` means the host could not read it, and the
1450
+ * editor then shows what it already has. `add` and `remove` never reject either: a not-ok answer means the host
1451
+ * did not store the change, and the editor takes it back. Both are idempotent (adding a tag that is attached, or
1452
+ * removing one that is not, changes nothing), and the tag must be one of the company's own (`EditorData.tagLibrary`).
1453
+ * Absent means the host cannot keep item tags: the editor holds them in memory for the session only, as it did
1454
+ * before this member existed.
1455
+ */
1456
+ itemTags?: {
1457
+ list(inspectionId: string): Promise<ItemTagMap | null>;
1458
+ add(inspectionId: string, itemId: string, tagId: string): Promise<CommandResult>;
1459
+ remove(inspectionId: string, itemId: string, tagId: string): Promise<CommandResult>;
1460
+ };
1434
1461
  /** The tenant's repair-item catalogue (it is not per inspection). `list` never rejects: a failed read answers none. */
1435
1462
  repairItems?: {
1436
1463
  list(): Promise<RepairItemOption[]>;
package/dist/index.d.ts CHANGED
@@ -1,5 +1,5 @@
1
- import { F as FieldCommand, C as CommandResult, a as CommandData, b as FieldDataSource, E as EditorData, I as InspectionPrefs } from './data-source-IaWUdrIc.js';
2
- export { A as AiAssistInput, c as AiAssistResult, d as AutoAdvanceMode, e as AutofillReason, B as BulkCreateUnitsBody, f as CollabConnector, g as CommandDataMap, h as CommandKey, i as CommentsLibraryEntry, j as CommentsLibraryQuery, k as CommentsLibraryRow, l as CommercialPresets, m as ComplianceCommand, n as CompliancePanelData, o as CostItemView, p as CostItemWrite, q as CostItemsListing, r as CoverPhotoOption, D as DateFormat, s as DecodeImage, t as DecodeImageError, u as DecodeImageOptions, v as DecodedImage, w as DefectCategory, x as DocumentReviewItemView, y as EditorInspection, z as ExecuteOptions, G as FieldResources, H as FieldUrls, J as GalleryPhoto, K as InspectionUnit, M as METADATA_PRESETS, L as MediaFileResult, N as MediaPoolListing, O as MediaUploader, P as NotifyOptions, Q as NotifyVariant, R as OutboundCoolingWindow, S as PcaNarrative, T as PcaNarrativeData, U as PendingMediaRecord, V as PendingMediaStore, W as PhotoAnnotateMeta, X as PhotoCropMeta, Y as PhotoCropTransform, Z as PhotoUploadMeta, _ as PropertyMetaField, $ as PsqView, a0 as PublishBlockingDefect, a1 as PublishReadiness, a2 as RatingLevel, a3 as RelianceText, a4 as RepairItemOption, a5 as ReportLinkTtl, a6 as ReportProfileOption, a7 as ReportSignoffView, a8 as ResultMap, a9 as ResultsDocHandle, aa as RevisionStatus, ab as SaveStructureTemplateCommand, ac as SchemaItem, ad as SchemaSection, ae as SessionInfo, af as SettingsSheetData, ag as StatutoryCoverage, ah as StatutoryDetails, ai as TagLibraryEntry, aj as TemplateItemBody, ak as TemplateSchema, al as TemplateSearchResult, am as TemplateSnapshot, an as TemplateSummary, ao as TimeFormat, ap as UnitCommand, aq as UnitProgress, ar as VersionSnapshotContent, as as VersionSnapshotEntry, at as VideoFinalizeInput, au as VideoUploadRef, av as VideoUploadTicket, aw as isDecodeImageError, ax as resolvePcaNarrative } from './data-source-IaWUdrIc.js';
1
+ import { F as FieldCommand, C as CommandResult, a as CommandData, b as FieldDataSource, E as EditorData, I as InspectionPrefs } from './data-source-B3NrVs6i.js';
2
+ export { A as AiAssistInput, c as AiAssistResult, d as AutoAdvanceMode, e as AutofillReason, B as BulkCreateUnitsBody, f as CollabConnector, g as CommandDataMap, h as CommandKey, i as CommentsLibraryEntry, j as CommentsLibraryQuery, k as CommentsLibraryRow, l as CommercialPresets, m as ComplianceCommand, n as CompliancePanelData, o as CostItemView, p as CostItemWrite, q as CostItemsListing, r as CoverPhotoOption, D as DateFormat, s as DecodeImage, t as DecodeImageError, u as DecodeImageOptions, v as DecodedImage, w as DefectCategory, x as DocumentReviewItemView, y as EditorInspection, z as ExecuteOptions, G as FieldResources, H as FieldUrls, J as GalleryPhoto, K as InspectionUnit, M as METADATA_PRESETS, L as MediaFileResult, N as MediaPoolListing, O as MediaUploader, P as NotifyOptions, Q as NotifyVariant, R as OutboundCoolingWindow, S as PcaNarrative, T as PcaNarrativeData, U as PendingMediaRecord, V as PendingMediaStore, W as PhotoAnnotateMeta, X as PhotoCropMeta, Y as PhotoCropTransform, Z as PhotoUploadMeta, _ as PropertyMetaField, $ as PsqView, a0 as PublishBlockingDefect, a1 as PublishReadiness, a2 as RatingLevel, a3 as RelianceText, a4 as RepairItemOption, a5 as ReportLinkTtl, a6 as ReportProfileOption, a7 as ReportSignoffView, a8 as ResultMap, a9 as ResultsDocHandle, aa as RevisionStatus, ab as SaveStructureTemplateCommand, ac as SchemaItem, ad as SchemaSection, ae as SessionInfo, af as SettingsSheetData, ag as StatutoryCoverage, ah as StatutoryDetails, ai as TagLibraryEntry, aj as TemplateItemBody, ak as TemplateSchema, al as TemplateSearchResult, am as TemplateSnapshot, an as TemplateSummary, ao as TimeFormat, ap as UnitCommand, aq as UnitProgress, ar as VersionSnapshotContent, as as VersionSnapshotEntry, at as VideoFinalizeInput, au as VideoUploadRef, av as VideoUploadTicket, aw as isDecodeImageError, ax as resolvePcaNarrative } from './data-source-B3NrVs6i.js';
3
3
  import * as React from 'react';
4
4
  import { ReactNode } from 'react';
5
5
  import * as Y from 'yjs';
@@ -126,13 +126,10 @@ interface FieldCommandRunner {
126
126
  */
127
127
  declare function useFieldCommand(inspectionId: string): FieldCommandRunner;
128
128
 
129
- /**
130
- * The inspection editor page. It reads everything from its `data` prop, the field data source and the host
131
- * slots, so any host (web route, native shell) mounts it the same way. `data` must follow the host's
132
- * revalidation: units, publish state and the rest are read from it on every render.
133
- */
134
- declare function FieldEditor({ data }: {
129
+ /** The inspection editor page. `readOnly` shows it for reading only: nothing in it can write, and the write controls are not offered. */
130
+ declare function FieldEditor({ data, readOnly }: {
135
131
  data: EditorData;
132
+ readOnly?: boolean;
136
133
  }): React.JSX.Element;
137
134
 
138
135
  declare function findingKey(unitId: string | null | undefined, sectionId: string, itemId: string): string;