@kohost/api-client 7.23.1 → 7.25.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/dist/.tsbuildinfo +1 -1
- package/dist/__typecheck_regression__.d.ts +1 -0
- package/dist/models/conciergeWorkspaceBill.d.ts +17 -0
- package/dist/models/cost.js +2 -0
- package/dist/models/cost.js.map +1 -1
- package/dist/models/order.d.ts +17 -0
- package/dist/models/system.js +2 -0
- package/dist/models/system.js.map +1 -1
- package/dist/schemas/bill.d.ts +20 -0
- package/dist/schemas/bill.js +2 -0
- package/dist/schemas/bill.js.map +1 -1
- package/dist/schemas/conciergeWorkspaceBill.d.ts +156 -0
- package/dist/schemas/cost.d.ts +20 -0
- package/dist/schemas/costEntry.d.ts +48 -0
- package/dist/schemas/costEntry.js +28 -1
- package/dist/schemas/costEntry.js.map +1 -1
- package/dist/schemas/order.d.ts +186 -0
- package/dist/schemas/system.d.ts +33 -0
- package/dist/schemas/system.js +25 -0
- package/dist/schemas/system.js.map +1 -1
- package/dist/schemas/thermostat.d.ts +0 -1
- package/dist/schemas/thermostat.js +1 -2
- package/dist/schemas/thermostat.js.map +1 -1
- package/dist/schemas/ticket.d.ts +20 -0
- package/dist/useCases/describeConciergeBillsSummary.d.ts +27 -0
- package/dist/useCases/listConciergeWorkspaceBillLines.d.ts +27 -0
- package/package.json +1 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
declare const mustBeAString: string;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { Entity } from "./entity.js";
|
|
2
|
+
import { validateConciergeWorkspaceBill as validate } from "../validate.js";
|
|
3
|
+
import { conciergeWorkspaceBillSchema, type ConciergeWorkspaceBillSchema } from "../schemas/conciergeWorkspaceBill.js";
|
|
4
|
+
/**
|
|
5
|
+
* Data type for ConciergeWorkspaceBill constructor - exported for backwards compatibility
|
|
6
|
+
*/
|
|
7
|
+
export type ConciergeWorkspaceBillData = ConciergeWorkspaceBillSchema;
|
|
8
|
+
/**
|
|
9
|
+
* One row of the cross-organization OneBill invoices view: a bill summary with its organization resolved and its total derived.
|
|
10
|
+
*/
|
|
11
|
+
export interface ConciergeWorkspaceBill extends ConciergeWorkspaceBillSchema {
|
|
12
|
+
}
|
|
13
|
+
export declare class ConciergeWorkspaceBill extends Entity {
|
|
14
|
+
schema: typeof conciergeWorkspaceBillSchema;
|
|
15
|
+
validator: typeof validate;
|
|
16
|
+
constructor(data: ConciergeWorkspaceBillSchema);
|
|
17
|
+
}
|
package/dist/models/cost.js
CHANGED
|
@@ -16,6 +16,8 @@ var Cost = class extends Entity {
|
|
|
16
16
|
if (data.categoryId !== void 0) this.categoryId = data.categoryId;
|
|
17
17
|
if (data.vendorInvoices !== void 0) this.vendorInvoices = data.vendorInvoices;
|
|
18
18
|
if (data.vendorInvoiceNumber !== void 0) this.vendorInvoiceNumber = data.vendorInvoiceNumber;
|
|
19
|
+
if (data.note !== void 0) this.note = data.note;
|
|
20
|
+
if (data.vendorPayment !== void 0) this.vendorPayment = data.vendorPayment;
|
|
19
21
|
if (data.billId !== void 0) this.billId = data.billId;
|
|
20
22
|
if (data.writtenOff !== void 0) this.writtenOff = data.writtenOff;
|
|
21
23
|
if (data.billingReview !== void 0) this.billingReview = data.billingReview;
|
package/dist/models/cost.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cost.js","names":["validate"],"sources":["../../.generated/models/cost.ts"],"sourcesContent":["/* This file is automatically generated. Do not modify it manually. */\n\nimport { Entity } from \"./entity.js\";\nimport { validateCost as validate } from \"../validate.js\";\nimport { costSchema, type CostSchema } from \"../schemas/cost.js\";\n\n/**\n * Data type for Cost constructor - exported for backwards compatibility\n */\nexport type CostData = CostSchema;\n\n/**\n * A OneBill cost entry that no ticket carries: a recurring vendor charge, an expense found while reconciling an invoice, a pass-through cost. It shares the money shape and reconciliation lifecycle of a ticket cost entry and moves through the uninvoiced pool the same way, but because no ticket carries it the DNE approval gate never applies. Stored platform-wide beside bills and stamped with its organization.\n */\nexport interface Cost extends CostSchema {}\nexport class Cost extends Entity {\n declare schema: typeof costSchema;\n declare validator: typeof validate;\n\n constructor(data: CostSchema) {\n super(data);\n this.id = data.id;\n this.description = data.description;\n this.currency = data.currency;\n this.price = data.price;\n this.estimate = data.estimate;\n if (data.actual !== undefined) this.actual = data.actual;\n this.markup = data.markup;\n if (data.vendorId !== undefined) this.vendorId = data.vendorId;\n if (data.categoryId !== undefined) this.categoryId = data.categoryId;\n if (data.vendorInvoices !== undefined) this.vendorInvoices = data.vendorInvoices;\n if (data.vendorInvoiceNumber !== undefined) this.vendorInvoiceNumber = data.vendorInvoiceNumber;\n if (data.billId !== undefined) this.billId = data.billId;\n if (data.writtenOff !== undefined) this.writtenOff = data.writtenOff;\n if (data.billingReview !== undefined) this.billingReview = data.billingReview;\n if (data.type !== undefined) this.type = data.type;\n if (data.source !== undefined) this.source = data.source;\n if (data.serviceContractId !== undefined) this.serviceContractId = data.serviceContractId;\n if (data.splitId !== undefined) this.splitId = data.splitId;\n if (data.periodStart !== undefined) this.periodStart = data.periodStart;\n if (data.customerPeriodStarts !== undefined) this.customerPeriodStarts = data.customerPeriodStarts;\n if (data.vendorPeriodStarts !== undefined) this.vendorPeriodStarts = data.vendorPeriodStarts;\n this.organizationId = data.organizationId;\n if (data.propertyId !== undefined) this.propertyId = data.propertyId;\n if (data.createdBy !== undefined) this.createdBy = data.createdBy;\n if (data.createdAt !== undefined) this.createdAt = data.createdAt;\n if (data.updatedAt !== undefined) this.updatedAt = data.updatedAt;\n }\n\n\n\n\n\n\n\n\n}\n\nObject.defineProperty(Cost.prototype, \"schema\", {\n value: costSchema\n});\n\nObject.defineProperty(Cost.prototype, \"validator\", {\n get: function() { return validate; }\n});\n"],"mappings":";;;;AAeA,IAAa,OAAb,cAA0B,OAAO;CAI/B,YAAY,MAAkB;EAC5B,MAAM,IAAI;EACV,KAAK,KAAK,KAAK;EACf,KAAK,cAAc,KAAK;EACxB,KAAK,WAAW,KAAK;EACrB,KAAK,QAAQ,KAAK;EAClB,KAAK,WAAW,KAAK;EACrB,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,KAAK,SAAS,KAAK;EACnB,IAAI,KAAK,aAAa,KAAA,GAAW,KAAK,WAAW,KAAK;EACtD,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,mBAAmB,KAAA,GAAW,KAAK,iBAAiB,KAAK;EAClE,IAAI,KAAK,wBAAwB,KAAA,GAAW,KAAK,sBAAsB,KAAK;EAC5E,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,kBAAkB,KAAA,GAAW,KAAK,gBAAgB,KAAK;EAChE,IAAI,KAAK,SAAS,KAAA,GAAW,KAAK,OAAO,KAAK;EAC9C,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,sBAAsB,KAAA,GAAW,KAAK,oBAAoB,KAAK;EACxE,IAAI,KAAK,YAAY,KAAA,GAAW,KAAK,UAAU,KAAK;EACpD,IAAI,KAAK,gBAAgB,KAAA,GAAW,KAAK,cAAc,KAAK;EAC5D,IAAI,KAAK,yBAAyB,KAAA,GAAW,KAAK,uBAAuB,KAAK;EAC9E,IAAI,KAAK,uBAAuB,KAAA,GAAW,KAAK,qBAAqB,KAAK;EAC1E,KAAK,iBAAiB,KAAK;EAC3B,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;CAC1D;AASF;AAEA,OAAO,eAAe,KAAK,WAAW,UAAU,EAC9C,OAAO,WACT,CAAC;AAED,OAAO,eAAe,KAAK,WAAW,aAAa,EACjD,KAAK,WAAW;CAAE,OAAOA;AAAU,EACrC,CAAC"}
|
|
1
|
+
{"version":3,"file":"cost.js","names":["validate"],"sources":["../../.generated/models/cost.ts"],"sourcesContent":["/* This file is automatically generated. Do not modify it manually. */\n\nimport { Entity } from \"./entity.js\";\nimport { validateCost as validate } from \"../validate.js\";\nimport { costSchema, type CostSchema } from \"../schemas/cost.js\";\n\n/**\n * Data type for Cost constructor - exported for backwards compatibility\n */\nexport type CostData = CostSchema;\n\n/**\n * A OneBill cost entry that no ticket carries: a recurring vendor charge, an expense found while reconciling an invoice, a pass-through cost. It shares the money shape and reconciliation lifecycle of a ticket cost entry and moves through the uninvoiced pool the same way, but because no ticket carries it the DNE approval gate never applies. Stored platform-wide beside bills and stamped with its organization.\n */\nexport interface Cost extends CostSchema {}\nexport class Cost extends Entity {\n declare schema: typeof costSchema;\n declare validator: typeof validate;\n\n constructor(data: CostSchema) {\n super(data);\n this.id = data.id;\n this.description = data.description;\n this.currency = data.currency;\n this.price = data.price;\n this.estimate = data.estimate;\n if (data.actual !== undefined) this.actual = data.actual;\n this.markup = data.markup;\n if (data.vendorId !== undefined) this.vendorId = data.vendorId;\n if (data.categoryId !== undefined) this.categoryId = data.categoryId;\n if (data.vendorInvoices !== undefined) this.vendorInvoices = data.vendorInvoices;\n if (data.vendorInvoiceNumber !== undefined) this.vendorInvoiceNumber = data.vendorInvoiceNumber;\n if (data.note !== undefined) this.note = data.note;\n if (data.vendorPayment !== undefined) this.vendorPayment = data.vendorPayment;\n if (data.billId !== undefined) this.billId = data.billId;\n if (data.writtenOff !== undefined) this.writtenOff = data.writtenOff;\n if (data.billingReview !== undefined) this.billingReview = data.billingReview;\n if (data.type !== undefined) this.type = data.type;\n if (data.source !== undefined) this.source = data.source;\n if (data.serviceContractId !== undefined) this.serviceContractId = data.serviceContractId;\n if (data.splitId !== undefined) this.splitId = data.splitId;\n if (data.periodStart !== undefined) this.periodStart = data.periodStart;\n if (data.customerPeriodStarts !== undefined) this.customerPeriodStarts = data.customerPeriodStarts;\n if (data.vendorPeriodStarts !== undefined) this.vendorPeriodStarts = data.vendorPeriodStarts;\n this.organizationId = data.organizationId;\n if (data.propertyId !== undefined) this.propertyId = data.propertyId;\n if (data.createdBy !== undefined) this.createdBy = data.createdBy;\n if (data.createdAt !== undefined) this.createdAt = data.createdAt;\n if (data.updatedAt !== undefined) this.updatedAt = data.updatedAt;\n }\n\n\n\n\n\n\n\n\n}\n\nObject.defineProperty(Cost.prototype, \"schema\", {\n value: costSchema\n});\n\nObject.defineProperty(Cost.prototype, \"validator\", {\n get: function() { return validate; }\n});\n"],"mappings":";;;;AAeA,IAAa,OAAb,cAA0B,OAAO;CAI/B,YAAY,MAAkB;EAC5B,MAAM,IAAI;EACV,KAAK,KAAK,KAAK;EACf,KAAK,cAAc,KAAK;EACxB,KAAK,WAAW,KAAK;EACrB,KAAK,QAAQ,KAAK;EAClB,KAAK,WAAW,KAAK;EACrB,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,KAAK,SAAS,KAAK;EACnB,IAAI,KAAK,aAAa,KAAA,GAAW,KAAK,WAAW,KAAK;EACtD,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,mBAAmB,KAAA,GAAW,KAAK,iBAAiB,KAAK;EAClE,IAAI,KAAK,wBAAwB,KAAA,GAAW,KAAK,sBAAsB,KAAK;EAC5E,IAAI,KAAK,SAAS,KAAA,GAAW,KAAK,OAAO,KAAK;EAC9C,IAAI,KAAK,kBAAkB,KAAA,GAAW,KAAK,gBAAgB,KAAK;EAChE,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,kBAAkB,KAAA,GAAW,KAAK,gBAAgB,KAAK;EAChE,IAAI,KAAK,SAAS,KAAA,GAAW,KAAK,OAAO,KAAK;EAC9C,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,sBAAsB,KAAA,GAAW,KAAK,oBAAoB,KAAK;EACxE,IAAI,KAAK,YAAY,KAAA,GAAW,KAAK,UAAU,KAAK;EACpD,IAAI,KAAK,gBAAgB,KAAA,GAAW,KAAK,cAAc,KAAK;EAC5D,IAAI,KAAK,yBAAyB,KAAA,GAAW,KAAK,uBAAuB,KAAK;EAC9E,IAAI,KAAK,uBAAuB,KAAA,GAAW,KAAK,qBAAqB,KAAK;EAC1E,KAAK,iBAAiB,KAAK;EAC3B,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;CAC1D;AASF;AAEA,OAAO,eAAe,KAAK,WAAW,UAAU,EAC9C,OAAO,WACT,CAAC;AAED,OAAO,eAAe,KAAK,WAAW,aAAa,EACjD,KAAK,WAAW;CAAE,OAAOA;AAAU,EACrC,CAAC"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { Entity } from "./entity.js";
|
|
2
|
+
import { validateOrder as validate } from "../validate.js";
|
|
3
|
+
import { orderSchema, type OrderSchema } from "../schemas/order.js";
|
|
4
|
+
/**
|
|
5
|
+
* Data type for Order constructor - exported for backwards compatibility
|
|
6
|
+
*/
|
|
7
|
+
export type OrderData = OrderSchema;
|
|
8
|
+
/**
|
|
9
|
+
* A purchase order for products or services.
|
|
10
|
+
*/
|
|
11
|
+
export interface Order extends OrderSchema {
|
|
12
|
+
}
|
|
13
|
+
export declare class Order extends Entity {
|
|
14
|
+
schema: typeof orderSchema;
|
|
15
|
+
validator: typeof validate;
|
|
16
|
+
constructor(data: OrderSchema);
|
|
17
|
+
}
|
package/dist/models/system.js
CHANGED
|
@@ -19,6 +19,8 @@ var System = class extends Entity {
|
|
|
19
19
|
if (data.contactInfo !== void 0) this.contactInfo = data.contactInfo;
|
|
20
20
|
if (data.emergency !== void 0) this.emergency = data.emergency;
|
|
21
21
|
if (data.supportedEmergencies !== void 0) this.supportedEmergencies = data.supportedEmergencies;
|
|
22
|
+
if (data.trippedSensors !== void 0) this.trippedSensors = data.trippedSensors;
|
|
23
|
+
if (data.supportedSensors !== void 0) this.supportedSensors = data.supportedSensors;
|
|
22
24
|
if (data.health !== void 0) this.health = data.health;
|
|
23
25
|
if (data.syncedAt !== void 0) this.syncedAt = data.syncedAt;
|
|
24
26
|
if (data.createdAt !== void 0) this.createdAt = data.createdAt;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"system.js","names":["validate"],"sources":["../../.generated/models/system.ts"],"sourcesContent":["/* This file is automatically generated. Do not modify it manually. */\n\nimport { Entity } from \"./entity.js\";\nimport { validateSystem as validate } from \"../validate.js\";\nimport { systemSchema, type SystemSchema } from \"../schemas/system.js\";\n\n/**\n * Data type for System constructor - exported for backwards compatibility\n */\nexport type SystemData = SystemSchema;\n\n/**\n * System\n */\nexport interface System extends SystemSchema {}\nexport class System extends Entity {\n declare schema: typeof systemSchema;\n declare validator: typeof validate;\n\n constructor(data: SystemSchema) {\n super(data);\n this.id = data.id;\n this.type = data.type;\n if (data.categories !== undefined) this.categories = data.categories;\n if (data.name !== undefined) this.name = data.name;\n this.driver = data.driver;\n if (data.organizationId !== undefined) this.organizationId = data.organizationId;\n if (data.propertyId !== undefined) this.propertyId = data.propertyId;\n this.entities = data.entities;\n if (data.driverApiVersion !== undefined) this.driverApiVersion = data.driverApiVersion;\n if (data.logo !== undefined) this.logo = data.logo;\n if (data.config !== undefined) this.config = data.config;\n if (data.contactInfo !== undefined) this.contactInfo = data.contactInfo;\n if (data.emergency !== undefined) this.emergency = data.emergency;\n if (data.supportedEmergencies !== undefined) this.supportedEmergencies = data.supportedEmergencies;\n if (data.health !== undefined) this.health = data.health;\n if (data.syncedAt !== undefined) this.syncedAt = data.syncedAt;\n if (data.createdAt !== undefined) this.createdAt = data.createdAt;\n if (data.updatedAt !== undefined) this.updatedAt = data.updatedAt;\n if (data.deletedAt !== undefined) this.deletedAt = data.deletedAt;\n }\n\n\n\n\n\n\n\n\n}\n\nObject.defineProperty(System.prototype, \"schema\", {\n value: systemSchema\n});\n\nObject.defineProperty(System.prototype, \"validator\", {\n get: function() { return validate; }\n});\n"],"mappings":";;;;AAeA,IAAa,SAAb,cAA4B,OAAO;CAIjC,YAAY,MAAoB;EAC9B,MAAM,IAAI;EACV,KAAK,KAAK,KAAK;EACf,KAAK,OAAO,KAAK;EACjB,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,SAAS,KAAA,GAAW,KAAK,OAAO,KAAK;EAC9C,KAAK,SAAS,KAAK;EACnB,IAAI,KAAK,mBAAmB,KAAA,GAAW,KAAK,iBAAiB,KAAK;EAClE,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,KAAK,WAAW,KAAK;EACrB,IAAI,KAAK,qBAAqB,KAAA,GAAW,KAAK,mBAAmB,KAAK;EACtE,IAAI,KAAK,SAAS,KAAA,GAAW,KAAK,OAAO,KAAK;EAC9C,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,gBAAgB,KAAA,GAAW,KAAK,cAAc,KAAK;EAC5D,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,yBAAyB,KAAA,GAAW,KAAK,uBAAuB,KAAK;EAC9E,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,aAAa,KAAA,GAAW,KAAK,WAAW,KAAK;EACtD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;CAC1D;AASF;AAEA,OAAO,eAAe,OAAO,WAAW,UAAU,EAChD,OAAO,aACT,CAAC;AAED,OAAO,eAAe,OAAO,WAAW,aAAa,EACnD,KAAK,WAAW;CAAE,OAAOA;AAAU,EACrC,CAAC"}
|
|
1
|
+
{"version":3,"file":"system.js","names":["validate"],"sources":["../../.generated/models/system.ts"],"sourcesContent":["/* This file is automatically generated. Do not modify it manually. */\n\nimport { Entity } from \"./entity.js\";\nimport { validateSystem as validate } from \"../validate.js\";\nimport { systemSchema, type SystemSchema } from \"../schemas/system.js\";\n\n/**\n * Data type for System constructor - exported for backwards compatibility\n */\nexport type SystemData = SystemSchema;\n\n/**\n * System\n */\nexport interface System extends SystemSchema {}\nexport class System extends Entity {\n declare schema: typeof systemSchema;\n declare validator: typeof validate;\n\n constructor(data: SystemSchema) {\n super(data);\n this.id = data.id;\n this.type = data.type;\n if (data.categories !== undefined) this.categories = data.categories;\n if (data.name !== undefined) this.name = data.name;\n this.driver = data.driver;\n if (data.organizationId !== undefined) this.organizationId = data.organizationId;\n if (data.propertyId !== undefined) this.propertyId = data.propertyId;\n this.entities = data.entities;\n if (data.driverApiVersion !== undefined) this.driverApiVersion = data.driverApiVersion;\n if (data.logo !== undefined) this.logo = data.logo;\n if (data.config !== undefined) this.config = data.config;\n if (data.contactInfo !== undefined) this.contactInfo = data.contactInfo;\n if (data.emergency !== undefined) this.emergency = data.emergency;\n if (data.supportedEmergencies !== undefined) this.supportedEmergencies = data.supportedEmergencies;\n if (data.trippedSensors !== undefined) this.trippedSensors = data.trippedSensors;\n if (data.supportedSensors !== undefined) this.supportedSensors = data.supportedSensors;\n if (data.health !== undefined) this.health = data.health;\n if (data.syncedAt !== undefined) this.syncedAt = data.syncedAt;\n if (data.createdAt !== undefined) this.createdAt = data.createdAt;\n if (data.updatedAt !== undefined) this.updatedAt = data.updatedAt;\n if (data.deletedAt !== undefined) this.deletedAt = data.deletedAt;\n }\n\n\n\n\n\n\n\n\n}\n\nObject.defineProperty(System.prototype, \"schema\", {\n value: systemSchema\n});\n\nObject.defineProperty(System.prototype, \"validator\", {\n get: function() { return validate; }\n});\n"],"mappings":";;;;AAeA,IAAa,SAAb,cAA4B,OAAO;CAIjC,YAAY,MAAoB;EAC9B,MAAM,IAAI;EACV,KAAK,KAAK,KAAK;EACf,KAAK,OAAO,KAAK;EACjB,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,IAAI,KAAK,SAAS,KAAA,GAAW,KAAK,OAAO,KAAK;EAC9C,KAAK,SAAS,KAAK;EACnB,IAAI,KAAK,mBAAmB,KAAA,GAAW,KAAK,iBAAiB,KAAK;EAClE,IAAI,KAAK,eAAe,KAAA,GAAW,KAAK,aAAa,KAAK;EAC1D,KAAK,WAAW,KAAK;EACrB,IAAI,KAAK,qBAAqB,KAAA,GAAW,KAAK,mBAAmB,KAAK;EACtE,IAAI,KAAK,SAAS,KAAA,GAAW,KAAK,OAAO,KAAK;EAC9C,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,gBAAgB,KAAA,GAAW,KAAK,cAAc,KAAK;EAC5D,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,yBAAyB,KAAA,GAAW,KAAK,uBAAuB,KAAK;EAC9E,IAAI,KAAK,mBAAmB,KAAA,GAAW,KAAK,iBAAiB,KAAK;EAClE,IAAI,KAAK,qBAAqB,KAAA,GAAW,KAAK,mBAAmB,KAAK;EACtE,IAAI,KAAK,WAAW,KAAA,GAAW,KAAK,SAAS,KAAK;EAClD,IAAI,KAAK,aAAa,KAAA,GAAW,KAAK,WAAW,KAAK;EACtD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;EACxD,IAAI,KAAK,cAAc,KAAA,GAAW,KAAK,YAAY,KAAK;CAC1D;AASF;AAEA,OAAO,eAAe,OAAO,WAAW,UAAU,EAChD,OAAO,aACT,CAAC;AAED,OAAO,eAAe,OAAO,WAAW,aAAa,EACnD,KAAK,WAAW;CAAE,OAAOA;AAAU,EACrC,CAAC"}
|
package/dist/schemas/bill.d.ts
CHANGED
|
@@ -197,6 +197,26 @@ export declare const billSchema: {
|
|
|
197
197
|
readonly additionalProperties: false;
|
|
198
198
|
readonly required: readonly ["id", "type", "description", "amount"];
|
|
199
199
|
readonly properties: {
|
|
200
|
+
readonly note: {
|
|
201
|
+
readonly type: readonly ["string", "null"];
|
|
202
|
+
readonly maxLength: 1000;
|
|
203
|
+
readonly default: null;
|
|
204
|
+
readonly description: string;
|
|
205
|
+
};
|
|
206
|
+
readonly vendorPayment: {
|
|
207
|
+
readonly type: readonly ["object", "null"];
|
|
208
|
+
readonly additionalProperties: false;
|
|
209
|
+
readonly required: readonly ["paidOn"];
|
|
210
|
+
readonly default: null;
|
|
211
|
+
readonly description: string;
|
|
212
|
+
readonly properties: {
|
|
213
|
+
readonly paidOn: {
|
|
214
|
+
readonly type: "string";
|
|
215
|
+
readonly pattern: "^\\d{4}-\\d{2}-\\d{2}$";
|
|
216
|
+
readonly description: "The calendar day the vendor was paid, as YYYY-MM-DD.";
|
|
217
|
+
};
|
|
218
|
+
};
|
|
219
|
+
};
|
|
200
220
|
readonly id: {
|
|
201
221
|
readonly type: "string";
|
|
202
222
|
readonly description: "Server-minted ID of the bill line.";
|
package/dist/schemas/bill.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { ledgerAnnotationProperties } from "./costEntry.js";
|
|
1
2
|
const billSchema = {
|
|
2
3
|
$schema: "http://json-schema.org/draft-07/schema",
|
|
3
4
|
$id: "bill.json",
|
|
@@ -260,6 +261,7 @@ const billSchema = {
|
|
|
260
261
|
default: null,
|
|
261
262
|
description: "The vendor's own invoice number. Internal, redacted org-side."
|
|
262
263
|
},
|
|
264
|
+
...ledgerAnnotationProperties,
|
|
263
265
|
taxable: {
|
|
264
266
|
type: "boolean",
|
|
265
267
|
default: false,
|
package/dist/schemas/bill.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bill.js","names":[],"sources":["../../.generated/schemas/bill.ts"],"sourcesContent":["import defs, { ISODateString } from \"./definitions\";\nimport type { FromSchema } from \"json-schema-to-ts\";\nimport { mediaFileSchema } from \"./mediaFile\";\n\n// One bill line is a discriminated union on `type`, so `lines.items` is their\n// `oneOf`. The two branches are disjoint via the `type` const plus\n// `additionalProperties: false`, so a line validates against exactly one.\n//\n// A cost line always names its entry by `costId`; `source` says which\n// collection to look it up in. A `ticket` line resolves through\n// `(ticketId, costId)`, a ticket-less line (`adhoc`, or `contract` for an\n// entry a Service contract minted) reads `costId` straight off the costs\n// collection with `ticketId` null. The claim path is what pairs the two, since\n// JSON Schema cannot state the pairing without splitting the branch and\n// breaking the `type` discriminator every reader keys off.\n//\n// While the bill is a draft the line carries only the reference, the picked\n// `categoryId`, and any draft-time adjustment; the customer-facing `amount`,\n// `description`, and `categoryName` are live-read from the claimed entry and\n// snapshotted onto the line at mark-sent. The billed amount is the marked-up\n// actual (or the `adjustedAmount` override, floored at zero) — vendor truth on\n// the entry is never touched.\n//\n// `vendorCost`, `vendorId` and `hasActual` are a derived snapshot of that\n// vendor truth, written at mark-sent beside `amount` and re-patched when a\n// late actual lands on the claimed entry, so the transactions view and period\n// margin read one collection. `propertyId` and `ticketNumber` are snapshotted\n// beside them so that reader can address the source ticket's property without\n// resolving the ticket. The entry stays the source of truth; the vendor\n// invoice number and files are read live from it, never snapshotted.\nconst costLineSchema = {\n type: \"object\",\n additionalProperties: false,\n required: [\"id\", \"type\"],\n properties: {\n id: {\n type: \"string\",\n description: \"Server-minted ID of the bill line.\",\n },\n type: {\n type: \"string\",\n enum: [\"cost\"],\n description: \"Discriminator: a line drawn from a recorded cost entry.\",\n },\n source: {\n type: \"string\",\n enum: [\"ticket\", \"adhoc\", \"contract\"],\n default: \"ticket\",\n description:\n \"Where the claimed cost entry lives, and therefore how `costId` \" +\n \"resolves: on a ticket, or in the costs collection. `contract` is a \" +\n \"costs-collection entry a Service contract minted; it bills by the \" +\n \"same rules as `adhoc`.\",\n },\n ticketId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The ID of the ticket the claimed cost entry lives on. Null on an \" +\n \"`adhoc` line, which no ticket carries.\",\n },\n costId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The ID of the claimed cost entry: an entry within the ticket on a \" +\n \"`ticket` line, a costs-collection document on an `adhoc` one.\",\n },\n propertyId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The property the claimed entry belongs to, snapshotted at \" +\n \"mark-sent: the source ticket's property on a `ticket` line, the \" +\n \"ad hoc entry's attributed property on an `adhoc` one. Lets a \" +\n \"cross-organization reader reach the ticket's property scope \" +\n \"without a ticket read. Internal, redacted org-side.\",\n },\n ticketNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The source ticket's number, snapshotted at mark-sent. Null on a \" +\n \"ticket-less line. Internal, redacted org-side.\",\n },\n serviceContractId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The Service contract that minted the claimed entry. Null on every \" +\n \"other line. Customer-facing: the org bill links the line to the \" +\n \"contract it recurs under.\",\n },\n serviceContractName: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The contract's name, snapshotted at mark-sent so a sent bill reads \" +\n \"the same after the contract is renamed. Null while drafting, when \" +\n \"it live-reads from the contract.\",\n },\n categoryId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The picked billing category, inherited from the claimed cost entry \" +\n \"when the claim does not name one. Optional while drafting, required \" +\n \"at mark-sent. Manual pick — never derived from the ticket's issue.\",\n },\n categoryName: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The category name snapshotted at mark-sent. Null while drafting, \" +\n \"when it live-reads from the category library.\",\n },\n adjustedAmount: {\n type: [\"integer\", \"null\"],\n minimum: 0,\n default: null,\n description:\n \"Optional draft-time override of the billed amount in integer cents, \" +\n \"floored at zero, replacing the marked-up actual at display and \" +\n \"snapshot. Requires `adjustmentReason`. A credit (below zero) is a \" +\n \"manual line instead.\",\n },\n adjustmentReason: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Short required reason accompanying `adjustedAmount`, kept for the \" +\n \"internal record.\",\n },\n amount: {\n type: [\"integer\", \"null\"],\n default: null,\n description:\n \"The billed amount in integer cents, snapshotted at mark-sent. Null \" +\n \"while drafting, when it live-reads (marked-up actual or the \" +\n \"adjustment) from the cost entry.\",\n },\n description: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The line description, snapshotted at mark-sent. Null while drafting, \" +\n \"when it live-reads from the cost entry.\",\n },\n vendorCost: {\n type: [\"integer\", \"null\"],\n default: null,\n description:\n \"What the claimed entry costs Kohost in integer cents, snapshotted \" +\n \"at mark-sent: the vendor actual when recorded, else the estimate. \" +\n \"Null while drafting or when the entry carries neither. Re-patched \" +\n \"when a late actual lands. Internal, redacted org-side.\",\n },\n vendorId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The org-scoped Vendor named on the claimed entry, snapshotted at \" +\n \"mark-sent. Internal, redacted org-side.\",\n },\n hasActual: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether `vendorCost` is the vendor's settled actual rather than the \" +\n \"estimate, snapshotted at mark-sent and re-patched when the actual \" +\n \"lands. Internal, redacted org-side.\",\n },\n taxable: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether the line's amount joins the bill's taxable subtotal. \" +\n \"Customer-facing: locks at mark-sent.\",\n },\n },\n} as const;\n\n// A manual line is a literal customer-facing row with no markup math: a\n// `description` and `amount` (which may be negative, serving as a credit) and\n// an optional `propertyId`. The independent internal fields — informational\n// `cost` (never derives the amount), `vendorId`, the vendor-invoice file, and\n// `vendorInvoiceNumber` — are redacted org-side via `canSeeCostSplit` and stay\n// editable in any bill state.\nconst manualLineSchema = {\n type: \"object\",\n additionalProperties: false,\n required: [\"id\", \"type\", \"description\", \"amount\"],\n properties: {\n id: {\n type: \"string\",\n description: \"Server-minted ID of the bill line.\",\n },\n type: {\n type: \"string\",\n enum: [\"manual\"],\n description: \"Discriminator: a literal, non-ticket line.\",\n },\n description: {\n type: \"string\",\n minLength: 1,\n description: \"The literal customer-facing description.\",\n },\n amount: {\n type: \"integer\",\n description:\n \"The billed amount in integer cents. May be negative, serving as a \" +\n \"credit (reference the reason in the description).\",\n },\n propertyId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The property the manual line is attributed to, when it concerns one.\",\n },\n categoryId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The picked billing category. Optional while drafting, required at \" +\n \"mark-sent.\",\n },\n categoryName: {\n type: [\"string\", \"null\"],\n default: null,\n description: \"The category name snapshotted at mark-sent.\",\n },\n cost: {\n type: [\"integer\", \"null\"],\n default: null,\n description:\n \"Informational internal vendor cost in integer cents. Never derives \" +\n \"the amount. Redacted org-side.\",\n },\n vendorId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Optional reference to the org-scoped Vendor. Internal, redacted \" +\n \"org-side.\",\n },\n vendorInvoice: {\n anyOf: [{ $ref: \"mediaFile.json\" }, { type: \"null\" }],\n default: null,\n description:\n \"The vendor's invoice file backing the line, mirroring the cost-entry \" +\n \"field. Internal, redacted org-side.\",\n },\n vendorInvoiceNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The vendor's own invoice number. Internal, redacted org-side.\",\n },\n taxable: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether the line's amount joins the bill's taxable subtotal. \" +\n \"Customer-facing: locks at mark-sent.\",\n },\n },\n} as const;\n\nexport const billSchema = {\n $schema: \"http://json-schema.org/draft-07/schema\",\n $id: \"bill.json\",\n title: \"Bill\",\n description:\n \"A OneBill bill, stored platform-wide and stamped with its organization: \" +\n \"KFC staff assemble billed lines from the \" +\n \"uninvoiced cost pool (plus manual lines) into a draft, then mark it sent \" +\n \"to freeze and reveal it to the customer. Lifecycle draft → sent → paid, \" +\n \"plus void. Customers see a bill in-app only once sent.\",\n type: \"object\",\n required: [\"id\", \"organizationId\", \"status\", \"currency\", \"lines\"],\n additionalProperties: false,\n properties: {\n id: {\n $ref: \"definitions.json#/definitions/id\",\n },\n type: {\n type: \"string\",\n enum: [\"bill\"],\n default: \"bill\",\n },\n organizationId: {\n type: \"string\",\n description:\n \"The organization the bill invoices. Bills live in one admin-database \" +\n \"collection across every organization, so each carries its owner \" +\n \"explicitly — stamped from the request context at creation, never \" +\n \"client-supplied.\",\n },\n status: {\n type: \"string\",\n enum: [\"draft\", \"sent\", \"paid\", \"void\"],\n default: \"draft\",\n description:\n \"Lifecycle state. `sent` freezes customer-facing fields and reveals \" +\n \"the bill to the org; `paid` records manual payment; `void` releases \" +\n \"cost-entry claims and hides the bill from the org view. Drafts \" +\n \"hard-delete rather than voiding.\",\n },\n invoiceNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Kohost's own invoice number, `KB-<n>` from a single global sequence. \" +\n \"System-assigned at mark-sent and never entered by hand: null while \" +\n \"the bill is a draft, immutable once set. A wrong bill is corrected \" +\n \"by void-and-reissue, so numbers gap and are never reused.\",\n },\n period: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n 'Display-only month label (e.g. \"July 2026\"). A UI hint; the bill\\'s ' +\n \"membership is defined by its lines, not a calendar bucket.\",\n },\n currency: {\n type: \"string\",\n enum: [\"USD\"],\n default: \"USD\",\n description: \"ISO 4217 currency code. USD only in v1.\",\n },\n fileId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The generated bill PDF's media-file ID, minted atomically at \" +\n \"mark-sent.\",\n },\n fileUrl: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The generated bill PDF's file-store URL, snapshotted at mark-sent \" +\n \"alongside fileId. Held so the sent-bill surface and the sent \" +\n \"notification email can mint a signed, unauthenticated download link \" +\n \"without a file lookup. Unsigned on its own (a bare link 401s).\",\n },\n memo: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Internal KFC-only note. Never customer-facing; editable in any state.\",\n },\n billingAddress: {\n anyOf: [\n { $ref: \"definitions.json#/definitions/address\" },\n { type: \"null\" },\n ],\n default: null,\n description:\n \"The org billing address snapshotted at mark-sent. Null while \" +\n \"drafting, when it live-reads from the Organization. Mark-sent \" +\n \"requires a complete address (line1, city, state, postalCode).\",\n },\n taxRate: {\n type: [\"number\", \"null\"],\n default: null,\n minimum: 0,\n description:\n \"Tax rate as a plain float percent applied to the taxable line \" +\n \"subtotal. While drafting, null means the platform default rate; the \" +\n \"effective rate is snapshotted at mark-sent.\",\n },\n taxExempt: {\n type: \"boolean\",\n default: false,\n description:\n \"The organization's tax exemption snapshotted at mark-sent. While \" +\n \"drafting it live-reads from the Organization.\",\n },\n shippingAmount: {\n type: [\"integer\", \"null\"],\n default: null,\n minimum: 0,\n description:\n \"Shipping & handling in integer cents, added to the grand total on \" +\n \"top of the line subtotal and tax. Null means none.\",\n },\n lines: {\n type: \"array\",\n default: [],\n description:\n \"The bill's lines: cost lines claimed from the uninvoiced pool and \" +\n \"literal manual lines.\",\n items: {\n oneOf: [costLineSchema, manualLineSchema],\n },\n },\n sentAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the bill was marked sent. Absent until sent.\",\n },\n paidAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the bill was marked paid. Absent until paid.\",\n },\n voidedAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the bill was voided. Absent unless voided.\",\n },\n createdAt: {\n $ref: \"definitions.json#/definitions/date\",\n },\n updatedAt: {\n $ref: \"definitions.json#/definitions/date\",\n },\n },\n} as const;\n\nexport type BillSchema = FromSchema<\n typeof billSchema,\n {\n references: [typeof defs, typeof mediaFileSchema];\n deserialize: [\n {\n pattern: {\n format: \"date-time\";\n };\n output: Date | ISODateString;\n },\n ];\n }\n>;\n\n/** One line on a bill: a cost line or a manual line. */\nexport type BillLine = NonNullable<BillSchema[\"lines\"]>[number];\n"],"mappings":"AA4QA,MAAa,aAAa;CACxB,SAAS;CACT,KAAK;CACL,OAAO;CACP,aACE;CAKF,MAAM;CACN,UAAU;EAAC;EAAM;EAAkB;EAAU;EAAY;CAAO;CAChE,sBAAsB;CACtB,YAAY;EACV,IAAI,EACF,MAAM,mCACR;EACA,MAAM;GACJ,MAAM;GACN,MAAM,CAAC,MAAM;GACb,SAAS;EACX;EACA,gBAAgB;GACd,MAAM;GACN,aACE;EAIJ;EACA,QAAQ;GACN,MAAM;GACN,MAAM;IAAC;IAAS;IAAQ;IAAQ;GAAM;GACtC,SAAS;GACT,aACE;EAIJ;EACA,eAAe;GACb,MAAM,CAAC,UAAU,MAAM;GACvB,SAAS;GACT,aACE;EAIJ;EACA,QAAQ;GACN,MAAM,CAAC,UAAU,MAAM;GACvB,SAAS;GACT,aACE;EAEJ;EACA,UAAU;GACR,MAAM;GACN,MAAM,CAAC,KAAK;GACZ,SAAS;GACT,aAAa;EACf;EACA,QAAQ;GACN,MAAM,CAAC,UAAU,MAAM;GACvB,SAAS;GACT,aACE;EAEJ;EACA,SAAS;GACP,MAAM,CAAC,UAAU,MAAM;GACvB,SAAS;GACT,aACE;EAIJ;EACA,MAAM;GACJ,MAAM,CAAC,UAAU,MAAM;GACvB,SAAS;GACT,aACE;EACJ;EACA,gBAAgB;GACd,OAAO,CACL,EAAE,MAAM,wCAAwC,GAChD,EAAE,MAAM,OAAO,CACjB;GACA,SAAS;GACT,aACE;EAGJ;EACA,SAAS;GACP,MAAM,CAAC,UAAU,MAAM;GACvB,SAAS;GACT,SAAS;GACT,aACE;EAGJ;EACA,WAAW;GACT,MAAM;GACN,SAAS;GACT,aACE;EAEJ;EACA,gBAAgB;GACd,MAAM,CAAC,WAAW,MAAM;GACxB,SAAS;GACT,SAAS;GACT,aACE;EAEJ;EACA,OAAO;GACL,MAAM;GACN,SAAS,CAAC;GACV,aACE;GAEF,OAAO,EACL,OAAO,CAAC;IA3Wd,MAAM;IACN,sBAAsB;IACtB,UAAU,CAAC,MAAM,MAAM;IACvB,YAAY;KACV,IAAI;MACF,MAAM;MACN,aAAa;KACf;KACA,MAAM;MACJ,MAAM;MACN,MAAM,CAAC,MAAM;MACb,aAAa;KACf;KACA,QAAQ;MACN,MAAM;MACN,MAAM;OAAC;OAAU;OAAS;MAAU;MACpC,SAAS;MACT,aACE;KAIJ;KACA,UAAU;MACR,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,QAAQ;MACN,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,YAAY;MACV,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAKJ;KACA,cAAc;MACZ,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,mBAAmB;MACjB,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAGJ;KACA,qBAAqB;MACnB,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAGJ;KACA,YAAY;MACV,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAGJ;KACA,cAAc;MACZ,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,gBAAgB;MACd,MAAM,CAAC,WAAW,MAAM;MACxB,SAAS;MACT,SAAS;MACT,aACE;KAIJ;KACA,kBAAkB;MAChB,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,QAAQ;MACN,MAAM,CAAC,WAAW,MAAM;MACxB,SAAS;MACT,aACE;KAGJ;KACA,aAAa;MACX,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,YAAY;MACV,MAAM,CAAC,WAAW,MAAM;MACxB,SAAS;MACT,aACE;KAIJ;KACA,UAAU;MACR,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,WAAW;MACT,MAAM;MACN,SAAS;MACT,aACE;KAGJ;KACA,SAAS;MACP,MAAM;MACN,SAAS;MACT,aACE;KAEJ;IACF;GAuNc,GAAgB;IA7M9B,MAAM;IACN,sBAAsB;IACtB,UAAU;KAAC;KAAM;KAAQ;KAAe;IAAQ;IAChD,YAAY;KACV,IAAI;MACF,MAAM;MACN,aAAa;KACf;KACA,MAAM;MACJ,MAAM;MACN,MAAM,CAAC,QAAQ;MACf,aAAa;KACf;KACA,aAAa;MACX,MAAM;MACN,WAAW;MACX,aAAa;KACf;KACA,QAAQ;MACN,MAAM;MACN,aACE;KAEJ;KACA,YAAY;MACV,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KACJ;KACA,YAAY;MACV,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,cAAc;MACZ,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aAAa;KACf;KACA,MAAM;MACJ,MAAM,CAAC,WAAW,MAAM;MACxB,SAAS;MACT,aACE;KAEJ;KACA,UAAU;MACR,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KAEJ;KACA,eAAe;MACb,OAAO,CAAC,EAAE,MAAM,iBAAiB,GAAG,EAAE,MAAM,OAAO,CAAC;MACpD,SAAS;MACT,aACE;KAEJ;KACA,qBAAqB;MACnB,MAAM,CAAC,UAAU,MAAM;MACvB,SAAS;MACT,aACE;KACJ;KACA,SAAS;MACP,MAAM;MACN,SAAS;MACT,aACE;KAEJ;IACF;GAiI8B,CAAgB,EAC1C;EACF;EACA,QAAQ;GACN,MAAM;GACN,aAAa;EACf;EACA,QAAQ;GACN,MAAM;GACN,aAAa;EACf;EACA,UAAU;GACR,MAAM;GACN,aAAa;EACf;EACA,WAAW,EACT,MAAM,qCACR;EACA,WAAW,EACT,MAAM,qCACR;CACF;AACF"}
|
|
1
|
+
{"version":3,"file":"bill.js","names":[],"sources":["../../.generated/schemas/bill.ts"],"sourcesContent":["import defs, { ISODateString } from \"./definitions\";\nimport type { FromSchema } from \"json-schema-to-ts\";\nimport { ledgerAnnotationProperties } from \"./costEntry\";\nimport { mediaFileSchema } from \"./mediaFile\";\n\n// One bill line is a discriminated union on `type`, so `lines.items` is their\n// `oneOf`. The two branches are disjoint via the `type` const plus\n// `additionalProperties: false`, so a line validates against exactly one.\n//\n// A cost line always names its entry by `costId`; `source` says which\n// collection to look it up in. A `ticket` line resolves through\n// `(ticketId, costId)`, a ticket-less line (`adhoc`, or `contract` for an\n// entry a Service contract minted) reads `costId` straight off the costs\n// collection with `ticketId` null. The claim path is what pairs the two, since\n// JSON Schema cannot state the pairing without splitting the branch and\n// breaking the `type` discriminator every reader keys off.\n//\n// While the bill is a draft the line carries only the reference, the picked\n// `categoryId`, and any draft-time adjustment; the customer-facing `amount`,\n// `description`, and `categoryName` are live-read from the claimed entry and\n// snapshotted onto the line at mark-sent. The billed amount is the marked-up\n// actual (or the `adjustedAmount` override, floored at zero) — vendor truth on\n// the entry is never touched.\n//\n// `vendorCost`, `vendorId` and `hasActual` are a derived snapshot of that\n// vendor truth, written at mark-sent beside `amount` and re-patched when a\n// late actual lands on the claimed entry, so the transactions view and period\n// margin read one collection. `propertyId` and `ticketNumber` are snapshotted\n// beside them so that reader can address the source ticket's property without\n// resolving the ticket. The entry stays the source of truth; the vendor\n// invoice number and files are read live from it, never snapshotted.\nconst costLineSchema = {\n type: \"object\",\n additionalProperties: false,\n required: [\"id\", \"type\"],\n properties: {\n id: {\n type: \"string\",\n description: \"Server-minted ID of the bill line.\",\n },\n type: {\n type: \"string\",\n enum: [\"cost\"],\n description: \"Discriminator: a line drawn from a recorded cost entry.\",\n },\n source: {\n type: \"string\",\n enum: [\"ticket\", \"adhoc\", \"contract\"],\n default: \"ticket\",\n description:\n \"Where the claimed cost entry lives, and therefore how `costId` \" +\n \"resolves: on a ticket, or in the costs collection. `contract` is a \" +\n \"costs-collection entry a Service contract minted; it bills by the \" +\n \"same rules as `adhoc`.\",\n },\n ticketId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The ID of the ticket the claimed cost entry lives on. Null on an \" +\n \"`adhoc` line, which no ticket carries.\",\n },\n costId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The ID of the claimed cost entry: an entry within the ticket on a \" +\n \"`ticket` line, a costs-collection document on an `adhoc` one.\",\n },\n propertyId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The property the claimed entry belongs to, snapshotted at \" +\n \"mark-sent: the source ticket's property on a `ticket` line, the \" +\n \"ad hoc entry's attributed property on an `adhoc` one. Lets a \" +\n \"cross-organization reader reach the ticket's property scope \" +\n \"without a ticket read. Internal, redacted org-side.\",\n },\n ticketNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The source ticket's number, snapshotted at mark-sent. Null on a \" +\n \"ticket-less line. Internal, redacted org-side.\",\n },\n serviceContractId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The Service contract that minted the claimed entry. Null on every \" +\n \"other line. Customer-facing: the org bill links the line to the \" +\n \"contract it recurs under.\",\n },\n serviceContractName: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The contract's name, snapshotted at mark-sent so a sent bill reads \" +\n \"the same after the contract is renamed. Null while drafting, when \" +\n \"it live-reads from the contract.\",\n },\n categoryId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The picked billing category, inherited from the claimed cost entry \" +\n \"when the claim does not name one. Optional while drafting, required \" +\n \"at mark-sent. Manual pick — never derived from the ticket's issue.\",\n },\n categoryName: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The category name snapshotted at mark-sent. Null while drafting, \" +\n \"when it live-reads from the category library.\",\n },\n adjustedAmount: {\n type: [\"integer\", \"null\"],\n minimum: 0,\n default: null,\n description:\n \"Optional draft-time override of the billed amount in integer cents, \" +\n \"floored at zero, replacing the marked-up actual at display and \" +\n \"snapshot. Requires `adjustmentReason`. A credit (below zero) is a \" +\n \"manual line instead.\",\n },\n adjustmentReason: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Short required reason accompanying `adjustedAmount`, kept for the \" +\n \"internal record.\",\n },\n amount: {\n type: [\"integer\", \"null\"],\n default: null,\n description:\n \"The billed amount in integer cents, snapshotted at mark-sent. Null \" +\n \"while drafting, when it live-reads (marked-up actual or the \" +\n \"adjustment) from the cost entry.\",\n },\n description: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The line description, snapshotted at mark-sent. Null while drafting, \" +\n \"when it live-reads from the cost entry.\",\n },\n vendorCost: {\n type: [\"integer\", \"null\"],\n default: null,\n description:\n \"What the claimed entry costs Kohost in integer cents, snapshotted \" +\n \"at mark-sent: the vendor actual when recorded, else the estimate. \" +\n \"Null while drafting or when the entry carries neither. Re-patched \" +\n \"when a late actual lands. Internal, redacted org-side.\",\n },\n vendorId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The org-scoped Vendor named on the claimed entry, snapshotted at \" +\n \"mark-sent. Internal, redacted org-side.\",\n },\n hasActual: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether `vendorCost` is the vendor's settled actual rather than the \" +\n \"estimate, snapshotted at mark-sent and re-patched when the actual \" +\n \"lands. Internal, redacted org-side.\",\n },\n taxable: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether the line's amount joins the bill's taxable subtotal. \" +\n \"Customer-facing: locks at mark-sent.\",\n },\n },\n} as const;\n\n// A manual line is a literal customer-facing row with no markup math: a\n// `description` and `amount` (which may be negative, serving as a credit) and\n// an optional `propertyId`. The independent internal fields — informational\n// `cost` (never derives the amount), `vendorId`, the vendor-invoice file, and\n// `vendorInvoiceNumber`, the Ledger note and the Vendor payment — are redacted\n// org-side via `canSeeCostSplit` and stay editable in any bill state.\nconst manualLineSchema = {\n type: \"object\",\n additionalProperties: false,\n required: [\"id\", \"type\", \"description\", \"amount\"],\n properties: {\n id: {\n type: \"string\",\n description: \"Server-minted ID of the bill line.\",\n },\n type: {\n type: \"string\",\n enum: [\"manual\"],\n description: \"Discriminator: a literal, non-ticket line.\",\n },\n description: {\n type: \"string\",\n minLength: 1,\n description: \"The literal customer-facing description.\",\n },\n amount: {\n type: \"integer\",\n description:\n \"The billed amount in integer cents. May be negative, serving as a \" +\n \"credit (reference the reason in the description).\",\n },\n propertyId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The property the manual line is attributed to, when it concerns one.\",\n },\n categoryId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The picked billing category. Optional while drafting, required at \" +\n \"mark-sent.\",\n },\n categoryName: {\n type: [\"string\", \"null\"],\n default: null,\n description: \"The category name snapshotted at mark-sent.\",\n },\n cost: {\n type: [\"integer\", \"null\"],\n default: null,\n description:\n \"Informational internal vendor cost in integer cents. Never derives \" +\n \"the amount. Redacted org-side.\",\n },\n vendorId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Optional reference to the org-scoped Vendor. Internal, redacted \" +\n \"org-side.\",\n },\n vendorInvoice: {\n anyOf: [{ $ref: \"mediaFile.json\" }, { type: \"null\" }],\n default: null,\n description:\n \"The vendor's invoice file backing the line, mirroring the cost-entry \" +\n \"field. Internal, redacted org-side.\",\n },\n vendorInvoiceNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The vendor's own invoice number. Internal, redacted org-side.\",\n },\n ...ledgerAnnotationProperties,\n taxable: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether the line's amount joins the bill's taxable subtotal. \" +\n \"Customer-facing: locks at mark-sent.\",\n },\n },\n} as const;\n\nexport const billSchema = {\n $schema: \"http://json-schema.org/draft-07/schema\",\n $id: \"bill.json\",\n title: \"Bill\",\n description:\n \"A OneBill bill, stored platform-wide and stamped with its organization: \" +\n \"KFC staff assemble billed lines from the \" +\n \"uninvoiced cost pool (plus manual lines) into a draft, then mark it sent \" +\n \"to freeze and reveal it to the customer. Lifecycle draft → sent → paid, \" +\n \"plus void. Customers see a bill in-app only once sent.\",\n type: \"object\",\n required: [\"id\", \"organizationId\", \"status\", \"currency\", \"lines\"],\n additionalProperties: false,\n properties: {\n id: {\n $ref: \"definitions.json#/definitions/id\",\n },\n type: {\n type: \"string\",\n enum: [\"bill\"],\n default: \"bill\",\n },\n organizationId: {\n type: \"string\",\n description:\n \"The organization the bill invoices. Bills live in one admin-database \" +\n \"collection across every organization, so each carries its owner \" +\n \"explicitly — stamped from the request context at creation, never \" +\n \"client-supplied.\",\n },\n status: {\n type: \"string\",\n enum: [\"draft\", \"sent\", \"paid\", \"void\"],\n default: \"draft\",\n description:\n \"Lifecycle state. `sent` freezes customer-facing fields and reveals \" +\n \"the bill to the org; `paid` records manual payment; `void` releases \" +\n \"cost-entry claims and hides the bill from the org view. Drafts \" +\n \"hard-delete rather than voiding.\",\n },\n invoiceNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Kohost's own invoice number, `KB-<n>` from a single global sequence. \" +\n \"System-assigned at mark-sent and never entered by hand: null while \" +\n \"the bill is a draft, immutable once set. A wrong bill is corrected \" +\n \"by void-and-reissue, so numbers gap and are never reused.\",\n },\n period: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n 'Display-only month label (e.g. \"July 2026\"). A UI hint; the bill\\'s ' +\n \"membership is defined by its lines, not a calendar bucket.\",\n },\n currency: {\n type: \"string\",\n enum: [\"USD\"],\n default: \"USD\",\n description: \"ISO 4217 currency code. USD only in v1.\",\n },\n fileId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The generated bill PDF's media-file ID, minted atomically at \" +\n \"mark-sent.\",\n },\n fileUrl: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The generated bill PDF's file-store URL, snapshotted at mark-sent \" +\n \"alongside fileId. Held so the sent-bill surface and the sent \" +\n \"notification email can mint a signed, unauthenticated download link \" +\n \"without a file lookup. Unsigned on its own (a bare link 401s).\",\n },\n memo: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Internal KFC-only note. Never customer-facing; editable in any state.\",\n },\n billingAddress: {\n anyOf: [\n { $ref: \"definitions.json#/definitions/address\" },\n { type: \"null\" },\n ],\n default: null,\n description:\n \"The org billing address snapshotted at mark-sent. Null while \" +\n \"drafting, when it live-reads from the Organization. Mark-sent \" +\n \"requires a complete address (line1, city, state, postalCode).\",\n },\n taxRate: {\n type: [\"number\", \"null\"],\n default: null,\n minimum: 0,\n description:\n \"Tax rate as a plain float percent applied to the taxable line \" +\n \"subtotal. While drafting, null means the platform default rate; the \" +\n \"effective rate is snapshotted at mark-sent.\",\n },\n taxExempt: {\n type: \"boolean\",\n default: false,\n description:\n \"The organization's tax exemption snapshotted at mark-sent. While \" +\n \"drafting it live-reads from the Organization.\",\n },\n shippingAmount: {\n type: [\"integer\", \"null\"],\n default: null,\n minimum: 0,\n description:\n \"Shipping & handling in integer cents, added to the grand total on \" +\n \"top of the line subtotal and tax. Null means none.\",\n },\n lines: {\n type: \"array\",\n default: [],\n description:\n \"The bill's lines: cost lines claimed from the uninvoiced pool and \" +\n \"literal manual lines.\",\n items: {\n oneOf: [costLineSchema, manualLineSchema],\n },\n },\n sentAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the bill was marked sent. Absent until sent.\",\n },\n paidAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the bill was marked paid. Absent until paid.\",\n },\n voidedAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the bill was voided. Absent unless voided.\",\n },\n createdAt: {\n $ref: \"definitions.json#/definitions/date\",\n },\n updatedAt: {\n $ref: \"definitions.json#/definitions/date\",\n },\n },\n} as const;\n\nexport type BillSchema = FromSchema<\n typeof billSchema,\n {\n references: [typeof defs, typeof mediaFileSchema];\n deserialize: [\n {\n pattern: {\n format: \"date-time\";\n };\n output: Date | ISODateString;\n },\n ];\n }\n>;\n\n/** One line on a bill: a cost line or a manual line. */\nexport type BillLine = NonNullable<BillSchema[\"lines\"]>[number];\n"],"mappings":"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"}
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
import type { FromSchema } from "json-schema-to-ts";
|
|
2
|
+
export declare const conciergeWorkspaceBillSchema: {
|
|
3
|
+
readonly $schema: "http://json-schema.org/draft-07/schema";
|
|
4
|
+
readonly $id: "conciergeWorkspaceBill.json";
|
|
5
|
+
readonly title: "ConciergeWorkspaceBill";
|
|
6
|
+
readonly description: string;
|
|
7
|
+
readonly type: "object";
|
|
8
|
+
readonly additionalProperties: false;
|
|
9
|
+
readonly required: readonly ["id", "organizationId", "organizationName", "invoiceNumber", "status", "effectiveDate", "sentAt", "createdAt", "period", "total", "currency", "lineCount"];
|
|
10
|
+
readonly properties: {
|
|
11
|
+
readonly id: {
|
|
12
|
+
readonly type: "string";
|
|
13
|
+
readonly description: "The bill's ID.";
|
|
14
|
+
};
|
|
15
|
+
readonly organizationId: {
|
|
16
|
+
readonly type: "string";
|
|
17
|
+
readonly description: "The organization the bill invoices.";
|
|
18
|
+
};
|
|
19
|
+
readonly organizationName: {
|
|
20
|
+
readonly type: "string";
|
|
21
|
+
readonly description: "The invoiced organization's display name.";
|
|
22
|
+
};
|
|
23
|
+
readonly invoiceNumber: {
|
|
24
|
+
readonly type: readonly ["string", "null"];
|
|
25
|
+
readonly description: string;
|
|
26
|
+
};
|
|
27
|
+
readonly status: {
|
|
28
|
+
readonly type: "string";
|
|
29
|
+
readonly enum: readonly ["draft", "sent", "paid", "void"];
|
|
30
|
+
readonly description: "The bill's lifecycle state.";
|
|
31
|
+
};
|
|
32
|
+
readonly effectiveDate: {
|
|
33
|
+
readonly type: "string";
|
|
34
|
+
readonly format: "date-time";
|
|
35
|
+
readonly description: string;
|
|
36
|
+
};
|
|
37
|
+
readonly sentAt: {
|
|
38
|
+
readonly type: readonly ["string", "null"];
|
|
39
|
+
readonly description: "When the bill was marked sent. Null until sent.";
|
|
40
|
+
};
|
|
41
|
+
readonly createdAt: {
|
|
42
|
+
readonly type: "string";
|
|
43
|
+
readonly format: "date-time";
|
|
44
|
+
readonly description: "When the bill was created.";
|
|
45
|
+
};
|
|
46
|
+
readonly period: {
|
|
47
|
+
readonly type: readonly ["string", "null"];
|
|
48
|
+
readonly description: 'Display-only month label (e.g. "July 2026").';
|
|
49
|
+
};
|
|
50
|
+
readonly total: {
|
|
51
|
+
readonly type: readonly ["integer", "null"];
|
|
52
|
+
readonly description: string;
|
|
53
|
+
};
|
|
54
|
+
readonly currency: {
|
|
55
|
+
readonly type: "string";
|
|
56
|
+
readonly description: "ISO 4217 currency code.";
|
|
57
|
+
};
|
|
58
|
+
readonly lineCount: {
|
|
59
|
+
readonly type: "integer";
|
|
60
|
+
readonly description: "How many lines the bill carries.";
|
|
61
|
+
};
|
|
62
|
+
};
|
|
63
|
+
};
|
|
64
|
+
export declare const conciergeWorkspaceBillsResponseSchema: {
|
|
65
|
+
readonly $schema: "http://json-schema.org/draft-07/schema";
|
|
66
|
+
readonly $id: "conciergeWorkspaceBillsResponse.json";
|
|
67
|
+
readonly title: "ConciergeWorkspaceBillsResponse";
|
|
68
|
+
readonly description: string;
|
|
69
|
+
readonly type: "object";
|
|
70
|
+
readonly additionalProperties: false;
|
|
71
|
+
readonly required: readonly ["bills", "page", "pages", "total"];
|
|
72
|
+
readonly properties: {
|
|
73
|
+
readonly bills: {
|
|
74
|
+
readonly type: "array";
|
|
75
|
+
readonly items: {
|
|
76
|
+
readonly $schema: "http://json-schema.org/draft-07/schema";
|
|
77
|
+
readonly $id: "conciergeWorkspaceBill.json";
|
|
78
|
+
readonly title: "ConciergeWorkspaceBill";
|
|
79
|
+
readonly description: string;
|
|
80
|
+
readonly type: "object";
|
|
81
|
+
readonly additionalProperties: false;
|
|
82
|
+
readonly required: readonly ["id", "organizationId", "organizationName", "invoiceNumber", "status", "effectiveDate", "sentAt", "createdAt", "period", "total", "currency", "lineCount"];
|
|
83
|
+
readonly properties: {
|
|
84
|
+
readonly id: {
|
|
85
|
+
readonly type: "string";
|
|
86
|
+
readonly description: "The bill's ID.";
|
|
87
|
+
};
|
|
88
|
+
readonly organizationId: {
|
|
89
|
+
readonly type: "string";
|
|
90
|
+
readonly description: "The organization the bill invoices.";
|
|
91
|
+
};
|
|
92
|
+
readonly organizationName: {
|
|
93
|
+
readonly type: "string";
|
|
94
|
+
readonly description: "The invoiced organization's display name.";
|
|
95
|
+
};
|
|
96
|
+
readonly invoiceNumber: {
|
|
97
|
+
readonly type: readonly ["string", "null"];
|
|
98
|
+
readonly description: string;
|
|
99
|
+
};
|
|
100
|
+
readonly status: {
|
|
101
|
+
readonly type: "string";
|
|
102
|
+
readonly enum: readonly ["draft", "sent", "paid", "void"];
|
|
103
|
+
readonly description: "The bill's lifecycle state.";
|
|
104
|
+
};
|
|
105
|
+
readonly effectiveDate: {
|
|
106
|
+
readonly type: "string";
|
|
107
|
+
readonly format: "date-time";
|
|
108
|
+
readonly description: string;
|
|
109
|
+
};
|
|
110
|
+
readonly sentAt: {
|
|
111
|
+
readonly type: readonly ["string", "null"];
|
|
112
|
+
readonly description: "When the bill was marked sent. Null until sent.";
|
|
113
|
+
};
|
|
114
|
+
readonly createdAt: {
|
|
115
|
+
readonly type: "string";
|
|
116
|
+
readonly format: "date-time";
|
|
117
|
+
readonly description: "When the bill was created.";
|
|
118
|
+
};
|
|
119
|
+
readonly period: {
|
|
120
|
+
readonly type: readonly ["string", "null"];
|
|
121
|
+
readonly description: 'Display-only month label (e.g. "July 2026").';
|
|
122
|
+
};
|
|
123
|
+
readonly total: {
|
|
124
|
+
readonly type: readonly ["integer", "null"];
|
|
125
|
+
readonly description: string;
|
|
126
|
+
};
|
|
127
|
+
readonly currency: {
|
|
128
|
+
readonly type: "string";
|
|
129
|
+
readonly description: "ISO 4217 currency code.";
|
|
130
|
+
};
|
|
131
|
+
readonly lineCount: {
|
|
132
|
+
readonly type: "integer";
|
|
133
|
+
readonly description: "How many lines the bill carries.";
|
|
134
|
+
};
|
|
135
|
+
};
|
|
136
|
+
};
|
|
137
|
+
};
|
|
138
|
+
readonly page: {
|
|
139
|
+
readonly type: "integer";
|
|
140
|
+
readonly minimum: 1;
|
|
141
|
+
readonly description: "The 1-based page returned.";
|
|
142
|
+
};
|
|
143
|
+
readonly pages: {
|
|
144
|
+
readonly type: "integer";
|
|
145
|
+
readonly minimum: 0;
|
|
146
|
+
readonly description: "How many pages the filtered set spans.";
|
|
147
|
+
};
|
|
148
|
+
readonly total: {
|
|
149
|
+
readonly type: "integer";
|
|
150
|
+
readonly minimum: 0;
|
|
151
|
+
readonly description: "How many bills match the filter across all pages.";
|
|
152
|
+
};
|
|
153
|
+
};
|
|
154
|
+
};
|
|
155
|
+
export type ConciergeWorkspaceBillSchema = FromSchema<typeof conciergeWorkspaceBillSchema>;
|
|
156
|
+
export type ConciergeWorkspaceBillsResponseSchema = FromSchema<typeof conciergeWorkspaceBillsResponseSchema>;
|
package/dist/schemas/cost.d.ts
CHANGED
|
@@ -10,6 +10,26 @@ export declare const costSchema: {
|
|
|
10
10
|
readonly required: readonly ["id", "description", "currency", "price", "estimate", "markup", "organizationId"];
|
|
11
11
|
readonly additionalProperties: false;
|
|
12
12
|
readonly properties: {
|
|
13
|
+
readonly note: {
|
|
14
|
+
readonly type: readonly ["string", "null"];
|
|
15
|
+
readonly maxLength: 1000;
|
|
16
|
+
readonly default: null;
|
|
17
|
+
readonly description: string;
|
|
18
|
+
};
|
|
19
|
+
readonly vendorPayment: {
|
|
20
|
+
readonly type: readonly ["object", "null"];
|
|
21
|
+
readonly additionalProperties: false;
|
|
22
|
+
readonly required: readonly ["paidOn"];
|
|
23
|
+
readonly default: null;
|
|
24
|
+
readonly description: string;
|
|
25
|
+
readonly properties: {
|
|
26
|
+
readonly paidOn: {
|
|
27
|
+
readonly type: "string";
|
|
28
|
+
readonly pattern: "^\\d{4}-\\d{2}-\\d{2}$";
|
|
29
|
+
readonly description: "The calendar day the vendor was paid, as YYYY-MM-DD.";
|
|
30
|
+
};
|
|
31
|
+
};
|
|
32
|
+
};
|
|
13
33
|
readonly id: {
|
|
14
34
|
readonly type: "string";
|
|
15
35
|
readonly description: "The ID of the cost entry.";
|
|
@@ -75,8 +75,56 @@ export declare const costBillingReview: <const Actions extends readonly string[]
|
|
|
75
75
|
};
|
|
76
76
|
};
|
|
77
77
|
};
|
|
78
|
+
/**
|
|
79
|
+
* Kohost's private bookkeeping on a Cost ledger row: the Ledger note and the
|
|
80
|
+
* Vendor payment. Every row kind carries both beside its vendor invoice, so a
|
|
81
|
+
* Manual line spreads these in too. Editable in any state, never attributed,
|
|
82
|
+
* and never part of a redacted projection.
|
|
83
|
+
*/
|
|
84
|
+
export declare const ledgerAnnotationProperties: {
|
|
85
|
+
readonly note: {
|
|
86
|
+
readonly type: readonly ["string", "null"];
|
|
87
|
+
readonly maxLength: 1000;
|
|
88
|
+
readonly default: null;
|
|
89
|
+
readonly description: string;
|
|
90
|
+
};
|
|
91
|
+
readonly vendorPayment: {
|
|
92
|
+
readonly type: readonly ["object", "null"];
|
|
93
|
+
readonly additionalProperties: false;
|
|
94
|
+
readonly required: readonly ["paidOn"];
|
|
95
|
+
readonly default: null;
|
|
96
|
+
readonly description: string;
|
|
97
|
+
readonly properties: {
|
|
98
|
+
readonly paidOn: {
|
|
99
|
+
readonly type: "string";
|
|
100
|
+
readonly pattern: "^\\d{4}-\\d{2}-\\d{2}$";
|
|
101
|
+
readonly description: "The calendar day the vendor was paid, as YYYY-MM-DD.";
|
|
102
|
+
};
|
|
103
|
+
};
|
|
104
|
+
};
|
|
105
|
+
};
|
|
78
106
|
export declare const costEntryRequired: readonly ["id", "description", "currency", "price", "estimate", "markup"];
|
|
79
107
|
export declare const costEntryProperties: {
|
|
108
|
+
readonly note: {
|
|
109
|
+
readonly type: readonly ["string", "null"];
|
|
110
|
+
readonly maxLength: 1000;
|
|
111
|
+
readonly default: null;
|
|
112
|
+
readonly description: string;
|
|
113
|
+
};
|
|
114
|
+
readonly vendorPayment: {
|
|
115
|
+
readonly type: readonly ["object", "null"];
|
|
116
|
+
readonly additionalProperties: false;
|
|
117
|
+
readonly required: readonly ["paidOn"];
|
|
118
|
+
readonly default: null;
|
|
119
|
+
readonly description: string;
|
|
120
|
+
readonly properties: {
|
|
121
|
+
readonly paidOn: {
|
|
122
|
+
readonly type: "string";
|
|
123
|
+
readonly pattern: "^\\d{4}-\\d{2}-\\d{2}$";
|
|
124
|
+
readonly description: "The calendar day the vendor was paid, as YYYY-MM-DD.";
|
|
125
|
+
};
|
|
126
|
+
};
|
|
127
|
+
};
|
|
80
128
|
readonly id: {
|
|
81
129
|
readonly type: "string";
|
|
82
130
|
readonly description: "The ID of the cost entry.";
|
|
@@ -93,6 +93,32 @@ const costBillingReview = (actions) => ({
|
|
|
93
93
|
}
|
|
94
94
|
}
|
|
95
95
|
});
|
|
96
|
+
/**
|
|
97
|
+
* Kohost's private bookkeeping on a Cost ledger row: the Ledger note and the
|
|
98
|
+
* Vendor payment. Every row kind carries both beside its vendor invoice, so a
|
|
99
|
+
* Manual line spreads these in too. Editable in any state, never attributed,
|
|
100
|
+
* and never part of a redacted projection.
|
|
101
|
+
*/
|
|
102
|
+
const ledgerAnnotationProperties = {
|
|
103
|
+
note: {
|
|
104
|
+
type: ["string", "null"],
|
|
105
|
+
maxLength: 1e3,
|
|
106
|
+
default: null,
|
|
107
|
+
description: "The Ledger note: Kohost's free-text note on the row, overwritten on edit with no attribution. Internal, redacted org-side."
|
|
108
|
+
},
|
|
109
|
+
vendorPayment: {
|
|
110
|
+
type: ["object", "null"],
|
|
111
|
+
additionalProperties: false,
|
|
112
|
+
required: ["paidOn"],
|
|
113
|
+
default: null,
|
|
114
|
+
description: "The Vendor payment: Kohost has paid the vendor for this row. Only a row with a vendor actual above zero carries one, and while it does that actual cannot be cleared or zeroed and the row cannot be voided or deleted. Gates nothing on the customer side. An object so it can grow a reference and amount. Internal, redacted org-side.",
|
|
115
|
+
properties: { paidOn: {
|
|
116
|
+
type: "string",
|
|
117
|
+
pattern: "^\\d{4}-\\d{2}-\\d{2}$",
|
|
118
|
+
description: "The calendar day the vendor was paid, as YYYY-MM-DD."
|
|
119
|
+
} }
|
|
120
|
+
}
|
|
121
|
+
};
|
|
96
122
|
const costEntryRequired = [
|
|
97
123
|
"id",
|
|
98
124
|
"description",
|
|
@@ -155,6 +181,7 @@ const costEntryProperties = {
|
|
|
155
181
|
default: null,
|
|
156
182
|
description: "The vendor's own invoice number. Internal, redacted org-side like the rest of the cost split."
|
|
157
183
|
},
|
|
184
|
+
...ledgerAnnotationProperties,
|
|
158
185
|
billId: {
|
|
159
186
|
type: ["string", "null"],
|
|
160
187
|
default: null,
|
|
@@ -172,6 +199,6 @@ const costEntryProperties = {
|
|
|
172
199
|
])
|
|
173
200
|
};
|
|
174
201
|
//#endregion
|
|
175
|
-
export { costBillingReview, costEntryProperties, costEntryRequired, nullableMoney };
|
|
202
|
+
export { costBillingReview, costEntryProperties, costEntryRequired, ledgerAnnotationProperties, nullableMoney };
|
|
176
203
|
|
|
177
204
|
//# sourceMappingURL=costEntry.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"costEntry.js","names":[],"sources":["../../.generated/schemas/costEntry.ts"],"sourcesContent":["// The cost-entry core: the money shape and reconciliation lifecycle every\n// OneBill cost carries, whether a Ticket embeds it or it stands alone in the\n// costs collection. Both hosts spread these consts into their own `properties`\n// and `required` rather than `$ref`-ing this file: draft-07 resolves `allOf`\n// against `additionalProperties: false` per subschema, so a composed entry\n// would reject every field the other half declared, and `FromSchema` derives\n// nothing useful from a reference it cannot inline.\n//\n// Nothing here is exported with a name ending in \"Schema\" and the model\n// generator skips this file by name (`scripts/generate-source-models.js`):\n// these are fragments, not an entity.\n\nconst moneyProperties = {\n amount: {\n type: \"integer\",\n minimum: 0,\n description: \"The amount in integer cents.\",\n },\n recordedBy: {\n type: \"string\",\n description: \"The ID of the user who recorded the amount.\",\n },\n recordedAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the amount was recorded.\",\n },\n} as const;\n\nconst moneyRequired = [\"amount\", \"recordedBy\", \"recordedAt\"] as const;\n\nconst money = (description: string) =>\n ({\n type: \"object\",\n additionalProperties: false,\n required: moneyRequired,\n description,\n properties: moneyProperties,\n }) as const;\n\n/**\n * The same phase on a host that admits a Pending cost, where `null` means the\n * amount is not known yet. Only the ticket cost entry takes this shape: a\n * ticket is what a vendor quote is awaited on.\n */\nexport const nullableMoney = (description: string) =>\n ({\n type: [\"object\", \"null\"],\n additionalProperties: false,\n required: moneyRequired,\n default: null,\n description,\n properties: moneyProperties,\n }) as const;\n\n/**\n * The append-only billing review history, over whichever actions the host\n * admits. A ticket cost can be voided (withdrawn from the customer); a\n * standalone cost has no ticket to withdraw it from, so its history stops at\n * write-offs and divergence acknowledgements.\n */\nexport const costBillingReview = <const Actions extends readonly string[]>(\n actions: Actions,\n) =>\n ({\n type: \"array\",\n default: [],\n description:\n \"Append-only billing review history for the entry (approval-history \" +\n \"pattern): reversible write-offs, and billed-vs-price divergence \" +\n \"acknowledgements. Internal, redacted org-side.\",\n items: {\n type: \"object\",\n additionalProperties: false,\n required: [\"id\", \"action\", \"performedAt\"],\n properties: {\n id: {\n type: \"string\",\n description: \"The ID of the billing review entry.\",\n },\n action: {\n type: \"string\",\n enum: actions,\n },\n performedBy: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The ID of the user whose write appended this entry. Null when \" +\n \"the write was not user-attributable.\",\n },\n performedAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the entry was appended.\",\n },\n note: {\n type: [\"string\", \"null\"],\n default: null,\n description: \"Free-text rationale for the action.\",\n },\n billedAmount: {\n type: \"integer\",\n minimum: 0,\n description:\n \"divergenceAcknowledged only: the amount a bill line already \" +\n \"charged for this entry, in integer cents, frozen at ack time.\",\n },\n priceAmount: {\n type: \"integer\",\n minimum: 0,\n description:\n \"divergenceAcknowledged only: the entry's stored customer price \" +\n \"in integer cents at ack time. A divergence is a billed line \" +\n \"that no longer matches the price behind it — a price corrected \" +\n \"after the cost was claimed — so the ack silences this one pair \" +\n \"and any later price move re-flags it. A vendor actual arriving \" +\n \"after billing is not a divergence: it moves margin, not what \" +\n \"the customer owes.\",\n },\n },\n },\n }) as const;\n\nexport const costEntryRequired = [\n \"id\",\n \"description\",\n \"currency\",\n \"price\",\n \"estimate\",\n \"markup\",\n] as const;\n\nexport const costEntryProperties = {\n id: {\n type: \"string\",\n description: \"The ID of the cost entry.\",\n },\n description: {\n type: \"string\",\n description: \"What the cost covers.\",\n },\n currency: {\n type: \"string\",\n default: \"USD\",\n description: \"ISO 4217 currency code of the entry's amounts.\",\n },\n price: money(\n \"The authoritative customer price — what the org is charged, what the \" +\n \"approval gate totals, and what a bill line bills. Seeded at recording \" +\n \"from the estimate and the markup, and from then on independent of all \" +\n \"three: editing `estimate`, `actual`, or `markup` never moves it. Only \" +\n \"an explicit price write does.\",\n ),\n estimate: money(\"The vendor cost estimate phase of the entry.\"),\n actual: money(\n \"The settled vendor cost, recorded once the vendor's figure is known.\",\n ),\n markup: {\n type: \"object\",\n additionalProperties: false,\n required: [\"percent\"],\n properties: {\n percent: {\n type: \"number\",\n description:\n \"Markup percent the price was derived at, uncapped in either \" +\n \"direction. Context for how the price was arrived at, not the \" +\n \"source of truth for any amount: `price` is stored, so re-keying \" +\n \"this percent prices nothing. A biller may charge under the vendor \" +\n \"cost as a deliberate comp, and this records that as the negative \" +\n \"percent it is rather than as a floor of zero the price never came \" +\n \"from.\",\n },\n custom: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether the percent was overridden by hand rather than keyed from \" +\n \"the configured markup tiers. Custom percents are never re-keyed on \" +\n \"estimate edits.\",\n },\n },\n },\n vendorId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The Vendor the charge is owed to. A plain reference — no rollups — \" +\n \"resolved inside the entry's own organization. Internal, redacted \" +\n \"org-side with the rest of the cost split.\",\n },\n categoryId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The billing category classifying this cost. `AddBillLine` snapshots \" +\n \"it onto the claiming line, which owns its own category from then on. \" +\n \"Internal, redacted org-side with the rest of the cost split.\",\n },\n vendorInvoices: {\n type: \"array\",\n items: { $ref: \"mediaFile.json\" },\n default: [],\n description:\n \"The vendor's paperwork backing the entry's amounts — an invoice plus \" +\n \"whatever came with it. Internal: the file-store cannot enforce \" +\n \"roster-only reads, so the boundary is this field living on the full \" +\n \"shape only, and the redacted projection never carries it.\",\n },\n vendorInvoiceNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The vendor's own invoice number. Internal, redacted org-side like the \" +\n \"rest of the cost split.\",\n },\n billId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Backlink to the bill whose draft claimed this cost as a line. Written \" +\n \"when a draft bill adds the line, cleared on line removal, draft \" +\n \"delete, or bill void; a claimed cost leaves the uninvoiced pool, \" +\n \"making double-invoicing structurally impossible. Server-maintained at \" +\n \"the repository, never set by clients.\",\n },\n writtenOff: {\n type: \"boolean\",\n default: false,\n description:\n \"Server-maintained denormalization of billingReview (approvalState \" +\n \"pattern): true after a writtenOff entry until a reinstated entry \" +\n \"follows. A written-off cost leaves the uninvoiced pool. Never set by \" +\n \"clients.\",\n },\n billingReview: costBillingReview([\n \"writtenOff\",\n \"reinstated\",\n \"divergenceAcknowledged\",\n ]),\n} as const;\n"],"mappings":";AAYA,MAAM,kBAAkB;CACtB,QAAQ;EACN,MAAM;EACN,SAAS;EACT,aAAa;CACf;CACA,YAAY;EACV,MAAM;EACN,aAAa;CACf;CACA,YAAY;EACV,MAAM;EACN,aAAa;CACf;AACF;AAEA,MAAM,gBAAgB;CAAC;CAAU;CAAc;AAAY;AAE3D,MAAM,SAAS,iBACZ;CACC,MAAM;CACN,sBAAsB;CACtB,UAAU;CACV;CACA,YAAY;AACd;;;;;;AAOF,MAAa,iBAAiB,iBAC3B;CACC,MAAM,CAAC,UAAU,MAAM;CACvB,sBAAsB;CACtB,UAAU;CACV,SAAS;CACT;CACA,YAAY;AACd;;;;;;;AAQF,MAAa,qBACX,aAEC;CACC,MAAM;CACN,SAAS,CAAC;CACV,aACE;CAGF,OAAO;EACL,MAAM;EACN,sBAAsB;EACtB,UAAU;GAAC;GAAM;GAAU;EAAa;EACxC,YAAY;GACV,IAAI;IACF,MAAM;IACN,aAAa;GACf;GACA,QAAQ;IACN,MAAM;IACN,MAAM;GACR;GACA,aAAa;IACX,MAAM,CAAC,UAAU,MAAM;IACvB,SAAS;IACT,aACE;GAEJ;GACA,aAAa;IACX,MAAM;IACN,aAAa;GACf;GACA,MAAM;IACJ,MAAM,CAAC,UAAU,MAAM;IACvB,SAAS;IACT,aAAa;GACf;GACA,cAAc;IACZ,MAAM;IACN,SAAS;IACT,aACE;GAEJ;GACA,aAAa;IACX,MAAM;IACN,SAAS;IACT,aACE;GAOJ;EACF;CACF;AACF;AAEF,MAAa,oBAAoB;CAC/B;CACA;CACA;CACA;CACA;CACA;AACF;AAEA,MAAa,sBAAsB;CACjC,IAAI;EACF,MAAM;EACN,aAAa;CACf;CACA,aAAa;EACX,MAAM;EACN,aAAa;CACf;CACA,UAAU;EACR,MAAM;EACN,SAAS;EACT,aAAa;CACf;CACA,OAAO,MACL,sTAKF;CACA,UAAU,MAAM,8CAA8C;CAC9D,QAAQ,MACN,sEACF;CACA,QAAQ;EACN,MAAM;EACN,sBAAsB;EACtB,UAAU,CAAC,SAAS;EACpB,YAAY;GACV,SAAS;IACP,MAAM;IACN,aACE;GAOJ;GACA,QAAQ;IACN,MAAM;IACN,SAAS;IACT,aACE;GAGJ;EACF;CACF;CACA,UAAU;EACR,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAGJ;CACA,YAAY;EACV,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAGJ;CACA,gBAAgB;EACd,MAAM;EACN,OAAO,EAAE,MAAM,iBAAiB;EAChC,SAAS,CAAC;EACV,aACE;CAIJ;CACA,qBAAqB;EACnB,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAEJ;CACA,QAAQ;EACN,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAKJ;CACA,YAAY;EACV,MAAM;EACN,SAAS;EACT,aACE;CAIJ;CACA,eAAe,kBAAkB;EAC/B;EACA;EACA;CACF,CAAC;AACH"}
|
|
1
|
+
{"version":3,"file":"costEntry.js","names":[],"sources":["../../.generated/schemas/costEntry.ts"],"sourcesContent":["// The cost-entry core: the money shape and reconciliation lifecycle every\n// OneBill cost carries, whether a Ticket embeds it or it stands alone in the\n// costs collection. Both hosts spread these consts into their own `properties`\n// and `required` rather than `$ref`-ing this file: draft-07 resolves `allOf`\n// against `additionalProperties: false` per subschema, so a composed entry\n// would reject every field the other half declared, and `FromSchema` derives\n// nothing useful from a reference it cannot inline.\n//\n// Nothing here is exported with a name ending in \"Schema\" and the model\n// generator skips this file by name (`scripts/generate-source-models.js`):\n// these are fragments, not an entity.\n\nconst moneyProperties = {\n amount: {\n type: \"integer\",\n minimum: 0,\n description: \"The amount in integer cents.\",\n },\n recordedBy: {\n type: \"string\",\n description: \"The ID of the user who recorded the amount.\",\n },\n recordedAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the amount was recorded.\",\n },\n} as const;\n\nconst moneyRequired = [\"amount\", \"recordedBy\", \"recordedAt\"] as const;\n\nconst money = (description: string) =>\n ({\n type: \"object\",\n additionalProperties: false,\n required: moneyRequired,\n description,\n properties: moneyProperties,\n }) as const;\n\n/**\n * The same phase on a host that admits a Pending cost, where `null` means the\n * amount is not known yet. Only the ticket cost entry takes this shape: a\n * ticket is what a vendor quote is awaited on.\n */\nexport const nullableMoney = (description: string) =>\n ({\n type: [\"object\", \"null\"],\n additionalProperties: false,\n required: moneyRequired,\n default: null,\n description,\n properties: moneyProperties,\n }) as const;\n\n/**\n * The append-only billing review history, over whichever actions the host\n * admits. A ticket cost can be voided (withdrawn from the customer); a\n * standalone cost has no ticket to withdraw it from, so its history stops at\n * write-offs and divergence acknowledgements.\n */\nexport const costBillingReview = <const Actions extends readonly string[]>(\n actions: Actions,\n) =>\n ({\n type: \"array\",\n default: [],\n description:\n \"Append-only billing review history for the entry (approval-history \" +\n \"pattern): reversible write-offs, and billed-vs-price divergence \" +\n \"acknowledgements. Internal, redacted org-side.\",\n items: {\n type: \"object\",\n additionalProperties: false,\n required: [\"id\", \"action\", \"performedAt\"],\n properties: {\n id: {\n type: \"string\",\n description: \"The ID of the billing review entry.\",\n },\n action: {\n type: \"string\",\n enum: actions,\n },\n performedBy: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The ID of the user whose write appended this entry. Null when \" +\n \"the write was not user-attributable.\",\n },\n performedAt: {\n $ref: \"definitions.json#/definitions/date\",\n description: \"When the entry was appended.\",\n },\n note: {\n type: [\"string\", \"null\"],\n default: null,\n description: \"Free-text rationale for the action.\",\n },\n billedAmount: {\n type: \"integer\",\n minimum: 0,\n description:\n \"divergenceAcknowledged only: the amount a bill line already \" +\n \"charged for this entry, in integer cents, frozen at ack time.\",\n },\n priceAmount: {\n type: \"integer\",\n minimum: 0,\n description:\n \"divergenceAcknowledged only: the entry's stored customer price \" +\n \"in integer cents at ack time. A divergence is a billed line \" +\n \"that no longer matches the price behind it — a price corrected \" +\n \"after the cost was claimed — so the ack silences this one pair \" +\n \"and any later price move re-flags it. A vendor actual arriving \" +\n \"after billing is not a divergence: it moves margin, not what \" +\n \"the customer owes.\",\n },\n },\n },\n }) as const;\n\n/**\n * Kohost's private bookkeeping on a Cost ledger row: the Ledger note and the\n * Vendor payment. Every row kind carries both beside its vendor invoice, so a\n * Manual line spreads these in too. Editable in any state, never attributed,\n * and never part of a redacted projection.\n */\nexport const ledgerAnnotationProperties = {\n note: {\n type: [\"string\", \"null\"],\n maxLength: 1000,\n default: null,\n description:\n \"The Ledger note: Kohost's free-text note on the row, overwritten on \" +\n \"edit with no attribution. Internal, redacted org-side.\",\n },\n vendorPayment: {\n type: [\"object\", \"null\"],\n additionalProperties: false,\n required: [\"paidOn\"],\n default: null,\n description:\n \"The Vendor payment: Kohost has paid the vendor for this row. Only a \" +\n \"row with a vendor actual above zero carries one, and while it does \" +\n \"that actual cannot be cleared or zeroed and the row cannot be voided \" +\n \"or deleted. Gates nothing on the customer side. An object so it can \" +\n \"grow a reference and amount. Internal, redacted org-side.\",\n properties: {\n paidOn: {\n type: \"string\",\n pattern: \"^\\\\d{4}-\\\\d{2}-\\\\d{2}$\",\n description: \"The calendar day the vendor was paid, as YYYY-MM-DD.\",\n },\n },\n },\n} as const;\n\nexport const costEntryRequired = [\n \"id\",\n \"description\",\n \"currency\",\n \"price\",\n \"estimate\",\n \"markup\",\n] as const;\n\nexport const costEntryProperties = {\n id: {\n type: \"string\",\n description: \"The ID of the cost entry.\",\n },\n description: {\n type: \"string\",\n description: \"What the cost covers.\",\n },\n currency: {\n type: \"string\",\n default: \"USD\",\n description: \"ISO 4217 currency code of the entry's amounts.\",\n },\n price: money(\n \"The authoritative customer price — what the org is charged, what the \" +\n \"approval gate totals, and what a bill line bills. Seeded at recording \" +\n \"from the estimate and the markup, and from then on independent of all \" +\n \"three: editing `estimate`, `actual`, or `markup` never moves it. Only \" +\n \"an explicit price write does.\",\n ),\n estimate: money(\"The vendor cost estimate phase of the entry.\"),\n actual: money(\n \"The settled vendor cost, recorded once the vendor's figure is known.\",\n ),\n markup: {\n type: \"object\",\n additionalProperties: false,\n required: [\"percent\"],\n properties: {\n percent: {\n type: \"number\",\n description:\n \"Markup percent the price was derived at, uncapped in either \" +\n \"direction. Context for how the price was arrived at, not the \" +\n \"source of truth for any amount: `price` is stored, so re-keying \" +\n \"this percent prices nothing. A biller may charge under the vendor \" +\n \"cost as a deliberate comp, and this records that as the negative \" +\n \"percent it is rather than as a floor of zero the price never came \" +\n \"from.\",\n },\n custom: {\n type: \"boolean\",\n default: false,\n description:\n \"Whether the percent was overridden by hand rather than keyed from \" +\n \"the configured markup tiers. Custom percents are never re-keyed on \" +\n \"estimate edits.\",\n },\n },\n },\n vendorId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The Vendor the charge is owed to. A plain reference — no rollups — \" +\n \"resolved inside the entry's own organization. Internal, redacted \" +\n \"org-side with the rest of the cost split.\",\n },\n categoryId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The billing category classifying this cost. `AddBillLine` snapshots \" +\n \"it onto the claiming line, which owns its own category from then on. \" +\n \"Internal, redacted org-side with the rest of the cost split.\",\n },\n vendorInvoices: {\n type: \"array\",\n items: { $ref: \"mediaFile.json\" },\n default: [],\n description:\n \"The vendor's paperwork backing the entry's amounts — an invoice plus \" +\n \"whatever came with it. Internal: the file-store cannot enforce \" +\n \"roster-only reads, so the boundary is this field living on the full \" +\n \"shape only, and the redacted projection never carries it.\",\n },\n vendorInvoiceNumber: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"The vendor's own invoice number. Internal, redacted org-side like the \" +\n \"rest of the cost split.\",\n },\n ...ledgerAnnotationProperties,\n billId: {\n type: [\"string\", \"null\"],\n default: null,\n description:\n \"Backlink to the bill whose draft claimed this cost as a line. Written \" +\n \"when a draft bill adds the line, cleared on line removal, draft \" +\n \"delete, or bill void; a claimed cost leaves the uninvoiced pool, \" +\n \"making double-invoicing structurally impossible. Server-maintained at \" +\n \"the repository, never set by clients.\",\n },\n writtenOff: {\n type: \"boolean\",\n default: false,\n description:\n \"Server-maintained denormalization of billingReview (approvalState \" +\n \"pattern): true after a writtenOff entry until a reinstated entry \" +\n \"follows. A written-off cost leaves the uninvoiced pool. Never set by \" +\n \"clients.\",\n },\n billingReview: costBillingReview([\n \"writtenOff\",\n \"reinstated\",\n \"divergenceAcknowledged\",\n ]),\n} as const;\n"],"mappings":";AAYA,MAAM,kBAAkB;CACtB,QAAQ;EACN,MAAM;EACN,SAAS;EACT,aAAa;CACf;CACA,YAAY;EACV,MAAM;EACN,aAAa;CACf;CACA,YAAY;EACV,MAAM;EACN,aAAa;CACf;AACF;AAEA,MAAM,gBAAgB;CAAC;CAAU;CAAc;AAAY;AAE3D,MAAM,SAAS,iBACZ;CACC,MAAM;CACN,sBAAsB;CACtB,UAAU;CACV;CACA,YAAY;AACd;;;;;;AAOF,MAAa,iBAAiB,iBAC3B;CACC,MAAM,CAAC,UAAU,MAAM;CACvB,sBAAsB;CACtB,UAAU;CACV,SAAS;CACT;CACA,YAAY;AACd;;;;;;;AAQF,MAAa,qBACX,aAEC;CACC,MAAM;CACN,SAAS,CAAC;CACV,aACE;CAGF,OAAO;EACL,MAAM;EACN,sBAAsB;EACtB,UAAU;GAAC;GAAM;GAAU;EAAa;EACxC,YAAY;GACV,IAAI;IACF,MAAM;IACN,aAAa;GACf;GACA,QAAQ;IACN,MAAM;IACN,MAAM;GACR;GACA,aAAa;IACX,MAAM,CAAC,UAAU,MAAM;IACvB,SAAS;IACT,aACE;GAEJ;GACA,aAAa;IACX,MAAM;IACN,aAAa;GACf;GACA,MAAM;IACJ,MAAM,CAAC,UAAU,MAAM;IACvB,SAAS;IACT,aAAa;GACf;GACA,cAAc;IACZ,MAAM;IACN,SAAS;IACT,aACE;GAEJ;GACA,aAAa;IACX,MAAM;IACN,SAAS;IACT,aACE;GAOJ;EACF;CACF;AACF;;;;;;;AAQF,MAAa,6BAA6B;CACxC,MAAM;EACJ,MAAM,CAAC,UAAU,MAAM;EACvB,WAAW;EACX,SAAS;EACT,aACE;CAEJ;CACA,eAAe;EACb,MAAM,CAAC,UAAU,MAAM;EACvB,sBAAsB;EACtB,UAAU,CAAC,QAAQ;EACnB,SAAS;EACT,aACE;EAKF,YAAY,EACV,QAAQ;GACN,MAAM;GACN,SAAS;GACT,aAAa;EACf,EACF;CACF;AACF;AAEA,MAAa,oBAAoB;CAC/B;CACA;CACA;CACA;CACA;CACA;AACF;AAEA,MAAa,sBAAsB;CACjC,IAAI;EACF,MAAM;EACN,aAAa;CACf;CACA,aAAa;EACX,MAAM;EACN,aAAa;CACf;CACA,UAAU;EACR,MAAM;EACN,SAAS;EACT,aAAa;CACf;CACA,OAAO,MACL,sTAKF;CACA,UAAU,MAAM,8CAA8C;CAC9D,QAAQ,MACN,sEACF;CACA,QAAQ;EACN,MAAM;EACN,sBAAsB;EACtB,UAAU,CAAC,SAAS;EACpB,YAAY;GACV,SAAS;IACP,MAAM;IACN,aACE;GAOJ;GACA,QAAQ;IACN,MAAM;IACN,SAAS;IACT,aACE;GAGJ;EACF;CACF;CACA,UAAU;EACR,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAGJ;CACA,YAAY;EACV,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAGJ;CACA,gBAAgB;EACd,MAAM;EACN,OAAO,EAAE,MAAM,iBAAiB;EAChC,SAAS,CAAC;EACV,aACE;CAIJ;CACA,qBAAqB;EACnB,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAEJ;CACA,GAAG;CACH,QAAQ;EACN,MAAM,CAAC,UAAU,MAAM;EACvB,SAAS;EACT,aACE;CAKJ;CACA,YAAY;EACV,MAAM;EACN,SAAS;EACT,aACE;CAIJ;CACA,eAAe,kBAAkB;EAC/B;EACA;EACA;CACF,CAAC;AACH"}
|