@slamb2k/dvx 1.0.7

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.
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/index.ts","../src/commands/auth-login.ts","../src/utils/table.ts","../src/commands/auth-list.ts","../src/commands/auth-select.ts","../src/commands/entities.ts","../src/commands/schema.ts","../src/commands/query.ts","../src/commands/get.ts","../src/utils/parse-json.ts","../src/utils/output.ts","../src/commands/create.ts","../src/commands/update.ts","../src/commands/upsert.ts","../src/commands/delete.ts","../src/commands/batch.ts","../src/commands/action.ts","../src/commands/demo.ts","../src/commands/completion.ts"],"sourcesContent":["import { Command, Option } from 'commander'\nimport { authLogin, authLogout } from './commands/auth-login.js'\nimport { authList } from './commands/auth-list.js'\nimport { authSelect } from './commands/auth-select.js'\nimport { entities } from './commands/entities.js'\nimport { schema } from './commands/schema.js'\nimport { query } from './commands/query.js'\nimport { get } from './commands/get.js'\nimport { createRecord } from './commands/create.js'\nimport { updateRecord } from './commands/update.js'\nimport { upsertRecord } from './commands/upsert.js'\nimport { deleteRecord } from './commands/delete.js'\nimport { batch } from './commands/batch.js'\nimport { actionCommand } from './commands/action.js'\nimport { demo } from './commands/demo.js'\nimport { completion } from './commands/completion.js'\nimport { createRequire } from 'node:module'\nimport { setUxOptions, logError, logInfo, stripAnsi } from './utils/cli.js'\n\nconst require = createRequire(import.meta.url)\nconst { version } = require('../package.json') as { version: string }\n\nconst BANNER = `\n\\x1b[36m{_____ {__ {__\\x1b[0m\\x1b[33m{__ {__\\x1b[0m\n\\x1b[36m{__ {__ {__ {__ \\x1b[0m\\x1b[33m{__ {__\\x1b[0m\n\\x1b[36m{__ {__ {__ {__ \\x1b[0m\\x1b[33m{__ {__\\x1b[0m\n\\x1b[36m{__ {__ {__ {__ \\x1b[0m\\x1b[33m {__\\x1b[0m\n\\x1b[36m{__ {__ {__ {__ \\x1b[0m\\x1b[33m{__ {__\\x1b[0m \\x1b[2mAgent-first CLI/MCP for\\x1b[0m\n\\x1b[36m{__ {__ {____ \\x1b[0m\\x1b[33m{__ {__\\x1b[0m \\x1b[2mMicrosoft Dataverse\\x1b[0m\n\\x1b[36m{_____ {__ \\x1b[0m\\x1b[33m{__ {__\\x1b[0m \\x1b[2mv${version}\\x1b[0m\n`\n\nconst program = new Command()\n\nprogram\n .name('dvx')\n .description('Agent-first CLI for Microsoft Dataverse CE/Sales/Service')\n .version(version)\n .option('--no-color', 'Disable color output')\n .option('--quiet', 'Suppress all progress output')\n .addHelpText('before', () => {\n const opts = program.opts()\n return opts.color === false ? stripAnsi(BANNER) : BANNER\n })\n .action(() => {\n program.outputHelp()\n })\n\nprogram.hook('preAction', (thisCommand) => {\n const opts = thisCommand.optsWithGlobals()\n setUxOptions({\n quiet: opts.quiet ?? false,\n noColor: opts.color === false,\n })\n})\n\n// Auth commands\nconst auth = program.command('auth').description('Manage authentication profiles')\n\nauth\n .command('login')\n .description('Sign in to a Dataverse environment')\n .option('--name <name>', 'Profile name', 'default')\n .option('--url <url>', 'Dataverse environment URL (auto-discovered if omitted)')\n .option('--tenant-id <id>', 'Entra tenant ID (auto-detected from sign-in if omitted)')\n .option('--client-id <id>', 'App registration client ID (auto-created if omitted)')\n .option('--service-principal', 'Use service principal (client credentials) auth')\n .option('--client-secret <secret>', 'Client secret (prefer DATAVERSE_CLIENT_SECRET env var)')\n .action(async (opts) => {\n await authLogin({\n name: opts.name,\n url: opts.url,\n tenantId: opts.tenantId,\n clientId: opts.clientId,\n clientSecret: opts.clientSecret,\n servicePrincipal: opts.servicePrincipal,\n })\n })\n\nauth\n .command('logout')\n .description('Remove auth profile')\n .option('--all', 'Remove all profiles')\n .action(async (opts) => {\n await authLogout({ all: opts.all })\n })\n\nauth\n .command('list')\n .alias('status')\n .description('List all authentication profiles')\n .addOption(new Option('--output <format>', 'Output format').choices(['json', 'table']).default('table'))\n .action(async (opts) => {\n await authList({ output: opts.output })\n })\n\nauth\n .command('select')\n .description('Switch active authentication profile')\n .argument('<profile>', 'Profile name to activate')\n .action(async (profileName) => {\n await authSelect(profileName)\n })\n\n// Entity list\nprogram\n .command('entities')\n .description('List all entities in the environment')\n .addOption(new Option('--output <format>', 'Output format').choices(['json', 'table', 'ndjson']).default('table'))\n .action(async (opts) => {\n await entities({ output: opts.output })\n })\n\n// Schema\nprogram\n .command('schema')\n .description('Get entity schema with attribute definitions')\n .argument('<entity>', 'Entity logical name')\n .addOption(new Option('--output <format>', 'Output format').choices(['json', 'table']).default('json'))\n .option('--no-cache', 'Force live fetch, bypass cache')\n .option('--refresh', 'Invalidate cached schema for this entity before fetching')\n .option('--refresh-all', 'Clear entire schema cache before fetching')\n .action(async (entityName, opts) => {\n await schema(entityName, { output: opts.output, noCache: !opts.cache, refresh: opts.refresh, refreshAll: opts.refreshAll })\n })\n\n// Query\nprogram\n .command('query')\n .description('Query records using OData or FetchXML')\n .option('--odata <expression>', 'OData query expression (entitySetName?$filter=...)')\n .option('--fetchxml <xml>', 'FetchXML query string')\n .option('--file <path>', 'Read query from file (auto-detects OData or FetchXML)')\n .option('--fields <fields>', 'Comma-separated field names to select')\n .option('--page-all', 'Stream all pages as NDJSON', false)\n .option('--max-rows <n>', 'Maximum rows to return', parseInt)\n .option('--dry-run', 'Preview the operation without executing', false)\n .addOption(new Option('--output <format>', 'Output format').choices(['json', 'ndjson', 'table']).default('json'))\n .action(async (opts) => {\n await query({\n odata: opts.odata,\n fetchxml: opts.fetchxml,\n file: opts.file,\n fields: opts.fields,\n pageAll: opts.pageAll,\n maxRows: opts.maxRows,\n output: opts.output,\n dryRun: opts.dryRun,\n })\n })\n\n// Get single record\nprogram\n .command('get')\n .description('Get a single record by ID')\n .argument('<entity>', 'Entity logical name')\n .argument('<id>', 'Record GUID')\n .option('--fields <fields>', 'Comma-separated field names to select')\n .addOption(new Option('--output <format>', 'Output format').choices(['json', 'table']).default('json'))\n .action(async (entityName, id, opts) => {\n await get(entityName, id, { fields: opts.fields, output: opts.output })\n })\n\n// Create\nprogram\n .command('create')\n .description('Create a new record')\n .argument('<entity>', 'Entity logical name')\n .requiredOption('--json <data>', 'JSON payload for the record')\n .option('--dry-run', 'Preview the operation without executing', false)\n .option('--as-user <id>', 'Run as this Entra user object ID (CallerObjectId)')\n .addOption(new Option('--output <format>', 'Output format: json|table').choices(['json', 'table']).default('table'))\n .action(async (entityName, opts) => {\n await createRecord(entityName, { json: opts.json, dryRun: opts.dryRun, callerObjectId: opts.asUser, output: opts.output })\n })\n\n// Update\nprogram\n .command('update')\n .description('Update an existing record')\n .argument('<entity>', 'Entity logical name')\n .argument('<id>', 'Record GUID')\n .requiredOption('--json <data>', 'JSON payload with fields to update')\n .option('--dry-run', 'Preview the operation without executing', false)\n .option('--as-user <id>', 'Run as this Entra user object ID (CallerObjectId)')\n .addOption(new Option('--output <format>', 'Output format: json|table').choices(['json', 'table']).default('table'))\n .action(async (entityName, id, opts) => {\n await updateRecord(entityName, id, { json: opts.json, dryRun: opts.dryRun, callerObjectId: opts.asUser, output: opts.output })\n })\n\n// Upsert\nprogram\n .command('upsert')\n .description('Create or update a record based on a match field')\n .argument('<entity>', 'Entity logical name')\n .requiredOption('--match-field <field>', 'Field to match on for upsert')\n .requiredOption('--json <data>', 'JSON payload for the record')\n .option('--dry-run', 'Preview the operation without executing', false)\n .option('--as-user <id>', 'Run as this Entra user object ID (CallerObjectId)')\n .addOption(new Option('--output <format>', 'Output format: json|table').choices(['json', 'table']).default('table'))\n .action(async (entityName, opts) => {\n await upsertRecord(entityName, { matchField: opts.matchField, json: opts.json, dryRun: opts.dryRun, callerObjectId: opts.asUser, output: opts.output })\n })\n\n// Delete\nprogram\n .command('delete')\n .description('Delete a record by ID')\n .argument('<entity>', 'Entity logical name')\n .argument('<id>', 'Record GUID')\n .option('--confirm', 'Skip confirmation prompt', false)\n .option('--dry-run', 'Preview the operation without executing', false)\n .option('--as-user <id>', 'Run as this Entra user object ID (CallerObjectId)')\n .addOption(new Option('--output <format>', 'Output format: json|table').choices(['json', 'table']).default('table'))\n .action(async (entityName, id, opts) => {\n await deleteRecord(entityName, id, { confirm: opts.confirm, dryRun: opts.dryRun, callerObjectId: opts.asUser, output: opts.output })\n })\n\n// Batch\nprogram\n .command('batch')\n .description('Execute batch operations from a file')\n .requiredOption('--file <path>', 'JSON file with batch operations')\n .option('--atomic', 'Wrap operations in a changeset for atomicity', false)\n .option('--dry-run', 'Preview the operation without executing', false)\n .option('--as-user <id>', 'Run as this Entra user object ID (CallerObjectId)')\n .addOption(new Option('--output <format>', 'Output format: json|table').choices(['json', 'table']).default('table'))\n .action(async (opts) => {\n await batch({ file: opts.file, atomic: opts.atomic, dryRun: opts.dryRun, callerObjectId: opts.asUser, output: opts.output })\n })\n\n// Action\nprogram\n .command('action')\n .description('Execute a Dataverse action or SDK message')\n .argument('<action>', 'Action name (PascalCase)')\n .requiredOption('--json <data>', 'JSON payload for the action')\n .option('--entity <entity>', 'Entity logical name for bound actions')\n .option('--id <id>', 'Record GUID for bound actions')\n .option('--dry-run', 'Preview the operation without executing', false)\n .option('--as-user <id>', 'Run as this Entra user object ID (CallerObjectId)')\n .addOption(new Option('--output <format>', 'Output format: json|table').choices(['json', 'table']).default('table'))\n .action(async (actionName, opts) => {\n await actionCommand(actionName, { json: opts.json, entity: opts.entity, id: opts.id, dryRun: opts.dryRun, callerObjectId: opts.asUser, output: opts.output })\n })\n\n// Demo\nprogram\n .command('demo')\n .description('Run interactive demo showcasing dvx capabilities')\n .addOption(new Option('--tier <tier>', 'Demo depth tier').choices(['read', 'write', 'full']))\n .addOption(new Option('--output <format>', 'Output format').choices(['json', 'table']).default('table'))\n .action(async (opts) => {\n await demo({ tier: opts.tier, output: opts.output })\n })\n\n// MCP server\nprogram\n .command('mcp')\n .description('Start MCP server for agent consumption')\n .option('--entities <entities>', 'Comma-separated entity logical names to scope tools')\n .option('--port <port>', 'Port for HTTP transport', parseInt)\n .addOption(new Option('--transport <transport>', 'Transport type: stdio|http').choices(['stdio', 'http']).default('stdio'))\n .action(async (options) => {\n const { startMcpServer } = await import('./mcp/server.js')\n await startMcpServer({\n entities: options.entities?.split(',').map((e: string) => e.trim()),\n transport: options.transport,\n port: options.port,\n })\n })\n\n// Shell completion\nprogram\n .command('completion')\n .description('Generate shell completion script')\n .argument('<shell>', 'Shell type: bash, zsh, or powershell')\n .action((shell) => {\n completion(shell as 'bash' | 'zsh' | 'powershell')\n })\n\nfunction getHint(error: Error, argv: string[]): string | undefined {\n const msg = error.message\n const args = argv.join(' ')\n\n // Shell expansion of $variables in OData queries\n if (msg.includes('Bad Request') && args.includes('--odata')) {\n const odataArg = argv[argv.indexOf('--odata') + 1] ?? ''\n if (odataArg.includes('?=') || odataArg.includes('&=') || !odataArg.includes('$')) {\n return \"Use single quotes to prevent shell expansion of $ in OData: --odata '/entities?$top=10'\"\n }\n }\n\n // No auth profile configured\n if (error.name === 'AuthProfileNotFoundError') {\n return 'Run `dvx auth login` to set up authentication.'\n }\n\n // Profile already exists\n if (error.name === 'AuthProfileExistsError') {\n return 'Use `dvx auth select <name>` to switch profiles, or `dvx auth logout` to remove the existing one.'\n }\n\n // Token acquisition failure\n if (error.name === 'TokenAcquisitionError' && msg.includes('Client secret not found')) {\n return 'Set DATAVERSE_CLIENT_SECRET env var, or use `dvx auth login` for delegated (browser) auth.'\n }\n\n // Entity not found\n if (error.name === 'EntityNotFoundError') {\n return 'Run `dvx entities` to list available entities. Entity names are singular (e.g., \"account\" not \"accounts\").'\n }\n\n // Record not found (bad GUID)\n if (error.name === 'RecordNotFoundError') {\n return 'Verify the record ID is correct. Use `dvx query` to search for records.'\n }\n\n // GUID validation\n if (error.name === 'ValidationError' && msg.includes('GUID')) {\n return 'GUIDs must be in format: 00000000-0000-0000-0000-000000000000'\n }\n\n // Impersonation\n if (error.name === 'ImpersonationPrivilegeError') {\n return 'The application user needs the prvActOnBehalfOfAnotherUser privilege. Assign it via a security role in Dataverse admin.'\n }\n\n // FetchXML parsing\n if (error.name === 'FetchXmlValidationError') {\n return 'Wrap FetchXML in single quotes to prevent shell interpretation of < and > characters.'\n }\n\n // HTTP 401\n if (error.name === 'DataverseError' && msg.includes('401')) {\n return 'Authentication expired or invalid. Run `dvx auth login` to re-authenticate.'\n }\n\n // HTTP 403\n if (error.name === 'DataverseError' && msg.includes('403')) {\n return 'Check that the authenticated user/app has the required security role in Dataverse.'\n }\n\n // JSON parse errors in --json flag\n if (msg.includes('JSON') || msg.includes('Unexpected token')) {\n if (args.includes('--json')) {\n return \"Ensure --json value is valid JSON. Use single quotes around the value: --json '{\\\"name\\\": \\\"value\\\"}'\"\n }\n }\n\n return undefined\n}\n\nfunction getOutputFormat(argv: string[]): string | undefined {\n const idx = argv.indexOf('--output')\n return idx >= 0 ? argv[idx + 1] : undefined\n}\n\nasync function main(): Promise<void> {\n try {\n await program.parseAsync(process.argv)\n } catch (error) {\n const outputFormat = getOutputFormat(process.argv)\n\n if (error instanceof Error) {\n if (outputFormat === 'json') {\n const hint = getHint(error, process.argv)\n const payload: Record<string, string> = {\n error: error.message,\n code: error.name,\n }\n if (hint) payload['hint'] = hint\n console.log(JSON.stringify(payload))\n } else {\n logError(error.message)\n const hint = getHint(error, process.argv)\n if (hint) {\n logInfo(hint)\n }\n }\n if (process.env['DVX_DEBUG'] === 'true') {\n console.error(error.stack)\n }\n } else {\n if (outputFormat === 'json') {\n console.log(JSON.stringify({ error: String(error), code: 'UnknownError' }))\n } else {\n console.error('Unknown error:', error)\n }\n }\n process.exit(1)\n }\n}\n\nexport default main\n\nmain()\n","import { PublicClientApplication } from '@azure/msal-node'\nimport { Client } from '@microsoft/microsoft-graph-client'\nimport * as clack from '@clack/prompts'\nimport { AuthProfile } from '../auth/auth-profile.js'\nimport { AuthManager } from '../auth/auth-manager.js'\nimport { MsalCachePlugin } from '../auth/msal-cache-plugin.js'\nimport { createClient } from '../client/create-client.js'\nimport { openBrowser } from '../utils/browser.js'\nimport { validateUrl } from '../utils/validation.js'\nimport { promptUrl, createSpinner, logStep, logSuccess, logWarn, logInfo, isInteractive } from '../utils/cli.js'\nimport * as path from 'node:path'\n\n// Well-known dvx bootstrapper app — multi-tenant, delegated Application.ReadWrite.All + CRM\nconst DVX_BOOTSTRAPPER_CLIENT_ID = '73f809fb-5469-4956-85f9-e0141af82d90'\n\nconst MANUAL_INSTRUCTIONS = `\nManual Setup Instructions:\n1. Go to https://portal.azure.com → Azure Active Directory → App registrations\n2. Click \"New registration\", set name to \"dvx\", type \"Single tenant\"\n3. Go to the new app → Certificates & secrets → New client secret\n4. Copy the Application (client) ID and the secret value\n5. In Dataverse admin, create an Application User with the client ID\n6. Assign the \"System Administrator\" or relevant security role\n`\n\nexport interface AuthLoginOptions {\n name: string\n url?: string | undefined\n tenantId?: string | undefined\n clientId?: string | undefined\n clientSecret?: string | undefined\n servicePrincipal?: boolean | undefined\n}\n\ninterface BootstrapSession {\n pca: PublicClientApplication\n tenantId: string\n}\n\nasync function bootstrapSignIn(tenantId: string | undefined): Promise<BootstrapSession> {\n const authority = tenantId\n ? `https://login.microsoftonline.com/${tenantId}`\n : 'https://login.microsoftonline.com/organizations'\n\n const cacheFilePath = path.join(process.cwd(), '.dvx', 'msal-cache-bootstrapper.json')\n const pca = new PublicClientApplication({\n auth: {\n clientId: DVX_BOOTSTRAPPER_CLIENT_ID,\n authority,\n },\n cache: {\n cachePlugin: new MsalCachePlugin(cacheFilePath),\n },\n })\n\n // Try silent first, then interactive\n const scopes = ['https://globaldisco.crm.dynamics.com//user_impersonation']\n const accounts = await pca.getAllAccounts()\n let discoveredTenantId = tenantId\n\n if (accounts.length > 0 && accounts[0]) {\n try {\n const result = await pca.acquireTokenSilent({ account: accounts[0], scopes })\n if (result?.accessToken && result.account?.tenantId) {\n return { pca, tenantId: discoveredTenantId ?? result.account.tenantId }\n }\n } catch {\n // Fall through to interactive\n }\n }\n\n const result = await pca.acquireTokenInteractive({\n scopes,\n openBrowser: async (url) => { openBrowser(url) },\n successTemplate: '<h1>Authentication complete. You may close this tab.</h1>',\n errorTemplate: '<h1>Authentication failed: {error}</h1>',\n })\n\n if (!result?.accessToken) {\n throw new Error('Failed to acquire token during sign-in')\n }\n\n discoveredTenantId = discoveredTenantId ?? result.account?.tenantId\n if (!discoveredTenantId) {\n throw new Error('Could not determine tenant ID from sign-in. Pass --tenant-id explicitly.')\n }\n\n return { pca, tenantId: discoveredTenantId }\n}\n\ninterface DiscoveredEnvironment {\n url: string\n friendlyName: string\n uniqueName: string\n state: string\n version: string\n}\n\nasync function discoverEnvironments(pca: PublicClientApplication): Promise<DiscoveredEnvironment[]> {\n const scopes = ['https://globaldisco.crm.dynamics.com//user_impersonation']\n const accounts = await pca.getAllAccounts()\n\n let accessToken: string | undefined\n\n if (accounts.length > 0 && accounts[0]) {\n try {\n const result = await pca.acquireTokenSilent({ account: accounts[0], scopes })\n accessToken = result?.accessToken\n } catch {\n // Can't get token silently\n }\n }\n\n if (!accessToken) {\n const result = await pca.acquireTokenInteractive({\n scopes,\n openBrowser: async (url) => { openBrowser(url) },\n successTemplate: '<h1>Authentication complete. You may close this tab.</h1>',\n errorTemplate: '<h1>Authentication failed: {error}</h1>',\n })\n accessToken = result?.accessToken\n }\n\n if (!accessToken) {\n throw new Error('Failed to acquire discovery token')\n }\n\n const response = await fetch('https://globaldisco.crm.dynamics.com/api/discovery/v2.0/Instances', {\n headers: { Authorization: `Bearer ${accessToken}` },\n })\n\n if (!response.ok) {\n throw new Error(`Discovery API returned ${response.status}: ${response.statusText}`)\n }\n\n const data = await response.json() as { value: Array<{ Url: string; FriendlyName: string; UniqueName: string; State: number; Version: string }> }\n\n return data.value\n .filter((env) => env.State === 0) // Only enabled environments\n .map((env) => ({\n url: env.Url,\n friendlyName: env.FriendlyName,\n uniqueName: env.UniqueName,\n state: env.State === 0 ? 'Enabled' : 'Disabled',\n version: env.Version,\n }))\n}\n\nasync function selectEnvironment(environments: DiscoveredEnvironment[]): Promise<string> {\n const options: Array<{ value: string; label: string; hint?: string }> = environments.map((env) => ({\n value: env.url,\n label: env.friendlyName || env.uniqueName,\n hint: env.url,\n }))\n\n options.push({\n value: '__manual__',\n label: 'Enter URL manually',\n hint: 'Specify a Dataverse environment URL',\n })\n\n const selected = await clack.select({\n message: 'Select a Dataverse environment',\n options,\n })\n\n if (clack.isCancel(selected)) {\n clack.cancel('Login cancelled.')\n process.exit(0)\n }\n\n if (selected === '__manual__') {\n const url = await clack.text({\n message: 'Dataverse environment URL',\n placeholder: 'https://org.crm.dynamics.com',\n validate: (value) => {\n if (!value) return 'Please enter a valid URL'\n try {\n new URL(value)\n } catch {\n return 'Please enter a valid URL'\n }\n },\n })\n\n if (clack.isCancel(url)) {\n clack.cancel('Login cancelled.')\n process.exit(0)\n }\n\n return url as string\n }\n\n return selected as string\n}\n\nasync function acquireGraphToken(pca: PublicClientApplication): Promise<string> {\n const scopes = ['https://graph.microsoft.com/Application.ReadWrite.All']\n const accounts = await pca.getAllAccounts()\n\n if (accounts.length > 0 && accounts[0]) {\n try {\n const result = await pca.acquireTokenSilent({ account: accounts[0], scopes })\n if (result?.accessToken) return result.accessToken\n } catch {\n // Fall through to interactive\n }\n }\n\n const result = await pca.acquireTokenInteractive({\n scopes,\n openBrowser: async (url) => { openBrowser(url) },\n successTemplate: '<h1>Authentication complete. You may close this tab.</h1>',\n errorTemplate: '<h1>Authentication failed: {error}</h1>',\n })\n\n if (!result?.accessToken) {\n throw new Error('Failed to acquire Graph API token')\n }\n\n return result.accessToken\n}\n\nasync function provisionViaGraph(pca: PublicClientApplication): Promise<string> {\n const accessToken = await acquireGraphToken(pca)\n\n const graphClient = Client.init({\n authProvider: (done) => { done(null, accessToken) },\n })\n\n // 1. Create app registration with redirect URI for PKCE\n logStep('Creating app registration \"dvx-service\"...')\n const app = await graphClient.api('/applications').post({\n displayName: 'dvx-service',\n signInAudience: 'AzureADMyOrg',\n publicClient: {\n redirectUris: ['http://localhost'],\n },\n requiredResourceAccess: [\n {\n resourceAppId: '00000007-0000-0000-c000-000000000000',\n resourceAccess: [\n { id: '78ce3f0f-a1ce-49c2-8cde-64b5c0896db4', type: 'Scope' },\n ],\n },\n ],\n }) as { appId: string; id: string }\n\n logSuccess(`App created: ${app.appId}`)\n\n // 2. Create service principal\n logStep('Creating service principal...')\n await graphClient.api('/servicePrincipals').post({\n appId: app.appId,\n })\n logSuccess('Service principal created')\n\n // 3. Grant admin consent for Dynamics CRM user_impersonation\n logStep('Granting admin consent for Dataverse access...')\n try {\n const crmSp = await graphClient.api('/servicePrincipals')\n .filter(\"appId eq '00000007-0000-0000-c000-000000000000'\")\n .select('id')\n .get() as { value: Array<{ id: string }> }\n\n const dvxSp = await graphClient.api('/servicePrincipals')\n .filter(`appId eq '${app.appId}'`)\n .select('id')\n .get() as { value: Array<{ id: string }> }\n\n if (crmSp.value[0] && dvxSp.value[0]) {\n await graphClient.api('/oauth2PermissionGrants').post({\n clientId: dvxSp.value[0].id,\n consentType: 'AllPrincipals',\n resourceId: crmSp.value[0].id,\n scope: 'user_impersonation',\n })\n logSuccess('Admin consent granted')\n }\n } catch {\n logWarn('Could not auto-grant consent (may require Global Admin). Users will be prompted on first login.')\n }\n\n return app.appId\n}\n\nexport async function authLogin(options: AuthLoginOptions): Promise<void> {\n if (options.servicePrincipal) {\n if (!options.url) {\n throw new Error('Environment URL required for service principal auth. Pass --url.')\n }\n const envUrl = validateUrl(options.url)\n const clientSecret = options.clientSecret ?? process.env['DATAVERSE_CLIENT_SECRET']\n if (!clientSecret) {\n throw new Error('Client secret required. Pass --client-secret or set DATAVERSE_CLIENT_SECRET.')\n }\n if (!options.clientId) {\n throw new Error('Client ID required for service principal auth. Pass --client-id.')\n }\n if (!options.tenantId) {\n throw new Error('Tenant ID required for service principal auth. Pass --tenant-id.')\n }\n\n const profile: AuthProfile = {\n name: options.name,\n type: 'service-principal',\n environmentUrl: envUrl,\n tenantId: options.tenantId,\n clientId: options.clientId,\n clientSecret,\n }\n\n const manager = new AuthManager()\n manager.createProfile(profile)\n\n process.env['DATAVERSE_CLIENT_SECRET'] = clientSecret\n\n const spSpinner = createSpinner()\n spSpinner.start('Validating connection...')\n let entityCount: number\n try {\n const { client } = await createClient()\n const entityList = await client.listEntities()\n entityCount = entityList.length\n spSpinner.stop(`Connected — found ${entityCount} entities`)\n } catch (err) {\n spSpinner.error('Connection failed')\n throw err\n }\n console.log(JSON.stringify({ profile: options.name, type: 'service-principal', status: 'logged_in', entityCount }))\n return\n }\n\n // ── Delegated flow ──────────────────────────────────────────\n\n if (isInteractive()) clack.intro('dvx auth login')\n\n let envUrl = options.url ? validateUrl(options.url) : undefined\n let tenantId = options.tenantId\n let clientId = options.clientId\n let session: BootstrapSession | undefined\n\n // Step 1: If no URL, sign in and discover environments\n if (!envUrl) {\n const s = createSpinner()\n s.start('Signing in to discover environments...')\n\n try {\n session = await bootstrapSignIn(tenantId)\n tenantId = session.tenantId\n s.stop('Signed in')\n } catch (err) {\n s.stop('Sign-in failed')\n const message = err instanceof Error ? err.message : String(err)\n logWarn(`Could not sign in for discovery: ${message}`)\n\n envUrl = validateUrl(await promptUrl('Dataverse environment URL'))\n }\n\n if (!envUrl && session) {\n const s2 = createSpinner()\n s2.start('Discovering environments...')\n\n try {\n const environments = await discoverEnvironments(session.pca)\n s2.stop(`Found ${environments.length} environment${environments.length === 1 ? '' : 's'}`)\n\n if (environments.length > 0) {\n envUrl = validateUrl(await selectEnvironment(environments))\n } else {\n logWarn('No Dataverse environments found for this account.')\n envUrl = validateUrl(await promptUrl('Dataverse environment URL'))\n }\n } catch (err) {\n s2.stop('Discovery failed')\n const message = err instanceof Error ? err.message : String(err)\n logWarn(`Discovery failed: ${message}`)\n\n envUrl = validateUrl(await promptUrl('Dataverse environment URL'))\n }\n }\n }\n\n if (!envUrl) {\n throw new Error('No environment URL determined. Pass --url explicitly.')\n }\n\n // Step 2: Auto-provision app registration if no client-id\n if (!clientId) {\n try {\n if (!session) {\n const s = createSpinner()\n s.start('Signing in for app registration...')\n session = await bootstrapSignIn(tenantId)\n tenantId = session.tenantId\n s.stop('Signed in')\n }\n\n clientId = await provisionViaGraph(session.pca)\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err)\n logWarn(`Automated app registration failed: ${message}`)\n logInfo(MANUAL_INSTRUCTIONS)\n\n const enteredClientId = await clack.text({ message: 'Enter client ID from app registration' })\n if (clack.isCancel(enteredClientId)) {\n clack.cancel('Login cancelled.')\n process.exit(0)\n }\n clientId = enteredClientId as string\n\n if (!tenantId) {\n const enteredTenantId = await clack.text({ message: 'Enter Entra tenant ID' })\n if (clack.isCancel(enteredTenantId)) {\n clack.cancel('Login cancelled.')\n process.exit(0)\n }\n tenantId = enteredTenantId as string\n }\n }\n }\n\n if (!tenantId) {\n throw new Error('Could not determine tenant ID. Pass --tenant-id explicitly.')\n }\n\n // Step 3: Create profile and sign in to Dataverse\n const profile: AuthProfile = {\n name: options.name,\n type: 'delegated',\n environmentUrl: envUrl,\n tenantId,\n clientId,\n }\n\n const manager = new AuthManager()\n manager.createProfile(profile)\n\n const finalSpinner = createSpinner()\n finalSpinner.start('Signing in to Dataverse...')\n await manager.getToken(options.name)\n finalSpinner.stop('Signed in')\n\n if (isInteractive()) clack.outro(`Logged in as '${options.name}' → ${envUrl}`)\n console.log(JSON.stringify({ profile: options.name, type: 'delegated', status: 'logged_in' }))\n}\n\nexport async function authLogout(options: { all?: boolean | undefined }): Promise<void> {\n const manager = new AuthManager()\n\n if (options.all) {\n manager.deleteAllProfiles()\n console.log('All auth profiles removed.')\n return\n }\n\n const active = manager.getActiveProfile()\n manager.deleteProfile(active.name)\n console.log(`Profile '${active.name}' removed.`)\n}\n","export interface TableOptions {\n dimHeaders?: boolean\n showRowCount?: boolean\n}\n\nexport function renderTable(rows: string[][], headers?: string[], options?: TableOptions): string {\n const allRows = headers ? [headers, ...rows] : rows\n if (allRows.length === 0) return ''\n\n const colCount = Math.max(...allRows.map((r) => r.length))\n const colWidths: number[] = []\n\n for (let col = 0; col < colCount; col++) {\n colWidths.push(Math.max(...allRows.map((r) => (r[col] ?? '').length)))\n }\n\n const lines: string[] = []\n\n for (let i = 0; i < allRows.length; i++) {\n const row = allRows[i]!\n const formatted = row.map((cell, col) => {\n let display = cell\n if (headers && i === 0 && options?.dimHeaders) {\n display = `\\x1b[2m${cell}\\x1b[0m`\n }\n if (col === row.length - 1) return display\n return display + ' '.repeat(Math.max(0, (colWidths[col] ?? 0) + 2 - cell.length))\n }).join('')\n lines.push(formatted)\n\n if (headers && i === 0) {\n lines.push('-'.repeat(colWidths.reduce((sum, w) => sum + w + 2, 0)))\n }\n }\n\n if (options?.showRowCount) {\n lines.push(`(${rows.length} rows)`)\n }\n\n return lines.join('\\n')\n}\n","import { createClient } from '../client/create-client.js'\nimport { renderTable } from '../utils/table.js'\n\ninterface AuthListOptions {\n output: 'json' | 'table'\n}\n\nexport async function authList(options: AuthListOptions): Promise<void> {\n const { authManager } = await createClient()\n const profiles = authManager.listProfiles()\n\n if (profiles.length === 0) {\n console.log('No auth profiles configured.')\n return\n }\n\n if (options.output === 'json') {\n console.log(JSON.stringify(profiles.map((p) => ({\n name: p.name,\n active: p.active,\n environmentUrl: p.profile.environmentUrl,\n })), null, 2))\n } else {\n const rows = profiles.map((p) => {\n const marker = p.active ? '*' : ' '\n return [marker, p.name, p.profile.environmentUrl]\n })\n console.log(renderTable(rows, [' ', 'Name', 'URL']))\n }\n}\n","import { createClient } from '../client/create-client.js'\nimport { ValidationError } from '../errors.js'\n\nexport async function authSelect(profileName: string): Promise<void> {\n if (!profileName.trim()) {\n throw new ValidationError('Profile name must be a non-empty string')\n }\n const { authManager } = await createClient()\n authManager.selectProfile(profileName)\n console.log(`Active profile switched to '${profileName}'.`)\n}\n","import { createClient } from '../client/create-client.js'\nimport { renderTable } from '../utils/table.js'\nimport { createSpinner } from '../utils/cli.js'\n\ninterface EntitiesOptions {\n output: 'json' | 'table' | 'ndjson'\n}\n\nexport async function entities(options: EntitiesOptions): Promise<void> {\n const { client } = await createClient()\n\n const s = createSpinner()\n s.start('Fetching entities...')\n let entityList: Awaited<ReturnType<typeof client.listEntities>>\n try {\n entityList = await client.listEntities()\n } catch (err) {\n s.error('Failed to fetch entities')\n throw err\n }\n s.stop(`Found ${entityList.length} entities`)\n\n if (options.output === 'json') {\n console.log(JSON.stringify(entityList, null, 2))\n } else if (options.output === 'ndjson') {\n for (const e of entityList) {\n console.log(JSON.stringify({ name: e.logicalName, displayName: e.displayName, entitySetName: e.entitySetName }))\n }\n } else {\n if (entityList.length === 0) {\n console.log('No entities found.')\n return\n }\n\n const rows = entityList.map((e) => [e.logicalName, e.displayName, e.entitySetName])\n console.log(renderTable(rows, ['LogicalName', 'DisplayName', 'EntitySetName']))\n }\n}\n","import { createClient } from '../client/create-client.js'\nimport { renderTable } from '../utils/table.js'\nimport { createSpinner } from '../utils/cli.js'\n\ninterface SchemaOptions {\n output: 'json' | 'table'\n noCache: boolean\n refresh?: boolean\n refreshAll?: boolean\n}\n\nexport async function schema(entityName: string, options: SchemaOptions): Promise<void> {\n const { client } = await createClient()\n\n if (options.refreshAll) {\n client.clearSchemaCache()\n } else if (options.refresh) {\n client.invalidateSchema(entityName)\n }\n\n const s = createSpinner()\n s.start(`Fetching schema for ${entityName}...`)\n let entry: Awaited<ReturnType<typeof client.getEntitySchema>>\n try {\n entry = await client.getEntitySchema(entityName, options.noCache)\n } catch (err) {\n s.error('Failed to fetch schema')\n throw err\n }\n s.stop(`Schema loaded: ${entry.attributes.length} attributes`)\n\n if (options.output === 'table') {\n const rows = entry.attributes.map((a) => [\n a.logicalName,\n a.displayName,\n a.attributeType,\n a.requiredLevel === 'ApplicationRequired' || a.requiredLevel === 'SystemRequired' ? 'Yes' : 'No',\n ])\n console.log(renderTable(rows, ['LogicalName', 'DisplayName', 'Type', 'Required']))\n } else {\n console.log(JSON.stringify(entry, null, 2))\n }\n}\n","import { readFileSync } from 'node:fs'\nimport { createClient } from '../client/create-client.js'\nimport { validateFetchXml } from '../utils/fetchxml.js'\nimport { ValidationError } from '../errors.js'\nimport { renderTable } from '../utils/table.js'\nimport { createSpinner } from '../utils/cli.js'\n\ninterface QueryOptions {\n odata?: string | undefined\n fetchxml?: string | undefined\n file?: string | undefined\n fields?: string | undefined\n pageAll: boolean\n maxRows?: number | undefined\n output: 'json' | 'ndjson' | 'table'\n dryRun?: boolean | undefined\n}\n\nfunction renderRecordTable(records: Record<string, unknown>[]): void {\n if (records.length === 0) {\n console.log('No records found.')\n return\n }\n const keys = Object.keys(records[0]!).filter((k) => !k.startsWith('@'))\n const rows = records.map((r) => keys.map((k) => String(r[k] ?? '')))\n console.log(renderTable(rows, keys))\n}\n\nexport async function query(options: QueryOptions): Promise<void> {\n const { client } = await createClient({ dryRun: options.dryRun })\n\n let fetchXmlContent: string | undefined\n let entityName: string | undefined\n\n if (options.file) {\n const content = readFileSync(options.file, 'utf-8')\n if (content.trimStart().startsWith('<')) {\n fetchXmlContent = content\n } else {\n options.odata = content.trim()\n }\n }\n\n if (options.fetchxml) {\n fetchXmlContent = options.fetchxml\n }\n\n const s = createSpinner()\n\n if (fetchXmlContent) {\n validateFetchXml(fetchXmlContent)\n\n const entityMatch = /entity\\s+name=[\"']([^\"']+)[\"']/i.exec(fetchXmlContent)\n entityName = entityMatch?.[1]\n if (!entityName) {\n throw new ValidationError('Could not determine entity name from FetchXML')\n }\n\n s.start('Querying...')\n\n if (options.output === 'ndjson' || options.pageAll) {\n let count = 0\n try {\n await client.queryFetchXml(entityName, fetchXmlContent, (record) => {\n count++\n console.log(JSON.stringify(record))\n })\n } catch (err) {\n s.error('Query failed')\n throw err\n }\n s.stop(`Query complete: ${count} records`)\n } else {\n let records: unknown[]\n try {\n records = await client.queryFetchXml(entityName, fetchXmlContent)\n } catch (err) {\n s.error('Query failed')\n throw err\n }\n s.stop(`Query complete: ${records.length} records`)\n\n if (options.output === 'json') {\n console.log(JSON.stringify(records, null, 2))\n } else {\n renderRecordTable(records as Record<string, unknown>[])\n }\n }\n return\n }\n\n if (!options.odata) {\n throw new ValidationError('Either --odata, --fetchxml, or --file is required')\n }\n\n const odataParts = options.odata.split('?')\n const entitySetName = odataParts[0] ?? ''\n const odataQuery = odataParts.slice(1).join('?')\n\n if (!entitySetName) {\n throw new ValidationError('OData expression must start with the entity set name (e.g., \"accounts?$filter=name eq \\'test\\'\")')\n }\n\n const fields = options.fields?.split(',').map((f) => f.trim())\n\n s.start('Querying...')\n\n if (options.output === 'ndjson' || options.pageAll) {\n let count = 0\n try {\n await client.query(entitySetName, odataQuery, {\n fields,\n pageAll: options.pageAll,\n maxRows: options.maxRows,\n onRecord: (record) => {\n count++\n console.log(JSON.stringify(record))\n },\n onProgress: (info) => {\n s.message(`Page ${info.pageNumber} — ${info.recordCount} records...`)\n },\n })\n } catch (err) {\n s.error('Query failed')\n throw err\n }\n s.stop(`Query complete: ${count} records`)\n } else {\n let records: Record<string, unknown>[]\n try {\n records = await client.query(entitySetName, odataQuery, {\n fields,\n pageAll: false,\n maxRows: options.maxRows,\n onProgress: (info) => {\n s.message(`Page ${info.pageNumber} — ${info.recordCount} records...`)\n },\n })\n } catch (err) {\n s.error('Query failed')\n throw err\n }\n s.stop(`Query complete: ${records.length} records`)\n\n if (options.output === 'json') {\n console.log(JSON.stringify(records, null, 2))\n } else {\n renderRecordTable(records)\n }\n }\n}\n","import { createClient } from '../client/create-client.js'\nimport { validateEntityName, validateGuid } from '../utils/validation.js'\nimport { renderTable } from '../utils/table.js'\nimport { createSpinner } from '../utils/cli.js'\n\ninterface GetOptions {\n fields?: string\n output: 'json' | 'table'\n}\n\nexport async function get(entityName: string, id: string, options: GetOptions): Promise<void> {\n validateEntityName(entityName)\n const validatedId = validateGuid(id)\n const { client } = await createClient()\n\n const fields = options.fields?.split(',').map((f) => f.trim()).filter((f) => f.length > 0)\n\n const s = createSpinner()\n s.start(`Fetching ${entityName} ${validatedId}...`)\n let record: Awaited<ReturnType<typeof client.getRecord>>\n try {\n record = await client.getRecord(entityName, validatedId, fields)\n } catch (err) {\n s.error('Failed to fetch record')\n throw err\n }\n s.stop('Record loaded')\n\n if (options.output === 'json') {\n console.log(JSON.stringify(record, null, 2))\n } else {\n const entries = Object.entries(record).filter(([k]) => !k.startsWith('@'))\n if (entries.length === 0) {\n console.log('No fields returned.')\n return\n }\n const rows = entries.map(([key, value]) => [key, String(value ?? '')])\n console.log(renderTable(rows, ['Field', 'Value']))\n }\n}\n","import { ValidationError } from '../errors.js'\n\nexport function parseJsonPayload(raw: string): Record<string, unknown> {\n let parsed: unknown\n try {\n parsed = JSON.parse(raw)\n } catch {\n throw new ValidationError('Invalid JSON payload')\n }\n if (typeof parsed !== 'object' || parsed === null || Array.isArray(parsed)) {\n throw new ValidationError('JSON payload must be an object')\n }\n return parsed as Record<string, unknown>\n}\n","export type OutputFormat = 'json' | 'table' | 'ndjson';\n\nexport function formatMutationResult(\n result: Record<string, unknown> | null,\n opts: { format: OutputFormat; id?: string }\n): void {\n const payload = result ?? (opts.id ? { ok: true, id: opts.id } : { ok: true });\n if (opts.format === 'json') {\n console.log(JSON.stringify(payload));\n } else {\n // table: print key-value pairs\n const entries = Object.entries(payload);\n if (entries.length === 0) {\n console.log('ok');\n } else {\n for (const [k, v] of entries) {\n console.log(`${k}: ${String(v)}`);\n }\n }\n }\n}\n","import { createClient } from '../client/create-client.js'\nimport { parseJsonPayload } from '../utils/parse-json.js'\nimport { validateEntityName } from '../utils/validation.js'\nimport { formatMutationResult } from '../utils/output.js'\nimport { BaseMutationOptions } from './types.js'\nimport { createSpinner, logMutationSuccess } from '../utils/cli.js'\n\ninterface CreateOptions extends BaseMutationOptions {\n json: string\n}\n\nexport async function createRecord(entityName: string, options: CreateOptions): Promise<void> {\n validateEntityName(entityName)\n const { client } = await createClient({ dryRun: options.dryRun, callerObjectId: options.callerObjectId })\n\n const data = parseJsonPayload(options.json)\n\n const s = createSpinner()\n s.start(`Creating ${entityName}...`)\n let id: string\n try {\n id = await client.createRecord(entityName, data)\n } catch (err) {\n s.error('Create failed')\n throw err\n }\n s.stop(`Created ${entityName}`)\n logMutationSuccess(`Created ${entityName} ${id}`)\n formatMutationResult(null, { format: options.output ?? 'table', id })\n}\n","import { createClient } from '../client/create-client.js'\nimport { parseJsonPayload } from '../utils/parse-json.js'\nimport { validateEntityName, validateGuid } from '../utils/validation.js'\nimport { formatMutationResult } from '../utils/output.js'\nimport { BaseMutationOptions } from './types.js'\nimport { createSpinner, logMutationSuccess } from '../utils/cli.js'\n\ninterface UpdateOptions extends BaseMutationOptions {\n json: string\n}\n\nexport async function updateRecord(entityName: string, id: string, options: UpdateOptions): Promise<void> {\n validateEntityName(entityName)\n validateGuid(id)\n const { client } = await createClient({ dryRun: options.dryRun, callerObjectId: options.callerObjectId })\n\n const data = parseJsonPayload(options.json)\n\n const s = createSpinner()\n s.start(`Updating ${entityName} ${id}...`)\n try {\n await client.updateRecord(entityName, id, data)\n } catch (err) {\n s.error('Update failed')\n throw err\n }\n s.stop(`Updated ${entityName}`)\n logMutationSuccess(`Updated ${entityName} ${id}`)\n formatMutationResult(null, { format: options.output ?? 'table' })\n}\n","import { createClient } from '../client/create-client.js'\nimport { ValidationError } from '../errors.js'\nimport { parseJsonPayload } from '../utils/parse-json.js'\nimport { validateEntityName } from '../utils/validation.js'\nimport { formatMutationResult } from '../utils/output.js'\nimport { BaseMutationOptions } from './types.js'\nimport { createSpinner, logMutationSuccess } from '../utils/cli.js'\n\ninterface UpsertOptions extends BaseMutationOptions {\n matchField: string\n json: string\n}\n\nexport async function upsertRecord(entityName: string, options: UpsertOptions): Promise<void> {\n validateEntityName(entityName)\n const { client } = await createClient({ dryRun: options.dryRun, callerObjectId: options.callerObjectId })\n\n const data = parseJsonPayload(options.json)\n\n const matchValue = data[options.matchField]\n if (matchValue === undefined) {\n throw new ValidationError(`Match field '${options.matchField}' not found in JSON payload`)\n }\n\n const schema = await client.getEntitySchema(entityName)\n\n const attr = schema.attributes.find((a) => a.logicalName === options.matchField)\n if (!attr) {\n throw new ValidationError(`Unknown field: ${options.matchField}`)\n }\n\n const escapedValue = typeof matchValue === 'string'\n ? `'${matchValue.replace(/'/g, \"''\")}'`\n : String(matchValue)\n const odata = `$filter=${options.matchField} eq ${escapedValue}&$select=${schema.primaryIdAttribute}`\n\n const s = createSpinner()\n s.start(`Upserting ${entityName}...`)\n try {\n const records = await client.query(schema.entitySetName, odata, { pageAll: false, maxRows: 1 })\n\n if (records.length > 0) {\n const existingId = String(records[0]![schema.primaryIdAttribute])\n await client.updateRecord(entityName, existingId, data)\n s.stop(`Upserted ${entityName}`)\n logMutationSuccess(`Upserted ${entityName} ${existingId} (updated)`)\n formatMutationResult({ action: 'updated', id: existingId }, { format: options.output ?? 'table', id: existingId })\n } else {\n const id = await client.createRecord(entityName, data)\n s.stop(`Upserted ${entityName}`)\n logMutationSuccess(`Upserted ${entityName} ${id} (created)`)\n formatMutationResult({ action: 'created', id }, { format: options.output ?? 'table', id })\n }\n } catch (err) {\n s.error('Upsert failed')\n throw err\n }\n}\n","import { createClient } from '../client/create-client.js'\nimport { validateEntityName, validateGuid } from '../utils/validation.js'\nimport { formatMutationResult } from '../utils/output.js'\nimport { ValidationError } from '../errors.js'\nimport { BaseMutationOptions } from './types.js'\nimport { isInteractive, promptConfirmClack, createSpinner, logMutationSuccess } from '../utils/cli.js'\n\ninterface DeleteOptions extends BaseMutationOptions {\n confirm?: boolean\n}\n\nexport async function deleteRecord(entityName: string, id: string, options: DeleteOptions): Promise<void> {\n validateEntityName(entityName)\n validateGuid(id)\n\n if (!options.confirm && !options.dryRun) {\n if (isInteractive()) {\n const confirmed = await promptConfirmClack(`Delete record '${id}' from '${entityName}'?`)\n if (!confirmed) {\n process.stderr.write('Aborted\\n')\n return\n }\n } else {\n throw new ValidationError('Non-interactive mode requires --confirm flag for delete operations')\n }\n }\n\n const { client } = await createClient({ dryRun: options.dryRun, callerObjectId: options.callerObjectId })\n\n const s = createSpinner()\n s.start(`Deleting ${entityName} ${id}...`)\n try {\n await client.deleteRecord(entityName, id)\n } catch (err) {\n s.error('Delete failed')\n throw err\n }\n s.stop(`Deleted ${entityName}`)\n logMutationSuccess(`Deleted ${id} from ${entityName}`)\n formatMutationResult(null, { format: options.output ?? 'table' })\n}\n","import { readFile } from 'node:fs/promises'\nimport { z } from 'zod'\nimport { createClient } from '../client/create-client.js'\nimport { buildBatchBody, chunkArray, type BatchOperation } from '../utils/batch-builder.js'\nimport { ValidationError } from '../errors.js'\nimport { formatMutationResult } from '../utils/output.js'\nimport { BaseMutationOptions } from './types.js'\nimport { createSpinner, logSuccess } from '../utils/cli.js'\n\nconst BatchOperationSchema = z.object({\n method: z.enum(['GET', 'POST', 'PATCH', 'DELETE']),\n path: z.string(),\n headers: z.record(z.string(), z.string()).optional(),\n body: z.unknown().optional(),\n contentId: z.string().optional(),\n})\n\nconst BatchFileSchema = z.array(BatchOperationSchema)\n\ninterface BatchOptions extends BaseMutationOptions {\n file: string\n atomic: boolean\n}\n\nexport async function batch(options: BatchOptions): Promise<void> {\n const { client } = await createClient({ dryRun: options.dryRun, callerObjectId: options.callerObjectId })\n\n const content = await readFile(options.file, 'utf-8')\n let parsed: unknown\n try {\n parsed = JSON.parse(content)\n } catch {\n throw new ValidationError('Invalid JSON in batch file')\n }\n\n const operations = BatchFileSchema.parse(parsed) as BatchOperation[]\n const chunks = chunkArray(operations, 1000)\n const totalOps = operations.length\n\n const s = createSpinner()\n\n for (let i = 0; i < chunks.length; i++) {\n const chunk = chunks[i]!\n const boundary = `batch_dvx_${Date.now()}_${i}`\n\n s.start(`Chunk ${i + 1}/${chunks.length} (${chunk.length} operations)...`)\n\n let result: string\n try {\n const body = buildBatchBody(chunk, boundary, { atomic: options.atomic })\n result = await client.executeBatch(body, boundary)\n } catch (err) {\n s.error(`Chunk ${i + 1}/${chunks.length} failed`)\n throw err\n }\n\n s.stop(`Chunk ${i + 1}/${chunks.length} complete`)\n\n formatMutationResult(\n { chunk: i + 1, totalChunks: chunks.length, operations: chunk.length, responseLength: result.length },\n { format: options.output ?? 'table' }\n )\n }\n\n logSuccess(`Batch complete: ${totalOps} operations across ${chunks.length} chunk${chunks.length === 1 ? '' : 's'}`)\n}\n","import { createClient } from '../client/create-client.js'\nimport { parseJsonPayload } from '../utils/parse-json.js'\nimport { ValidationError } from '../errors.js'\nimport { formatMutationResult } from '../utils/output.js'\nimport { BaseMutationOptions } from './types.js'\nimport { createSpinner, logMutationSuccess } from '../utils/cli.js'\n\ninterface ActionOptions extends BaseMutationOptions {\n json: string\n entity?: string\n id?: string\n}\n\nexport async function actionCommand(actionName: string, options: ActionOptions): Promise<void> {\n if (!!options.entity !== !!options.id) {\n throw new ValidationError('--entity and --id must both be provided for bound actions')\n }\n\n const payload = parseJsonPayload(options.json)\n const { client } = await createClient({ dryRun: options.dryRun, callerObjectId: options.callerObjectId })\n\n const s = createSpinner()\n s.start(`Executing ${actionName}...`)\n let result: unknown\n try {\n result = await client.executeAction(actionName, payload, {\n entityName: options.entity,\n id: options.id,\n })\n } catch (err) {\n s.error('Action failed')\n throw err\n }\n s.stop('Action complete')\n logMutationSuccess(`Executed ${actionName}`)\n\n const resultRecord = (result && typeof result === 'object' && !Array.isArray(result))\n ? result as Record<string, unknown>\n : { result: JSON.stringify(result) }\n\n formatMutationResult(resultRecord, { format: options.output ?? 'table' })\n}\n","import * as clack from '@clack/prompts'\nimport { createClient } from '../client/create-client.js'\nimport { buildBatchBody, type BatchOperation } from '../utils/batch-builder.js'\nimport { renderTable } from '../utils/table.js'\nimport { DataverseError, EntityNotFoundError, ImpersonationPrivilegeError, ValidationError } from '../errors.js'\nimport { createSpinner, isInteractive, logWarn, type SpinnerHandle } from '../utils/cli.js'\nimport type { DataverseClient } from '../client/dataverse-client.js'\n\ntype DemoTier = 'read' | 'write' | 'full'\n\ninterface DemoOptions {\n tier?: DemoTier | undefined\n output?: 'json' | 'table' | undefined\n}\n\ninterface DemoResult {\n name: string\n status: 'pass' | 'skip' | 'fail'\n elapsedMs: number\n error?: string\n}\n\ninterface DemoContext {\n client: DataverseClient\n createdIds: Map<string, string>\n hasOpportunity: boolean\n}\n\ninterface DemoStep {\n name: string\n tier: DemoTier\n callout: string\n run: (ctx: DemoContext, s: SpinnerHandle) => Promise<string | void>\n}\n\nconst DEMO_PREFIX = '[dvx-demo]'\n\nconst TIER_ORDER: DemoTier[] = ['read', 'write', 'full']\n\nfunction callout(msg: string): void {\n const text = `\\u26A1 dvx advantage: ${msg}`\n if (isInteractive()) {\n clack.log.info(text)\n } else {\n process.stderr.write(`${text}\\n`)\n }\n}\n\nasync function selectTier(options: DemoOptions): Promise<DemoTier> {\n if (options.tier) return options.tier\n\n if (!isInteractive()) {\n throw new ValidationError('--tier is required in non-interactive mode (choices: read, write, full)')\n }\n\n const result = await clack.select({\n message: 'Select demo tier',\n options: [\n { value: 'read' as const, label: 'Read', hint: 'Schema discovery, queries, FetchXML — no data changes' },\n { value: 'write' as const, label: 'Write', hint: 'Read + CRUD lifecycle with auto-cleanup' },\n { value: 'full' as const, label: 'Full', hint: 'Write + batch, actions, impersonation, aggregation' },\n ],\n })\n\n if (clack.isCancel(result)) {\n clack.cancel('Demo cancelled.')\n process.exit(0)\n }\n\n return result as DemoTier\n}\n\nasync function checkOpportunityAvailable(client: DataverseClient): Promise<boolean> {\n try {\n await client.getEntitySchema('opportunity')\n return true\n } catch (err) {\n if (err instanceof EntityNotFoundError) return false\n if (err instanceof DataverseError && (err.statusCode === 404 || err.message.includes('does not exist'))) return false\n throw err\n }\n}\n\nfunction logData(text: string): void {\n if (isInteractive()) {\n clack.log.step(text)\n } else {\n console.log(text)\n }\n}\n\nfunction formatRecords(records: Record<string, unknown>[], maxRows = 5): string {\n if (records.length === 0) return '(no records)'\n const subset = records.slice(0, maxRows)\n const keys = Object.keys(subset[0]!)\n const rows = subset.map((r) => keys.map((k) => String(r[k] ?? '')))\n let out = renderTable(rows, keys, { dimHeaders: true })\n if (records.length > maxRows) out += `\\n ... and ${records.length - maxRows} more`\n return out\n}\n\nasync function runStep(step: DemoStep, ctx: DemoContext): Promise<DemoResult> {\n const s = createSpinner()\n const start = performance.now()\n try {\n s.start(step.name)\n const output = await step.run(ctx, s)\n s.stop(step.name)\n if (output) logData(output)\n callout(step.callout)\n return { name: step.name, status: 'pass', elapsedMs: Math.round(performance.now() - start) }\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err)\n s.error(`${step.name} — ${msg}`)\n if (err instanceof ImpersonationPrivilegeError) {\n return { name: step.name, status: 'skip', elapsedMs: Math.round(performance.now() - start), error: msg }\n }\n return { name: step.name, status: 'fail', elapsedMs: Math.round(performance.now() - start), error: msg }\n }\n}\n\nasync function cleanup(client: DataverseClient, createdIds: Map<string, string>): Promise<void> {\n // Delete tracked records in reverse order (contacts before accounts)\n const entries = [...createdIds.entries()].reverse()\n for (const [entity, id] of entries) {\n try {\n await client.deleteRecord(entity, id)\n } catch {\n logWarn(`Cleanup: failed to delete ${entity} ${id}`)\n }\n }\n\n // Sweep for orphan demo records\n try {\n const orphans = await client.query('accounts', `$filter=startswith(name,'${DEMO_PREFIX}')&$select=accountid`)\n for (const orphan of orphans) {\n const id = orphan['accountid'] as string | undefined\n if (id) {\n try {\n await client.deleteRecord('account', id)\n } catch {\n logWarn(`Cleanup: failed to delete orphan account ${id}`)\n }\n }\n }\n } catch {\n logWarn('Cleanup: orphan sweep failed')\n }\n\n try {\n const orphanContacts = await client.query('contacts', `$filter=startswith(firstname,'${DEMO_PREFIX}')&$select=contactid`)\n for (const orphan of orphanContacts) {\n const id = orphan['contactid'] as string | undefined\n if (id) {\n try {\n await client.deleteRecord('contact', id)\n } catch {\n logWarn(`Cleanup: failed to delete orphan contact ${id}`)\n }\n }\n }\n } catch {\n logWarn('Cleanup: contact orphan sweep failed')\n }\n}\n\nfunction renderSummary(results: DemoResult[]): void {\n const rows = results.map((r) => {\n let status: string\n switch (r.status) {\n case 'pass': status = '\\x1b[32mPASS\\x1b[0m'; break\n case 'skip': status = '\\x1b[33mSKIP\\x1b[0m'; break\n case 'fail': status = '\\x1b[31mFAIL\\x1b[0m'; break\n }\n return [r.name, status, `${r.elapsedMs}ms`]\n })\n console.log(renderTable(rows, ['Demo', 'Status', 'Elapsed'], { dimHeaders: true }))\n}\n\nconst ALL_DEMO_STEPS: DemoStep[] = [\n // === Read tier ===\n {\n name: 'List entities',\n tier: 'read',\n callout: 'Full entity catalog with display names — native MCP only exposes pre-configured entities',\n async run(ctx, s) {\n const list = await ctx.client.listEntities()\n s.message(`Found ${list.length} entities`)\n const sample = list.slice(0, 8)\n const rows = sample.map((e) => [e.logicalName, e.displayName, e.entitySetName])\n let out = renderTable(rows, ['Logical Name', 'Display Name', 'Entity Set'], { dimHeaders: true })\n if (list.length > 8) out += `\\n ... and ${list.length - 8} more`\n return out\n },\n },\n {\n name: 'Schema introspection',\n tier: 'read',\n callout: 'Live schema with attribute types and required levels — native MCP has no schema introspection',\n async run(ctx, s) {\n const schema = await ctx.client.getEntitySchema('account')\n s.message(`account: ${schema.attributes.length} attributes`)\n const sample = schema.attributes.slice(0, 8)\n const rows = sample.map((a) => [a.logicalName, a.attributeType, a.requiredLevel])\n let out = renderTable(rows, ['Attribute', 'Type', 'Required'], { dimHeaders: true })\n if (schema.attributes.length > 8) out += `\\n ... and ${schema.attributes.length - 8} more`\n return out\n },\n },\n\n // === Write tier (create data before read steps query it) ===\n {\n name: 'Create account',\n tier: 'write',\n callout: 'Create with auto-schema resolution — dvx maps logical name to entity set automatically',\n async run(ctx) {\n const id = await ctx.client.createRecord('account', {\n name: `${DEMO_PREFIX} Contoso Ltd`,\n description: 'Demo account created by dvx demo — will be auto-cleaned',\n })\n ctx.createdIds.set('account', id)\n return `Created account ${id}`\n },\n },\n {\n name: 'Update account',\n tier: 'write',\n callout: 'Partial update via PATCH — only changed fields sent, not full record replacement',\n async run(ctx) {\n const id = ctx.createdIds.get('account')\n if (!id) throw new Error('No account to update — create step must run first')\n await ctx.client.updateRecord('account', id, {\n websiteurl: 'https://dvx.dev',\n telephone1: '+1-555-DVX-DEMO',\n })\n return `Updated ${id}: websiteurl, telephone1`\n },\n },\n {\n name: 'Upsert contact',\n tier: 'write',\n callout: 'Upsert with alternate key matching — dvx resolves match fields automatically',\n async run(ctx) {\n const accountId = ctx.createdIds.get('account')\n const id = await ctx.client.createRecord('contact', {\n firstname: `${DEMO_PREFIX}`,\n lastname: 'Demo User',\n emailaddress1: 'demo@dvx.dev',\n ...(accountId ? { 'parentcustomerid_account@odata.bind': `/accounts(${accountId})` } : {}),\n })\n ctx.createdIds.set('contact', id)\n return `Created contact ${id}${accountId ? ` (linked to account ${accountId})` : ''}`\n },\n },\n\n // === Read tier (queries — run after write tier creates data) ===\n {\n name: 'OData query',\n tier: 'read',\n callout: 'Full OData $filter/$orderby/$select/$expand — native MCP limited to basic retrieval',\n async run(ctx, s) {\n const results = await ctx.client.query('accounts', \"$filter=startswith(name,'[dvx-demo]')&$orderby=name&$top=5&$select=name,accountid\")\n s.message(`${results.length} account(s) matched`)\n return formatRecords(results)\n },\n },\n {\n name: 'FetchXML with joins',\n tier: 'read',\n callout: 'FetchXML with linked entities and paging — native MCP has no FetchXML support',\n async run(ctx, s) {\n const fetchXml = `<fetch top=\"5\">\n <entity name=\"account\">\n <attribute name=\"name\" />\n <attribute name=\"accountid\" />\n <filter>\n <condition attribute=\"name\" operator=\"like\" value=\"${DEMO_PREFIX}%\" />\n </filter>\n <link-entity name=\"contact\" from=\"parentcustomerid\" to=\"accountid\" link-type=\"outer\">\n <attribute name=\"fullname\" />\n </link-entity>\n </entity>\n</fetch>`\n const results = await ctx.client.queryFetchXml('account', fetchXml) as Record<string, unknown>[]\n s.message(`${results.length} record(s) with linked contacts`)\n return formatRecords(results)\n },\n },\n {\n name: 'Get single record',\n tier: 'read',\n callout: 'Field-level $select on single record — native MCP returns all fields always',\n async run(ctx, s) {\n const list = await ctx.client.query('accounts', '$top=1&$select=accountid,name')\n if (list.length === 0) {\n s.message('No accounts available')\n return\n }\n const id = list[0]!['accountid'] as string\n const record = await ctx.client.getRecord('account', id, ['name', 'createdon'])\n s.message(`Retrieved: ${(record['name'] as string) ?? id}`)\n const keys = Object.keys(record)\n const rows = keys.map((k) => [k, String(record[k] ?? '')])\n return renderTable(rows, ['Field', 'Value'], { dimHeaders: true })\n },\n },\n\n // === Write tier (delete) ===\n {\n name: 'Delete record',\n tier: 'write',\n callout: 'Delete with GUID validation and confirmation — dvx validates before sending to API',\n async run(ctx) {\n const id = ctx.createdIds.get('account')\n if (!id) throw new Error('No account to delete — create step must run first')\n await ctx.client.deleteRecord('account', id)\n ctx.createdIds.delete('account')\n return `Deleted account ${id}`\n },\n },\n\n // === Full tier ===\n {\n name: 'Batch atomic create',\n tier: 'full',\n callout: 'Atomic batch with changeset — all-or-nothing, 1000 ops/request — native MCP has no batch',\n async run(ctx) {\n const ops: BatchOperation[] = Array.from({ length: 5 }, (_, i) => ({\n method: 'POST' as const,\n path: 'accounts',\n body: { name: `${DEMO_PREFIX} Batch ${i + 1}` },\n }))\n const boundary = `batch_dvx_demo_${Date.now()}`\n const body = buildBatchBody(ops, boundary, { atomic: true })\n await ctx.client.executeBatch(body, boundary)\n return `5 accounts created atomically in a single changeset`\n },\n },\n {\n name: 'WhoAmI action',\n tier: 'full',\n callout: 'Custom action execution — call any action/SDK message — native MCP cannot call actions',\n async run(ctx, s) {\n const result = await ctx.client.executeAction('WhoAmI', {}) as Record<string, unknown>\n const userId = result['UserId'] as string | undefined\n if (userId) s.message(`Authenticated as ${userId}`)\n const keys = Object.keys(result)\n const rows = keys.map((k) => [k, String(result[k] ?? '')])\n return renderTable(rows, ['Field', 'Value'], { dimHeaders: true })\n },\n },\n {\n name: 'Impersonated query',\n tier: 'full',\n callout: 'CallerObjectId impersonation — run as another user for audit trails',\n async run(ctx, s) {\n // Use WhoAmI to get current user, then impersonate as self (safe)\n const whoami = await ctx.client.executeAction('WhoAmI', {}) as Record<string, unknown>\n const userId = whoami['UserId'] as string | undefined\n if (!userId) {\n s.message('Could not determine user ID — skipping impersonation')\n return\n }\n const { client: impersonatedClient } = await createClient({ callerObjectId: userId })\n const results = await impersonatedClient.query('accounts', '$top=1&$select=name')\n s.message(`Impersonated query returned ${results.length} record(s)`)\n return formatRecords(results)\n },\n },\n {\n name: 'FetchXML aggregation',\n tier: 'full',\n callout: 'FetchXML aggregation with groupby — server-side analytics, not possible via native MCP',\n async run(ctx, s) {\n const fetchXml = `<fetch aggregate=\"true\">\n <entity name=\"account\">\n <attribute name=\"statecode\" groupby=\"true\" alias=\"state\" />\n <attribute name=\"accountid\" aggregate=\"count\" alias=\"count\" />\n </entity>\n</fetch>`\n const results = await ctx.client.queryFetchXml('account', fetchXml) as Record<string, unknown>[]\n s.message(`${results.length} state group(s)`)\n return formatRecords(results)\n },\n },\n]\n\nexport async function demo(options: DemoOptions): Promise<void> {\n const selectedTier = await selectTier(options)\n\n if (isInteractive()) {\n clack.intro(`dvx demo \\u2014 ${selectedTier} tier`)\n }\n\n const { client } = await createClient()\n const hasOpportunity = await checkOpportunityAvailable(client)\n\n const maxIdx = TIER_ORDER.indexOf(selectedTier)\n const activeSteps = ALL_DEMO_STEPS.filter((s) => TIER_ORDER.indexOf(s.tier) <= maxIdx)\n\n const ctx: DemoContext = { client, createdIds: new Map(), hasOpportunity }\n const results: DemoResult[] = []\n const totalStart = performance.now()\n\n try {\n for (const step of activeSteps) {\n const result = await runStep(step, ctx)\n results.push(result)\n }\n } finally {\n if (ctx.createdIds.size > 0) {\n const s = createSpinner()\n s.start('Cleaning up demo data...')\n await cleanup(client, ctx.createdIds)\n s.stop('Cleanup complete')\n }\n // Always run orphan sweep for batch-created records\n if (TIER_ORDER.indexOf(selectedTier) >= TIER_ORDER.indexOf('full')) {\n const s = createSpinner()\n s.start('Sweeping orphan demo records...')\n await cleanup(client, new Map())\n s.stop('Orphan sweep complete')\n }\n }\n\n const totalMs = Math.round(performance.now() - totalStart)\n const passed = results.filter((r) => r.status === 'pass').length\n\n if (options.output === 'json') {\n console.log(JSON.stringify({\n tier: selectedTier,\n totalMs,\n passed,\n total: results.length,\n results: results.map((r) => ({ name: r.name, status: r.status, elapsedMs: r.elapsedMs, ...(r.error ? { error: r.error } : {}) })),\n }, null, 2))\n } else {\n console.log('')\n renderSummary(results)\n }\n\n if (isInteractive()) {\n clack.outro(`${passed}/${results.length} demos passed in ${totalMs}ms`)\n }\n}\n","export type Shell = 'bash' | 'zsh' | 'powershell';\n\nconst COMMANDS = ['auth', 'entities', 'schema', 'query', 'get', 'create', 'update', 'upsert', 'delete', 'batch', 'action', 'mcp', 'init', 'completion'];\n\nconst BASH_COMPLETION = `\n# dvx bash completion\n_dvx_completion() {\n local cur prev words\n COMPREPLY=()\n cur=\"\\${COMP_WORDS[COMP_CWORD]}\"\n prev=\"\\${COMP_WORDS[COMP_CWORD-1]}\"\n\n local commands=\"${COMMANDS.join(' ')}\"\n local auth_commands=\"create select login list\"\n\n case \"\\${prev}\" in\n dvx) COMPREPLY=($(compgen -W \"\\${commands}\" -- \"\\${cur}\")) ;;\n auth) COMPREPLY=($(compgen -W \"\\${auth_commands}\" -- \"\\${cur}\")) ;;\n completion) COMPREPLY=($(compgen -W \"bash zsh powershell\" -- \"\\${cur}\")) ;;\n *) COMPREPLY=($(compgen -f -- \"\\${cur}\")) ;;\n esac\n}\ncomplete -F _dvx_completion dvx\n`.trim();\n\nconst ZSH_COMPLETION = `\n#compdef dvx\n_dvx() {\n local state\n _arguments \\\\\n '1: :->cmd' \\\\\n '*: :->args'\n case \\$state in\n cmd) _values 'commands' ${COMMANDS.join(' ')} ;;\n args) case \\$words[2] in\n auth) _values 'auth commands' create select login list ;;\n completion) _values 'shells' bash zsh powershell ;;\n esac ;;\n esac\n}\n_dvx \"\\$@\"\n`.trim();\n\nconst POWERSHELL_COMPLETION = `\nRegister-ArgumentCompleter -Native -CommandName dvx -ScriptBlock {\n param(\\$wordToComplete, \\$commandAst, \\$cursorPosition)\n \\$commands = @(${COMMANDS.map(c => `'${c}'`).join(',')})\n \\$commands | Where-Object { \\$_ -like \"\\${wordToComplete}*\" } | ForEach-Object {\n [System.Management.Automation.CompletionResult]::new(\\$_, \\$_, 'ParameterValue', \\$_)\n }\n}\n`.trim();\n\nexport function completion(shell: Shell): void {\n switch (shell) {\n case 'bash': console.log(BASH_COMPLETION); break;\n case 'zsh': console.log(ZSH_COMPLETION); break;\n case 'powershell': console.log(POWERSHELL_COMPLETION); break;\n }\n}\n"],"mappings":"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","names":["result","envUrl","profile","manager","schema","clack","text","schema","require"]}
@@ -0,0 +1,318 @@
1
+ #!/usr/bin/env node
2
+ import {
3
+ ValidationError,
4
+ buildBatchBody,
5
+ createClient
6
+ } from "./chunk-QFYVVOAX.js";
7
+
8
+ // src/mcp/server.ts
9
+ import { randomUUID } from "crypto";
10
+ import { text } from "stream/consumers";
11
+ import { Server } from "@modelcontextprotocol/sdk/server/index.js";
12
+ import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
13
+ import { StreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/streamableHttp.js";
14
+ import { CallToolRequestSchema, ListToolsRequestSchema } from "@modelcontextprotocol/sdk/types.js";
15
+
16
+ // src/mcp/meta-tools.ts
17
+ function getMetaToolDefinitions() {
18
+ return [
19
+ {
20
+ name: "discover_entity",
21
+ description: "Fetch schema for a Dataverse entity by logical name",
22
+ inputSchema: {
23
+ type: "object",
24
+ properties: {
25
+ entity_name: { type: "string", description: "Logical name of the entity" }
26
+ },
27
+ required: ["entity_name"]
28
+ }
29
+ },
30
+ {
31
+ name: "list_entities",
32
+ description: "List all Dataverse entity logical names",
33
+ inputSchema: { type: "object", properties: {} }
34
+ },
35
+ {
36
+ name: "execute_query",
37
+ description: "Execute an OData or FetchXML query against Dataverse",
38
+ inputSchema: {
39
+ type: "object",
40
+ properties: {
41
+ entity: { type: "string", description: "Entity logical name (required for fetchxml)" },
42
+ odata: { type: "string", description: "OData query string (entitySetName?$filter=...)" },
43
+ fetchxml: { type: "string", description: "FetchXML query string" }
44
+ }
45
+ }
46
+ },
47
+ {
48
+ name: "execute_action",
49
+ description: "Execute a Dataverse custom action or SDK message",
50
+ inputSchema: {
51
+ type: "object",
52
+ properties: {
53
+ name: { type: "string", description: "Action name (PascalCase)" },
54
+ payload: { type: "object", description: "Action input parameters" },
55
+ entity: { type: "string", description: "Entity logical name for bound actions" },
56
+ id: { type: "string", description: "Record GUID for bound actions" }
57
+ },
58
+ required: ["name", "payload"]
59
+ }
60
+ },
61
+ {
62
+ name: "batch_execute",
63
+ description: "Execute multiple Dataverse operations in a single batch request",
64
+ inputSchema: {
65
+ type: "object",
66
+ properties: {
67
+ operations: {
68
+ type: "array",
69
+ items: {
70
+ type: "object",
71
+ properties: {
72
+ method: { type: "string", enum: ["GET", "POST", "PATCH", "DELETE"] },
73
+ path: { type: "string" },
74
+ body: { type: "object" }
75
+ },
76
+ required: ["method", "path"]
77
+ }
78
+ },
79
+ atomic: { type: "boolean", description: "Wrap in changeset for transactional semantics" }
80
+ },
81
+ required: ["operations"]
82
+ }
83
+ }
84
+ ];
85
+ }
86
+ async function handleMetaTool(name, args, client) {
87
+ let result;
88
+ switch (name) {
89
+ case "discover_entity": {
90
+ result = await client.getEntitySchema(args["entity_name"]);
91
+ break;
92
+ }
93
+ case "list_entities": {
94
+ result = await client.listEntities();
95
+ break;
96
+ }
97
+ case "execute_query": {
98
+ if (args["odata"]) {
99
+ const odata = args["odata"];
100
+ const qIndex = odata.indexOf("?");
101
+ const entitySetName = qIndex >= 0 ? odata.slice(0, qIndex) : odata;
102
+ const queryString = qIndex >= 0 ? odata.slice(qIndex + 1) : "";
103
+ result = await client.query(entitySetName, queryString, { pageAll: true });
104
+ } else if (args["fetchxml"]) {
105
+ if (!args["entity"]) throw new ValidationError("entity is required for fetchxml queries");
106
+ const entityName = args["entity"];
107
+ const records = [];
108
+ await client.queryFetchXml(entityName, args["fetchxml"], (record) => {
109
+ records.push(record);
110
+ });
111
+ result = records;
112
+ } else {
113
+ throw new ValidationError("Either odata or fetchxml must be provided");
114
+ }
115
+ break;
116
+ }
117
+ case "execute_action": {
118
+ result = await client.executeAction(
119
+ args["name"],
120
+ args["payload"] ?? {},
121
+ { entityName: args["entity"], id: args["id"] }
122
+ );
123
+ break;
124
+ }
125
+ case "batch_execute": {
126
+ const operations = args["operations"];
127
+ const atomic = Boolean(args["atomic"]);
128
+ const boundary = `batch_dvx_mcp_${Date.now()}`;
129
+ const body = buildBatchBody(operations, boundary, { atomic });
130
+ result = await client.executeBatch(body, boundary);
131
+ break;
132
+ }
133
+ default:
134
+ throw new ValidationError(`Unknown meta-tool: ${name}`);
135
+ }
136
+ return { content: [{ type: "text", text: JSON.stringify(result) }] };
137
+ }
138
+
139
+ // src/mcp/dynamic-tools.ts
140
+ var ENTITY_TOOL_PREFIXES = ["create_", "update_", "get_", "query_"];
141
+ function buildEntityToolDefinitions(schemas) {
142
+ const tools = [];
143
+ const entitySetMap = /* @__PURE__ */ new Map();
144
+ for (const schema of schemas) {
145
+ const { logicalName, entitySetName, attributes } = schema;
146
+ entitySetMap.set(logicalName, entitySetName);
147
+ const attrProps = {};
148
+ for (const attr of attributes) {
149
+ attrProps[attr.logicalName] = { type: "string", description: attr.displayName };
150
+ }
151
+ tools.push(
152
+ {
153
+ name: `create_${logicalName}`,
154
+ description: `Create a new ${logicalName} record`,
155
+ inputSchema: { type: "object", properties: attrProps }
156
+ },
157
+ {
158
+ name: `update_${logicalName}`,
159
+ description: `Update an existing ${logicalName} record`,
160
+ inputSchema: {
161
+ type: "object",
162
+ properties: { id: { type: "string", description: "Record GUID" }, ...attrProps },
163
+ required: ["id"]
164
+ }
165
+ },
166
+ {
167
+ name: `get_${logicalName}`,
168
+ description: `Get a ${logicalName} record by ID`,
169
+ inputSchema: {
170
+ type: "object",
171
+ properties: {
172
+ id: { type: "string", description: "Record GUID" },
173
+ fields: { type: "string", description: "Comma-separated field names" }
174
+ },
175
+ required: ["id"]
176
+ }
177
+ },
178
+ {
179
+ name: `query_${logicalName}`,
180
+ description: `Query ${logicalName} records with OData filter`,
181
+ inputSchema: {
182
+ type: "object",
183
+ properties: {
184
+ filter: { type: "string", description: "OData filter expression" },
185
+ fields: { type: "string", description: "Comma-separated field names" },
186
+ top: { type: "number", description: "Max records to return" }
187
+ }
188
+ }
189
+ }
190
+ );
191
+ }
192
+ return { tools, entitySetMap };
193
+ }
194
+ async function handleEntityTool(name, args, client, entitySetMap) {
195
+ const prefixes = [...ENTITY_TOOL_PREFIXES];
196
+ const prefix = prefixes.find((p) => name.startsWith(p));
197
+ if (!prefix) throw new ValidationError(`Unknown entity tool: ${name}`);
198
+ const entityName = name.slice(prefix.length);
199
+ let result;
200
+ switch (prefix) {
201
+ case "create_": {
202
+ result = await client.createRecord(entityName, args);
203
+ break;
204
+ }
205
+ case "update_": {
206
+ const { id, ...payload } = args;
207
+ result = await client.updateRecord(entityName, id, payload);
208
+ break;
209
+ }
210
+ case "get_": {
211
+ const fields = args["fields"]?.split(",").map((f) => f.trim());
212
+ result = await client.getRecord(entityName, args["id"], fields);
213
+ break;
214
+ }
215
+ case "query_": {
216
+ const resolvedEntitySetName = entitySetMap?.get(entityName) ?? (await client.getEntitySchema(entityName)).entitySetName;
217
+ const parts = [];
218
+ if (args["filter"]) parts.push(`$filter=${args["filter"]}`);
219
+ if (args["fields"]) parts.push(`$select=${args["fields"]}`);
220
+ if (args["top"]) parts.push(`$top=${args["top"]}`);
221
+ const queryString = parts.join("&");
222
+ result = await client.query(resolvedEntitySetName, queryString, { pageAll: true });
223
+ break;
224
+ }
225
+ }
226
+ return { content: [{ type: "text", text: JSON.stringify(result) }] };
227
+ }
228
+
229
+ // src/mcp/server.ts
230
+ var META_TOOL_NAMES = /* @__PURE__ */ new Set(["discover_entity", "list_entities", "execute_query", "execute_action", "batch_execute"]);
231
+ async function parseBody(req) {
232
+ try {
233
+ const body = await text(req);
234
+ return JSON.parse(body);
235
+ } catch {
236
+ return void 0;
237
+ }
238
+ }
239
+ function createMcpServer(client, entitySchemas) {
240
+ const server = new Server(
241
+ { name: "dvx", version: "0.1.0" },
242
+ { capabilities: { tools: {} } }
243
+ );
244
+ const { tools: entityTools, entitySetMap } = buildEntityToolDefinitions(entitySchemas);
245
+ const allTools = [
246
+ ...getMetaToolDefinitions(),
247
+ ...entityTools
248
+ ];
249
+ server.setRequestHandler(ListToolsRequestSchema, async () => ({ tools: allTools }));
250
+ server.setRequestHandler(CallToolRequestSchema, async (request) => {
251
+ const { name, arguments: args } = request.params;
252
+ const safeArgs = args ?? {};
253
+ if (META_TOOL_NAMES.has(name)) {
254
+ return handleMetaTool(name, safeArgs, client);
255
+ }
256
+ if (ENTITY_TOOL_PREFIXES.some((p) => name.startsWith(p))) {
257
+ return handleEntityTool(name, safeArgs, client, entitySetMap);
258
+ }
259
+ throw new ValidationError(`Unknown tool: ${name}`);
260
+ });
261
+ return server;
262
+ }
263
+ async function startMcpServer(opts) {
264
+ const { client } = await createClient();
265
+ const entitySchemas = opts.entities ? await Promise.all(opts.entities.map((e) => client.getEntitySchema(e))) : [];
266
+ if (opts.transport === "http") {
267
+ const { createServer } = await import("http");
268
+ const port = opts.port ?? 3e3;
269
+ const sessions = /* @__PURE__ */ new Map();
270
+ const httpServer = createServer(async (req, res) => {
271
+ if (req.method === "GET" && req.url === "/health") {
272
+ res.writeHead(200, { "Content-Type": "application/json" });
273
+ res.end(JSON.stringify({ ok: true }));
274
+ return;
275
+ }
276
+ const sessionId = req.headers["mcp-session-id"];
277
+ if (req.method === "DELETE" && req.url === "/mcp") {
278
+ if (sessionId && sessions.has(sessionId)) {
279
+ const session = sessions.get(sessionId);
280
+ await session.transport.close();
281
+ sessions.delete(sessionId);
282
+ }
283
+ res.writeHead(204);
284
+ res.end();
285
+ return;
286
+ }
287
+ if (sessionId && sessions.has(sessionId)) {
288
+ const session = sessions.get(sessionId);
289
+ await session.transport.handleRequest(req, res, await parseBody(req));
290
+ return;
291
+ }
292
+ const mcpServer = createMcpServer(client, entitySchemas);
293
+ const transport2 = new StreamableHTTPServerTransport({
294
+ sessionIdGenerator: () => randomUUID(),
295
+ onsessioninitialized: (sid) => {
296
+ sessions.set(sid, { transport: transport2, server: mcpServer });
297
+ },
298
+ onsessionclosed: (sid) => {
299
+ sessions.delete(sid);
300
+ }
301
+ });
302
+ await mcpServer.connect(transport2);
303
+ await transport2.handleRequest(req, res, await parseBody(req));
304
+ });
305
+ httpServer.listen(port, () => {
306
+ console.error(`dvx MCP HTTP server listening on port ${port}`);
307
+ console.error("Stateful session mode \u2014 SSE subscriptions and batch progress streaming are supported.");
308
+ });
309
+ return;
310
+ }
311
+ const server = createMcpServer(client, entitySchemas);
312
+ const transport = new StdioServerTransport();
313
+ await server.connect(transport);
314
+ }
315
+ export {
316
+ startMcpServer
317
+ };
318
+ //# sourceMappingURL=server-KJMLJWZI.js.map