@thegraphitelab/n8n-nodes-servicetitan 0.5.0 → 0.6.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 +103 -25
- package/dist/nodes/ServiceTitan/GenericFunctions.d.ts +23 -0
- package/dist/nodes/ServiceTitan/GenericFunctions.js +50 -0
- package/dist/nodes/ServiceTitan/GenericFunctions.js.map +1 -1
- package/dist/nodes/ServiceTitan/ServiceTitanTrigger.node.js +77 -36
- package/dist/nodes/ServiceTitan/ServiceTitanTrigger.node.js.map +1 -1
- package/dist/nodes/ServiceTitan/TglServiceTitan.node.d.ts +10 -1
- package/dist/nodes/ServiceTitan/TglServiceTitan.node.js +16 -12
- package/dist/nodes/ServiceTitan/TglServiceTitan.node.js.map +1 -1
- package/dist/nodes/ServiceTitan/resources/index.d.ts +18 -0
- package/dist/nodes/ServiceTitan/resources/index.js +28 -0
- package/dist/nodes/ServiceTitan/resources/index.js.map +1 -0
- package/dist/nodes/ServiceTitan/servicetitan.dark.svg +64 -3
- package/dist/nodes/ServiceTitan/servicetitan.svg +64 -3
- package/dist/nodes/ServiceTitan/triggerResources.d.ts +37 -0
- package/dist/nodes/ServiceTitan/triggerResources.js +39 -0
- package/dist/nodes/ServiceTitan/triggerResources.js.map +1 -0
- package/dist/nodes/ServiceTitan/types/common.d.ts +27 -0
- package/dist/nodes/ServiceTitan/types/common.js +9 -0
- package/dist/nodes/ServiceTitan/types/common.js.map +1 -0
- package/dist/nodes/ServiceTitan/types/customer.d.ts +15 -0
- package/dist/nodes/ServiceTitan/types/customer.js +3 -0
- package/dist/nodes/ServiceTitan/types/customer.js.map +1 -0
- package/dist/nodes/ServiceTitan/types/index.d.ts +3 -0
- package/dist/nodes/ServiceTitan/types/index.js +3 -0
- package/dist/nodes/ServiceTitan/types/index.js.map +1 -0
- package/dist/nodes/ServiceTitan/types/job.d.ts +21 -0
- package/dist/nodes/ServiceTitan/types/job.js +3 -0
- package/dist/nodes/ServiceTitan/types/job.js.map +1 -0
- package/dist/package.json +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,48 +1,126 @@
|
|
|
1
1
|
# @thegraphitelab/n8n-nodes-servicetitan
|
|
2
2
|
|
|
3
|
-
n8n custom node for ServiceTitan.
|
|
3
|
+
n8n custom node package for ServiceTitan. Built by The Graphite Lab, published publicly on npmjs.org under the `@thegraphitelab` scope. Primary consumer is TGL's Railway-hosted n8n fleet; the package is openly browsable.
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
**Current version: 0.6.0**
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
- **Credentials**: OAuth 2.0 client_credentials grant + ST-App-Key header, environment switch (Integration sandbox vs Production)
|
|
9
|
-
- **Customer**: Get by ID
|
|
7
|
+
## Installation
|
|
10
8
|
|
|
11
|
-
|
|
9
|
+
In each n8n instance, go to **Settings → Community Nodes → Install** and enter:
|
|
12
10
|
|
|
13
|
-
|
|
11
|
+
```
|
|
12
|
+
@thegraphitelab/n8n-nodes-servicetitan
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
Accept the disclaimer and install.
|
|
16
|
+
|
|
17
|
+
### Required env var
|
|
18
|
+
|
|
19
|
+
Set on the n8n service (both primary and worker if running queue mode):
|
|
20
|
+
|
|
21
|
+
```
|
|
22
|
+
TGL_SERVICETITAN_APP_KEY=<TGL ServiceTitan ST-App-Key>
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
This is the TGL-owned `ST-App-Key` from our ServiceTitan developer portal app — same across all TGL clients, sourced from env so the value never sits in client-visible credential fields. See the [repo root README](../../README.md#installing-in-n8n) for the broader rationale.
|
|
26
|
+
|
|
27
|
+
## What ships today
|
|
28
|
+
|
|
29
|
+
### Credential: ServiceTitan API
|
|
30
|
+
|
|
31
|
+
- OAuth 2.0 `client_credentials` grant
|
|
32
|
+
- `ST-App-Key` header sourced from `TGL_SERVICETITAN_APP_KEY`
|
|
33
|
+
- Environment switch: `Integration (Sandbox)` vs `Production`
|
|
34
|
+
- `preAuthentication` caches an `expirable` `accessToken` in the credential data (15min TTL)
|
|
35
|
+
- Test endpoint: `/settings/v2/tenant/{tenantId}/user-roles?page=1&pageSize=1`
|
|
36
|
+
|
|
37
|
+
UI fields (per-client, set when creating the credential in n8n):
|
|
14
38
|
|
|
15
|
-
Required UI fields (per-client, set when creating a credential in n8n):
|
|
16
39
|
- **Environment** — `Integration (Sandbox)` or `Production`
|
|
17
|
-
- **Tenant ID** —
|
|
40
|
+
- **Tenant ID** — from ServiceTitan → Settings → API Application Access
|
|
18
41
|
- **Client ID** — OAuth client ID, per-client
|
|
19
42
|
- **Client Secret** — OAuth client secret, per-client
|
|
20
43
|
|
|
21
|
-
|
|
22
|
-
|
|
44
|
+
### Action node: ServiceTitan
|
|
45
|
+
|
|
46
|
+
Picker label: **ServiceTitan**. Internal n8n name: `tglServiceTitan`.
|
|
47
|
+
|
|
48
|
+
Resource + Operation pattern.
|
|
49
|
+
|
|
50
|
+
| Resource | Operations |
|
|
51
|
+
|---|---|
|
|
52
|
+
| Customer | Get by ID |
|
|
53
|
+
|
|
54
|
+
The Customer.Get response includes both raw `customFields[]` and a flattened `customFieldsByName` sibling object (see Custom fields below).
|
|
55
|
+
|
|
56
|
+
### Trigger node: ServiceTitan Trigger
|
|
23
57
|
|
|
24
|
-
|
|
58
|
+
Picker label: **ServiceTitan Trigger**. Sits next to the action node in n8n's node picker when the user searches "ServiceTitan".
|
|
25
59
|
|
|
26
|
-
|
|
60
|
+
Two-level Resource + Event picker inside the node, matching the action node's pattern. Resource determines which Event options show.
|
|
27
61
|
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
62
|
+
| Resource | Events |
|
|
63
|
+
|---|---|
|
|
64
|
+
| Job | Created or Modified |
|
|
65
|
+
|
|
66
|
+
Polling-based with `modifiedOnOrAfter` cursor and a boundary-id dedup set to avoid duplicate emissions on overlap windows.
|
|
67
|
+
|
|
68
|
+
## Architecture
|
|
69
|
+
|
|
70
|
+
Resource-config table pattern. The trigger and action nodes share:
|
|
71
|
+
|
|
72
|
+
- `GenericFunctions.ts` — `serviceTitanApiRequest`, pagination helpers, customFields flattening
|
|
73
|
+
- `resources/<resource>/` — per-resource folder, one file per operation, declarative-style routing
|
|
74
|
+
- `triggerResources.ts` — resource-config table that drives the trigger's two-level Resource + Event picker
|
|
75
|
+
|
|
76
|
+
Adding a new resource or trigger event is a localized change — see [`CONTRIBUTING.md`](../../CONTRIBUTING.md) at the repo root.
|
|
77
|
+
|
|
78
|
+
## Custom fields behavior
|
|
79
|
+
|
|
80
|
+
ServiceTitan returns custom fields as an array of `{typeId, name, value}` objects. That shape is awkward to consume in downstream n8n nodes — every workflow has to write a JS-code step to find a field by name.
|
|
81
|
+
|
|
82
|
+
This package returns **both** shapes on every entity that has custom fields:
|
|
83
|
+
|
|
84
|
+
- `customFields` — the raw array, untouched, so anything that depends on the ServiceTitan shape still works
|
|
85
|
+
- `customFieldsByName` — sibling object, keys are field names, values are `{typeId, value}`
|
|
86
|
+
|
|
87
|
+
Downstream workflows can use `{{ $json.customFieldsByName["Field Name"].value }}` directly without a code step. A workflow that already does the manual flattening keeps working because `customFields` is unchanged.
|
|
88
|
+
|
|
89
|
+
## Roadmap
|
|
90
|
+
|
|
91
|
+
Phase 1 (current): refactored framework that scales, shipping the existing Customer.Get + Jobs trigger through it.
|
|
92
|
+
|
|
93
|
+
Phase 3: port the rest of TGL's ServiceTitan Zapier operations resource-by-resource. Reference source: [`/Users/jacobnolley/projects/advanced_servicetitan_zapier_app`](../../../advanced_servicetitan_zapier_app) (the live Zapier custom app).
|
|
94
|
+
|
|
95
|
+
Resources to port (non-exhaustive):
|
|
96
|
+
- Jobs (more operations beyond the trigger)
|
|
97
|
+
- Customers (full CRUD)
|
|
98
|
+
- Estimates
|
|
99
|
+
- Appointments
|
|
100
|
+
- Invoices
|
|
101
|
+
- Projects
|
|
102
|
+
- Payments
|
|
103
|
+
- Calls
|
|
104
|
+
- Leads
|
|
105
|
+
- Locations
|
|
106
|
+
- Technicians
|
|
107
|
+
- Vendors
|
|
108
|
+
- Employees
|
|
109
|
+
- Bookings
|
|
110
|
+
|
|
111
|
+
Each resource lands as a minor bump; each new operation on an existing resource is a patch.
|
|
32
112
|
|
|
33
113
|
## Local dev
|
|
34
114
|
|
|
35
115
|
```bash
|
|
116
|
+
# From this directory
|
|
36
117
|
pnpm dev
|
|
37
|
-
# Opens http://localhost:5678 with an embedded n8n and this node pre-loaded
|
|
38
118
|
```
|
|
39
119
|
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
Endpoints and operation catalog are ported from `The-Graphite-Lab/advanced_servicetitan_zapier_app`.
|
|
120
|
+
Boots embedded n8n at http://localhost:5678 with this package pre-loaded and hot reload. ServiceTitan sandbox credentials go in the local n8n credential store (`~/.n8n`).
|
|
43
121
|
|
|
44
|
-
##
|
|
122
|
+
## Reference
|
|
45
123
|
|
|
46
|
-
- [
|
|
47
|
-
-
|
|
48
|
-
-
|
|
124
|
+
- Repo root: [`../../README.md`](../../README.md)
|
|
125
|
+
- Recipes for adding resources, trigger events, new packages: [`../../CONTRIBUTING.md`](../../CONTRIBUTING.md)
|
|
126
|
+
- Source-of-truth Zapier app being ported from: `/Users/jacobnolley/projects/advanced_servicetitan_zapier_app`
|
|
@@ -5,3 +5,26 @@ import type { IDataObject, IExecuteFunctions, IHttpRequestMethods, ILoadOptionsF
|
|
|
5
5
|
* injection from TGL_SERVICETITAN_APP_KEY) runs on every call.
|
|
6
6
|
*/
|
|
7
7
|
export declare function serviceTitanApiRequest(this: IExecuteFunctions | IPollFunctions | ILoadOptionsFunctions, method: IHttpRequestMethods, path: string, qs?: IDataObject, body?: IDataObject | undefined): Promise<IDataObject>;
|
|
8
|
+
/**
|
|
9
|
+
* Paginates a ServiceTitan list endpoint and returns the flattened set of
|
|
10
|
+
* `data[]` rows across all pages.
|
|
11
|
+
*
|
|
12
|
+
* Mirrors the trigger's pagination contract:
|
|
13
|
+
* - 50-page safety cap (matches ServiceTitanTrigger)
|
|
14
|
+
* - relies on response.hasMore as the loop terminator
|
|
15
|
+
* - threads `page` through the query string; caller supplies the rest
|
|
16
|
+
*
|
|
17
|
+
* Caller is responsible for sort/filter qs. We do not enforce pageSize here
|
|
18
|
+
* because some ST endpoints have endpoint-specific caps.
|
|
19
|
+
*/
|
|
20
|
+
export declare function serviceTitanApiRequestAllItems(this: IExecuteFunctions | IPollFunctions | ILoadOptionsFunctions, method: IHttpRequestMethods, path: string, qs?: IDataObject, body?: IDataObject | undefined): Promise<IDataObject[]>;
|
|
21
|
+
/**
|
|
22
|
+
* Returns the same item with a sibling `customFieldsByName` object added,
|
|
23
|
+
* keyed by the customField's `name`, mapping to `{ typeId, value }`.
|
|
24
|
+
*
|
|
25
|
+
* Idempotent and non-destructive:
|
|
26
|
+
* - Original `customFields[]` array is left untouched
|
|
27
|
+
* - Missing or non-array `customFields` returns the input unchanged
|
|
28
|
+
* - Duplicate names: last write wins (ST doesn't normally emit duplicates)
|
|
29
|
+
*/
|
|
30
|
+
export declare function flattenCustomFields(item: IDataObject): IDataObject;
|
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.serviceTitanApiRequest = serviceTitanApiRequest;
|
|
4
|
+
exports.serviceTitanApiRequestAllItems = serviceTitanApiRequestAllItems;
|
|
5
|
+
exports.flattenCustomFields = flattenCustomFields;
|
|
4
6
|
const ServiceTitanApi_credentials_1 = require("../../credentials/ServiceTitanApi.credentials");
|
|
5
7
|
/**
|
|
6
8
|
* Shared ServiceTitan API request helper. Routes through n8n's auth helper so
|
|
@@ -25,4 +27,52 @@ async function serviceTitanApiRequest(method, path, qs = {}, body = undefined) {
|
|
|
25
27
|
options.body = body;
|
|
26
28
|
return (await this.helpers.httpRequestWithAuthentication.call(this, 'serviceTitanApi', options));
|
|
27
29
|
}
|
|
30
|
+
/**
|
|
31
|
+
* Paginates a ServiceTitan list endpoint and returns the flattened set of
|
|
32
|
+
* `data[]` rows across all pages.
|
|
33
|
+
*
|
|
34
|
+
* Mirrors the trigger's pagination contract:
|
|
35
|
+
* - 50-page safety cap (matches ServiceTitanTrigger)
|
|
36
|
+
* - relies on response.hasMore as the loop terminator
|
|
37
|
+
* - threads `page` through the query string; caller supplies the rest
|
|
38
|
+
*
|
|
39
|
+
* Caller is responsible for sort/filter qs. We do not enforce pageSize here
|
|
40
|
+
* because some ST endpoints have endpoint-specific caps.
|
|
41
|
+
*/
|
|
42
|
+
async function serviceTitanApiRequestAllItems(method, path, qs = {}, body = undefined) {
|
|
43
|
+
const collected = [];
|
|
44
|
+
let page = 1;
|
|
45
|
+
const maxPages = 50;
|
|
46
|
+
while (page <= maxPages) {
|
|
47
|
+
const response = (await serviceTitanApiRequest.call(this, method, path, { ...qs, page }, body));
|
|
48
|
+
if (Array.isArray(response.data)) {
|
|
49
|
+
collected.push(...response.data);
|
|
50
|
+
}
|
|
51
|
+
if (!response.hasMore)
|
|
52
|
+
break;
|
|
53
|
+
page += 1;
|
|
54
|
+
}
|
|
55
|
+
return collected;
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* Returns the same item with a sibling `customFieldsByName` object added,
|
|
59
|
+
* keyed by the customField's `name`, mapping to `{ typeId, value }`.
|
|
60
|
+
*
|
|
61
|
+
* Idempotent and non-destructive:
|
|
62
|
+
* - Original `customFields[]` array is left untouched
|
|
63
|
+
* - Missing or non-array `customFields` returns the input unchanged
|
|
64
|
+
* - Duplicate names: last write wins (ST doesn't normally emit duplicates)
|
|
65
|
+
*/
|
|
66
|
+
function flattenCustomFields(item) {
|
|
67
|
+
const customFields = item.customFields;
|
|
68
|
+
if (!Array.isArray(customFields))
|
|
69
|
+
return item;
|
|
70
|
+
const byName = {};
|
|
71
|
+
for (const raw of customFields) {
|
|
72
|
+
if (!raw || typeof raw.name !== 'string')
|
|
73
|
+
continue;
|
|
74
|
+
byName[raw.name] = { typeId: raw.typeId, value: raw.value };
|
|
75
|
+
}
|
|
76
|
+
return { ...item, customFieldsByName: byName };
|
|
77
|
+
}
|
|
28
78
|
//# sourceMappingURL=GenericFunctions.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"GenericFunctions.js","sourceRoot":"","sources":["../../../nodes/ServiceTitan/GenericFunctions.ts"],"names":[],"mappings":";;
|
|
1
|
+
{"version":3,"file":"GenericFunctions.js","sourceRoot":"","sources":["../../../nodes/ServiceTitan/GenericFunctions.ts"],"names":[],"mappings":";;AAiBA,wDA4BC;AAcD,wEAwBC;AAWD,kDAWC;AAhGD,+FAA2E;AAG3E;;;;GAIG;AACI,KAAK,UAAU,sBAAsB,CAE3C,MAA2B,EAC3B,IAAY,EACZ,KAAkB,EAAE,EACpB,OAAgC,SAAS;IAEzC,MAAM,WAAW,GAAG,MAAM,IAAI,CAAC,cAAc,CAAC,iBAAiB,CAAC,CAAC;IACjE,MAAM,WAAW,GAAI,WAAW,CAAC,WAAsB,IAAI,aAAa,CAAC;IACzE,MAAM,OAAO,GAAG,IAAA,wCAAU,EAAC,WAAW,CAAC,CAAC;IAExC,MAAM,OAAO,GAAwB;QACpC,MAAM;QACN,GAAG,EAAE,WAAW,OAAO,GAAG,IAAI,EAAE;QAChC,EAAE;QACF,OAAO,EAAE;YACR,MAAM,EAAE,kBAAkB;YAC1B,cAAc,EAAE,kBAAkB;SAClC;QACD,IAAI,EAAE,IAAI;KACV,CAAC;IACF,IAAI,IAAI,KAAK,SAAS;QAAE,OAAO,CAAC,IAAI,GAAG,IAAI,CAAC;IAE5C,OAAO,CAAC,MAAM,IAAI,CAAC,OAAO,CAAC,6BAA6B,CAAC,IAAI,CAC5D,IAAI,EACJ,iBAAiB,EACjB,OAAO,CACP,CAAgB,CAAC;AACnB,CAAC;AAED;;;;;;;;;;;GAWG;AACI,KAAK,UAAU,8BAA8B,CAEnD,MAA2B,EAC3B,IAAY,EACZ,KAAkB,EAAE,EACpB,OAAgC,SAAS;IAEzC,MAAM,SAAS,GAAkB,EAAE,CAAC;IACpC,IAAI,IAAI,GAAG,CAAC,CAAC;IACb,MAAM,QAAQ,GAAG,EAAE,CAAC;IAEpB,OAAO,IAAI,IAAI,QAAQ,EAAE,CAAC;QACzB,MAAM,QAAQ,GAAG,CAAC,MAAM,sBAAsB,CAAC,IAAI,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,EAAE,GAAG,EAAE,EAAE,IAAI,EAAE,EAAE,IAAI,CAAC,CAClE,CAAC;QAE7B,IAAI,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;YAClC,SAAS,CAAC,IAAI,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,CAAC;QAClC,CAAC;QAED,IAAI,CAAC,QAAQ,CAAC,OAAO;YAAE,MAAM;QAC7B,IAAI,IAAI,CAAC,CAAC;IACX,CAAC;IAED,OAAO,SAAS,CAAC;AAClB,CAAC;AAED;;;;;;;;GAQG;AACH,SAAgB,mBAAmB,CAAC,IAAiB;IACpD,MAAM,YAAY,GAAG,IAAI,CAAC,YAAY,CAAC;IACvC,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,YAAY,CAAC;QAAE,OAAO,IAAI,CAAC;IAE9C,MAAM,MAAM,GAAuD,EAAE,CAAC;IACtE,KAAK,MAAM,GAAG,IAAI,YAA+B,EAAE,CAAC;QACnD,IAAI,CAAC,GAAG,IAAI,OAAO,GAAG,CAAC,IAAI,KAAK,QAAQ;YAAE,SAAS;QACnD,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,CAAC,MAAM,EAAE,KAAK,EAAE,GAAG,CAAC,KAAK,EAAE,CAAC;IAC7D,CAAC;IAED,OAAO,EAAE,GAAG,IAAI,EAAE,kBAAkB,EAAE,MAAM,EAAE,CAAC;AAChD,CAAC"}
|
|
@@ -3,7 +3,34 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.ServiceTitanTrigger = void 0;
|
|
4
4
|
const n8n_workflow_1 = require("n8n-workflow");
|
|
5
5
|
const GenericFunctions_1 = require("./GenericFunctions");
|
|
6
|
+
const triggerResources_1 = require("./triggerResources");
|
|
6
7
|
const JOB_STATUSES = ['Scheduled', 'InProgress', 'Hold', 'Completed', 'Canceled'];
|
|
8
|
+
/**
|
|
9
|
+
* Resource dropdown options, derived from the TRIGGER_RESOURCES table.
|
|
10
|
+
*/
|
|
11
|
+
const resourceOptions = triggerResources_1.TRIGGER_RESOURCES.map((r) => ({
|
|
12
|
+
name: r.resourceLabel,
|
|
13
|
+
value: r.resource,
|
|
14
|
+
}));
|
|
15
|
+
/**
|
|
16
|
+
* Event property descriptors — one per resource, gated by displayOptions.show.resource.
|
|
17
|
+
* n8n renders the union of these as a single "Event" field whose option list swaps
|
|
18
|
+
* based on the selected Resource.
|
|
19
|
+
*/
|
|
20
|
+
const eventPropertyDefinitions = triggerResources_1.TRIGGER_RESOURCES.map((r) => ({
|
|
21
|
+
displayName: 'Event',
|
|
22
|
+
name: 'event',
|
|
23
|
+
type: 'options',
|
|
24
|
+
noDataExpression: true,
|
|
25
|
+
default: r.events[0]?.event ?? '',
|
|
26
|
+
displayOptions: { show: { resource: [r.resource] } },
|
|
27
|
+
options: r.events.map((e) => ({
|
|
28
|
+
name: e.label,
|
|
29
|
+
value: e.event,
|
|
30
|
+
description: e.description,
|
|
31
|
+
})),
|
|
32
|
+
description: 'ServiceTitan updates modifiedOn for any field change including internal status churn, so expect more fires than human-meaningful changes — filter downstream',
|
|
33
|
+
}));
|
|
7
34
|
class ServiceTitanTrigger {
|
|
8
35
|
description = {
|
|
9
36
|
displayName: 'ServiceTitan Trigger',
|
|
@@ -15,7 +42,7 @@ class ServiceTitanTrigger {
|
|
|
15
42
|
group: ['trigger'],
|
|
16
43
|
version: 1,
|
|
17
44
|
description: 'Starts the workflow when ServiceTitan records are created or modified',
|
|
18
|
-
subtitle: '={{$parameter.event}}',
|
|
45
|
+
subtitle: '={{$parameter.resource}}: {{$parameter.event}}',
|
|
19
46
|
defaults: {
|
|
20
47
|
name: 'ServiceTitan Trigger',
|
|
21
48
|
},
|
|
@@ -31,27 +58,23 @@ class ServiceTitanTrigger {
|
|
|
31
58
|
],
|
|
32
59
|
properties: [
|
|
33
60
|
{
|
|
34
|
-
displayName: '
|
|
35
|
-
name: '
|
|
61
|
+
displayName: 'Resource',
|
|
62
|
+
name: 'resource',
|
|
36
63
|
type: 'options',
|
|
37
64
|
noDataExpression: true,
|
|
38
|
-
default: '
|
|
39
|
-
options:
|
|
40
|
-
{
|
|
41
|
-
name: 'Job Created or Modified',
|
|
42
|
-
value: 'jobCreatedOrModified',
|
|
43
|
-
description: 'Fires for any job whose modifiedOn timestamp has advanced since the last poll',
|
|
44
|
-
},
|
|
45
|
-
],
|
|
46
|
-
description: 'ServiceTitan updates modifiedOn for any field change including internal status churn, so expect more fires than human-meaningful changes — filter downstream',
|
|
65
|
+
default: 'job',
|
|
66
|
+
options: resourceOptions,
|
|
47
67
|
},
|
|
68
|
+
...eventPropertyDefinitions,
|
|
48
69
|
{
|
|
70
|
+
// Job-specific filters. Gated on resource='job' so we can add other
|
|
71
|
+
// resources' filter collections side-by-side later.
|
|
49
72
|
displayName: 'Filters',
|
|
50
73
|
name: 'filters',
|
|
51
74
|
type: 'collection',
|
|
52
75
|
placeholder: 'Add Filter',
|
|
53
76
|
default: {},
|
|
54
|
-
displayOptions: { show: {
|
|
77
|
+
displayOptions: { show: { resource: ['job'] } },
|
|
55
78
|
options: [
|
|
56
79
|
{
|
|
57
80
|
displayName: 'Business Unit ID',
|
|
@@ -105,40 +128,56 @@ class ServiceTitanTrigger {
|
|
|
105
128
|
// First run: start the watermark at activation time so we don't drain ST history.
|
|
106
129
|
const since = staticData.lastTimeChecked ?? now;
|
|
107
130
|
const boundaryIds = new Set(staticData.boundaryIds ?? []);
|
|
131
|
+
const resource = this.getNodeParameter('resource', 0);
|
|
108
132
|
const event = this.getNodeParameter('event', 0);
|
|
109
|
-
|
|
133
|
+
const eventConfig = (0, triggerResources_1.findTriggerEvent)(resource, event);
|
|
134
|
+
if (!eventConfig) {
|
|
135
|
+
// Unrecognized resource/event pair — silently no-op rather than throw,
|
|
136
|
+
// matching the previous trigger's defensive shape.
|
|
110
137
|
return null;
|
|
111
138
|
}
|
|
112
|
-
const
|
|
139
|
+
const path = eventConfig.path.replace('{tenantId}', tenantId);
|
|
140
|
+
const timestampField = eventConfig.timestampField;
|
|
141
|
+
// Resource-specific filter handling. Job is the only one in Phase 1.
|
|
113
142
|
const baseQs = {
|
|
114
|
-
|
|
115
|
-
modifiedBefore: now,
|
|
116
|
-
sort: '+ModifiedOn',
|
|
143
|
+
sort: eventConfig.sortField,
|
|
117
144
|
pageSize: 100,
|
|
118
145
|
includeTotal: false,
|
|
119
|
-
active: filters.includeInactive ? 'Any' : 'True',
|
|
120
146
|
};
|
|
121
|
-
|
|
122
|
-
|
|
147
|
+
// ST's modifiedOnOrAfter / modifiedBefore convention is consistent across
|
|
148
|
+
// the jpm/crm/dispatch list endpoints for the `modifiedOn` cursor pattern.
|
|
149
|
+
// If future events need a different windowing field, add it to the config.
|
|
150
|
+
if (timestampField === 'modifiedOn') {
|
|
151
|
+
baseQs.modifiedOnOrAfter = since;
|
|
152
|
+
baseQs.modifiedBefore = now;
|
|
153
|
+
}
|
|
154
|
+
if (resource === 'job') {
|
|
155
|
+
const filters = this.getNodeParameter('filters', 0, {});
|
|
156
|
+
baseQs.active = filters.includeInactive ? 'Any' : 'True';
|
|
157
|
+
if (filters.jobStatus && filters.jobStatus.length > 0) {
|
|
158
|
+
baseQs.jobStatus = filters.jobStatus[0];
|
|
159
|
+
}
|
|
160
|
+
if (filters.businessUnitId)
|
|
161
|
+
baseQs.businessUnitId = filters.businessUnitId;
|
|
162
|
+
if (filters.jobTypeId)
|
|
163
|
+
baseQs.jobTypeId = filters.jobTypeId;
|
|
164
|
+
if (filters.customerId)
|
|
165
|
+
baseQs.customerId = filters.customerId;
|
|
123
166
|
}
|
|
124
|
-
if (filters.businessUnitId)
|
|
125
|
-
baseQs.businessUnitId = filters.businessUnitId;
|
|
126
|
-
if (filters.jobTypeId)
|
|
127
|
-
baseQs.jobTypeId = filters.jobTypeId;
|
|
128
|
-
if (filters.customerId)
|
|
129
|
-
baseQs.customerId = filters.customerId;
|
|
130
167
|
const collected = [];
|
|
131
168
|
let page = 1;
|
|
132
169
|
const maxPages = 50;
|
|
133
170
|
try {
|
|
134
171
|
while (page <= maxPages) {
|
|
135
|
-
const response = (await GenericFunctions_1.serviceTitanApiRequest.call(this, 'GET',
|
|
172
|
+
const response = (await GenericFunctions_1.serviceTitanApiRequest.call(this, 'GET', path, { ...baseQs, page }));
|
|
136
173
|
const rows = Array.isArray(response.data) ? response.data : [];
|
|
137
|
-
for (const
|
|
138
|
-
const id = Number(
|
|
174
|
+
for (const row of rows) {
|
|
175
|
+
const id = Number(row.id);
|
|
139
176
|
if (Number.isFinite(id) && boundaryIds.has(id))
|
|
140
177
|
continue;
|
|
141
|
-
|
|
178
|
+
// Decision: emit BOTH raw customFields[] AND a flattened
|
|
179
|
+
// customFieldsByName sibling.
|
|
180
|
+
collected.push((0, GenericFunctions_1.flattenCustomFields)(row));
|
|
142
181
|
}
|
|
143
182
|
if (!response.hasMore)
|
|
144
183
|
break;
|
|
@@ -159,12 +198,14 @@ class ServiceTitanTrigger {
|
|
|
159
198
|
}
|
|
160
199
|
// Advance cursor only on success.
|
|
161
200
|
staticData.lastTimeChecked = now;
|
|
162
|
-
// Boundary-id Set: ids of any returned
|
|
163
|
-
// cursor, so the next poll's inclusive
|
|
201
|
+
// Boundary-id Set: ids of any returned row whose timestampField equals
|
|
202
|
+
// the new cursor, so the next poll's inclusive lower-bound doesn't
|
|
203
|
+
// duplicate-fire.
|
|
164
204
|
const newBoundary = [];
|
|
165
|
-
for (const
|
|
166
|
-
|
|
167
|
-
|
|
205
|
+
for (const row of collected) {
|
|
206
|
+
const ts = row[timestampField];
|
|
207
|
+
if (typeof ts === 'string' && ts === now) {
|
|
208
|
+
const id = Number(row.id);
|
|
168
209
|
if (Number.isFinite(id))
|
|
169
210
|
newBoundary.push(id);
|
|
170
211
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ServiceTitanTrigger.node.js","sourceRoot":"","sources":["../../../nodes/ServiceTitan/ServiceTitanTrigger.node.ts"],"names":[],"mappings":";;;AAAA,+
|
|
1
|
+
{"version":3,"file":"ServiceTitanTrigger.node.js","sourceRoot":"","sources":["../../../nodes/ServiceTitan/ServiceTitanTrigger.node.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,4 +1,13 @@
|
|
|
1
1
|
import { type INodeType, type INodeTypeDescription } from 'n8n-workflow';
|
|
2
|
-
|
|
2
|
+
/**
|
|
3
|
+
* Action node for ServiceTitan.
|
|
4
|
+
*
|
|
5
|
+
* Filename note: this file MUST stay named `TglServiceTitan.node.ts` because
|
|
6
|
+
* n8n's `node-filename-against-convention` lint rule maps the filename to the
|
|
7
|
+
* `name` field. We keep `name: 'tglServiceTitan'` for collision safety against
|
|
8
|
+
* any future official n8n ServiceTitan node, so the file follows. The exported
|
|
9
|
+
* class is `ServiceTitan` — that's what consumers (and the n8n loader) see.
|
|
10
|
+
*/
|
|
11
|
+
export declare class ServiceTitan implements INodeType {
|
|
3
12
|
description: INodeTypeDescription;
|
|
4
13
|
}
|
|
@@ -1,9 +1,18 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.
|
|
3
|
+
exports.ServiceTitan = void 0;
|
|
4
4
|
const n8n_workflow_1 = require("n8n-workflow");
|
|
5
|
-
const
|
|
6
|
-
|
|
5
|
+
const resources_1 = require("./resources");
|
|
6
|
+
/**
|
|
7
|
+
* Action node for ServiceTitan.
|
|
8
|
+
*
|
|
9
|
+
* Filename note: this file MUST stay named `TglServiceTitan.node.ts` because
|
|
10
|
+
* n8n's `node-filename-against-convention` lint rule maps the filename to the
|
|
11
|
+
* `name` field. We keep `name: 'tglServiceTitan'` for collision safety against
|
|
12
|
+
* any future official n8n ServiceTitan node, so the file follows. The exported
|
|
13
|
+
* class is `ServiceTitan` — that's what consumers (and the n8n loader) see.
|
|
14
|
+
*/
|
|
15
|
+
class ServiceTitan {
|
|
7
16
|
description = {
|
|
8
17
|
displayName: 'ServiceTitan',
|
|
9
18
|
name: 'tglServiceTitan',
|
|
@@ -40,18 +49,13 @@ class TglServiceTitan {
|
|
|
40
49
|
name: 'resource',
|
|
41
50
|
type: 'options',
|
|
42
51
|
noDataExpression: true,
|
|
43
|
-
options:
|
|
44
|
-
{
|
|
45
|
-
name: 'Customer',
|
|
46
|
-
value: 'customer',
|
|
47
|
-
},
|
|
48
|
-
],
|
|
52
|
+
options: resources_1.resourceSelectOptions,
|
|
49
53
|
default: 'customer',
|
|
50
54
|
},
|
|
51
|
-
...
|
|
52
|
-
...
|
|
55
|
+
...resources_1.allResources.flatMap((r) => r.resourceOperations),
|
|
56
|
+
...resources_1.allResources.flatMap((r) => r.resourceFields),
|
|
53
57
|
],
|
|
54
58
|
};
|
|
55
59
|
}
|
|
56
|
-
exports.
|
|
60
|
+
exports.ServiceTitan = ServiceTitan;
|
|
57
61
|
//# sourceMappingURL=TglServiceTitan.node.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TglServiceTitan.node.js","sourceRoot":"","sources":["../../../nodes/ServiceTitan/TglServiceTitan.node.ts"],"names":[],"mappings":";;;AAAA,+CAIsB;AAEtB,
|
|
1
|
+
{"version":3,"file":"TglServiceTitan.node.js","sourceRoot":"","sources":["../../../nodes/ServiceTitan/TglServiceTitan.node.ts"],"names":[],"mappings":";;;AAAA,+CAIsB;AAEtB,2CAAkE;AAElE;;;;;;;;GAQG;AACH,MAAa,YAAY;IACxB,WAAW,GAAyB;QACnC,WAAW,EAAE,cAAc;QAC3B,IAAI,EAAE,iBAAiB;QACvB,IAAI,EAAE;YACL,KAAK,EAAE,uBAAuB;YAC9B,IAAI,EAAE,4BAA4B;SAClC;QACD,KAAK,EAAE,CAAC,WAAW,CAAC;QACpB,OAAO,EAAE,CAAC;QACV,QAAQ,EAAE,oDAAoD;QAC9D,WAAW,EAAE,oCAAoC;QACjD,QAAQ,EAAE;YACT,IAAI,EAAE,cAAc;SACpB;QACD,YAAY,EAAE,IAAI;QAClB,MAAM,EAAE,CAAC,kCAAmB,CAAC,IAAI,CAAC;QAClC,OAAO,EAAE,CAAC,kCAAmB,CAAC,IAAI,CAAC;QACnC,WAAW,EAAE;YACZ;gBACC,IAAI,EAAE,iBAAiB;gBACvB,QAAQ,EAAE,IAAI;aACd;SACD;QACD,eAAe,EAAE;YAChB,OAAO,EACN,oHAAoH;YACrH,OAAO,EAAE;gBACR,cAAc,EAAE,kBAAkB;gBAClC,MAAM,EAAE,kBAAkB;aAC1B;SACD;QACD,UAAU,EAAE;YACX;gBACC,WAAW,EAAE,UAAU;gBACvB,IAAI,EAAE,UAAU;gBAChB,IAAI,EAAE,SAAS;gBACf,gBAAgB,EAAE,IAAI;gBACtB,OAAO,EAAE,iCAAqB;gBAC9B,OAAO,EAAE,UAAU;aACnB;YACD,GAAG,wBAAY,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,kBAAkB,CAAC;YACpD,GAAG,wBAAY,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,cAAc,CAAC;SAChD;KACD,CAAC;CACF;AA7CD,oCA6CC"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { INodeProperties, INodePropertyOptions } from 'n8n-workflow';
|
|
2
|
+
/**
|
|
3
|
+
* Aggregator for action-node resources.
|
|
4
|
+
*
|
|
5
|
+
* Adding a new resource means:
|
|
6
|
+
* 1. Create resources/<name>/ with `<name>Operations` + `<name>Fields` exports
|
|
7
|
+
* 2. Add an entry to `allResources` below
|
|
8
|
+
* 3. Add a corresponding option to `resourceSelectOptions`
|
|
9
|
+
*
|
|
10
|
+
* The action node (TglServiceTitan.node.ts) spreads these directly into its
|
|
11
|
+
* `properties[]` and never has to be touched again for a new resource.
|
|
12
|
+
*/
|
|
13
|
+
export declare const resourceSelectOptions: INodePropertyOptions[];
|
|
14
|
+
export interface ResourceBundle {
|
|
15
|
+
resourceOperations: INodeProperties[];
|
|
16
|
+
resourceFields: INodeProperties[];
|
|
17
|
+
}
|
|
18
|
+
export declare const allResources: ResourceBundle[];
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.allResources = exports.resourceSelectOptions = void 0;
|
|
4
|
+
const customer_1 = require("./customer");
|
|
5
|
+
/**
|
|
6
|
+
* Aggregator for action-node resources.
|
|
7
|
+
*
|
|
8
|
+
* Adding a new resource means:
|
|
9
|
+
* 1. Create resources/<name>/ with `<name>Operations` + `<name>Fields` exports
|
|
10
|
+
* 2. Add an entry to `allResources` below
|
|
11
|
+
* 3. Add a corresponding option to `resourceSelectOptions`
|
|
12
|
+
*
|
|
13
|
+
* The action node (TglServiceTitan.node.ts) spreads these directly into its
|
|
14
|
+
* `properties[]` and never has to be touched again for a new resource.
|
|
15
|
+
*/
|
|
16
|
+
exports.resourceSelectOptions = [
|
|
17
|
+
{
|
|
18
|
+
name: 'Customer',
|
|
19
|
+
value: 'customer',
|
|
20
|
+
},
|
|
21
|
+
];
|
|
22
|
+
exports.allResources = [
|
|
23
|
+
{
|
|
24
|
+
resourceOperations: customer_1.customerOperations,
|
|
25
|
+
resourceFields: customer_1.customerFields,
|
|
26
|
+
},
|
|
27
|
+
];
|
|
28
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../nodes/ServiceTitan/resources/index.ts"],"names":[],"mappings":";;;AAEA,yCAAgE;AAEhE;;;;;;;;;;GAUG;AAEU,QAAA,qBAAqB,GAA2B;IAC5D;QACC,IAAI,EAAE,UAAU;QAChB,KAAK,EAAE,UAAU;KACjB;CACD,CAAC;AAOW,QAAA,YAAY,GAAqB;IAC7C;QACC,kBAAkB,EAAE,6BAAkB;QACtC,cAAc,EAAE,yBAAc;KAC9B;CACD,CAAC"}
|
|
@@ -1,4 +1,65 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
1
|
+
<?xml version="1.0" encoding="utf-8"?>
|
|
2
|
+
<!-- ServiceTitan wordmark (dark-theme variant — white fill). Same paths as the light variant. -->
|
|
3
|
+
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="-131 222 585 106">
|
|
4
|
+
<path fill="#FFFFFF" d="M41.8,264.1c-2.7-2.3-6.2-3.9-10.1-3.9c-2.7,0-6.2,1.6-6.2,4.7c0,3.5,3.9,4.7,6.6,5.5l3.9,1.2c8.2,2.3,14.4,6.2,14.4,15.6
|
|
5
|
+
c0,5.8-1.6,11.7-5.8,15.6c-4.7,3.9-10.5,5.5-16.4,5.5c-7.4,0-14.4-2.3-20.3-6.6l6.2-12.1c3.9,3.1,8.2,5.8,13.2,5.8
|
|
6
|
+
c3.5,0,7.4-1.9,7.4-5.8c0-4.3-5.8-5.8-9-6.6c-9.4-2.7-15.6-5.1-15.6-16.4c0-11.7,8.2-19.5,19.9-19.5c5.8,0,12.9,1.9,17.9,4.7
|
|
7
|
+
L41.8,264.1z M83.5,281.7c-0.8-3.9-4.3-6.2-7.8-6.2c-3.9,0-7.4,2.3-8.2,6.2H83.5z M96.4,289.5H67.1c0,5.8,3.1,9,8.6,9
|
|
8
|
+
c3.1,0,5.1-0.8,6.6-3.5h13.2c-2.3,9.7-10.9,13.6-19.9,13.6c-12.9,0-22.6-7.4-22.6-21c0-13.2,9-21,21.8-21c13.6,0,21.4,8.6,21.4,21.8
|
|
9
|
+
V289.5z M113.5,275.8c3.1-5.8,7.4-7.4,12.9-7.4h2.7v13.2c-2.3-1.2-3.9-1.2-5.8-1.2c-7.8,0-9.7,5.1-9.7,11.7v16H99.9v-39.4h13.6
|
|
10
|
+
V275.8z M151.7,288.7l9.4-19.9h15.6l-20.7,39h-9l-20.3-39h15.6L151.7,288.7z M192.2,307.8h-14.4v-39.4h14.4V307.8z M193,255.2
|
|
11
|
+
c0,4.3-3.5,7.8-7.8,7.8c-4.3,0-7.8-3.5-7.8-7.8c0-4.3,3.5-7.8,7.8-7.8C189.5,247.4,193,250.9,193,255.2z M227.7,280.5
|
|
12
|
+
c-2.3-1.6-4.7-2.7-7.4-2.7c-5.5,0-9.7,4.3-9.7,9.7c0,5.8,4.3,9.7,9.7,9.7c2.3,0,4.7-1.2,7-2.7v11.7c-3.5,1.6-6.6,2.3-9.7,2.3
|
|
13
|
+
c-11.7,0-21.4-8.6-21.4-20.6c0-12.5,9.7-21.4,22.2-21.4c3.1,0,6.6,0.8,9.4,2.3V280.5z M261.6,281.7c-0.8-3.9-4.3-6.2-7.8-6.2
|
|
14
|
+
c-3.9,0-7.4,2.3-8.2,6.2H261.6z M274.4,289.5h-29.2c0,5.8,3.1,9,8.6,9c3.1,0,5.1-0.8,6.6-3.5h13.2c-2.3,9.7-10.9,13.6-19.9,13.6
|
|
15
|
+
c-12.9,0-22.6-7.4-22.6-21c0-13.2,9-21,21.8-21c13.6,0,21.4,8.6,21.4,21.8V289.5z M302.1,307.8h-14.4V263h-12.9v-12.5h39.7V263
|
|
16
|
+
h-12.5V307.8z M331.7,307.8h-14v-39.4h14V307.8z M332.5,255.2c0,4.3-3.5,7.8-7.8,7.8s-7.8-3.5-7.8-7.8c0-4.3,3.5-7.8,7.8-7.8
|
|
17
|
+
S332.5,250.9,332.5,255.2z M354.3,307.8h-14v-27.7H336v-11.3h4.3v-12.1h14v12.1h7.8v11.3h-7.8V307.8z M376.1,288.3c0,5.1,3.1,9,9,9
|
|
18
|
+
c5.8,0,9-3.9,9-9c0-4.7-3.1-9-9-9C379.6,279.3,376.1,283.6,376.1,288.3z M407.7,307.8h-14v-4.3c-2.3,3.9-7.4,5.8-11.7,5.8
|
|
19
|
+
c-11.7,0-19.9-9.7-19.9-21s8.2-21,19.5-21c4.7,0,9,1.6,12.1,5.1v-3.9h14V307.8z M426,273.9c3.5-4.7,7.4-6.2,12.9-6.2
|
|
20
|
+
c10.5,0,14.8,6.6,14.8,16.4v24.2h-14v-19.1c0-3.9,0.8-10.1-6.2-10.1c-5.8,0-7.4,4.3-7.4,9v20.3h-14v-39.4h14V273.9z M460.7,266.5
|
|
21
|
+
v1.6h1.2c0.8,0,2.3,0,2.3-0.8c0-0.8-0.8-0.8-1.6-0.8H460.7z M464.9,272.3h-1.2l-1.6-3.1h-1.6v3.1h-0.8v-7h2.7c1.2,0,2.3,0.4,2.3,1.9
|
|
22
|
+
c0,1.2-0.8,1.9-1.9,1.9L464.9,272.3z M457.2,268.8c0,2.7,2.3,5.1,5.1,5.1c2.7,0,5.1-2.3,5.1-5.1c0-2.7-2.3-5.1-5.1-5.1
|
|
23
|
+
C459.5,263.8,457.2,265.7,457.2,268.8z M456,268.8c0-3.5,2.7-6.2,6.2-6.2c3.5,0,6.2,2.7,6.2,6.2c0,3.5-2.7,6.2-6.2,6.2
|
|
24
|
+
C458.7,274.7,456,271.9,456,268.8z M-121.8,317.1c0,0,5.8,2.3,5.8,4.7c0,0-0.4,1.9-2.3,1.9c-1.9,0-4.7-3.1-4.7-4.7
|
|
25
|
+
S-121.8,317.1-121.8,317.1z M-128,287.9C-128.4,287.9-128.4,287.5-128,287.9c-0.4-0.4-0.4-0.4-0.4-0.4c-1.2,0.4-3.1,1.9-3.1,4.7
|
|
26
|
+
c0,10.5,28.4,11.7,44,30.8c1.6,1.9,4.3,3.1,7,3.1c3.5,0,7-0.4,10.1-0.8c0.4,0,0.8-0.4,0.8-0.8c0-0.4,0-0.8,0-1.2
|
|
27
|
+
C-88.7,297.3-124.9,303.5-128,287.9z M-87.1,254.8c-1.9-1.9-7-0.4-9.7,1.9c-2.7,2.3-1.6,3.9-1.6,3.9c2.3-3.1,5.8-4.7,8.2-5.1
|
|
28
|
+
C-88.3,255.6-87.1,254.8-87.1,254.8z M-28.7,260.2c0,0-3.9,0.8-7.4-3.1c0,0,1.6,0,1.9-1.9C-34.5,255.2-32.2,259.5-28.7,260.2z
|
|
29
|
+
M-29.9,278.2c0,0-0.8,4.3-5.8,4.3c-5.5,0-10.1-7.4-11.7-24.9c1.2,1.9,2.7,3.9,3.5,6.2c0-2.3,1.2-6.6-4.3-10.5
|
|
30
|
+
c0,0,14.4,3.1,14.8,17.9c0,2.7-1.6,5.1-2.3,6.2c0,0-0.8,0.4-0.4,1.6c0.4,0.8,1.6,0.8,2.7-0.4S-29.9,275.8-29.9,278.2z M-50.1,286.3
|
|
31
|
+
c0,0-3.9,7.4-9.4,7.4c-2.3,0-3.9-1.6-3.9-3.5s2.7-9.7,14-9.7c2.7,0,4.7,0.4,4.7,2.3C-44.3,284-47,286.7-50.1,286.3z M-50.1,249.3
|
|
32
|
+
c0,0-1.6-0.4-1.2-2.7c0.4-0.8,0.4-0.8,0.4-1.9c0-1.2,0.4-2.3,1.2-2.7c0,0,1.6,0,1.6,4.3C-48.2,248.2-50.1,249.3-50.1,249.3z
|
|
33
|
+
M-55.2,249.3c-2.3-0.4-0.8-3.9-2.3-3.9c-0.8,0-0.8,3.9-1.6,3.5c-1.6-1.2-0.4-3.9-0.4-5.1c0-1.2,0.8-2.7-0.4-1.9
|
|
34
|
+
c-1.2,0.8-1.9,2.7-2.3,4.3c-0.4,1.6,0.4,2.3,1.2,4.3c0.8,1.9-0.4,1.2-0.4,1.2c-5.8-3.5-1.6-11.3-1.6-11.3c2.7-4.3,6.6-3.1,6.6-3.1
|
|
35
|
+
c0.8,0.4,0.8,0.8,0.8,1.6c0,0.8,0.4,1.2,1.2,1.6c1.2,0.4,1.6,1.6,1.6,3.9C-52.8,247-54.4,249.7-55.2,249.3z M-46.2,248.9l9.7,3.1
|
|
36
|
+
c0,0,1.9,3.5-1.9,2.3c-3.5-1.2-7-1.9-7-1.9S-47,251.3-46.2,248.9z M-94.1,263.7c-7,1.2-9.4-0.8-9.4-2.7c0-5.5,16-9.7,20.3-9.7
|
|
37
|
+
c0.8,1.2-0.8,1.2-1.2,3.1c-0.8,1.9-2.3,2.7-4.7,3.1c-2.3,0.4-4.7,1.6-6.2,2.7c-1.6,1.2,0,1.9,2.7,1.2c2.7-0.8,3.1,0.4,4.3,0
|
|
38
|
+
c1.2-0.4,0-1.9,0.8-1.9c0.8-0.4,2.3,0.8,2.3,0.8l3.9,2.7l-4.7,2.3c-0.4,0-0.8,0.4-0.8,1.2c0,0.8,2.3,0.8,3.5,0.8
|
|
39
|
+
c0.8,0,1.2,1.6,1.2,1.6c-1.2,1.6-4.7,1.6-4.7,1.6c0.8,1.6,5.1,1.2,5.8,1.6c0.8,0,0.8,1.2,1.6,3.1c0.4,1.9,3.1,2.7,3.1,2.7
|
|
40
|
+
c0.8,3.1-2.7,3.9-5.1,3.9C-95.7,280.9-94.1,263.7-94.1,263.7z M-92.6,241.9C-93,241.9-93,241.9-92.6,241.9
|
|
41
|
+
c-1.2-5.8,1.2-12.5,1.2-12.5s-5.8,4.7-5.5,12.5c-5.1,0-12.5,0.4-16.8,4.3c-6.2,5.1-7,14.8-7.4,17.5c0,0,0,0.4-0.4,0.4h-0.4
|
|
42
|
+
c-1.6-0.8-4.7-3.9-2.3-10.5c3.1-8.6,12.5-25.7,30.8-26.9c0,0,5.8-0.4,9.4,1.9c0,0,0.4,0,0.4,0.4v0.4c-1.6,1.2-6.6,5.8-8.2,12.9
|
|
43
|
+
c0,0.4-0.4,0.4-0.4,0.4C-92.2,241.9-92.6,241.9-92.6,241.9z M-78.9,264.9c0,0,1.6,7.4,5.1,10.1c0,0,0,0.8-1.2,0.8
|
|
44
|
+
c-1.2,0-3.1-1.6-3.9-5.8C-79.7,266.1-78.9,264.9-78.9,264.9z M-73.9,246.2c-4.3,0-6.2-3.9-6.2-3.9s5.1,4.7,12.1,0.8
|
|
45
|
+
C-68,243.5-69.6,246.2-73.9,246.2z M-20.1,252.5c-1.2-2.3-2.7-3.9-6.2-4.7c-3.1-0.8-5.8-0.4-7.8,1.2l-6.2-2.3
|
|
46
|
+
c-0.8-1.6-1.2-3.1-1.9-4.3c-0.4-1.2-1.2-1.9-1.9-2.3c-4.3-2.3-15.6-8.2-19.9-2.3c0,0-0.4,0.4-0.4,0.8l-1.6-0.4
|
|
47
|
+
c-0.8-2.3-3.1-4.3-6.2-5.1c-1.9-0.4-3.9-0.4-5.5,0.4c-1.2,0.4-1.2,1.9,0,2.3l5.1,1.9c1.2,0.4,1.9,1.6,1.2,2.7
|
|
48
|
+
c-0.4,1.2-1.6,1.9-2.7,1.2c0,0-3.1-0.8-5.5-1.6c-1.2-0.4-2.3,0.8-1.9,1.9c0.8,2.3,3.1,4.7,6.2,5.5c2.7,0.8,5.5,0,7.4-1.2l1.2,0.4
|
|
49
|
+
c0,2.7,2.3,6.2,4.3,7.4c3.1,1.9,5.8,0.4,9-1.6c0,0,8.2,6.2,4.3,24.5c-10.1,1.2-14,4.7-17.5,8.6c-2.3-0.8-9.4-1.6-13.2-0.4
|
|
50
|
+
c1.2-1.2,2.7-2.3,5.1-3.1c1.2-0.4,1.6-1.2,1.6-2.3c0,0,4.7-1.6,4.7-3.1c0-1.6-5.8-1.6-8.2-14c-0.4-1.6-0.8-2.7-3.1-3.5
|
|
51
|
+
c0,0-0.8-1.2,0.4-2.7c1.2-1.6,1.6-1.9,1.2-3.1c-0.4-1.2-1.9-1.9-1.9-1.9v-1.9c0,0-4.7-3.5-4.7-8.6c0-5.1,6.6-10.9,8.2-12.5v-0.4
|
|
52
|
+
c0,0,0-0.4-0.4-0.4c-2.3-1.6-6.6-3.9-13.6-3.9c-27.3,0-33.5,24.5-39.4,36.2c0,0.4,0,0.4,0,0.8c5.8,11.7,15.2,10.5,16,20.6
|
|
53
|
+
c0.4,7.8-1.6,7.8-3.1,7.8c-1.2,0-3.1-1.2-3.9-1.9h-0.4c0,0-0.4,0.4,0,0.4c0.8,1.9,2.7,6.6,9,6.6c3.1,0,3.9-2.7,3.9-5.5v-9
|
|
54
|
+
c0-0.8-0.4-1.6-0.8-2.3c-1.9-1.9-6.6-6.2-6.6-9.7c0-1.6,1.2-2.3,2.3-2.3c2.3,0,4.7,3.5,6.6,8.2c0.4,1.2,1.2,1.9,1.6,2.3h0.4
|
|
55
|
+
c0,0,0,0,0-0.4c-0.8-2.7-0.8-5.5-1.2-6.6c0-0.4-0.4-1.2-0.8-1.6c-1.9-1.6-6.6-6.2-6.6-13.2c0-9.4,15.2-8.6,18.3-8.6
|
|
56
|
+
c0.8,3.1,2.7,4.7,3.9,5.1c-4.7,1.6-14.8,5.1-14.8,10.9c0,6.2,10.5,5.8,10.5,5.8s-1.6,12.5,10.1,16.4c0,0-1.9,1.9-8.2,1.9
|
|
57
|
+
c-5.8,0-8.6-2.7-10.1-5.8c0,0,0-0.4-0.4-0.4c0,0-0.4,0-0.4,0.4c-0.4,0.8-0.4,2.3,0.4,3.9c1.6,2.7,3.9,4.3,3.9,7.8
|
|
58
|
+
c0,2.7-2.3,4.3-3.5,4.7c2.3,0.4,12.9,3.1,19.9,6.6c0.8-0.4,7-4.3,7.4-9.7c0,0,0.4-3.5-4.7-3.9c0,0,2.3-0.8,6.2-0.8
|
|
59
|
+
c3.9,0,8.2,3.1,0.4,19.5c0,0,0,0,0,0.4c1.2,0.8,10.1,6.6,16,12.1h0.4c0,0,0.4,0,0.4-0.4c0.8-0.8,2.3-3.5,3.1-10.1
|
|
60
|
+
c0-0.8,0.4-1.2,1.2-1.2c3.5-1.2,15.2-4.7,20.3-11.7c5.8-8.2,8.2-9.4,8.2-9.4s3.9-2.3,2.3-8.2c-0.8-3.1-5.5-10.9-10.1-19.1
|
|
61
|
+
c1.2,0.8,2.3,1.2,3.5,1.6c2.7,0.8,5.5,0.4,7.4-0.8c0.4-0.4,0.8-0.8,0.8-1.2c0-0.4-0.4-0.8-0.8-1.2l-5.1-1.9
|
|
62
|
+
c-1.2-0.4-1.9-1.9-1.6-3.1c0.4-1.2,1.9-1.9,3.1-1.6l4.7,1.6c0.4,0,0.8,0,1.2-0.4C-19.7,252.8-20.1,253.2-20.1,252.5z M-89.1,267.2
|
|
63
|
+
c0,0-1.9,0.4-1.6,3.5c0.4,2.7,2.7,2.7,2.7,2.7C-89.9,271.1-89.1,267.2-89.1,267.2z M-123,305.8c7,3.9,22.6,8.6,25.7,16.8
|
|
64
|
+
c0,0,1.2,1.9-5.1,1.9c-4.7,0-5.8-1.2-9-5.1c-4.7-5.5-14.4-9-14.4-13.2C-126.1,306.6-125.7,304.3-123,305.8z"/>
|
|
4
65
|
</svg>
|
|
@@ -1,4 +1,65 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
1
|
+
<?xml version="1.0" encoding="utf-8"?>
|
|
2
|
+
<!-- ServiceTitan wordmark — official mark, sourced from Wikimedia Commons (public domain: consists only of simple geometric shapes and text). -->
|
|
3
|
+
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="-131 222 585 106">
|
|
4
|
+
<path fill="#000000" d="M41.8,264.1c-2.7-2.3-6.2-3.9-10.1-3.9c-2.7,0-6.2,1.6-6.2,4.7c0,3.5,3.9,4.7,6.6,5.5l3.9,1.2c8.2,2.3,14.4,6.2,14.4,15.6
|
|
5
|
+
c0,5.8-1.6,11.7-5.8,15.6c-4.7,3.9-10.5,5.5-16.4,5.5c-7.4,0-14.4-2.3-20.3-6.6l6.2-12.1c3.9,3.1,8.2,5.8,13.2,5.8
|
|
6
|
+
c3.5,0,7.4-1.9,7.4-5.8c0-4.3-5.8-5.8-9-6.6c-9.4-2.7-15.6-5.1-15.6-16.4c0-11.7,8.2-19.5,19.9-19.5c5.8,0,12.9,1.9,17.9,4.7
|
|
7
|
+
L41.8,264.1z M83.5,281.7c-0.8-3.9-4.3-6.2-7.8-6.2c-3.9,0-7.4,2.3-8.2,6.2H83.5z M96.4,289.5H67.1c0,5.8,3.1,9,8.6,9
|
|
8
|
+
c3.1,0,5.1-0.8,6.6-3.5h13.2c-2.3,9.7-10.9,13.6-19.9,13.6c-12.9,0-22.6-7.4-22.6-21c0-13.2,9-21,21.8-21c13.6,0,21.4,8.6,21.4,21.8
|
|
9
|
+
V289.5z M113.5,275.8c3.1-5.8,7.4-7.4,12.9-7.4h2.7v13.2c-2.3-1.2-3.9-1.2-5.8-1.2c-7.8,0-9.7,5.1-9.7,11.7v16H99.9v-39.4h13.6
|
|
10
|
+
V275.8z M151.7,288.7l9.4-19.9h15.6l-20.7,39h-9l-20.3-39h15.6L151.7,288.7z M192.2,307.8h-14.4v-39.4h14.4V307.8z M193,255.2
|
|
11
|
+
c0,4.3-3.5,7.8-7.8,7.8c-4.3,0-7.8-3.5-7.8-7.8c0-4.3,3.5-7.8,7.8-7.8C189.5,247.4,193,250.9,193,255.2z M227.7,280.5
|
|
12
|
+
c-2.3-1.6-4.7-2.7-7.4-2.7c-5.5,0-9.7,4.3-9.7,9.7c0,5.8,4.3,9.7,9.7,9.7c2.3,0,4.7-1.2,7-2.7v11.7c-3.5,1.6-6.6,2.3-9.7,2.3
|
|
13
|
+
c-11.7,0-21.4-8.6-21.4-20.6c0-12.5,9.7-21.4,22.2-21.4c3.1,0,6.6,0.8,9.4,2.3V280.5z M261.6,281.7c-0.8-3.9-4.3-6.2-7.8-6.2
|
|
14
|
+
c-3.9,0-7.4,2.3-8.2,6.2H261.6z M274.4,289.5h-29.2c0,5.8,3.1,9,8.6,9c3.1,0,5.1-0.8,6.6-3.5h13.2c-2.3,9.7-10.9,13.6-19.9,13.6
|
|
15
|
+
c-12.9,0-22.6-7.4-22.6-21c0-13.2,9-21,21.8-21c13.6,0,21.4,8.6,21.4,21.8V289.5z M302.1,307.8h-14.4V263h-12.9v-12.5h39.7V263
|
|
16
|
+
h-12.5V307.8z M331.7,307.8h-14v-39.4h14V307.8z M332.5,255.2c0,4.3-3.5,7.8-7.8,7.8s-7.8-3.5-7.8-7.8c0-4.3,3.5-7.8,7.8-7.8
|
|
17
|
+
S332.5,250.9,332.5,255.2z M354.3,307.8h-14v-27.7H336v-11.3h4.3v-12.1h14v12.1h7.8v11.3h-7.8V307.8z M376.1,288.3c0,5.1,3.1,9,9,9
|
|
18
|
+
c5.8,0,9-3.9,9-9c0-4.7-3.1-9-9-9C379.6,279.3,376.1,283.6,376.1,288.3z M407.7,307.8h-14v-4.3c-2.3,3.9-7.4,5.8-11.7,5.8
|
|
19
|
+
c-11.7,0-19.9-9.7-19.9-21s8.2-21,19.5-21c4.7,0,9,1.6,12.1,5.1v-3.9h14V307.8z M426,273.9c3.5-4.7,7.4-6.2,12.9-6.2
|
|
20
|
+
c10.5,0,14.8,6.6,14.8,16.4v24.2h-14v-19.1c0-3.9,0.8-10.1-6.2-10.1c-5.8,0-7.4,4.3-7.4,9v20.3h-14v-39.4h14V273.9z M460.7,266.5
|
|
21
|
+
v1.6h1.2c0.8,0,2.3,0,2.3-0.8c0-0.8-0.8-0.8-1.6-0.8H460.7z M464.9,272.3h-1.2l-1.6-3.1h-1.6v3.1h-0.8v-7h2.7c1.2,0,2.3,0.4,2.3,1.9
|
|
22
|
+
c0,1.2-0.8,1.9-1.9,1.9L464.9,272.3z M457.2,268.8c0,2.7,2.3,5.1,5.1,5.1c2.7,0,5.1-2.3,5.1-5.1c0-2.7-2.3-5.1-5.1-5.1
|
|
23
|
+
C459.5,263.8,457.2,265.7,457.2,268.8z M456,268.8c0-3.5,2.7-6.2,6.2-6.2c3.5,0,6.2,2.7,6.2,6.2c0,3.5-2.7,6.2-6.2,6.2
|
|
24
|
+
C458.7,274.7,456,271.9,456,268.8z M-121.8,317.1c0,0,5.8,2.3,5.8,4.7c0,0-0.4,1.9-2.3,1.9c-1.9,0-4.7-3.1-4.7-4.7
|
|
25
|
+
S-121.8,317.1-121.8,317.1z M-128,287.9C-128.4,287.9-128.4,287.5-128,287.9c-0.4-0.4-0.4-0.4-0.4-0.4c-1.2,0.4-3.1,1.9-3.1,4.7
|
|
26
|
+
c0,10.5,28.4,11.7,44,30.8c1.6,1.9,4.3,3.1,7,3.1c3.5,0,7-0.4,10.1-0.8c0.4,0,0.8-0.4,0.8-0.8c0-0.4,0-0.8,0-1.2
|
|
27
|
+
C-88.7,297.3-124.9,303.5-128,287.9z M-87.1,254.8c-1.9-1.9-7-0.4-9.7,1.9c-2.7,2.3-1.6,3.9-1.6,3.9c2.3-3.1,5.8-4.7,8.2-5.1
|
|
28
|
+
C-88.3,255.6-87.1,254.8-87.1,254.8z M-28.7,260.2c0,0-3.9,0.8-7.4-3.1c0,0,1.6,0,1.9-1.9C-34.5,255.2-32.2,259.5-28.7,260.2z
|
|
29
|
+
M-29.9,278.2c0,0-0.8,4.3-5.8,4.3c-5.5,0-10.1-7.4-11.7-24.9c1.2,1.9,2.7,3.9,3.5,6.2c0-2.3,1.2-6.6-4.3-10.5
|
|
30
|
+
c0,0,14.4,3.1,14.8,17.9c0,2.7-1.6,5.1-2.3,6.2c0,0-0.8,0.4-0.4,1.6c0.4,0.8,1.6,0.8,2.7-0.4S-29.9,275.8-29.9,278.2z M-50.1,286.3
|
|
31
|
+
c0,0-3.9,7.4-9.4,7.4c-2.3,0-3.9-1.6-3.9-3.5s2.7-9.7,14-9.7c2.7,0,4.7,0.4,4.7,2.3C-44.3,284-47,286.7-50.1,286.3z M-50.1,249.3
|
|
32
|
+
c0,0-1.6-0.4-1.2-2.7c0.4-0.8,0.4-0.8,0.4-1.9c0-1.2,0.4-2.3,1.2-2.7c0,0,1.6,0,1.6,4.3C-48.2,248.2-50.1,249.3-50.1,249.3z
|
|
33
|
+
M-55.2,249.3c-2.3-0.4-0.8-3.9-2.3-3.9c-0.8,0-0.8,3.9-1.6,3.5c-1.6-1.2-0.4-3.9-0.4-5.1c0-1.2,0.8-2.7-0.4-1.9
|
|
34
|
+
c-1.2,0.8-1.9,2.7-2.3,4.3c-0.4,1.6,0.4,2.3,1.2,4.3c0.8,1.9-0.4,1.2-0.4,1.2c-5.8-3.5-1.6-11.3-1.6-11.3c2.7-4.3,6.6-3.1,6.6-3.1
|
|
35
|
+
c0.8,0.4,0.8,0.8,0.8,1.6c0,0.8,0.4,1.2,1.2,1.6c1.2,0.4,1.6,1.6,1.6,3.9C-52.8,247-54.4,249.7-55.2,249.3z M-46.2,248.9l9.7,3.1
|
|
36
|
+
c0,0,1.9,3.5-1.9,2.3c-3.5-1.2-7-1.9-7-1.9S-47,251.3-46.2,248.9z M-94.1,263.7c-7,1.2-9.4-0.8-9.4-2.7c0-5.5,16-9.7,20.3-9.7
|
|
37
|
+
c0.8,1.2-0.8,1.2-1.2,3.1c-0.8,1.9-2.3,2.7-4.7,3.1c-2.3,0.4-4.7,1.6-6.2,2.7c-1.6,1.2,0,1.9,2.7,1.2c2.7-0.8,3.1,0.4,4.3,0
|
|
38
|
+
c1.2-0.4,0-1.9,0.8-1.9c0.8-0.4,2.3,0.8,2.3,0.8l3.9,2.7l-4.7,2.3c-0.4,0-0.8,0.4-0.8,1.2c0,0.8,2.3,0.8,3.5,0.8
|
|
39
|
+
c0.8,0,1.2,1.6,1.2,1.6c-1.2,1.6-4.7,1.6-4.7,1.6c0.8,1.6,5.1,1.2,5.8,1.6c0.8,0,0.8,1.2,1.6,3.1c0.4,1.9,3.1,2.7,3.1,2.7
|
|
40
|
+
c0.8,3.1-2.7,3.9-5.1,3.9C-95.7,280.9-94.1,263.7-94.1,263.7z M-92.6,241.9C-93,241.9-93,241.9-92.6,241.9
|
|
41
|
+
c-1.2-5.8,1.2-12.5,1.2-12.5s-5.8,4.7-5.5,12.5c-5.1,0-12.5,0.4-16.8,4.3c-6.2,5.1-7,14.8-7.4,17.5c0,0,0,0.4-0.4,0.4h-0.4
|
|
42
|
+
c-1.6-0.8-4.7-3.9-2.3-10.5c3.1-8.6,12.5-25.7,30.8-26.9c0,0,5.8-0.4,9.4,1.9c0,0,0.4,0,0.4,0.4v0.4c-1.6,1.2-6.6,5.8-8.2,12.9
|
|
43
|
+
c0,0.4-0.4,0.4-0.4,0.4C-92.2,241.9-92.6,241.9-92.6,241.9z M-78.9,264.9c0,0,1.6,7.4,5.1,10.1c0,0,0,0.8-1.2,0.8
|
|
44
|
+
c-1.2,0-3.1-1.6-3.9-5.8C-79.7,266.1-78.9,264.9-78.9,264.9z M-73.9,246.2c-4.3,0-6.2-3.9-6.2-3.9s5.1,4.7,12.1,0.8
|
|
45
|
+
C-68,243.5-69.6,246.2-73.9,246.2z M-20.1,252.5c-1.2-2.3-2.7-3.9-6.2-4.7c-3.1-0.8-5.8-0.4-7.8,1.2l-6.2-2.3
|
|
46
|
+
c-0.8-1.6-1.2-3.1-1.9-4.3c-0.4-1.2-1.2-1.9-1.9-2.3c-4.3-2.3-15.6-8.2-19.9-2.3c0,0-0.4,0.4-0.4,0.8l-1.6-0.4
|
|
47
|
+
c-0.8-2.3-3.1-4.3-6.2-5.1c-1.9-0.4-3.9-0.4-5.5,0.4c-1.2,0.4-1.2,1.9,0,2.3l5.1,1.9c1.2,0.4,1.9,1.6,1.2,2.7
|
|
48
|
+
c-0.4,1.2-1.6,1.9-2.7,1.2c0,0-3.1-0.8-5.5-1.6c-1.2-0.4-2.3,0.8-1.9,1.9c0.8,2.3,3.1,4.7,6.2,5.5c2.7,0.8,5.5,0,7.4-1.2l1.2,0.4
|
|
49
|
+
c0,2.7,2.3,6.2,4.3,7.4c3.1,1.9,5.8,0.4,9-1.6c0,0,8.2,6.2,4.3,24.5c-10.1,1.2-14,4.7-17.5,8.6c-2.3-0.8-9.4-1.6-13.2-0.4
|
|
50
|
+
c1.2-1.2,2.7-2.3,5.1-3.1c1.2-0.4,1.6-1.2,1.6-2.3c0,0,4.7-1.6,4.7-3.1c0-1.6-5.8-1.6-8.2-14c-0.4-1.6-0.8-2.7-3.1-3.5
|
|
51
|
+
c0,0-0.8-1.2,0.4-2.7c1.2-1.6,1.6-1.9,1.2-3.1c-0.4-1.2-1.9-1.9-1.9-1.9v-1.9c0,0-4.7-3.5-4.7-8.6c0-5.1,6.6-10.9,8.2-12.5v-0.4
|
|
52
|
+
c0,0,0-0.4-0.4-0.4c-2.3-1.6-6.6-3.9-13.6-3.9c-27.3,0-33.5,24.5-39.4,36.2c0,0.4,0,0.4,0,0.8c5.8,11.7,15.2,10.5,16,20.6
|
|
53
|
+
c0.4,7.8-1.6,7.8-3.1,7.8c-1.2,0-3.1-1.2-3.9-1.9h-0.4c0,0-0.4,0.4,0,0.4c0.8,1.9,2.7,6.6,9,6.6c3.1,0,3.9-2.7,3.9-5.5v-9
|
|
54
|
+
c0-0.8-0.4-1.6-0.8-2.3c-1.9-1.9-6.6-6.2-6.6-9.7c0-1.6,1.2-2.3,2.3-2.3c2.3,0,4.7,3.5,6.6,8.2c0.4,1.2,1.2,1.9,1.6,2.3h0.4
|
|
55
|
+
c0,0,0,0,0-0.4c-0.8-2.7-0.8-5.5-1.2-6.6c0-0.4-0.4-1.2-0.8-1.6c-1.9-1.6-6.6-6.2-6.6-13.2c0-9.4,15.2-8.6,18.3-8.6
|
|
56
|
+
c0.8,3.1,2.7,4.7,3.9,5.1c-4.7,1.6-14.8,5.1-14.8,10.9c0,6.2,10.5,5.8,10.5,5.8s-1.6,12.5,10.1,16.4c0,0-1.9,1.9-8.2,1.9
|
|
57
|
+
c-5.8,0-8.6-2.7-10.1-5.8c0,0,0-0.4-0.4-0.4c0,0-0.4,0-0.4,0.4c-0.4,0.8-0.4,2.3,0.4,3.9c1.6,2.7,3.9,4.3,3.9,7.8
|
|
58
|
+
c0,2.7-2.3,4.3-3.5,4.7c2.3,0.4,12.9,3.1,19.9,6.6c0.8-0.4,7-4.3,7.4-9.7c0,0,0.4-3.5-4.7-3.9c0,0,2.3-0.8,6.2-0.8
|
|
59
|
+
c3.9,0,8.2,3.1,0.4,19.5c0,0,0,0,0,0.4c1.2,0.8,10.1,6.6,16,12.1h0.4c0,0,0.4,0,0.4-0.4c0.8-0.8,2.3-3.5,3.1-10.1
|
|
60
|
+
c0-0.8,0.4-1.2,1.2-1.2c3.5-1.2,15.2-4.7,20.3-11.7c5.8-8.2,8.2-9.4,8.2-9.4s3.9-2.3,2.3-8.2c-0.8-3.1-5.5-10.9-10.1-19.1
|
|
61
|
+
c1.2,0.8,2.3,1.2,3.5,1.6c2.7,0.8,5.5,0.4,7.4-0.8c0.4-0.4,0.8-0.8,0.8-1.2c0-0.4-0.4-0.8-0.8-1.2l-5.1-1.9
|
|
62
|
+
c-1.2-0.4-1.9-1.9-1.6-3.1c0.4-1.2,1.9-1.9,3.1-1.6l4.7,1.6c0.4,0,0.8,0,1.2-0.4C-19.7,252.8-20.1,253.2-20.1,252.5z M-89.1,267.2
|
|
63
|
+
c0,0-1.9,0.4-1.6,3.5c0.4,2.7,2.7,2.7,2.7,2.7C-89.9,271.1-89.1,267.2-89.1,267.2z M-123,305.8c7,3.9,22.6,8.6,25.7,16.8
|
|
64
|
+
c0,0,1.2,1.9-5.1,1.9c-4.7,0-5.8-1.2-9-5.1c-4.7-5.5-14.4-9-14.4-13.2C-126.1,306.6-125.7,304.3-123,305.8z"/>
|
|
4
65
|
</svg>
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Trigger resource/event configuration table.
|
|
3
|
+
*
|
|
4
|
+
* The ServiceTitan trigger uses a two-level Resource → Event picker. This
|
|
5
|
+
* table is the single source of truth for which (resource, event) pairs the
|
|
6
|
+
* trigger supports and how they map to the underlying ST list endpoint.
|
|
7
|
+
*
|
|
8
|
+
* To add a new event in Phase 3, add an entry here and (if needed) gate any
|
|
9
|
+
* resource-specific filters on `resource` via displayOptions in the node.
|
|
10
|
+
*/
|
|
11
|
+
export interface TriggerEventConfig {
|
|
12
|
+
/** Internal event value within the resource (e.g. 'createdOrModified'). */
|
|
13
|
+
event: string;
|
|
14
|
+
/** UI label for the event dropdown. */
|
|
15
|
+
label: string;
|
|
16
|
+
/** UI description shown under the dropdown. */
|
|
17
|
+
description: string;
|
|
18
|
+
/** ServiceTitan list endpoint path. `{tenantId}` is substituted at poll-time. */
|
|
19
|
+
path: string;
|
|
20
|
+
/** Sort parameter to pass to ST (e.g. '+ModifiedOn'). */
|
|
21
|
+
sortField: string;
|
|
22
|
+
/** Field on the row used for boundary-id dedup (e.g. 'modifiedOn'). */
|
|
23
|
+
timestampField: string;
|
|
24
|
+
}
|
|
25
|
+
export interface TriggerResourceConfig {
|
|
26
|
+
/** Internal resource value (e.g. 'job'). */
|
|
27
|
+
resource: string;
|
|
28
|
+
/** UI label for the resource dropdown. */
|
|
29
|
+
resourceLabel: string;
|
|
30
|
+
events: TriggerEventConfig[];
|
|
31
|
+
}
|
|
32
|
+
export declare const TRIGGER_RESOURCES: TriggerResourceConfig[];
|
|
33
|
+
/**
|
|
34
|
+
* Lookup helper — returns the event config for the chosen resource+event, or
|
|
35
|
+
* undefined if the pair isn't recognized.
|
|
36
|
+
*/
|
|
37
|
+
export declare function findTriggerEvent(resource: string, event: string): TriggerEventConfig | undefined;
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Trigger resource/event configuration table.
|
|
4
|
+
*
|
|
5
|
+
* The ServiceTitan trigger uses a two-level Resource → Event picker. This
|
|
6
|
+
* table is the single source of truth for which (resource, event) pairs the
|
|
7
|
+
* trigger supports and how they map to the underlying ST list endpoint.
|
|
8
|
+
*
|
|
9
|
+
* To add a new event in Phase 3, add an entry here and (if needed) gate any
|
|
10
|
+
* resource-specific filters on `resource` via displayOptions in the node.
|
|
11
|
+
*/
|
|
12
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
13
|
+
exports.TRIGGER_RESOURCES = void 0;
|
|
14
|
+
exports.findTriggerEvent = findTriggerEvent;
|
|
15
|
+
exports.TRIGGER_RESOURCES = [
|
|
16
|
+
{
|
|
17
|
+
resource: 'job',
|
|
18
|
+
resourceLabel: 'Job',
|
|
19
|
+
events: [
|
|
20
|
+
{
|
|
21
|
+
event: 'createdOrModified',
|
|
22
|
+
label: 'Created or Modified',
|
|
23
|
+
description: 'Fires for any job whose modifiedOn has advanced since the last poll',
|
|
24
|
+
path: '/jpm/v2/tenant/{tenantId}/jobs',
|
|
25
|
+
sortField: '+ModifiedOn',
|
|
26
|
+
timestampField: 'modifiedOn',
|
|
27
|
+
},
|
|
28
|
+
],
|
|
29
|
+
},
|
|
30
|
+
];
|
|
31
|
+
/**
|
|
32
|
+
* Lookup helper — returns the event config for the chosen resource+event, or
|
|
33
|
+
* undefined if the pair isn't recognized.
|
|
34
|
+
*/
|
|
35
|
+
function findTriggerEvent(resource, event) {
|
|
36
|
+
const r = exports.TRIGGER_RESOURCES.find((entry) => entry.resource === resource);
|
|
37
|
+
return r?.events.find((e) => e.event === event);
|
|
38
|
+
}
|
|
39
|
+
//# sourceMappingURL=triggerResources.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"triggerResources.js","sourceRoot":"","sources":["../../../nodes/ServiceTitan/triggerResources.ts"],"names":[],"mappings":";AAAA;;;;;;;;;GASG;;;AA+CH,4CAMC;AA5BY,QAAA,iBAAiB,GAA4B;IACzD;QACC,QAAQ,EAAE,KAAK;QACf,aAAa,EAAE,KAAK;QACpB,MAAM,EAAE;YACP;gBACC,KAAK,EAAE,mBAAmB;gBAC1B,KAAK,EAAE,qBAAqB;gBAC5B,WAAW,EACV,qEAAqE;gBACtE,IAAI,EAAE,gCAAgC;gBACtC,SAAS,EAAE,aAAa;gBACxB,cAAc,EAAE,YAAY;aAC5B;SACD;KACD;CACD,CAAC;AAEF;;;GAGG;AACH,SAAgB,gBAAgB,CAC/B,QAAgB,EAChB,KAAa;IAEb,MAAM,CAAC,GAAG,yBAAiB,CAAC,IAAI,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,KAAK,CAAC,QAAQ,KAAK,QAAQ,CAAC,CAAC;IACzE,OAAO,CAAC,EAAE,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,KAAK,KAAK,CAAC,CAAC;AACjD,CAAC"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared, low-churn ServiceTitan API shapes.
|
|
3
|
+
*
|
|
4
|
+
* These are first-pass and intentionally narrow — only fields we actively read
|
|
5
|
+
* across the codebase. Extend as new resources are ported.
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Standard ServiceTitan list-envelope. Almost every ST list endpoint returns
|
|
9
|
+
* the same wrapper: page metadata + a `data` array of the resource.
|
|
10
|
+
*/
|
|
11
|
+
export interface STListEnvelope<T> {
|
|
12
|
+
page?: number;
|
|
13
|
+
pageSize?: number;
|
|
14
|
+
hasMore?: boolean;
|
|
15
|
+
totalCount?: number;
|
|
16
|
+
data?: T[];
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Raw shape ServiceTitan returns inside `customFields[]` on most resources.
|
|
20
|
+
* `value` is `unknown` because ST encodes typed values per `typeId` and we
|
|
21
|
+
* don't normalize them yet.
|
|
22
|
+
*/
|
|
23
|
+
export interface STCustomField {
|
|
24
|
+
name: string;
|
|
25
|
+
typeId: number;
|
|
26
|
+
value: unknown;
|
|
27
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Shared, low-churn ServiceTitan API shapes.
|
|
4
|
+
*
|
|
5
|
+
* These are first-pass and intentionally narrow — only fields we actively read
|
|
6
|
+
* across the codebase. Extend as new resources are ported.
|
|
7
|
+
*/
|
|
8
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
|
+
//# sourceMappingURL=common.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"common.js","sourceRoot":"","sources":["../../../../nodes/ServiceTitan/types/common.ts"],"names":[],"mappings":";AAAA;;;;;GAKG"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import type { STCustomField } from './common';
|
|
2
|
+
/**
|
|
3
|
+
* Minimal ServiceTitan `Customer` shape. First-pass — extend as the Customer
|
|
4
|
+
* resource grows beyond Customer.Get.
|
|
5
|
+
*/
|
|
6
|
+
export interface Customer {
|
|
7
|
+
id: number;
|
|
8
|
+
name: string;
|
|
9
|
+
type?: string;
|
|
10
|
+
address?: unknown;
|
|
11
|
+
customFields?: STCustomField[];
|
|
12
|
+
modifiedOn?: string;
|
|
13
|
+
createdOn?: string;
|
|
14
|
+
active: boolean;
|
|
15
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"customer.js","sourceRoot":"","sources":["../../../../nodes/ServiceTitan/types/customer.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../nodes/ServiceTitan/types/index.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import type { STCustomField } from './common';
|
|
2
|
+
/**
|
|
3
|
+
* Subset of the ServiceTitan `Job` shape we read in the trigger and downstream
|
|
4
|
+
* helpers. First-pass — extend as new fields are needed.
|
|
5
|
+
*/
|
|
6
|
+
export interface Job {
|
|
7
|
+
id: number;
|
|
8
|
+
jobNumber?: string;
|
|
9
|
+
customerId?: number;
|
|
10
|
+
locationId?: number;
|
|
11
|
+
jobStatus?: string;
|
|
12
|
+
businessUnitId?: number;
|
|
13
|
+
jobTypeId?: number;
|
|
14
|
+
campaignId?: number;
|
|
15
|
+
modifiedOn?: string;
|
|
16
|
+
createdOn?: string;
|
|
17
|
+
completedOn?: string;
|
|
18
|
+
summary?: string;
|
|
19
|
+
customFields?: STCustomField[];
|
|
20
|
+
jobAssignments?: unknown[];
|
|
21
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"job.js","sourceRoot":"","sources":["../../../../nodes/ServiceTitan/types/job.ts"],"names":[],"mappings":""}
|
package/dist/package.json
CHANGED