MaintenanceTicket
zensile-sdk/company/maintenanceTicket.ts. A facility repair/issue ticket at a Location, optionally narrowed to a specific Room, with up to MAX_TICKET_PHOTOS photos and MAX_TICKET_DOCUMENTS documents attached via the generic media system.
Fields
LazyMaintenanceTicketData: id, companyID, locationID, roomID?: string | null, name?: string | null, state: MaintenanceTicketState, priority: MaintenanceTicketPriority.
MaintenanceTicketData extends LazyMaintenanceTicketData adds description?, notes?, resolvedAt?: Date | null, createdAt, updatedAt (free-text detail fields only present on the non-lazy fetch).
CreateMaintenanceTicketData: locationID, roomID?, name?, description?, notes?, state?, priority?.
Enums
MaintenanceTicketState = "active" | "paused" | "resolved" (MaintenanceTicketStateOptions for display labels).
MaintenanceTicketPriority = "low" | "medium" | "high" | "urgent" (MaintenanceTicketPriorityOptions for display labels).
Media constants and pattern
export const MAX_TICKET_PHOTOS = 5;
export const MAX_TICKET_DOCUMENTS = 10;MEDIA_RESOURCE_TYPES["maintenanceTicket"].maxItems (15) — kept in sync manually since photos and documents are both stored in the generic media table, not columns on maintenance_tickets. Photos and documents share one backend-enforced pool; these two constants just split that pool into a soft per-kind allotment on the client (5 + 10 = 15).interface TicketPhoto { id: string; url: string; contentType?: string; createdAt: Date; }
interface TicketDocument { id: string; url: string; contentType?: string; createdAt: Date; } // same wire shape as TicketPhoto, kept distinct by kindticket.UploadPhoto(file: File | Blob, contentType: string = "image/jpeg")
ticket.GetPhotos(): Promise<TicketPhoto[]>
ticket.DeletePhoto(id: string)
ticket.UploadDocument(file: File | Blob, contentType: string)
ticket.GetDocuments(): Promise<TicketDocument[]>
ticket.DeleteDocument(id: string)GetPhotos() lists every active media item via ListMedia and filters to items with no stored contentType or one starting with image/ — items with no contentType are treated as photos rather than excluded, since older rows predate contentType being recorded (before documents existed, every upload was a photo). GetDocuments() filters to the complementary set (contentType set and not starting with image/).Getters / helpers
get ticket.location(): Location | undefined // cached instance from locationID
get ticket.room(): Room | undefined // cached instance from roomID
get ticket.IsResolved(): boolean // state === "resolved"
// Detail route: /company/{cID}/maintenanceTickets/{id}ticket.Resolve(): Promise<SimpleResult<EventData>>Sets state: "resolved" + resolvedAt: new Date() via setData (new object spread) and calls save().
Static methods
MaintenanceTicket.create(company: Company, tickets: CreateMaintenanceTicketData[]): Promise<EventData<string[]>>
MaintenanceTicket.query(company: Company, data: QueryRequest): Promise<SimpleResult<MaintenanceTicket[]>>Endpoint: /company/{cID}/maintenanceTickets (create/save/delete), /company/{cID}/maintenanceTickets/query (query).