node-autotask 0.9.0 → 0.10.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/MCP_TOOL_CATALOG.json +2 -2
- package/MCP_TOOL_MANIFEST.md +4 -4
- package/N8N_MCP_MANIFEST.json +2 -2
- package/N8N_MCP_MANIFEST.md +3 -3
- package/capabilities.json +1259 -1259
- package/dist/capabilities.cjs +2 -3
- package/dist/capabilities.js +1 -2
- package/dist/{chunk-UYJ5V262.js → chunk-3VB6N44U.js} +32 -182
- package/dist/{chunk-BZPFDRAE.js → chunk-6KFP5HV3.js} +1258 -1259
- package/dist/chunk-DMMMWO6A.js +0 -0
- package/dist/chunk-FLB2X6O5.cjs +1 -0
- package/dist/{chunk-UDWV4VVD.js → chunk-HWC2WPX2.js} +214 -20
- package/dist/chunk-IDPB4N2Q.cjs +1 -0
- package/dist/{chunk-QJU2N32V.js → chunk-NVJ2PTN3.js} +2 -3
- package/dist/{chunk-53MC2QRQ.cjs → chunk-QUM74WLQ.cjs} +135 -136
- package/dist/{chunk-OYHKIYVR.cjs → chunk-S7VMY5KN.cjs} +422 -572
- package/dist/chunk-UPQIUWOS.js +0 -0
- package/dist/{chunk-LTKMTXUR.cjs → chunk-WTVD2JZN.cjs} +1258 -1259
- package/dist/{chunk-RWLPTU67.cjs → chunk-WTVLHMZA.cjs} +235 -41
- package/dist/{index-ZknpNhtc.d.ts → index-BOyh7S65.d.cts} +8 -8
- package/dist/{index-CfU1JDgS.d.cts → index-DGgMD8aq.d.ts} +8 -8
- package/dist/{index-O2zzIMcQ.d.cts → index-cQ6CRexR.d.cts} +3 -1
- package/dist/{index-O2zzIMcQ.d.ts → index-cQ6CRexR.d.ts} +3 -1
- package/dist/index.cjs +21 -22
- package/dist/index.d.cts +4 -4
- package/dist/index.d.ts +4 -4
- package/dist/index.js +6 -7
- package/dist/operations/index.cjs +133 -129
- package/dist/operations/index.d.cts +8 -3
- package/dist/operations/index.d.ts +8 -3
- package/dist/operations/index.js +9 -5
- package/dist/pool.cjs +36 -12
- package/dist/pool.d.cts +2 -2
- package/dist/pool.d.ts +2 -2
- package/dist/pool.js +31 -7
- package/dist/resources/index.cjs +5 -6
- package/dist/resources/index.d.cts +2 -2
- package/dist/resources/index.d.ts +2 -2
- package/dist/resources/index.js +4 -5
- package/dist/types/index.cjs +1 -2
- package/dist/types/index.d.cts +1 -1
- package/dist/types/index.d.ts +1 -1
- package/dist/types/index.js +1 -2
- package/dist/untrusted.cjs +0 -1
- package/dist/untrusted.js +0 -1
- package/docs/API.md +12 -6
- package/package.json +1 -1
- package/dist/capabilities.cjs.map +0 -1
- package/dist/capabilities.js.map +0 -1
- package/dist/chunk-53MC2QRQ.cjs.map +0 -1
- package/dist/chunk-BZPFDRAE.js.map +0 -1
- package/dist/chunk-CXM35TEC.cjs +0 -1
- package/dist/chunk-CXM35TEC.cjs.map +0 -1
- package/dist/chunk-GIVD2CQ3.js +0 -1
- package/dist/chunk-GIVD2CQ3.js.map +0 -1
- package/dist/chunk-LTKMTXUR.cjs.map +0 -1
- package/dist/chunk-MHBMSBTA.js +0 -1
- package/dist/chunk-MHBMSBTA.js.map +0 -1
- package/dist/chunk-NZUFSSIZ.cjs +0 -1
- package/dist/chunk-NZUFSSIZ.cjs.map +0 -1
- package/dist/chunk-OYHKIYVR.cjs.map +0 -1
- package/dist/chunk-QJU2N32V.js.map +0 -1
- package/dist/chunk-RWLPTU67.cjs.map +0 -1
- package/dist/chunk-UDWV4VVD.js.map +0 -1
- package/dist/chunk-UYJ5V262.js.map +0 -1
- package/dist/index.cjs.map +0 -1
- package/dist/index.js.map +0 -1
- package/dist/operations/index.cjs.map +0 -1
- package/dist/operations/index.js.map +0 -1
- package/dist/pool.cjs.map +0 -1
- package/dist/pool.js.map +0 -1
- package/dist/resources/index.cjs.map +0 -1
- package/dist/resources/index.js.map +0 -1
- package/dist/types/index.cjs.map +0 -1
- package/dist/types/index.js.map +0 -1
- package/dist/untrusted.cjs.map +0 -1
- package/dist/untrusted.js.map +0 -1
package/dist/capabilities.cjs
CHANGED
|
@@ -2,10 +2,9 @@
|
|
|
2
2
|
|
|
3
3
|
|
|
4
4
|
|
|
5
|
-
var
|
|
5
|
+
var _chunkWTVD2JZNcjs = require('./chunk-WTVD2JZN.cjs');
|
|
6
6
|
|
|
7
7
|
|
|
8
8
|
|
|
9
9
|
|
|
10
|
-
exports.CAPABILITIES =
|
|
11
|
-
//# sourceMappingURL=capabilities.cjs.map
|
|
10
|
+
exports.CAPABILITIES = _chunkWTVD2JZNcjs.CAPABILITIES; exports.CAPABILITY_GROUPS = _chunkWTVD2JZNcjs.CAPABILITY_GROUPS; exports.CAPABILITY_PLAN_HASHES = _chunkWTVD2JZNcjs.CAPABILITY_PLAN_HASHES;
|
package/dist/capabilities.js
CHANGED
|
@@ -4,34 +4,36 @@ import {
|
|
|
4
4
|
BLIND_SURFACE_STAMPS,
|
|
5
5
|
BaseResource,
|
|
6
6
|
ConflictError,
|
|
7
|
-
FIELD_CATALOG_HONESTY_NOTE,
|
|
8
7
|
NotFoundError,
|
|
9
8
|
RELATIONSHIP_MAP,
|
|
10
9
|
ResolutionError,
|
|
11
10
|
StaleObjectError,
|
|
11
|
+
TICKET_LABEL_FIELDS,
|
|
12
12
|
UNTRUSTED_FIELDS_BY_RESOURCE,
|
|
13
|
+
addLabelSibling,
|
|
14
|
+
addNameSibling,
|
|
13
15
|
blindStampFor,
|
|
14
16
|
buildDryRunResult,
|
|
15
17
|
buildFilter,
|
|
16
18
|
clampPageSize,
|
|
19
|
+
createNamePlan,
|
|
17
20
|
cursorToPath,
|
|
18
21
|
decodeFileData,
|
|
19
|
-
expandResourceNames,
|
|
20
|
-
fieldCatalog,
|
|
21
22
|
formatVendorDetail,
|
|
22
23
|
isAutotaskError,
|
|
23
24
|
mergePartialBody,
|
|
24
25
|
parseIdentifier,
|
|
25
26
|
parseVendorErrors,
|
|
27
|
+
resolveCompositeNames,
|
|
26
28
|
resolveFieldsPreset,
|
|
27
29
|
truncateNoteChars,
|
|
28
30
|
unwrapItem,
|
|
29
31
|
unwrapItems,
|
|
30
32
|
unwrapOperation
|
|
31
|
-
} from "./chunk-
|
|
33
|
+
} from "./chunk-HWC2WPX2.js";
|
|
32
34
|
import {
|
|
33
35
|
CAPABILITIES
|
|
34
|
-
} from "./chunk-
|
|
36
|
+
} from "./chunk-6KFP5HV3.js";
|
|
35
37
|
|
|
36
38
|
// src/resources/appointments.ts
|
|
37
39
|
var AppointmentsResource = class extends BaseResource {
|
|
@@ -820,181 +822,6 @@ var ClassificationIconsResource = class extends BaseResource {
|
|
|
820
822
|
}
|
|
821
823
|
};
|
|
822
824
|
|
|
823
|
-
// src/operations/compositeNames.ts
|
|
824
|
-
var DEFAULT_MAX_NAME_READS = 20;
|
|
825
|
-
var TICKET_LABEL_FIELDS = ["status", "priority", "ticketType", "issueType", "subIssueType", "source", "queueID"];
|
|
826
|
-
function isVendorId(value) {
|
|
827
|
-
if (typeof value === "number") return Number.isSafeInteger(value) && value >= 0;
|
|
828
|
-
if (typeof value === "string") return /^\d+$/.test(value);
|
|
829
|
-
return false;
|
|
830
|
-
}
|
|
831
|
-
function createNamePlan(labelFields = []) {
|
|
832
|
-
const resourceIds = [];
|
|
833
|
-
const resSeen = /* @__PURE__ */ new Set();
|
|
834
|
-
const recordFks = [];
|
|
835
|
-
const fkSeen = /* @__PURE__ */ new Set();
|
|
836
|
-
return {
|
|
837
|
-
plan: () => ({ resourceIds, recordFks, labelFields }),
|
|
838
|
-
addResource: (value) => {
|
|
839
|
-
if (!isVendorId(value)) return;
|
|
840
|
-
const k = String(value);
|
|
841
|
-
if (!resSeen.has(k)) {
|
|
842
|
-
resSeen.add(k);
|
|
843
|
-
resourceIds.push(value);
|
|
844
|
-
}
|
|
845
|
-
},
|
|
846
|
-
addFk: (table, value) => {
|
|
847
|
-
if (!isVendorId(value)) return;
|
|
848
|
-
const k = `${table}:${String(value)}`;
|
|
849
|
-
if (!fkSeen.has(k)) {
|
|
850
|
-
fkSeen.add(k);
|
|
851
|
-
recordFks.push({ table, id: value });
|
|
852
|
-
}
|
|
853
|
-
}
|
|
854
|
-
};
|
|
855
|
-
}
|
|
856
|
-
function addNameSibling(row, field, resolve) {
|
|
857
|
-
const value = row[field];
|
|
858
|
-
if (value === void 0) return;
|
|
859
|
-
row[`${field}Name`] = isVendorId(value) ? resolve(value) : null;
|
|
860
|
-
}
|
|
861
|
-
function addLabelSibling(row, field, names) {
|
|
862
|
-
const value = row[field];
|
|
863
|
-
if (value === void 0) return;
|
|
864
|
-
row[`${field}Label`] = names.labelFor(field, value);
|
|
865
|
-
}
|
|
866
|
-
var FK_TABLE_PATH = {
|
|
867
|
-
role: "/V1.0/Roles",
|
|
868
|
-
billingCode: "/V1.0/BillingCodes",
|
|
869
|
-
contract: "/V1.0/Contracts"
|
|
870
|
-
};
|
|
871
|
-
var FK_NAME_FIELD = {
|
|
872
|
-
role: "name",
|
|
873
|
-
billingCode: "name",
|
|
874
|
-
contract: "contractName"
|
|
875
|
-
};
|
|
876
|
-
function fkName(record, table) {
|
|
877
|
-
const value = record[FK_NAME_FIELD[table]];
|
|
878
|
-
return typeof value === "string" && value.trim() !== "" ? value : null;
|
|
879
|
-
}
|
|
880
|
-
function faultRow(err) {
|
|
881
|
-
const e = err;
|
|
882
|
-
return e.httpStatus !== void 0 ? { code: e.code, message: e.message, httpStatus: e.httpStatus } : { code: e.code, message: e.message };
|
|
883
|
-
}
|
|
884
|
-
async function resolveCompositeNames(http, plan, opts = {}) {
|
|
885
|
-
if (opts.maxNameReads !== void 0 && (!Number.isInteger(opts.maxNameReads) || opts.maxNameReads < 1)) {
|
|
886
|
-
throw new AutotaskConfigError(`composite names: maxNameReads must be an integer >= 1 (got ${String(opts.maxNameReads)})`);
|
|
887
|
-
}
|
|
888
|
-
const budget = Math.min(DEFAULT_MAX_NAME_READS, opts.maxNameReads ?? DEFAULT_MAX_NAME_READS);
|
|
889
|
-
const client = http.client;
|
|
890
|
-
if (client === void 0) {
|
|
891
|
-
throw new AutotaskConfigError("composite names: the transport is not wired to an AutotaskClient (the composite must run through the client)");
|
|
892
|
-
}
|
|
893
|
-
const readCache = http.readCache;
|
|
894
|
-
const nameCache = http.resourceNameCache;
|
|
895
|
-
const section = { truncated: false, rows: {}, reasons: {} };
|
|
896
|
-
let remaining = budget;
|
|
897
|
-
const coldResource = [];
|
|
898
|
-
for (const id of plan.resourceIds) {
|
|
899
|
-
if (nameCache !== void 0 && nameCache.get(id) !== void 0) continue;
|
|
900
|
-
if (readCache !== void 0 && readCache.get(`/V1.0/Resources/${id}`) !== void 0) continue;
|
|
901
|
-
coldResource.push(id);
|
|
902
|
-
}
|
|
903
|
-
const withinBudget = coldResource.slice(0, remaining);
|
|
904
|
-
const overBudgetResource = coldResource.slice(remaining);
|
|
905
|
-
remaining -= withinBudget.length;
|
|
906
|
-
for (const id of overBudgetResource) {
|
|
907
|
-
section.rows[`resource:${id}`] = { name: null, blind: false, capped: true };
|
|
908
|
-
section.truncated = true;
|
|
909
|
-
}
|
|
910
|
-
const overSet = new Set(overBudgetResource.map((id) => String(id)));
|
|
911
|
-
const opIds = plan.resourceIds.filter((id) => !overSet.has(String(id)));
|
|
912
|
-
if (opIds.length > 0) {
|
|
913
|
-
let pass = opIds;
|
|
914
|
-
if (pass.length > 500) {
|
|
915
|
-
for (const id of pass.slice(500)) {
|
|
916
|
-
section.rows[`resource:${id}`] = { name: null, blind: false, capped: true };
|
|
917
|
-
section.truncated = true;
|
|
918
|
-
}
|
|
919
|
-
pass = pass.slice(0, 500);
|
|
920
|
-
}
|
|
921
|
-
const res = await expandResourceNames(client, pass);
|
|
922
|
-
for (const r of res.results) {
|
|
923
|
-
const row = { name: r.name, blind: r.blind, capped: false };
|
|
924
|
-
if (r.error !== void 0) row.error = faultRow(r.error);
|
|
925
|
-
section.rows[`resource:${r.id}`] = row;
|
|
926
|
-
}
|
|
927
|
-
}
|
|
928
|
-
const holders = {
|
|
929
|
-
role: client.roles,
|
|
930
|
-
billingCode: client.billingCodes,
|
|
931
|
-
contract: client.contracts
|
|
932
|
-
};
|
|
933
|
-
for (const fk of plan.recordFks) {
|
|
934
|
-
const key = `${fk.table}:${fk.id}`;
|
|
935
|
-
const cold = readCache === void 0 || readCache.get(`${FK_TABLE_PATH[fk.table]}/${fk.id}`) === void 0;
|
|
936
|
-
if (cold) {
|
|
937
|
-
if (remaining < 1) {
|
|
938
|
-
section.rows[key] = { name: null, blind: false, capped: true };
|
|
939
|
-
section.truncated = true;
|
|
940
|
-
continue;
|
|
941
|
-
}
|
|
942
|
-
remaining -= 1;
|
|
943
|
-
}
|
|
944
|
-
try {
|
|
945
|
-
const record = await holders[fk.table].get(fk.id);
|
|
946
|
-
section.rows[key] = { name: fkName(record, fk.table), blind: false, capped: false };
|
|
947
|
-
} catch (err) {
|
|
948
|
-
if (err instanceof NotFoundError) {
|
|
949
|
-
section.rows[key] = { name: null, blind: true, capped: false };
|
|
950
|
-
} else if (isAutotaskError(err) && err.code !== "ABORTED") {
|
|
951
|
-
section.rows[key] = { name: null, blind: false, capped: false, error: faultRow(err) };
|
|
952
|
-
} else {
|
|
953
|
-
throw err;
|
|
954
|
-
}
|
|
955
|
-
}
|
|
956
|
-
}
|
|
957
|
-
const picklists = {};
|
|
958
|
-
if (plan.labelFields.length > 0) {
|
|
959
|
-
let usable = true;
|
|
960
|
-
try {
|
|
961
|
-
const catalog = await fieldCatalog(client, { resources: ["tickets"], labels: true, fields: [...plan.labelFields] });
|
|
962
|
-
const row = catalog.rows.find((r) => r.resource === "tickets");
|
|
963
|
-
if (row === void 0 || row.error !== null || row.fields === void 0) {
|
|
964
|
-
usable = false;
|
|
965
|
-
} else {
|
|
966
|
-
for (const f of plan.labelFields) {
|
|
967
|
-
const frow = row.fields.find((x) => x.name === f);
|
|
968
|
-
picklists[f] = frow?.picklistValues;
|
|
969
|
-
}
|
|
970
|
-
}
|
|
971
|
-
} catch (err) {
|
|
972
|
-
if (isAutotaskError(err) && err.code !== "ABORTED") usable = false;
|
|
973
|
-
else throw err;
|
|
974
|
-
}
|
|
975
|
-
if (!usable) for (const f of plan.labelFields) section.reasons[f] = FIELD_CATALOG_HONESTY_NOTE;
|
|
976
|
-
}
|
|
977
|
-
return {
|
|
978
|
-
section,
|
|
979
|
-
resourceName: (id) => section.rows[`resource:${id}`]?.name ?? null,
|
|
980
|
-
recordName: (table, id) => section.rows[`${table}:${id}`]?.name ?? null,
|
|
981
|
-
labelFor: (field, value) => {
|
|
982
|
-
if (value === null || value === void 0) return null;
|
|
983
|
-
const values = picklists[field];
|
|
984
|
-
if (values === void 0) {
|
|
985
|
-
section.reasons[field] = FIELD_CATALOG_HONESTY_NOTE;
|
|
986
|
-
return null;
|
|
987
|
-
}
|
|
988
|
-
const hit = values.find((v) => String(v.value) === String(value));
|
|
989
|
-
if (hit === void 0) {
|
|
990
|
-
section.reasons[field] = FIELD_CATALOG_HONESTY_NOTE;
|
|
991
|
-
return null;
|
|
992
|
-
}
|
|
993
|
-
return typeof hit.label === "string" ? hit.label : null;
|
|
994
|
-
}
|
|
995
|
-
};
|
|
996
|
-
}
|
|
997
|
-
|
|
998
825
|
// src/resources/special/companies.ts
|
|
999
826
|
var DEFAULT_LIMIT2 = 25;
|
|
1000
827
|
var MAX_LIMIT2 = 500;
|
|
@@ -1092,6 +919,22 @@ async function familyChildPage(http, parentID) {
|
|
|
1092
919
|
const { items, pageDetails } = unwrapItems(res, "companies.search");
|
|
1093
920
|
return { rows: items, hasNext: pageDetails.nextPageUrl !== null };
|
|
1094
921
|
}
|
|
922
|
+
function assertSearchWithDetailOpts(opts) {
|
|
923
|
+
if (opts === void 0) return;
|
|
924
|
+
if (typeof opts !== "object" || opts === null || Array.isArray(opts)) {
|
|
925
|
+
throw new AutotaskConfigError("companies.searchWithDetail: opts must be an object { limit?: number }", {
|
|
926
|
+
operation: "companies.searchWithDetail"
|
|
927
|
+
});
|
|
928
|
+
}
|
|
929
|
+
for (const key of Object.keys(opts)) {
|
|
930
|
+
if (key !== "limit") {
|
|
931
|
+
throw new AutotaskConfigError(
|
|
932
|
+
`companies.searchWithDetail: unknown opts key "${key}" \u2014 the bag is closed: limit (includeFamily is a companies.search option)`,
|
|
933
|
+
{ operation: "companies.searchWithDetail" }
|
|
934
|
+
);
|
|
935
|
+
}
|
|
936
|
+
}
|
|
937
|
+
}
|
|
1095
938
|
async function searchWithFamily(_resource, query, opts = {}, http) {
|
|
1096
939
|
if (opts !== void 0 && (typeof opts !== "object" || opts === null || Array.isArray(opts))) {
|
|
1097
940
|
throw new AutotaskConfigError("companies.search: opts must be an object { limit?: number, includeFamily?: boolean }");
|
|
@@ -1640,7 +1483,8 @@ async function unbilledWork(resource, companyId, opts = {}, http) {
|
|
|
1640
1483
|
capped: false,
|
|
1641
1484
|
hasMore: false,
|
|
1642
1485
|
status: "skipped",
|
|
1643
|
-
|
|
1486
|
+
// joinNotes ride the skipped part too: an empty join set from a PARTIAL read (e.g. a full projects page) is not a true zero
|
|
1487
|
+
note: ["skipped: the company (set) has no tickets or tasks in the returned join set \u2014 no tasks/tickets to join against is NOT evidence of no time entries (zero wire)", ...joinNotes].join(" | ")
|
|
1644
1488
|
};
|
|
1645
1489
|
} else {
|
|
1646
1490
|
const timeConditions = taskCap.ids.length > 0 && ticketCap.ids.length > 0 ? [{ op: "or", items: [{ field: "taskID", op: "in", value: taskCap.ids }, { field: "ticketID", op: "in", value: ticketCap.ids }] }] : taskCap.ids.length > 0 ? [{ field: "taskID", op: "in", value: taskCap.ids }] : [{ field: "ticketID", op: "in", value: ticketCap.ids }];
|
|
@@ -1833,6 +1677,13 @@ var CompaniesResource = class extends BaseResource {
|
|
|
1833
1677
|
async search(query, opts) {
|
|
1834
1678
|
return searchWithFamily(this, query, opts, this.http);
|
|
1835
1679
|
}
|
|
1680
|
+
/** `search` with an empty result explained. Same closed opts discipline as `search`: only `limit` is
|
|
1681
|
+
* accepted here (an unknown key is refused pre-request, zero wire — never silently dropped); the
|
|
1682
|
+
* family block is a `search`-only option. */
|
|
1683
|
+
async searchWithDetail(query, opts = {}) {
|
|
1684
|
+
assertSearchWithDetailOpts(opts);
|
|
1685
|
+
return super.searchWithDetail(query, opts);
|
|
1686
|
+
}
|
|
1836
1687
|
/** Get the Company with its primary context records in one call (each part a single-record
|
|
1837
1688
|
* fetch; no sub-lists; absent/dangling references come back null). */
|
|
1838
1689
|
async getContext(id) {
|
|
@@ -11082,4 +10933,3 @@ export {
|
|
|
11082
10933
|
VersionResource,
|
|
11083
10934
|
ZoneInformationResource
|
|
11084
10935
|
};
|
|
11085
|
-
//# sourceMappingURL=chunk-UYJ5V262.js.map
|