@codegame.dev/careerflow-mcp 1.1.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.
Files changed (47) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +398 -0
  3. package/dist/client.js +110 -0
  4. package/dist/client.js.map +1 -0
  5. package/dist/config.js +37 -0
  6. package/dist/config.js.map +1 -0
  7. package/dist/helpers.js +192 -0
  8. package/dist/helpers.js.map +1 -0
  9. package/dist/index.js +194 -0
  10. package/dist/index.js.map +1 -0
  11. package/dist/setup.js +296 -0
  12. package/dist/setup.js.map +1 -0
  13. package/dist/tools/admin.js +232 -0
  14. package/dist/tools/admin.js.map +1 -0
  15. package/dist/tools/benefit-funds.js +243 -0
  16. package/dist/tools/benefit-funds.js.map +1 -0
  17. package/dist/tools/chat-extra.js +172 -0
  18. package/dist/tools/chat-extra.js.map +1 -0
  19. package/dist/tools/chat.js +125 -0
  20. package/dist/tools/chat.js.map +1 -0
  21. package/dist/tools/cms.js +145 -0
  22. package/dist/tools/cms.js.map +1 -0
  23. package/dist/tools/crm-admin.js +269 -0
  24. package/dist/tools/crm-admin.js.map +1 -0
  25. package/dist/tools/crm.js +632 -0
  26. package/dist/tools/crm.js.map +1 -0
  27. package/dist/tools/dev-tickets.js +94 -0
  28. package/dist/tools/dev-tickets.js.map +1 -0
  29. package/dist/tools/forms.js +105 -0
  30. package/dist/tools/forms.js.map +1 -0
  31. package/dist/tools/hr.js +517 -0
  32. package/dist/tools/hr.js.map +1 -0
  33. package/dist/tools/kanban-extra.js +403 -0
  34. package/dist/tools/kanban-extra.js.map +1 -0
  35. package/dist/tools/misc.js +159 -0
  36. package/dist/tools/misc.js.map +1 -0
  37. package/dist/tools/projects.js +138 -0
  38. package/dist/tools/projects.js.map +1 -0
  39. package/dist/tools/tasks.js +342 -0
  40. package/dist/tools/tasks.js.map +1 -0
  41. package/dist/tools/time.js +129 -0
  42. package/dist/tools/time.js.map +1 -0
  43. package/dist/tools/workplace.js +110 -0
  44. package/dist/tools/workplace.js.map +1 -0
  45. package/dist/tools/workspace.js +199 -0
  46. package/dist/tools/workspace.js.map +1 -0
  47. package/package.json +61 -0
package/dist/setup.js ADDED
@@ -0,0 +1,296 @@
1
+ /**
2
+ * `careerflow-mcp init` — a guided setup that turns "edit a JSON config by
3
+ * hand" into one command.
4
+ *
5
+ * Asks for the connection details (or takes them from flags, so a vendor can
6
+ * print a copy-paste one-liner), then writes them straight into the chosen
7
+ * client's configuration (Claude Code, Claude Desktop, ZCode, Cursor) or
8
+ * prints a ready-to-paste block for anything else. Deliberately
9
+ * dependency-free: node:readline and node:fs cover everything.
10
+ *
11
+ * The token is never accepted as a flag: argv is readable by every other
12
+ * process on the machine, so it is always prompted for with input hidden.
13
+ */
14
+ import { existsSync, mkdirSync, readFileSync, writeFileSync, copyFileSync } from "node:fs";
15
+ import { homedir } from "node:os";
16
+ import { dirname, join } from "node:path";
17
+ import { spawnSync } from "node:child_process";
18
+ import * as readline from "node:readline/promises";
19
+ const DEFAULT_SERVER_NAME = "careerflow";
20
+ /** The npm package the client configs run via npx. */
21
+ const PACKAGE_NAME = "@codegame.dev/careerflow-mcp";
22
+ function makeReadline() {
23
+ return readline.createInterface({ input: process.stdin, output: process.stdout });
24
+ }
25
+ async function ask(rl, question, fallback = "") {
26
+ const suffix = fallback ? ` [${fallback}]` : "";
27
+ const answer = (await rl.question(`${question}${suffix}: `)).trim();
28
+ return answer || fallback;
29
+ }
30
+ /** Asks a question with the answer suppressed, for the token. */
31
+ async function askSecret(rl, question) {
32
+ const output = rl.output;
33
+ const write = output.write.bind(output);
34
+ rl._writeToOutput = (stringToWrite) => {
35
+ // echo the prompt, mute whatever follows it (the typed token)
36
+ if (!stringToWrite.includes(question))
37
+ return;
38
+ write(stringToWrite);
39
+ };
40
+ try {
41
+ const answer = (await rl.question(`${question}: `)).trim();
42
+ output.write("\n");
43
+ return answer;
44
+ }
45
+ finally {
46
+ ;
47
+ rl._writeToOutput = (stringToWrite) => write(stringToWrite);
48
+ }
49
+ }
50
+ /** Reads a JSON config, lets the callback add its server entry, writes it back pretty. */
51
+ function updateJsonConfig(configPath, update) {
52
+ const existed = existsSync(configPath);
53
+ let config = {};
54
+ if (existed) {
55
+ try {
56
+ config = JSON.parse(readFileSync(configPath, "utf8"));
57
+ }
58
+ catch {
59
+ copyFileSync(configPath, `${configPath}.backup`);
60
+ console.log(` Could not parse the existing config; saved a copy to ${configPath}.backup`);
61
+ config = {};
62
+ }
63
+ }
64
+ update(config);
65
+ mkdirSync(dirname(configPath), { recursive: true });
66
+ writeFileSync(configPath, JSON.stringify(config, null, 2) + "\n");
67
+ return { existed };
68
+ }
69
+ function serverEnv(connection) {
70
+ return {
71
+ CAREERFLOW_BASE_URL: connection.baseUrl,
72
+ CAREERFLOW_TOKEN: connection.token,
73
+ ...(connection.companyId ? { CAREERFLOW_COMPANY_ID: connection.companyId } : {})
74
+ };
75
+ }
76
+ function claudeDesktopConfigPath() {
77
+ switch (process.platform) {
78
+ case "darwin":
79
+ return join(homedir(), "Library", "Application Support", "Claude", "claude_desktop_config.json");
80
+ case "win32":
81
+ return join(process.env.APPDATA ?? join(homedir(), "AppData", "Roaming"), "Claude", "claude_desktop_config.json");
82
+ default:
83
+ return join(homedir(), ".config", "Claude", "claude_desktop_config.json");
84
+ }
85
+ }
86
+ function isOnPath(command) {
87
+ const result = spawnSync(command, ["--version"], { stdio: "ignore", shell: process.platform === "win32" });
88
+ return !result.error;
89
+ }
90
+ const CLIENTS = [
91
+ {
92
+ id: "claude-code",
93
+ label: "Claude Code",
94
+ detect: () => isOnPath("claude"),
95
+ apply: async (connection, serverName) => {
96
+ const args = ["mcp", "add", "--scope", "user", serverName];
97
+ for (const [key, value] of Object.entries(serverEnv(connection))) {
98
+ args.push("--env", `${key}=${value}`);
99
+ }
100
+ args.push("--", "npx", "-y", PACKAGE_NAME);
101
+ const result = spawnSync("claude", args, { stdio: "inherit", shell: process.platform === "win32" });
102
+ if (result.status !== 0) {
103
+ throw new Error(`claude mcp add exited with ${result.status ?? "an error"}`);
104
+ }
105
+ console.log(`\nAdded to Claude Code (user scope) as "${serverName}". Start it and ask "what are my tasks?"`);
106
+ }
107
+ },
108
+ {
109
+ id: "claude-desktop",
110
+ label: "Claude Desktop",
111
+ detect: () => existsSync(dirname(claudeDesktopConfigPath())),
112
+ apply: async (connection, serverName) => {
113
+ const configPath = claudeDesktopConfigPath();
114
+ const { existed } = updateJsonConfig(configPath, (config) => {
115
+ config.mcpServers = {
116
+ ...(config.mcpServers ?? {}),
117
+ [serverName]: { command: "npx", args: ["-y", PACKAGE_NAME], env: serverEnv(connection) }
118
+ };
119
+ });
120
+ console.log(`\n${existed ? "Updated" : "Created"} ${configPath} (server name: "${serverName}")`);
121
+ console.log(`Restart Claude Desktop and ask "what are my tasks?"`);
122
+ }
123
+ },
124
+ {
125
+ id: "zcode",
126
+ label: "ZCode (Z.ai)",
127
+ detect: () => existsSync(join(homedir(), ".zcode")),
128
+ apply: async (connection, serverName) => {
129
+ const configPath = join(homedir(), ".zcode", "cli", "config.json");
130
+ const { existed } = updateJsonConfig(configPath, (config) => {
131
+ config.mcp = {
132
+ ...(config.mcp ?? {}),
133
+ servers: {
134
+ ...(config.mcp?.servers ?? {}),
135
+ [serverName]: {
136
+ type: "stdio",
137
+ command: "npx",
138
+ args: ["-y", PACKAGE_NAME],
139
+ env: serverEnv(connection)
140
+ }
141
+ }
142
+ };
143
+ });
144
+ console.log(`\n${existed ? "Updated" : "Created"} ${configPath} (server name: "${serverName}")`);
145
+ console.log(`Restart ZCode and ask "what are my tasks?"`);
146
+ }
147
+ },
148
+ {
149
+ id: "cursor",
150
+ label: "Cursor",
151
+ detect: () => existsSync(join(homedir(), ".cursor")),
152
+ apply: async (connection, serverName) => {
153
+ const configPath = join(homedir(), ".cursor", "mcp.json");
154
+ const { existed } = updateJsonConfig(configPath, (config) => {
155
+ config.mcpServers = {
156
+ ...(config.mcpServers ?? {}),
157
+ [serverName]: { command: "npx", args: ["-y", PACKAGE_NAME], env: serverEnv(connection) }
158
+ };
159
+ });
160
+ console.log(`\n${existed ? "Updated" : "Created"} ${configPath} (server name: "${serverName}")`);
161
+ console.log(`Restart Cursor and ask "what are my tasks?"`);
162
+ }
163
+ },
164
+ {
165
+ id: "other",
166
+ label: "Anything else (print a config block to paste)",
167
+ detect: () => true,
168
+ apply: async (connection, serverName) => {
169
+ console.log(`\nAdd this to your client's MCP configuration` +
170
+ `(Claude Desktop: claude_desktop_config.json, Cursor: ~/.cursor/mcp.json, ` +
171
+ `ZCode: ~/.zcode/cli/config.json under "mcp"."servers"):`);
172
+ console.log(JSON.stringify({
173
+ mcpServers: {
174
+ [serverName]: {
175
+ command: "npx",
176
+ args: ["-y", PACKAGE_NAME],
177
+ env: serverEnv(connection)
178
+ }
179
+ }
180
+ }, null, 2));
181
+ }
182
+ }
183
+ ];
184
+ /**
185
+ * Parses the `init` subcommand's flags. Only non-secret values belong here:
186
+ * the token is prompted for with hidden input instead, because argv is
187
+ * readable by other processes on the machine.
188
+ */
189
+ export function parseInitFlags(args) {
190
+ const flags = {};
191
+ const values = {
192
+ "--base-url": "baseUrl",
193
+ "--name": "name",
194
+ "--company-id": "companyId",
195
+ "--client": "client"
196
+ };
197
+ for (let i = 0; i < args.length; i++) {
198
+ const field = values[args[i]];
199
+ if (!field) {
200
+ throw new Error(`Unknown init option: ${args[i]}. Supported: ${Object.keys(values).join(", ")}.`);
201
+ }
202
+ const value = args[++i];
203
+ if (value === undefined || value.startsWith("--")) {
204
+ throw new Error(`${args[i - 1]} needs a value, e.g. ${args[i - 1]} https://app.example.com`);
205
+ }
206
+ ;
207
+ flags[field] = value;
208
+ }
209
+ if (flags.baseUrl && !/^https?:\/\//i.test(flags.baseUrl)) {
210
+ throw new Error("--base-url must start with http:// or https://");
211
+ }
212
+ if (flags.name && !/^[a-zA-Z0-9][a-zA-Z0-9_-]*$/.test(flags.name)) {
213
+ throw new Error("--name must be letters, digits, dashes, or underscores (used as the server's config key).");
214
+ }
215
+ if (flags.companyId && !/^\d+$/.test(flags.companyId)) {
216
+ throw new Error("--company-id must be a number.");
217
+ }
218
+ if (flags.client && !CLIENTS.some((client) => client.id === flags.client)) {
219
+ throw new Error(`--client must be one of: ${CLIENTS.map((c) => c.id).join(", ")}.`);
220
+ }
221
+ return flags;
222
+ }
223
+ export async function runSetup(args = []) {
224
+ const flags = parseInitFlags(args);
225
+ const serverName = flags.name ?? DEFAULT_SERVER_NAME;
226
+ // The wizard reads answers one prompt at a time, which only works when the
227
+ // user (not a pipe) controls stdin; with piped input every line arrives
228
+ // before the matching prompt and the wizard would hang silently. Flags make
229
+ // no difference — the token always needs a real terminal.
230
+ if (!process.stdin.isTTY) {
231
+ throw new Error("init is interactive and needs a real terminal " +
232
+ "(it asks for your token with hidden input). " +
233
+ "To configure a client by hand, see the README's manual setup section.");
234
+ }
235
+ console.log(`CareerFlow MCP setup\n`);
236
+ let connection;
237
+ let clientOption;
238
+ if (flags.baseUrl) {
239
+ console.log(`CareerFlow host: ${flags.baseUrl}${flags.companyId ? ` (company ${flags.companyId})` : ""}`);
240
+ }
241
+ else {
242
+ console.log(`You need a CareerFlow personal access token: Settings > Access Tokens > Create access token.\n` +
243
+ `It is shown once, so have it ready.\n`);
244
+ }
245
+ const rl = makeReadline();
246
+ try {
247
+ let baseUrl = flags.baseUrl;
248
+ let companyId = flags.companyId;
249
+ if (!baseUrl) {
250
+ baseUrl = await ask(rl, "CareerFlow base URL (e.g. https://app.example.com)");
251
+ if (!/^https?:\/\//i.test(baseUrl)) {
252
+ throw new Error("The base URL must start with http:// or https://");
253
+ }
254
+ baseUrl = baseUrl.replace(/\/+$/, "");
255
+ companyId = (await ask(rl, "Default company id (optional, Enter to skip)")) || undefined;
256
+ }
257
+ const token = await askSecret(rl, "Access token (input hidden)");
258
+ if (!token) {
259
+ throw new Error("A token is required. Create one under Settings > Access Tokens.");
260
+ }
261
+ if (!token.startsWith("cf_pat_")) {
262
+ console.log(` Note: tokens usually start with cf_pat_ — using the value as typed.`);
263
+ }
264
+ connection = { baseUrl, token, companyId };
265
+ }
266
+ finally {
267
+ rl.close();
268
+ }
269
+ const detected = CLIENTS.map((client) => ({ client, available: client.detect() }));
270
+ if (flags.client) {
271
+ clientOption = CLIENTS.find((client) => client.id === flags.client);
272
+ // parseInitFlags already validated the id; this satisfies the type checker
273
+ if (!clientOption)
274
+ throw new Error(`Unknown client: ${flags.client}`);
275
+ }
276
+ else {
277
+ console.log(`\nWhere should this server be installed?\n`);
278
+ detected.forEach(({ client, available }, index) => {
279
+ console.log(` ${index + 1}. ${client.label}${available ? "" : " (not detected)"}`);
280
+ });
281
+ const rlChoice = makeReadline();
282
+ try {
283
+ const raw = await ask(rlChoice, `Choose 1-${detected.length}`, "1");
284
+ const index = Number(raw);
285
+ if (!Number.isInteger(index) || index < 1 || index > detected.length) {
286
+ throw new Error(`"${raw}" is not one of 1-${detected.length}`);
287
+ }
288
+ clientOption = detected[index - 1].client;
289
+ }
290
+ finally {
291
+ rlChoice.close();
292
+ }
293
+ }
294
+ await clientOption.apply(connection, serverName);
295
+ }
296
+ //# sourceMappingURL=setup.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"setup.js","sourceRoot":"","sources":["../src/setup.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,232 @@
1
+ import { z } from "zod";
2
+ import { companyIdSchema, resolveCompanyId, safeHandler, summariseUser, textResult } from "../helpers.js";
3
+ /**
4
+ * Organization units carry ~30 raw columns (five joined image variants,
5
+ * duplicated parent/parent2 titles, supervisor contact fields) per row for the
6
+ * web app's tree editor. An assistant only ever needs enough to identify the
7
+ * unit and file/report against it.
8
+ */
9
+ function summariseOrgUnit(unit) {
10
+ return {
11
+ id: unit.id,
12
+ title: unit.title?.fa || unit.title?.en || undefined,
13
+ parent_id: unit.parent_id ?? undefined,
14
+ num: unit.num,
15
+ supervisor_id: unit.supervisor_id ?? undefined,
16
+ supervisor_name: [unit.supervisor_firstname, unit.supervisor_lastname].filter(Boolean).join(" ") || undefined,
17
+ children_count: unit.children_count ?? undefined
18
+ };
19
+ }
20
+ /**
21
+ * Org-chart nodes come back as a flat list meant for a JS tree-rendering
22
+ * widget: every node (company root, org unit, or user) repeats five image
23
+ * path variants plus every supervisor contact field, regardless of node type.
24
+ * `pid` is the only structural field a caller needs to rebuild the tree.
25
+ */
26
+ function summariseOrgChartNode(node) {
27
+ return {
28
+ id: node.id,
29
+ pid: node.pid ?? undefined,
30
+ company_id: node.company_id ?? undefined,
31
+ organization_unit_id: node.organization_unit_id ?? undefined,
32
+ user_id: node.user_id ?? undefined,
33
+ title: node.title || undefined,
34
+ name: node.user || undefined,
35
+ staff_number: node.user_staff_number_with_prefix || undefined
36
+ };
37
+ }
38
+ /**
39
+ * Company and user administration: creating/editing company users, roles, and
40
+ * company settings. These need users:write / roles:write / company:write
41
+ * scopes and change things other people depend on — the model should confirm
42
+ * with the caller before creating or disabling accounts.
43
+ */
44
+ export function registerAdminTools(server, client) {
45
+ server.registerTool("create_user", {
46
+ title: "Create a company user",
47
+ description: "Create a new user in the company. Give either an email or a mobile number (at least one is " +
48
+ "required). This creates a real account — confirm details with the caller before calling it.",
49
+ inputSchema: {
50
+ company_id: companyIdSchema,
51
+ firstname: z.string().min(1),
52
+ lastname: z.string().min(1),
53
+ staff_number: z.string().min(1),
54
+ email: z.string().optional(),
55
+ mobile: z.string().optional(),
56
+ status: z.enum(["enable", "disable", "block"]).optional().default("enable"),
57
+ role_id: z.number().int().optional(),
58
+ post: z.string().optional(),
59
+ organization_unit_id: z.number().int().optional(),
60
+ supervisor_id: z.number().int().optional(),
61
+ hire_date: z.string().optional()
62
+ }
63
+ }, safeHandler(async (args) => {
64
+ const companyId = resolveCompanyId(client, args.company_id);
65
+ const response = await client.post("users/create", {
66
+ company_id: companyId,
67
+ type: "company-user",
68
+ firstname: args.firstname,
69
+ lastname: args.lastname,
70
+ staff_number: args.staff_number,
71
+ email: args.email,
72
+ mobile: args.mobile,
73
+ status: args.status,
74
+ role_id: args.role_id,
75
+ post: args.post,
76
+ organization_unit_id: args.organization_unit_id,
77
+ supervisor_id: args.supervisor_id,
78
+ hire_date: args.hire_date
79
+ });
80
+ const user = response.data?.user;
81
+ return textResult({ created: true, user: user ? summariseUser(user) : undefined });
82
+ }));
83
+ server.registerTool("update_user", {
84
+ title: "Update a company user",
85
+ description: "Change fields on an existing user. Only the fields passed are altered — the user is read " +
86
+ "first and unmentioned fields keep their current values (the underlying API replaces the " +
87
+ "whole row, so this tool merges for you).",
88
+ inputSchema: {
89
+ company_id: companyIdSchema,
90
+ user_id: z.number().int(),
91
+ firstname: z.string().optional(),
92
+ lastname: z.string().optional(),
93
+ email: z.string().optional(),
94
+ mobile: z.string().optional(),
95
+ staff_number: z.string().optional(),
96
+ organization_unit_id: z.number().int().optional(),
97
+ supervisor_id: z.number().int().optional(),
98
+ hire_date: z.string().optional()
99
+ }
100
+ }, safeHandler(async (args) => {
101
+ const companyId = resolveCompanyId(client, args.company_id);
102
+ const current = await client.get(`users/${args.user_id}`, { company_id: companyId });
103
+ const user = current.data ?? {};
104
+ const response = await client.post("users/edit", {
105
+ company_id: companyId,
106
+ id: args.user_id,
107
+ type: "company-user",
108
+ firstname: args.firstname ?? user.firstname,
109
+ lastname: args.lastname ?? user.lastname,
110
+ email: args.email ?? user.email,
111
+ mobile: args.mobile ?? user.mobile,
112
+ staff_number: args.staff_number ?? user.staff_number,
113
+ organization_unit_id: args.organization_unit_id ?? user.organization_unit_id,
114
+ supervisor_id: args.supervisor_id ?? user.supervisor_id,
115
+ hire_date: args.hire_date ?? user.hire_date
116
+ });
117
+ return textResult({ updated: true, user: summariseUser(response.data ?? {}) });
118
+ }));
119
+ server.registerTool("set_user_status", {
120
+ title: "Enable, disable, or block a user",
121
+ description: "Change a user's account status. 'block' locks them out immediately and resets failed-login " +
122
+ "tracking — this is a real access change, confirm with the caller first.",
123
+ inputSchema: {
124
+ company_id: companyIdSchema,
125
+ user_id: z.number().int(),
126
+ status: z.enum(["enable", "disable", "block"])
127
+ }
128
+ }, safeHandler(async (args) => {
129
+ const companyId = resolveCompanyId(client, args.company_id);
130
+ await client.post("users/status", { company_id: companyId, user_id: args.user_id, status: args.status });
131
+ return textResult({ user_id: args.user_id, status: args.status });
132
+ }));
133
+ server.registerTool("set_user_role", {
134
+ title: "Change a user's role",
135
+ description: "Assign a different permission role to a user. Use list_roles to see available roles.",
136
+ inputSchema: { company_id: companyIdSchema, user_id: z.number().int(), role_id: z.number().int() }
137
+ }, safeHandler(async (args) => {
138
+ const companyId = resolveCompanyId(client, args.company_id);
139
+ await client.post("users/role", { company_id: companyId, user_id: args.user_id, role_id: args.role_id });
140
+ return textResult({ user_id: args.user_id, role_id: args.role_id });
141
+ }));
142
+ server.registerTool("get_user", {
143
+ title: "Get a user",
144
+ description: "Fetch one user's full profile by id.",
145
+ inputSchema: { company_id: companyIdSchema, user_id: z.number().int() }
146
+ }, safeHandler(async (args) => {
147
+ const companyId = resolveCompanyId(client, args.company_id);
148
+ const response = await client.get(`users/${args.user_id}`, {
149
+ company_id: companyId
150
+ });
151
+ const user = response.data?.user;
152
+ return textResult(summariseUser(user ?? {}));
153
+ }));
154
+ server.registerTool("list_roles", {
155
+ title: "List company roles",
156
+ description: "List the permission roles defined for a company.",
157
+ inputSchema: { company_id: companyIdSchema }
158
+ }, safeHandler(async (args) => {
159
+ const companyId = resolveCompanyId(client, args.company_id);
160
+ const response = await client.get("roles/all", { company_id: companyId });
161
+ return textResult((response.data ?? []).map((r) => ({
162
+ id: r.id,
163
+ name: r.name,
164
+ allow_crm_leads_scope: r.allow_crm_leads_scope
165
+ })));
166
+ }));
167
+ server.registerTool("get_organization_chart", {
168
+ title: "Get the organization chart",
169
+ description: "Get the company's reporting-structure tree, grouped by organization unit.",
170
+ inputSchema: { company_id: companyIdSchema }
171
+ }, safeHandler(async (args) => {
172
+ const companyId = resolveCompanyId(client, args.company_id);
173
+ const response = await client.get("companies/organization-chart", { company_id: companyId });
174
+ const data = response.data ?? {};
175
+ return textResult({
176
+ nodes: (data.nodes ?? []).map(summariseOrgChartNode),
177
+ excluded_users: (data.excluded_users ?? []).map(summariseUser),
178
+ tips: data.tips
179
+ });
180
+ }));
181
+ server.registerTool("get_company", {
182
+ title: "Get company details",
183
+ description: "Fetch one company's profile (name, domain, contact info, plan).",
184
+ inputSchema: { company_id: z.number().int() }
185
+ }, safeHandler(async (args) => {
186
+ const response = await client.get(`companies/${args.company_id}`, {});
187
+ const c = response.data ?? {};
188
+ return textResult({
189
+ id: c.id,
190
+ title: c.title,
191
+ description: c.description || undefined,
192
+ timezone: c.timezone || undefined,
193
+ owner_name: [c.user_firstname, c.user_lastname].filter(Boolean).join(" ") || undefined,
194
+ owner_email: c.user_email || undefined,
195
+ owner_mobile: c.user_mobile || undefined,
196
+ career_domain: c.career_domain || undefined,
197
+ payroll_domain: c.payroll_domain || undefined,
198
+ currency_id: c.currency_id ?? undefined,
199
+ is_food_module_enable: Boolean(c.is_food_module_enable),
200
+ is_survey_module_enable: Boolean(c.is_survey_module_enable),
201
+ is_benefit_fund_module_enable: Boolean(c.is_benefit_fund_module_enable),
202
+ created: c.created || undefined
203
+ });
204
+ }));
205
+ server.registerTool("list_organization_units", {
206
+ title: "List organization units",
207
+ description: "List a company's organization units (departments/teams), used to file users and categorize records.",
208
+ inputSchema: {
209
+ company_id: companyIdSchema,
210
+ parent_id: z.number().int().optional(),
211
+ search: z.string().optional(),
212
+ limit: z.number().int().min(1).max(100).optional().default(50),
213
+ page: z.number().int().min(1).optional().default(1)
214
+ }
215
+ }, safeHandler(async (args) => {
216
+ const companyId = resolveCompanyId(client, args.company_id);
217
+ const response = await client.get("categories/search", {
218
+ company_id: companyId,
219
+ type: "organization-unit",
220
+ parent_id: args.parent_id,
221
+ search: args.search,
222
+ limit: args.limit,
223
+ page: args.page
224
+ });
225
+ const data = response.data ?? {};
226
+ return textResult({
227
+ count: data.total ?? (data.categories ?? []).length,
228
+ organization_units: (data.categories ?? []).map(summariseOrgUnit)
229
+ });
230
+ }));
231
+ }
232
+ //# sourceMappingURL=admin.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"admin.js","sourceRoot":"","sources":["../../src/tools/admin.ts"],"names":[],"mappings":"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"}