@mcp-z/mcp-gmail 1.0.12 → 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.
package/bin/server.js CHANGED
@@ -1,5 +1,20 @@
1
1
  #!/usr/bin/env node
2
2
 
3
- // biome-ignore lint/security/noGlobalEval: dual esm and cjs
4
- if (typeof require === 'undefined') eval("import('../dist/esm/index.js').then((cli) => cli.default(process.argv.slice(2), 'mcp-gmail')).catch((err) => { console.error(err); process.exit(-1); });");
5
- else require('../dist/cjs/index.js')(process.argv.slice(2), 'mcp-gmail');
3
+ // Checks --version/--help/`version` via the dependency-free version-help module before ever
4
+ // touching index.js, which statically re-exports the mcp/setup/schemas namespaces (googleapis,
5
+ // @modelcontextprotocol/sdk, @mcp-z/oauth-google, @mcp-z/server et al.) -- importing index.js at
6
+ // all, even without calling anything in it, evaluates that whole graph.
7
+ if (typeof require === 'undefined') {
8
+ // biome-ignore lint/security/noGlobalEval: dual esm and cjs
9
+ eval(
10
+ "import('../dist/esm/setup/version-help.js').then(({ handleVersionHelp }) => { const result = handleVersionHelp(process.argv.slice(2)); if (result.handled) { console.log(result.output); process.exit(0); } return import('../dist/esm/index.js').then((cli) => cli.default(process.argv.slice(2), 'mcp-gmail')); }).catch((err) => { console.error(err); process.exit(-1); });"
11
+ );
12
+ } else {
13
+ const { handleVersionHelp } = require('../dist/cjs/setup/version-help.js');
14
+ const result = handleVersionHelp(process.argv.slice(2));
15
+ if (result.handled) {
16
+ console.log(result.output);
17
+ process.exit(0);
18
+ }
19
+ require('../dist/cjs/index.js')(process.argv.slice(2), 'mcp-gmail');
20
+ }
package/dist/cjs/index.js CHANGED
@@ -34,9 +34,7 @@ _export(exports, {
34
34
  return startServer;
35
35
  }
36
36
  });
37
- var _configts = require("./setup/config.js");
38
- var _httpts = require("./setup/http.js");
39
- var _stdiots = require("./setup/stdio.js");
37
+ var _versionhelpts = require("./setup/version-help.js");
40
38
  var _constantsts = require("./constants.js");
41
39
  var _indexts = /*#__PURE__*/ _interop_require_wildcard(require("./mcp/index.js"));
42
40
  var _categorieslistts = require("./mcp/tools/categories-list.js");
@@ -214,33 +212,49 @@ function _ts_generator(thisArg, body) {
214
212
  }
215
213
  function startServer(config) {
216
214
  return _async_to_generator(function() {
217
- var _ref, logger, close, _tmp;
215
+ var createHTTPServer, createStdioServer, _ref, logger, close, _tmp;
218
216
  return _ts_generator(this, function(_state) {
219
217
  switch(_state.label){
220
218
  case 0:
221
- if (!(config.transport.type === 'stdio')) return [
222
- 3,
223
- 2
224
- ];
225
219
  return [
226
220
  4,
227
- (0, _stdiots.createStdioServer)(config)
221
+ Promise.resolve().then(function() {
222
+ return /*#__PURE__*/ _interop_require_wildcard(require("./setup/http.js"));
223
+ })
228
224
  ];
229
225
  case 1:
230
- _tmp = _state.sent();
226
+ createHTTPServer = _state.sent().createHTTPServer;
231
227
  return [
228
+ 4,
229
+ Promise.resolve().then(function() {
230
+ return /*#__PURE__*/ _interop_require_wildcard(require("./setup/stdio.js"));
231
+ })
232
+ ];
233
+ case 2:
234
+ createStdioServer = _state.sent().createStdioServer;
235
+ if (!(config.transport.type === 'stdio')) return [
232
236
  3,
233
237
  4
234
238
  ];
235
- case 2:
236
239
  return [
237
240
  4,
238
- (0, _httpts.createHTTPServer)(config)
241
+ createStdioServer(config)
239
242
  ];
240
243
  case 3:
241
244
  _tmp = _state.sent();
242
- _state.label = 4;
245
+ return [
246
+ 3,
247
+ 6
248
+ ];
243
249
  case 4:
250
+ return [
251
+ 4,
252
+ createHTTPServer(config)
253
+ ];
254
+ case 5:
255
+ _tmp = _state.sent();
256
+ _state.label = 6;
257
+ case 6:
244
258
  _ref = _tmp, logger = _ref.logger, close = _ref.close;
245
259
  process.on('SIGINT', function() {
246
260
  return _async_to_generator(function() {
@@ -266,7 +280,7 @@ function startServer(config) {
266
280
  4,
267
281
  new Promise(function() {})
268
282
  ];
269
- case 5:
283
+ case 7:
270
284
  _state.sent();
271
285
  return [
272
286
  2
@@ -277,23 +291,30 @@ function startServer(config) {
277
291
  }
278
292
  function main() {
279
293
  return _async_to_generator(function() {
280
- var versionHelpResult, config;
294
+ var versionHelpResult, createConfig, config;
281
295
  return _ts_generator(this, function(_state) {
282
296
  switch(_state.label){
283
297
  case 0:
284
298
  // Check for help/version flags FIRST, before config parsing
285
- versionHelpResult = (0, _configts.handleVersionHelp)(process.argv);
299
+ versionHelpResult = (0, _versionhelpts.handleVersionHelp)(process.argv);
286
300
  if (versionHelpResult.handled) {
287
301
  console.log(versionHelpResult.output);
288
302
  process.exit(0);
289
303
  }
290
- // Only parse config if no help/version flags
291
- config = (0, _configts.createConfig)();
292
304
  return [
293
305
  4,
294
- startServer(config)
306
+ Promise.resolve().then(function() {
307
+ return /*#__PURE__*/ _interop_require_wildcard(require("./setup/config.js"));
308
+ })
295
309
  ];
296
310
  case 1:
311
+ createConfig = _state.sent().createConfig;
312
+ config = createConfig();
313
+ return [
314
+ 4,
315
+ startServer(config)
316
+ ];
317
+ case 2:
297
318
  _state.sent();
298
319
  return [
299
320
  2
@@ -1 +1 @@
1
- {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/index.ts"],"sourcesContent":["import { createConfig, handleVersionHelp } from './setup/config.ts';\nimport { createHTTPServer } from './setup/http.ts';\nimport { createStdioServer } from './setup/stdio.ts';\nimport type { ServerConfig } from './types.ts';\n\nexport { GOOGLE_SCOPE } from './constants.ts';\nexport * as mcp from './mcp/index.ts';\n// Export types and schemas for documentation\nexport type { Input as CategoriesListInput } from './mcp/tools/categories-list.ts';\nexport { inputSchema as CategoriesListInputSchema } from './mcp/tools/categories-list.ts';\nexport type { Input as LabelsListInput } from './mcp/tools/labels-list.ts';\nexport { inputSchema as LabelsListInputSchema } from './mcp/tools/labels-list.ts';\nexport * as schemas from './schemas/index.ts';\nexport * as setup from './setup/index.ts';\nexport * from './types.ts';\n\nexport async function startServer(config: ServerConfig): Promise<void> {\n const { logger, close } = config.transport.type === 'stdio' ? await createStdioServer(config) : await createHTTPServer(config);\n\n process.on('SIGINT', async () => {\n await close();\n process.exit(0);\n });\n\n logger.info(`Server started with ${config.transport.type} transport`);\n await new Promise(() => {});\n}\n\nexport default async function main(): Promise<void> {\n // Check for help/version flags FIRST, before config parsing\n const versionHelpResult = handleVersionHelp(process.argv);\n if (versionHelpResult.handled) {\n console.log(versionHelpResult.output);\n process.exit(0);\n }\n\n // Only parse config if no help/version flags\n const config = createConfig();\n await startServer(config);\n}\n\nif (process.argv[1] === new URL(import.meta.url).pathname) {\n main();\n}\n"],"names":["CategoriesListInputSchema","inputSchema","GOOGLE_SCOPE","LabelsListInputSchema","main","mcp","schemas","setup","startServer","config","logger","close","transport","type","createStdioServer","createHTTPServer","process","on","exit","info","Promise","versionHelpResult","handleVersionHelp","argv","handled","console","log","output","createConfig","URL","pathname"],"mappings":";;;;;;;;;;;QASwBA;eAAfC,6BAAW;;QAJXC;eAAAA,yBAAY;;QAMGC;eAAfF,yBAAW;;QAiBpB;eAA8BG;;QAtBlBC;;;QAMAC;;;QACAC;;;QAGUC;eAAAA;;;wBAhB0B;sBACf;uBACC;2BAGL;+DACR;gCAGoC;4BAEJ;gEAC5B;gEACF;qBACT;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAEP,SAAeA,YAAYC,MAAoB;;YAC1BA,MAAlBC,QAAQC;;;;yBAAUF,CAAAA,OAAOG,SAAS,CAACC,IAAI,KAAK,OAAM,GAAhCJ;;;;oBAAoC;;wBAAMK,IAAAA,0BAAiB,EAACL;;;2BAAxB;;;;;;oBAAkC;;wBAAMM,IAAAA,wBAAgB,EAACN;;;2BAAvB;;;oBAAtEA,aAAlBC,SAAkBD,KAAlBC,QAAQC,QAAUF,KAAVE;oBAEhBK,QAAQC,EAAE,CAAC,UAAU;;;;;wCACnB;;4CAAMN;;;wCAAN;wCACAK,QAAQE,IAAI,CAAC;;;;;;wBACf;;oBAEAR,OAAOS,IAAI,CAAC,AAAC,uBAA4C,OAAtBV,OAAOG,SAAS,CAACC,IAAI,EAAC;oBACzD;;wBAAM,IAAIO,QAAQ,YAAO;;;oBAAzB;;;;;;IACF;;AAEe,SAAehB;;YAEtBiB,mBAOAZ;;;;oBARN,4DAA4D;oBACtDY,oBAAoBC,IAAAA,2BAAiB,EAACN,QAAQO,IAAI;oBACxD,IAAIF,kBAAkBG,OAAO,EAAE;wBAC7BC,QAAQC,GAAG,CAACL,kBAAkBM,MAAM;wBACpCX,QAAQE,IAAI,CAAC;oBACf;oBAEA,6CAA6C;oBACvCT,SAASmB,IAAAA,sBAAY;oBAC3B;;wBAAMpB,YAAYC;;;oBAAlB;;;;;;IACF;;AAEA,IAAIO,QAAQO,IAAI,CAAC,EAAE,KAAK,IAAIM,IAAI,qDAAiBC,QAAQ,EAAE;IACzD1B;AACF"}
1
+ {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/index.ts"],"sourcesContent":["import { handleVersionHelp } from './setup/version-help.ts';\nimport type { ServerConfig } from './types.ts';\n\nexport { GOOGLE_SCOPE } from './constants.ts';\nexport * as mcp from './mcp/index.ts';\n// Export types and schemas for documentation\nexport type { Input as CategoriesListInput } from './mcp/tools/categories-list.ts';\nexport { inputSchema as CategoriesListInputSchema } from './mcp/tools/categories-list.ts';\nexport type { Input as LabelsListInput } from './mcp/tools/labels-list.ts';\nexport { inputSchema as LabelsListInputSchema } from './mcp/tools/labels-list.ts';\nexport * as schemas from './schemas/index.ts';\nexport * as setup from './setup/index.ts';\nexport * from './types.ts';\n\nexport async function startServer(config: ServerConfig): Promise<void> {\n // createHTTPServer/createStdioServer pull in @modelcontextprotocol/sdk and every mcp/tools/*.ts\n // (googleapis included); deferred so a --version/--help run never reaches them.\n const { createHTTPServer } = await import('./setup/http.ts');\n const { createStdioServer } = await import('./setup/stdio.ts');\n const { logger, close } = config.transport.type === 'stdio' ? await createStdioServer(config) : await createHTTPServer(config);\n\n process.on('SIGINT', async () => {\n await close();\n process.exit(0);\n });\n\n logger.info(`Server started with ${config.transport.type} transport`);\n await new Promise(() => {});\n}\n\nexport default async function main(): Promise<void> {\n // Check for help/version flags FIRST, before config parsing\n const versionHelpResult = handleVersionHelp(process.argv);\n if (versionHelpResult.handled) {\n console.log(versionHelpResult.output);\n process.exit(0);\n }\n\n // Only parse config if no help/version flags. config.ts's own heavy imports (@mcp-z/oauth-google,\n // @mcp-z/server) are deferred internally, so this static-looking call stays cheap until here.\n const { createConfig } = await import('./setup/config.ts');\n const config = createConfig();\n await startServer(config);\n}\n\nif (process.argv[1] === new URL(import.meta.url).pathname) {\n main();\n}\n"],"names":["CategoriesListInputSchema","inputSchema","GOOGLE_SCOPE","LabelsListInputSchema","main","mcp","schemas","setup","startServer","config","createHTTPServer","createStdioServer","logger","close","transport","type","process","on","exit","info","Promise","versionHelpResult","createConfig","handleVersionHelp","argv","handled","console","log","output","URL","pathname"],"mappings":";;;;;;;;;;;QAOwBA;eAAfC,6BAAW;;QAJXC;eAAAA,yBAAY;;QAMGC;eAAfF,yBAAW;;QAqBpB;eAA8BG;;QA1BlBC;;;QAMAC;;;QACAC;;;QAGUC;eAAAA;;;6BAdY;2BAGL;+DACR;gCAGoC;4BAEJ;gEAC5B;gEACF;qBACT;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAEP,SAAeA,YAAYC,MAAoB;;YAG5CC,kBACAC,mBACkBF,MAAlBG,QAAQC;;;;oBAFa;;wBAAM;2EAAA,QAAO;;;;oBAAlCH,mBAAqB,cAArBA;oBACsB;;wBAAM;2EAAA,QAAO;;;;oBAAnCC,oBAAsB,cAAtBA;yBACkBF,CAAAA,OAAOK,SAAS,CAACC,IAAI,KAAK,OAAM,GAAhCN;;;;oBAAoC;;wBAAME,kBAAkBF;;;2BAAxB;;;;;;oBAAkC;;wBAAMC,iBAAiBD;;;2BAAvB;;;oBAAtEA,aAAlBG,SAAkBH,KAAlBG,QAAQC,QAAUJ,KAAVI;oBAEhBG,QAAQC,EAAE,CAAC,UAAU;;;;;wCACnB;;4CAAMJ;;;wCAAN;wCACAG,QAAQE,IAAI,CAAC;;;;;;wBACf;;oBAEAN,OAAOO,IAAI,CAAC,AAAC,uBAA4C,OAAtBV,OAAOK,SAAS,CAACC,IAAI,EAAC;oBACzD;;wBAAM,IAAIK,QAAQ,YAAO;;;oBAAzB;;;;;;IACF;;AAEe,SAAehB;;YAEtBiB,mBAQEC,cACFb;;;;oBAVN,4DAA4D;oBACtDY,oBAAoBE,IAAAA,gCAAiB,EAACP,QAAQQ,IAAI;oBACxD,IAAIH,kBAAkBI,OAAO,EAAE;wBAC7BC,QAAQC,GAAG,CAACN,kBAAkBO,MAAM;wBACpCZ,QAAQE,IAAI,CAAC;oBACf;oBAIyB;;wBAAM;2EAAA,QAAO;;;;oBAA9BI,eAAiB,cAAjBA;oBACFb,SAASa;oBACf;;wBAAMd,YAAYC;;;oBAAlB;;;;;;IACF;;AAEA,IAAIO,QAAQQ,IAAI,CAAC,EAAE,KAAK,IAAIK,IAAI,qDAAiBC,QAAQ,EAAE;IACzD1B;AACF"}
@@ -1,12 +1,4 @@
1
1
  import type { ServerConfig } from '../types.js';
2
- /**
3
- * Handle --version and --help flags before config parsing.
4
- * These should work without requiring any configuration.
5
- */
6
- export declare function handleVersionHelp(args: string[]): {
7
- handled: boolean;
8
- output?: string;
9
- };
10
2
  /**
11
3
  * Parse Gmail server configuration from CLI arguments and environment.
12
4
  *
@@ -1,12 +1,4 @@
1
1
  import type { ServerConfig } from '../types.js';
2
- /**
3
- * Handle --version and --help flags before config parsing.
4
- * These should work without requiring any configuration.
5
- */
6
- export declare function handleVersionHelp(args: string[]): {
7
- handled: boolean;
8
- output?: string;
9
- };
10
2
  /**
11
3
  * Parse Gmail server configuration from CLI arguments and environment.
12
4
  *
@@ -12,22 +12,16 @@ _export(exports, {
12
12
  get createConfig () {
13
13
  return createConfig;
14
14
  },
15
- get handleVersionHelp () {
16
- return handleVersionHelp;
17
- },
18
15
  get parseConfig () {
19
16
  return parseConfig;
20
17
  }
21
18
  });
22
- var _oauthgoogle = require("@mcp-z/oauth-google");
23
- var _server = require("@mcp-z/server");
24
- var _fs = /*#__PURE__*/ _interop_require_wildcard(require("fs"));
25
- var _modulerootsync = /*#__PURE__*/ _interop_require_default(require("module-root-sync"));
19
+ var _module = require("module");
26
20
  var _os = require("os");
27
21
  var _path = /*#__PURE__*/ _interop_require_wildcard(require("path"));
28
- var _url = /*#__PURE__*/ _interop_require_wildcard(require("url"));
29
22
  var _util = require("util");
30
23
  var _constantsts = require("../constants.js");
24
+ var _versionhelpts = require("./version-help.js");
31
25
  function _define_property(obj, key, value) {
32
26
  if (key in obj) {
33
27
  Object.defineProperty(obj, key, {
@@ -39,11 +33,6 @@ function _define_property(obj, key, value) {
39
33
  } else obj[key] = value;
40
34
  return obj;
41
35
  }
42
- function _interop_require_default(obj) {
43
- return obj && obj.__esModule ? obj : {
44
- default: obj
45
- };
46
- }
47
36
  function _getRequireWildcardCache(nodeInterop) {
48
37
  if (typeof WeakMap !== "function") return null;
49
38
  var cacheBabelInterop = new WeakMap();
@@ -116,39 +105,18 @@ function _type_of(obj) {
116
105
  "@swc/helpers - typeof";
117
106
  return obj && typeof Symbol !== "undefined" && obj.constructor === Symbol ? "symbol" : typeof obj;
118
107
  }
119
- var pkg = JSON.parse(_fs.readFileSync(_path.join((0, _modulerootsync.default)(_url.fileURLToPath(require("url").pathToFileURL(__filename).toString())), 'package.json'), 'utf-8'));
120
- var HELP_TEXT = "\nUsage: mcp-gmail [options]\n\nMCP server for Gmail email management with OAuth authentication.\n\nOptions:\n --version Show version number\n --help Show this help message\n --auth=<mode> Authentication mode (default: loopback-oauth)\n Modes: loopback-oauth, service-account, dcr\n --headless Disable browser auto-open, return auth URL instead\n --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n --dcr-verify-url=<url> External verification endpoint (required for external mode)\n --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n --port=<port> Enable HTTP transport on specified port\n --stdio Enable stdio transport (default if no port)\n --log-level=<level> Logging level (default: info)\n --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n --base-url=<url> Base URL for HTTP file serving (optional)\n\nEnvironment Variables:\n GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n AUTH_MODE Default authentication mode (optional)\n HEADLESS Disable browser auto-open (optional)\n DCR_MODE DCR mode (optional, same format as --dcr-mode)\n DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n TOKEN_STORE_URI Token storage URI (optional)\n PORT Default HTTP port (optional)\n LOG_LEVEL Default logging level (optional)\n RESOURCE_STORE_URI Resource store URI (optional, file://)\n BASE_URL Default base URL for file serving (optional)\n\nOAuth Scopes:\n openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n\nExamples:\n mcp-gmail # Use default settings\n mcp-gmail --auth=service-account # Use service account auth\n mcp-gmail --port=3000 # HTTP transport on port 3000\n mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI\n GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var\n".trim();
121
- function handleVersionHelp(args) {
122
- var values = (0, _util.parseArgs)({
123
- args: args,
124
- options: {
125
- version: {
126
- type: 'boolean'
127
- },
128
- help: {
129
- type: 'boolean'
130
- }
131
- },
132
- strict: false
133
- }).values;
134
- if (values.version) return {
135
- handled: true,
136
- output: pkg.version
137
- };
138
- if (values.help) return {
139
- handled: true,
140
- output: HELP_TEXT
141
- };
142
- return {
143
- handled: false
144
- };
145
- }
108
+ var pkg = (0, _versionhelpts.readPkg)();
109
+ // @mcp-z/oauth-google and @mcp-z/server are requireable at the >=20 floor; deferred so
110
+ // --version/--help (handled via version-help.ts, never this file) load neither package.
111
+ var _require = typeof require === 'undefined' ? _module.Module.createRequire(require("url").pathToFileURL(__filename).toString()) : require;
146
112
  function parseConfig(args, env) {
147
113
  var _ref, _ref1, _ref2;
148
- var transportConfig = (0, _server.parseConfig)(args, env);
149
- var oauthConfig = (0, _oauthgoogle.parseConfig)(args, env);
114
+ var oauthGoogle = _require('@mcp-z/oauth-google');
115
+ var mcpServer = _require('@mcp-z/server');
116
+ var transportConfig = mcpServer.parseConfig(args, env);
117
+ var oauthConfig = oauthGoogle.parseConfig(args, env);
150
118
  // Parse DCR configuration if DCR mode is enabled
151
- var dcrConfig = oauthConfig.auth === 'dcr' ? (0, _oauthgoogle.parseDcrConfig)(args, env, _constantsts.GOOGLE_SCOPE) : undefined;
119
+ var dcrConfig = oauthConfig.auth === 'dcr' ? oauthGoogle.parseDcrConfig(args, env, _constantsts.GOOGLE_SCOPE) : undefined;
152
120
  // Parse application-level config (LOG_LEVEL, RESOURCE_STORE_URI, BASE_URL)
153
121
  var values = (0, _util.parseArgs)({
154
122
  args: args,
@@ -172,7 +140,7 @@ function parseConfig(args, env) {
172
140
  var repositoryUrl = (_ref = rawRepoUrl === null || rawRepoUrl === void 0 ? void 0 : rawRepoUrl.replace(/^git\+/, '').replace(/\.git$/, '')) !== null && _ref !== void 0 ? _ref : "https://github.com/mcp-z/".concat(name);
173
141
  var rootDir = (0, _os.homedir)();
174
142
  try {
175
- var configPath = (0, _server.findConfigPath)({
143
+ var configPath = mcpServer.findConfigPath({
176
144
  config: '.mcp.json',
177
145
  cwd: process.cwd(),
178
146
  stopDir: (0, _os.homedir)()
@@ -1 +1 @@
1
- {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/setup/config.ts"],"sourcesContent":["import { parseDcrConfig, parseConfig as parseOAuthConfig } from '@mcp-z/oauth-google';\nimport { findConfigPath, parseConfig as parseTransportConfig } from '@mcp-z/server';\nimport * as fs from 'fs';\nimport moduleRoot from 'module-root-sync';\nimport { homedir } from 'os';\nimport * as path from 'path';\nimport * as url from 'url';\nimport { parseArgs } from 'util';\nimport { GOOGLE_SCOPE } from '../constants.ts';\nimport type { ServerConfig } from '../types.ts';\n\nconst pkg = JSON.parse(fs.readFileSync(path.join(moduleRoot(url.fileURLToPath(import.meta.url)), 'package.json'), 'utf-8'));\n\nconst HELP_TEXT = `\nUsage: mcp-gmail [options]\n\nMCP server for Gmail email management with OAuth authentication.\n\nOptions:\n --version Show version number\n --help Show this help message\n --auth=<mode> Authentication mode (default: loopback-oauth)\n Modes: loopback-oauth, service-account, dcr\n --headless Disable browser auto-open, return auth URL instead\n --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n --dcr-verify-url=<url> External verification endpoint (required for external mode)\n --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n --port=<port> Enable HTTP transport on specified port\n --stdio Enable stdio transport (default if no port)\n --log-level=<level> Logging level (default: info)\n --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n --base-url=<url> Base URL for HTTP file serving (optional)\n\nEnvironment Variables:\n GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n AUTH_MODE Default authentication mode (optional)\n HEADLESS Disable browser auto-open (optional)\n DCR_MODE DCR mode (optional, same format as --dcr-mode)\n DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n TOKEN_STORE_URI Token storage URI (optional)\n PORT Default HTTP port (optional)\n LOG_LEVEL Default logging level (optional)\n RESOURCE_STORE_URI Resource store URI (optional, file://)\n BASE_URL Default base URL for file serving (optional)\n\nOAuth Scopes:\n openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n\nExamples:\n mcp-gmail # Use default settings\n mcp-gmail --auth=service-account # Use service account auth\n mcp-gmail --port=3000 # HTTP transport on port 3000\n mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI\n GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var\n`.trim();\n\n/**\n * Handle --version and --help flags before config parsing.\n * These should work without requiring any configuration.\n */\nexport function handleVersionHelp(args: string[]): { handled: boolean; output?: string } {\n const { values } = parseArgs({\n args,\n options: {\n version: { type: 'boolean' },\n help: { type: 'boolean' },\n },\n strict: false,\n });\n\n if (values.version) return { handled: true, output: pkg.version };\n if (values.help) return { handled: true, output: HELP_TEXT };\n return { handled: false };\n}\n\n/**\n * Parse Gmail server configuration from CLI arguments and environment.\n *\n * CLI Arguments (all optional):\n * - --auth=<mode> Authentication mode (default: loopback-oauth)\n * Modes: loopback-oauth, service-account, dcr\n * - --headless Disable browser auto-open, return auth URL instead\n * - --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n * - --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n * - --dcr-verify-url=<url> External verification endpoint (required for external mode)\n * - --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n * - --port=<port> Enable HTTP transport on specified port\n * - --stdio Enable stdio transport (default if no port)\n * - --log-level=<level> Logging level (default: info)\n * - --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n * - --base-url=<url> Base URL for HTTP file serving (optional)\n *\n * Environment Variables:\n * - GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n * - GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n * - AUTH_MODE Default authentication mode (optional)\n * - HEADLESS Disable browser auto-open (optional)\n * - DCR_MODE DCR mode (optional, same format as --dcr-mode)\n * - DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n * - DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n * - TOKEN_STORE_URI Token storage URI (optional)\n * - PORT Default HTTP port (optional)\n * - LOG_LEVEL Default logging level (optional)\n * - RESOURCE_STORE_URI Resource store URI (optional, file://)\n * - BASE_URL Default base URL for file serving (optional)\n *\n * OAuth Scopes (from constants.ts):\n * openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n */\nexport function parseConfig(args: string[], env: Record<string, string | undefined>): ServerConfig {\n const transportConfig = parseTransportConfig(args, env);\n const oauthConfig = parseOAuthConfig(args, env);\n\n // Parse DCR configuration if DCR mode is enabled\n const dcrConfig = oauthConfig.auth === 'dcr' ? parseDcrConfig(args, env, GOOGLE_SCOPE) : undefined;\n\n // Parse application-level config (LOG_LEVEL, RESOURCE_STORE_URI, BASE_URL)\n const { values } = parseArgs({\n args,\n options: {\n 'log-level': { type: 'string' },\n 'base-url': { type: 'string' },\n 'resource-store-uri': { type: 'string' },\n },\n strict: false, // Allow other arguments\n allowPositionals: true,\n });\n\n const name = pkg.name.replace(/^@[^/]+\\//, '');\n // Parse repository URL from package.json, stripping git+ prefix and .git suffix\n const rawRepoUrl = typeof pkg.repository === 'object' ? pkg.repository.url : pkg.repository;\n const repositoryUrl = rawRepoUrl?.replace(/^git\\+/, '').replace(/\\.git$/, '') ?? `https://github.com/mcp-z/${name}`;\n let rootDir = homedir();\n try {\n const configPath = findConfigPath({ config: '.mcp.json', cwd: process.cwd(), stopDir: homedir() });\n rootDir = path.dirname(configPath);\n } catch {\n rootDir = homedir();\n }\n const baseDir = path.join(rootDir, '.mcp-z');\n const cliLogLevel = typeof values['log-level'] === 'string' ? values['log-level'] : undefined;\n const envLogLevel = env.LOG_LEVEL;\n const logLevel = cliLogLevel ?? envLogLevel ?? 'info';\n\n // Parse storage configuration\n const cliResourceStoreUri = typeof values['resource-store-uri'] === 'string' ? values['resource-store-uri'] : undefined;\n const envResourceStoreUri = env.RESOURCE_STORE_URI;\n const defaultResourceStorePath = path.join(baseDir, name, 'files');\n const resourceStoreUri = normalizeResourceStoreUri(cliResourceStoreUri ?? envResourceStoreUri ?? defaultResourceStorePath);\n\n const cliBaseUrl = typeof values['base-url'] === 'string' ? values['base-url'] : undefined;\n const envBaseUrl = env.BASE_URL;\n const baseUrl = cliBaseUrl ?? envBaseUrl;\n\n // Combine configs\n const result: ServerConfig = {\n ...oauthConfig, // Includes clientId, auth, headless, redirectUri, serviceAccountKeyFile\n transport: transportConfig.transport,\n logLevel,\n baseDir,\n name,\n version: pkg.version,\n repositoryUrl,\n resourceStoreUri,\n };\n if (baseUrl) result.baseUrl = baseUrl;\n if (dcrConfig !== undefined) result.dcrConfig = dcrConfig;\n return result;\n}\n\n/**\n * Build production configuration from process globals.\n * Entry point for production server.\n */\nexport function createConfig(): ServerConfig {\n return parseConfig(process.argv, process.env);\n}\n\nfunction normalizeResourceStoreUri(resourceStoreUri: string): string {\n const filePrefix = 'file://';\n if (resourceStoreUri.startsWith(filePrefix)) {\n const rawPath = resourceStoreUri.slice(filePrefix.length);\n const expandedPath = rawPath.startsWith('~') ? rawPath.replace(/^~/, homedir()) : rawPath;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n }\n\n if (resourceStoreUri.includes('://')) return resourceStoreUri;\n\n const expandedPath = resourceStoreUri.startsWith('~') ? resourceStoreUri.replace(/^~/, homedir()) : resourceStoreUri;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n}\n"],"names":["createConfig","handleVersionHelp","parseConfig","pkg","JSON","parse","fs","readFileSync","path","join","moduleRoot","url","fileURLToPath","HELP_TEXT","trim","args","values","parseArgs","options","version","type","help","strict","handled","output","env","cliLogLevel","cliResourceStoreUri","transportConfig","parseTransportConfig","oauthConfig","parseOAuthConfig","dcrConfig","auth","parseDcrConfig","GOOGLE_SCOPE","undefined","allowPositionals","name","replace","rawRepoUrl","repository","repositoryUrl","rootDir","homedir","configPath","findConfigPath","config","cwd","process","stopDir","dirname","baseDir","envLogLevel","LOG_LEVEL","logLevel","envResourceStoreUri","RESOURCE_STORE_URI","defaultResourceStorePath","resourceStoreUri","normalizeResourceStoreUri","cliBaseUrl","envBaseUrl","BASE_URL","baseUrl","result","transport","argv","filePrefix","startsWith","rawPath","slice","length","expandedPath","resolve","includes"],"mappings":"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"}
1
+ {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/setup/config.ts"],"sourcesContent":["import type * as OAuthGoogle from '@mcp-z/oauth-google';\nimport type * as McpServer from '@mcp-z/server';\nimport { Module } from 'module';\nimport { homedir } from 'os';\nimport * as path from 'path';\nimport { parseArgs } from 'util';\nimport { GOOGLE_SCOPE } from '../constants.ts';\nimport type { ServerConfig } from '../types.ts';\nimport { readPkg } from './version-help.ts';\n\nconst pkg = readPkg();\n\n// @mcp-z/oauth-google and @mcp-z/server are requireable at the >=20 floor; deferred so\n// --version/--help (handled via version-help.ts, never this file) load neither package.\nconst _require = typeof require === 'undefined' ? Module.createRequire(import.meta.url) : require;\n\n/**\n * Parse Gmail server configuration from CLI arguments and environment.\n *\n * CLI Arguments (all optional):\n * - --auth=<mode> Authentication mode (default: loopback-oauth)\n * Modes: loopback-oauth, service-account, dcr\n * - --headless Disable browser auto-open, return auth URL instead\n * - --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n * - --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n * - --dcr-verify-url=<url> External verification endpoint (required for external mode)\n * - --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n * - --port=<port> Enable HTTP transport on specified port\n * - --stdio Enable stdio transport (default if no port)\n * - --log-level=<level> Logging level (default: info)\n * - --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n * - --base-url=<url> Base URL for HTTP file serving (optional)\n *\n * Environment Variables:\n * - GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n * - GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n * - AUTH_MODE Default authentication mode (optional)\n * - HEADLESS Disable browser auto-open (optional)\n * - DCR_MODE DCR mode (optional, same format as --dcr-mode)\n * - DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n * - DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n * - TOKEN_STORE_URI Token storage URI (optional)\n * - PORT Default HTTP port (optional)\n * - LOG_LEVEL Default logging level (optional)\n * - RESOURCE_STORE_URI Resource store URI (optional, file://)\n * - BASE_URL Default base URL for file serving (optional)\n *\n * OAuth Scopes (from constants.ts):\n * openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n */\nexport function parseConfig(args: string[], env: Record<string, string | undefined>): ServerConfig {\n const oauthGoogle = _require('@mcp-z/oauth-google') as typeof OAuthGoogle;\n const mcpServer = _require('@mcp-z/server') as typeof McpServer;\n\n const transportConfig = mcpServer.parseConfig(args, env);\n const oauthConfig = oauthGoogle.parseConfig(args, env);\n\n // Parse DCR configuration if DCR mode is enabled\n const dcrConfig = oauthConfig.auth === 'dcr' ? oauthGoogle.parseDcrConfig(args, env, GOOGLE_SCOPE) : undefined;\n\n // Parse application-level config (LOG_LEVEL, RESOURCE_STORE_URI, BASE_URL)\n const { values } = parseArgs({\n args,\n options: {\n 'log-level': { type: 'string' },\n 'base-url': { type: 'string' },\n 'resource-store-uri': { type: 'string' },\n },\n strict: false, // Allow other arguments\n allowPositionals: true,\n });\n\n const name = pkg.name.replace(/^@[^/]+\\//, '');\n // Parse repository URL from package.json, stripping git+ prefix and .git suffix\n const rawRepoUrl = typeof pkg.repository === 'object' ? pkg.repository.url : pkg.repository;\n const repositoryUrl = rawRepoUrl?.replace(/^git\\+/, '').replace(/\\.git$/, '') ?? `https://github.com/mcp-z/${name}`;\n let rootDir = homedir();\n try {\n const configPath = mcpServer.findConfigPath({ config: '.mcp.json', cwd: process.cwd(), stopDir: homedir() });\n rootDir = path.dirname(configPath);\n } catch {\n rootDir = homedir();\n }\n const baseDir = path.join(rootDir, '.mcp-z');\n const cliLogLevel = typeof values['log-level'] === 'string' ? values['log-level'] : undefined;\n const envLogLevel = env.LOG_LEVEL;\n const logLevel = cliLogLevel ?? envLogLevel ?? 'info';\n\n // Parse storage configuration\n const cliResourceStoreUri = typeof values['resource-store-uri'] === 'string' ? values['resource-store-uri'] : undefined;\n const envResourceStoreUri = env.RESOURCE_STORE_URI;\n const defaultResourceStorePath = path.join(baseDir, name, 'files');\n const resourceStoreUri = normalizeResourceStoreUri(cliResourceStoreUri ?? envResourceStoreUri ?? defaultResourceStorePath);\n\n const cliBaseUrl = typeof values['base-url'] === 'string' ? values['base-url'] : undefined;\n const envBaseUrl = env.BASE_URL;\n const baseUrl = cliBaseUrl ?? envBaseUrl;\n\n // Combine configs\n const result: ServerConfig = {\n ...oauthConfig, // Includes clientId, auth, headless, redirectUri, serviceAccountKeyFile\n transport: transportConfig.transport,\n logLevel,\n baseDir,\n name,\n version: pkg.version,\n repositoryUrl,\n resourceStoreUri,\n };\n if (baseUrl) result.baseUrl = baseUrl;\n if (dcrConfig !== undefined) result.dcrConfig = dcrConfig;\n return result;\n}\n\n/**\n * Build production configuration from process globals.\n * Entry point for production server.\n */\nexport function createConfig(): ServerConfig {\n return parseConfig(process.argv, process.env);\n}\n\nfunction normalizeResourceStoreUri(resourceStoreUri: string): string {\n const filePrefix = 'file://';\n if (resourceStoreUri.startsWith(filePrefix)) {\n const rawPath = resourceStoreUri.slice(filePrefix.length);\n const expandedPath = rawPath.startsWith('~') ? rawPath.replace(/^~/, homedir()) : rawPath;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n }\n\n if (resourceStoreUri.includes('://')) return resourceStoreUri;\n\n const expandedPath = resourceStoreUri.startsWith('~') ? resourceStoreUri.replace(/^~/, homedir()) : resourceStoreUri;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n}\n"],"names":["createConfig","parseConfig","pkg","readPkg","_require","require","Module","createRequire","args","env","cliLogLevel","cliResourceStoreUri","oauthGoogle","mcpServer","transportConfig","oauthConfig","dcrConfig","auth","parseDcrConfig","GOOGLE_SCOPE","undefined","values","parseArgs","options","type","strict","allowPositionals","name","replace","rawRepoUrl","repository","url","repositoryUrl","rootDir","homedir","configPath","findConfigPath","config","cwd","process","stopDir","path","dirname","baseDir","join","envLogLevel","LOG_LEVEL","logLevel","envResourceStoreUri","RESOURCE_STORE_URI","defaultResourceStorePath","resourceStoreUri","normalizeResourceStoreUri","cliBaseUrl","envBaseUrl","BASE_URL","baseUrl","result","transport","version","argv","filePrefix","startsWith","rawPath","slice","length","expandedPath","resolve","includes"],"mappings":"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"}
@@ -0,0 +1,16 @@
1
+ /** Package metadata read from package.json, resolved relative to this file. */
2
+ export declare function readPkg(): {
3
+ name: string;
4
+ version: string;
5
+ repository?: string | {
6
+ url?: string;
7
+ };
8
+ };
9
+ /**
10
+ * Handle --version/--help flags and the `version` subcommand before config parsing.
11
+ * These must work without requiring any configuration or heavy dependency.
12
+ */
13
+ export declare function handleVersionHelp(args: string[]): {
14
+ handled: boolean;
15
+ output?: string;
16
+ };
@@ -0,0 +1,16 @@
1
+ /** Package metadata read from package.json, resolved relative to this file. */
2
+ export declare function readPkg(): {
3
+ name: string;
4
+ version: string;
5
+ repository?: string | {
6
+ url?: string;
7
+ };
8
+ };
9
+ /**
10
+ * Handle --version/--help flags and the `version` subcommand before config parsing.
11
+ * These must work without requiring any configuration or heavy dependency.
12
+ */
13
+ export declare function handleVersionHelp(args: string[]): {
14
+ handled: boolean;
15
+ output?: string;
16
+ };
@@ -0,0 +1,93 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", {
3
+ value: true
4
+ });
5
+ function _export(target, all) {
6
+ for(var name in all)Object.defineProperty(target, name, {
7
+ enumerable: true,
8
+ get: Object.getOwnPropertyDescriptor(all, name).get
9
+ });
10
+ }
11
+ _export(exports, {
12
+ get handleVersionHelp () {
13
+ return handleVersionHelp;
14
+ },
15
+ get readPkg () {
16
+ return readPkg;
17
+ }
18
+ });
19
+ var _fs = /*#__PURE__*/ _interop_require_wildcard(require("fs"));
20
+ var _modulerootsync = /*#__PURE__*/ _interop_require_default(require("module-root-sync"));
21
+ var _path = /*#__PURE__*/ _interop_require_wildcard(require("path"));
22
+ var _url = /*#__PURE__*/ _interop_require_wildcard(require("url"));
23
+ var _util = require("util");
24
+ function _interop_require_default(obj) {
25
+ return obj && obj.__esModule ? obj : {
26
+ default: obj
27
+ };
28
+ }
29
+ function _getRequireWildcardCache(nodeInterop) {
30
+ if (typeof WeakMap !== "function") return null;
31
+ var cacheBabelInterop = new WeakMap();
32
+ var cacheNodeInterop = new WeakMap();
33
+ return (_getRequireWildcardCache = function(nodeInterop) {
34
+ return nodeInterop ? cacheNodeInterop : cacheBabelInterop;
35
+ })(nodeInterop);
36
+ }
37
+ function _interop_require_wildcard(obj, nodeInterop) {
38
+ if (!nodeInterop && obj && obj.__esModule) return obj;
39
+ if (obj === null || typeof obj !== "object" && typeof obj !== "function") return {
40
+ default: obj
41
+ };
42
+ var cache = _getRequireWildcardCache(nodeInterop);
43
+ if (cache && cache.has(obj)) return cache.get(obj);
44
+ var newObj = {
45
+ __proto__: null
46
+ };
47
+ var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor;
48
+ for(var key in obj){
49
+ if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) {
50
+ var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null;
51
+ if (desc && (desc.get || desc.set)) Object.defineProperty(newObj, key, desc);
52
+ else newObj[key] = obj[key];
53
+ }
54
+ }
55
+ newObj.default = obj;
56
+ if (cache) cache.set(obj, newObj);
57
+ return newObj;
58
+ }
59
+ // Kept dependency-free (fs/path/url/module-root-sync only) so `--version`/`--help`/`version`
60
+ // resolve nothing beyond Node startup: config.ts's parseConfig pulls in @mcp-z/oauth-google and
61
+ // @mcp-z/server, which this path must not touch.
62
+ var pkg = JSON.parse(_fs.readFileSync(_path.join((0, _modulerootsync.default)(_url.fileURLToPath(require("url").pathToFileURL(__filename).toString())), 'package.json'), 'utf-8'));
63
+ var HELP_TEXT = "\nUsage: mcp-gmail [options]\n\nMCP server for Gmail email management with OAuth authentication.\n\nOptions:\n --version Show version number\n --help Show this help message\n --auth=<mode> Authentication mode (default: loopback-oauth)\n Modes: loopback-oauth, service-account, dcr\n --headless Disable browser auto-open, return auth URL instead\n --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n --dcr-verify-url=<url> External verification endpoint (required for external mode)\n --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n --port=<port> Enable HTTP transport on specified port\n --stdio Enable stdio transport (default if no port)\n --log-level=<level> Logging level (default: info)\n --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n --base-url=<url> Base URL for HTTP file serving (optional)\n\nCommands:\n version Show version number\n\nEnvironment Variables:\n GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n AUTH_MODE Default authentication mode (optional)\n HEADLESS Disable browser auto-open (optional)\n DCR_MODE DCR mode (optional, same format as --dcr-mode)\n DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n TOKEN_STORE_URI Token storage URI (optional)\n PORT Default HTTP port (optional)\n LOG_LEVEL Default logging level (optional)\n RESOURCE_STORE_URI Resource store URI (optional, file://)\n BASE_URL Default base URL for file serving (optional)\n\nOAuth Scopes:\n openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n\nExamples:\n mcp-gmail # Use default settings\n mcp-gmail version # Print version number\n mcp-gmail --auth=service-account # Use service account auth\n mcp-gmail --port=3000 # HTTP transport on port 3000\n mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI\n GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var\n".trim();
64
+ function readPkg() {
65
+ return pkg;
66
+ }
67
+ function handleVersionHelp(args) {
68
+ var _parseArgs = (0, _util.parseArgs)({
69
+ args: args,
70
+ options: {
71
+ version: {
72
+ type: 'boolean'
73
+ },
74
+ help: {
75
+ type: 'boolean'
76
+ }
77
+ },
78
+ strict: false,
79
+ allowPositionals: true
80
+ }), values = _parseArgs.values, positionals = _parseArgs.positionals;
81
+ if (values.version || positionals[0] === 'version') return {
82
+ handled: true,
83
+ output: pkg.version
84
+ };
85
+ if (values.help) return {
86
+ handled: true,
87
+ output: HELP_TEXT
88
+ };
89
+ return {
90
+ handled: false
91
+ };
92
+ }
93
+ /* CJS INTEROP */ if (exports.__esModule && exports.default) { try { Object.defineProperty(exports.default, '__esModule', { value: true }); for (var key in exports) { exports.default[key] = exports[key]; } } catch (_) {}; module.exports = exports.default; }
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/setup/version-help.ts"],"sourcesContent":["import * as fs from 'fs';\nimport moduleRoot from 'module-root-sync';\nimport * as path from 'path';\nimport * as url from 'url';\nimport { parseArgs } from 'util';\n\n// Kept dependency-free (fs/path/url/module-root-sync only) so `--version`/`--help`/`version`\n// resolve nothing beyond Node startup: config.ts's parseConfig pulls in @mcp-z/oauth-google and\n// @mcp-z/server, which this path must not touch.\nconst pkg = JSON.parse(fs.readFileSync(path.join(moduleRoot(url.fileURLToPath(import.meta.url)), 'package.json'), 'utf-8'));\n\nconst HELP_TEXT = `\nUsage: mcp-gmail [options]\n\nMCP server for Gmail email management with OAuth authentication.\n\nOptions:\n --version Show version number\n --help Show this help message\n --auth=<mode> Authentication mode (default: loopback-oauth)\n Modes: loopback-oauth, service-account, dcr\n --headless Disable browser auto-open, return auth URL instead\n --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n --dcr-verify-url=<url> External verification endpoint (required for external mode)\n --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n --port=<port> Enable HTTP transport on specified port\n --stdio Enable stdio transport (default if no port)\n --log-level=<level> Logging level (default: info)\n --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n --base-url=<url> Base URL for HTTP file serving (optional)\n\nCommands:\n version Show version number\n\nEnvironment Variables:\n GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n AUTH_MODE Default authentication mode (optional)\n HEADLESS Disable browser auto-open (optional)\n DCR_MODE DCR mode (optional, same format as --dcr-mode)\n DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n TOKEN_STORE_URI Token storage URI (optional)\n PORT Default HTTP port (optional)\n LOG_LEVEL Default logging level (optional)\n RESOURCE_STORE_URI Resource store URI (optional, file://)\n BASE_URL Default base URL for file serving (optional)\n\nOAuth Scopes:\n openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n\nExamples:\n mcp-gmail # Use default settings\n mcp-gmail version # Print version number\n mcp-gmail --auth=service-account # Use service account auth\n mcp-gmail --port=3000 # HTTP transport on port 3000\n mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI\n GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var\n`.trim();\n\n/** Package metadata read from package.json, resolved relative to this file. */\nexport function readPkg(): { name: string; version: string; repository?: string | { url?: string } } {\n return pkg;\n}\n\n/**\n * Handle --version/--help flags and the `version` subcommand before config parsing.\n * These must work without requiring any configuration or heavy dependency.\n */\nexport function handleVersionHelp(args: string[]): { handled: boolean; output?: string } {\n const { values, positionals } = parseArgs({\n args,\n options: {\n version: { type: 'boolean' },\n help: { type: 'boolean' },\n },\n strict: false,\n allowPositionals: true,\n });\n\n if (values.version || positionals[0] === 'version') return { handled: true, output: pkg.version };\n if (values.help) return { handled: true, output: HELP_TEXT };\n return { handled: false };\n}\n"],"names":["handleVersionHelp","readPkg","pkg","JSON","parse","fs","readFileSync","path","join","moduleRoot","url","fileURLToPath","HELP_TEXT","trim","args","parseArgs","options","version","type","help","strict","allowPositionals","values","positionals","handled","output"],"mappings":";;;;;;;;;;;QAsEgBA;eAAAA;;QARAC;eAAAA;;;0DA9DI;qEACG;4DACD;2DACD;oBACK;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAE1B,6FAA6F;AAC7F,gGAAgG;AAChG,iDAAiD;AACjD,IAAMC,MAAMC,KAAKC,KAAK,CAACC,IAAGC,YAAY,CAACC,MAAKC,IAAI,CAACC,IAAAA,uBAAU,EAACC,KAAIC,aAAa,CAAC,uDAAmB,iBAAiB;AAElH,IAAMC,YAAY,8gFAgDhBC,IAAI;AAGC,SAASZ;IACd,OAAOC;AACT;AAMO,SAASF,kBAAkBc,IAAc;IAC9C,IAAgCC,aAAAA,IAAAA,eAAS,EAAC;QACxCD,MAAAA;QACAE,SAAS;YACPC,SAAS;gBAAEC,MAAM;YAAU;YAC3BC,MAAM;gBAAED,MAAM;YAAU;QAC1B;QACAE,QAAQ;QACRC,kBAAkB;IACpB,IARQC,SAAwBP,WAAxBO,QAAQC,cAAgBR,WAAhBQ;IAUhB,IAAID,OAAOL,OAAO,IAAIM,WAAW,CAAC,EAAE,KAAK,WAAW,OAAO;QAAEC,SAAS;QAAMC,QAAQvB,IAAIe,OAAO;IAAC;IAChG,IAAIK,OAAOH,IAAI,EAAE,OAAO;QAAEK,SAAS;QAAMC,QAAQb;IAAU;IAC3D,OAAO;QAAEY,SAAS;IAAM;AAC1B"}
package/dist/esm/index.js CHANGED
@@ -1,6 +1,4 @@
1
- import { createConfig, handleVersionHelp } from './setup/config.js';
2
- import { createHTTPServer } from './setup/http.js';
3
- import { createStdioServer } from './setup/stdio.js';
1
+ import { handleVersionHelp } from './setup/version-help.js';
4
2
  export { GOOGLE_SCOPE } from './constants.js';
5
3
  import * as _mcp from './mcp/index.js';
6
4
  export { _mcp as mcp };
@@ -12,6 +10,10 @@ import * as _setup from './setup/index.js';
12
10
  export { _setup as setup };
13
11
  export * from './types.js';
14
12
  export async function startServer(config) {
13
+ // createHTTPServer/createStdioServer pull in @modelcontextprotocol/sdk and every mcp/tools/*.ts
14
+ // (googleapis included); deferred so a --version/--help run never reaches them.
15
+ const { createHTTPServer } = await import('./setup/http.js');
16
+ const { createStdioServer } = await import('./setup/stdio.js');
15
17
  const { logger, close } = config.transport.type === 'stdio' ? await createStdioServer(config) : await createHTTPServer(config);
16
18
  process.on('SIGINT', async ()=>{
17
19
  await close();
@@ -27,7 +29,9 @@ export default async function main() {
27
29
  console.log(versionHelpResult.output);
28
30
  process.exit(0);
29
31
  }
30
- // Only parse config if no help/version flags
32
+ // Only parse config if no help/version flags. config.ts's own heavy imports (@mcp-z/oauth-google,
33
+ // @mcp-z/server) are deferred internally, so this static-looking call stays cheap until here.
34
+ const { createConfig } = await import('./setup/config.js');
31
35
  const config = createConfig();
32
36
  await startServer(config);
33
37
  }
@@ -1 +1 @@
1
- {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/index.ts"],"sourcesContent":["import { createConfig, handleVersionHelp } from './setup/config.ts';\nimport { createHTTPServer } from './setup/http.ts';\nimport { createStdioServer } from './setup/stdio.ts';\nimport type { ServerConfig } from './types.ts';\n\nexport { GOOGLE_SCOPE } from './constants.ts';\nexport * as mcp from './mcp/index.ts';\n// Export types and schemas for documentation\nexport type { Input as CategoriesListInput } from './mcp/tools/categories-list.ts';\nexport { inputSchema as CategoriesListInputSchema } from './mcp/tools/categories-list.ts';\nexport type { Input as LabelsListInput } from './mcp/tools/labels-list.ts';\nexport { inputSchema as LabelsListInputSchema } from './mcp/tools/labels-list.ts';\nexport * as schemas from './schemas/index.ts';\nexport * as setup from './setup/index.ts';\nexport * from './types.ts';\n\nexport async function startServer(config: ServerConfig): Promise<void> {\n const { logger, close } = config.transport.type === 'stdio' ? await createStdioServer(config) : await createHTTPServer(config);\n\n process.on('SIGINT', async () => {\n await close();\n process.exit(0);\n });\n\n logger.info(`Server started with ${config.transport.type} transport`);\n await new Promise(() => {});\n}\n\nexport default async function main(): Promise<void> {\n // Check for help/version flags FIRST, before config parsing\n const versionHelpResult = handleVersionHelp(process.argv);\n if (versionHelpResult.handled) {\n console.log(versionHelpResult.output);\n process.exit(0);\n }\n\n // Only parse config if no help/version flags\n const config = createConfig();\n await startServer(config);\n}\n\nif (process.argv[1] === new URL(import.meta.url).pathname) {\n main();\n}\n"],"names":["createConfig","handleVersionHelp","createHTTPServer","createStdioServer","GOOGLE_SCOPE","mcp","inputSchema","CategoriesListInputSchema","LabelsListInputSchema","schemas","setup","startServer","config","logger","close","transport","type","process","on","exit","info","Promise","main","versionHelpResult","argv","handled","console","log","output","URL","url","pathname"],"mappings":"AAAA,SAASA,YAAY,EAAEC,iBAAiB,QAAQ,oBAAoB;AACpE,SAASC,gBAAgB,QAAQ,kBAAkB;AACnD,SAASC,iBAAiB,QAAQ,mBAAmB;AAGrD,SAASC,YAAY,QAAQ,iBAAiB;AAC9C,sBAAqB,iBAAiB;AAAtC,SAAO,QAAKC,GAAG,GAAuB;AAGtC,SAASC,eAAeC,yBAAyB,QAAQ,iCAAiC;AAE1F,SAASD,eAAeE,qBAAqB,QAAQ,6BAA6B;AAClF,0BAAyB,qBAAqB;AAA9C,SAAO,YAAKC,OAAO,GAA2B;AAC9C,wBAAuB,mBAAmB;AAA1C,SAAO,UAAKC,KAAK,GAAyB;AAC1C,cAAc,aAAa;AAE3B,OAAO,eAAeC,YAAYC,MAAoB;IACpD,MAAM,EAAEC,MAAM,EAAEC,KAAK,EAAE,GAAGF,OAAOG,SAAS,CAACC,IAAI,KAAK,UAAU,MAAMb,kBAAkBS,UAAU,MAAMV,iBAAiBU;IAEvHK,QAAQC,EAAE,CAAC,UAAU;QACnB,MAAMJ;QACNG,QAAQE,IAAI,CAAC;IACf;IAEAN,OAAOO,IAAI,CAAC,CAAC,oBAAoB,EAAER,OAAOG,SAAS,CAACC,IAAI,CAAC,UAAU,CAAC;IACpE,MAAM,IAAIK,QAAQ,KAAO;AAC3B;AAEA,eAAe,eAAeC;IAC5B,4DAA4D;IAC5D,MAAMC,oBAAoBtB,kBAAkBgB,QAAQO,IAAI;IACxD,IAAID,kBAAkBE,OAAO,EAAE;QAC7BC,QAAQC,GAAG,CAACJ,kBAAkBK,MAAM;QACpCX,QAAQE,IAAI,CAAC;IACf;IAEA,6CAA6C;IAC7C,MAAMP,SAASZ;IACf,MAAMW,YAAYC;AACpB;AAEA,IAAIK,QAAQO,IAAI,CAAC,EAAE,KAAK,IAAIK,IAAI,YAAYC,GAAG,EAAEC,QAAQ,EAAE;IACzDT;AACF"}
1
+ {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/index.ts"],"sourcesContent":["import { handleVersionHelp } from './setup/version-help.ts';\nimport type { ServerConfig } from './types.ts';\n\nexport { GOOGLE_SCOPE } from './constants.ts';\nexport * as mcp from './mcp/index.ts';\n// Export types and schemas for documentation\nexport type { Input as CategoriesListInput } from './mcp/tools/categories-list.ts';\nexport { inputSchema as CategoriesListInputSchema } from './mcp/tools/categories-list.ts';\nexport type { Input as LabelsListInput } from './mcp/tools/labels-list.ts';\nexport { inputSchema as LabelsListInputSchema } from './mcp/tools/labels-list.ts';\nexport * as schemas from './schemas/index.ts';\nexport * as setup from './setup/index.ts';\nexport * from './types.ts';\n\nexport async function startServer(config: ServerConfig): Promise<void> {\n // createHTTPServer/createStdioServer pull in @modelcontextprotocol/sdk and every mcp/tools/*.ts\n // (googleapis included); deferred so a --version/--help run never reaches them.\n const { createHTTPServer } = await import('./setup/http.ts');\n const { createStdioServer } = await import('./setup/stdio.ts');\n const { logger, close } = config.transport.type === 'stdio' ? await createStdioServer(config) : await createHTTPServer(config);\n\n process.on('SIGINT', async () => {\n await close();\n process.exit(0);\n });\n\n logger.info(`Server started with ${config.transport.type} transport`);\n await new Promise(() => {});\n}\n\nexport default async function main(): Promise<void> {\n // Check for help/version flags FIRST, before config parsing\n const versionHelpResult = handleVersionHelp(process.argv);\n if (versionHelpResult.handled) {\n console.log(versionHelpResult.output);\n process.exit(0);\n }\n\n // Only parse config if no help/version flags. config.ts's own heavy imports (@mcp-z/oauth-google,\n // @mcp-z/server) are deferred internally, so this static-looking call stays cheap until here.\n const { createConfig } = await import('./setup/config.ts');\n const config = createConfig();\n await startServer(config);\n}\n\nif (process.argv[1] === new URL(import.meta.url).pathname) {\n main();\n}\n"],"names":["handleVersionHelp","GOOGLE_SCOPE","mcp","inputSchema","CategoriesListInputSchema","LabelsListInputSchema","schemas","setup","startServer","config","createHTTPServer","createStdioServer","logger","close","transport","type","process","on","exit","info","Promise","main","versionHelpResult","argv","handled","console","log","output","createConfig","URL","url","pathname"],"mappings":"AAAA,SAASA,iBAAiB,QAAQ,0BAA0B;AAG5D,SAASC,YAAY,QAAQ,iBAAiB;AAC9C,sBAAqB,iBAAiB;AAAtC,SAAO,QAAKC,GAAG,GAAuB;AAGtC,SAASC,eAAeC,yBAAyB,QAAQ,iCAAiC;AAE1F,SAASD,eAAeE,qBAAqB,QAAQ,6BAA6B;AAClF,0BAAyB,qBAAqB;AAA9C,SAAO,YAAKC,OAAO,GAA2B;AAC9C,wBAAuB,mBAAmB;AAA1C,SAAO,UAAKC,KAAK,GAAyB;AAC1C,cAAc,aAAa;AAE3B,OAAO,eAAeC,YAAYC,MAAoB;IACpD,gGAAgG;IAChG,gFAAgF;IAChF,MAAM,EAAEC,gBAAgB,EAAE,GAAG,MAAM,MAAM,CAAC;IAC1C,MAAM,EAAEC,iBAAiB,EAAE,GAAG,MAAM,MAAM,CAAC;IAC3C,MAAM,EAAEC,MAAM,EAAEC,KAAK,EAAE,GAAGJ,OAAOK,SAAS,CAACC,IAAI,KAAK,UAAU,MAAMJ,kBAAkBF,UAAU,MAAMC,iBAAiBD;IAEvHO,QAAQC,EAAE,CAAC,UAAU;QACnB,MAAMJ;QACNG,QAAQE,IAAI,CAAC;IACf;IAEAN,OAAOO,IAAI,CAAC,CAAC,oBAAoB,EAAEV,OAAOK,SAAS,CAACC,IAAI,CAAC,UAAU,CAAC;IACpE,MAAM,IAAIK,QAAQ,KAAO;AAC3B;AAEA,eAAe,eAAeC;IAC5B,4DAA4D;IAC5D,MAAMC,oBAAoBtB,kBAAkBgB,QAAQO,IAAI;IACxD,IAAID,kBAAkBE,OAAO,EAAE;QAC7BC,QAAQC,GAAG,CAACJ,kBAAkBK,MAAM;QACpCX,QAAQE,IAAI,CAAC;IACf;IAEA,kGAAkG;IAClG,8FAA8F;IAC9F,MAAM,EAAEU,YAAY,EAAE,GAAG,MAAM,MAAM,CAAC;IACtC,MAAMnB,SAASmB;IACf,MAAMpB,YAAYC;AACpB;AAEA,IAAIO,QAAQO,IAAI,CAAC,EAAE,KAAK,IAAIM,IAAI,YAAYC,GAAG,EAAEC,QAAQ,EAAE;IACzDV;AACF"}
@@ -1,12 +1,4 @@
1
1
  import type { ServerConfig } from '../types.js';
2
- /**
3
- * Handle --version and --help flags before config parsing.
4
- * These should work without requiring any configuration.
5
- */
6
- export declare function handleVersionHelp(args: string[]): {
7
- handled: boolean;
8
- output?: string;
9
- };
10
2
  /**
11
3
  * Parse Gmail server configuration from CLI arguments and environment.
12
4
  *
@@ -1,86 +1,13 @@
1
- import { parseDcrConfig, parseConfig as parseOAuthConfig } from '@mcp-z/oauth-google';
2
- import { findConfigPath, parseConfig as parseTransportConfig } from '@mcp-z/server';
3
- import * as fs from 'fs';
4
- import moduleRoot from 'module-root-sync';
1
+ import { Module } from 'module';
5
2
  import { homedir } from 'os';
6
3
  import * as path from 'path';
7
- import * as url from 'url';
8
4
  import { parseArgs } from 'util';
9
5
  import { GOOGLE_SCOPE } from '../constants.js';
10
- const pkg = JSON.parse(fs.readFileSync(path.join(moduleRoot(url.fileURLToPath(import.meta.url)), 'package.json'), 'utf-8'));
11
- const HELP_TEXT = `
12
- Usage: mcp-gmail [options]
13
-
14
- MCP server for Gmail email management with OAuth authentication.
15
-
16
- Options:
17
- --version Show version number
18
- --help Show this help message
19
- --auth=<mode> Authentication mode (default: loopback-oauth)
20
- Modes: loopback-oauth, service-account, dcr
21
- --headless Disable browser auto-open, return auth URL instead
22
- --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)
23
- --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)
24
- --dcr-verify-url=<url> External verification endpoint (required for external mode)
25
- --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)
26
- --port=<port> Enable HTTP transport on specified port
27
- --stdio Enable stdio transport (default if no port)
28
- --log-level=<level> Logging level (default: info)
29
- --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)
30
- --base-url=<url> Base URL for HTTP file serving (optional)
31
-
32
- Environment Variables:
33
- GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)
34
- GOOGLE_CLIENT_SECRET OAuth client secret (optional)
35
- AUTH_MODE Default authentication mode (optional)
36
- HEADLESS Disable browser auto-open (optional)
37
- DCR_MODE DCR mode (optional, same format as --dcr-mode)
38
- DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)
39
- DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)
40
- TOKEN_STORE_URI Token storage URI (optional)
41
- PORT Default HTTP port (optional)
42
- LOG_LEVEL Default logging level (optional)
43
- RESOURCE_STORE_URI Resource store URI (optional, file://)
44
- BASE_URL Default base URL for file serving (optional)
45
-
46
- OAuth Scopes:
47
- openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/
48
-
49
- Examples:
50
- mcp-gmail # Use default settings
51
- mcp-gmail --auth=service-account # Use service account auth
52
- mcp-gmail --port=3000 # HTTP transport on port 3000
53
- mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI
54
- GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var
55
- `.trim();
56
- /**
57
- * Handle --version and --help flags before config parsing.
58
- * These should work without requiring any configuration.
59
- */ export function handleVersionHelp(args) {
60
- const { values } = parseArgs({
61
- args,
62
- options: {
63
- version: {
64
- type: 'boolean'
65
- },
66
- help: {
67
- type: 'boolean'
68
- }
69
- },
70
- strict: false
71
- });
72
- if (values.version) return {
73
- handled: true,
74
- output: pkg.version
75
- };
76
- if (values.help) return {
77
- handled: true,
78
- output: HELP_TEXT
79
- };
80
- return {
81
- handled: false
82
- };
83
- }
6
+ import { readPkg } from './version-help.js';
7
+ const pkg = readPkg();
8
+ // @mcp-z/oauth-google and @mcp-z/server are requireable at the >=20 floor; deferred so
9
+ // --version/--help (handled via version-help.ts, never this file) load neither package.
10
+ const _require = typeof require === 'undefined' ? Module.createRequire(import.meta.url) : require;
84
11
  /**
85
12
  * Parse Gmail server configuration from CLI arguments and environment.
86
13
  *
@@ -116,10 +43,12 @@ Examples:
116
43
  * openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/
117
44
  */ export function parseConfig(args, env) {
118
45
  var _ref, _ref1, _ref2;
119
- const transportConfig = parseTransportConfig(args, env);
120
- const oauthConfig = parseOAuthConfig(args, env);
46
+ const oauthGoogle = _require('@mcp-z/oauth-google');
47
+ const mcpServer = _require('@mcp-z/server');
48
+ const transportConfig = mcpServer.parseConfig(args, env);
49
+ const oauthConfig = oauthGoogle.parseConfig(args, env);
121
50
  // Parse DCR configuration if DCR mode is enabled
122
- const dcrConfig = oauthConfig.auth === 'dcr' ? parseDcrConfig(args, env, GOOGLE_SCOPE) : undefined;
51
+ const dcrConfig = oauthConfig.auth === 'dcr' ? oauthGoogle.parseDcrConfig(args, env, GOOGLE_SCOPE) : undefined;
123
52
  // Parse application-level config (LOG_LEVEL, RESOURCE_STORE_URI, BASE_URL)
124
53
  const { values } = parseArgs({
125
54
  args,
@@ -143,7 +72,7 @@ Examples:
143
72
  const repositoryUrl = (_ref = rawRepoUrl === null || rawRepoUrl === void 0 ? void 0 : rawRepoUrl.replace(/^git\+/, '').replace(/\.git$/, '')) !== null && _ref !== void 0 ? _ref : `https://github.com/mcp-z/${name}`;
144
73
  let rootDir = homedir();
145
74
  try {
146
- const configPath = findConfigPath({
75
+ const configPath = mcpServer.findConfigPath({
147
76
  config: '.mcp.json',
148
77
  cwd: process.cwd(),
149
78
  stopDir: homedir()
@@ -1 +1 @@
1
- {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/setup/config.ts"],"sourcesContent":["import { parseDcrConfig, parseConfig as parseOAuthConfig } from '@mcp-z/oauth-google';\nimport { findConfigPath, parseConfig as parseTransportConfig } from '@mcp-z/server';\nimport * as fs from 'fs';\nimport moduleRoot from 'module-root-sync';\nimport { homedir } from 'os';\nimport * as path from 'path';\nimport * as url from 'url';\nimport { parseArgs } from 'util';\nimport { GOOGLE_SCOPE } from '../constants.ts';\nimport type { ServerConfig } from '../types.ts';\n\nconst pkg = JSON.parse(fs.readFileSync(path.join(moduleRoot(url.fileURLToPath(import.meta.url)), 'package.json'), 'utf-8'));\n\nconst HELP_TEXT = `\nUsage: mcp-gmail [options]\n\nMCP server for Gmail email management with OAuth authentication.\n\nOptions:\n --version Show version number\n --help Show this help message\n --auth=<mode> Authentication mode (default: loopback-oauth)\n Modes: loopback-oauth, service-account, dcr\n --headless Disable browser auto-open, return auth URL instead\n --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n --dcr-verify-url=<url> External verification endpoint (required for external mode)\n --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n --port=<port> Enable HTTP transport on specified port\n --stdio Enable stdio transport (default if no port)\n --log-level=<level> Logging level (default: info)\n --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n --base-url=<url> Base URL for HTTP file serving (optional)\n\nEnvironment Variables:\n GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n AUTH_MODE Default authentication mode (optional)\n HEADLESS Disable browser auto-open (optional)\n DCR_MODE DCR mode (optional, same format as --dcr-mode)\n DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n TOKEN_STORE_URI Token storage URI (optional)\n PORT Default HTTP port (optional)\n LOG_LEVEL Default logging level (optional)\n RESOURCE_STORE_URI Resource store URI (optional, file://)\n BASE_URL Default base URL for file serving (optional)\n\nOAuth Scopes:\n openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n\nExamples:\n mcp-gmail # Use default settings\n mcp-gmail --auth=service-account # Use service account auth\n mcp-gmail --port=3000 # HTTP transport on port 3000\n mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI\n GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var\n`.trim();\n\n/**\n * Handle --version and --help flags before config parsing.\n * These should work without requiring any configuration.\n */\nexport function handleVersionHelp(args: string[]): { handled: boolean; output?: string } {\n const { values } = parseArgs({\n args,\n options: {\n version: { type: 'boolean' },\n help: { type: 'boolean' },\n },\n strict: false,\n });\n\n if (values.version) return { handled: true, output: pkg.version };\n if (values.help) return { handled: true, output: HELP_TEXT };\n return { handled: false };\n}\n\n/**\n * Parse Gmail server configuration from CLI arguments and environment.\n *\n * CLI Arguments (all optional):\n * - --auth=<mode> Authentication mode (default: loopback-oauth)\n * Modes: loopback-oauth, service-account, dcr\n * - --headless Disable browser auto-open, return auth URL instead\n * - --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n * - --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n * - --dcr-verify-url=<url> External verification endpoint (required for external mode)\n * - --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n * - --port=<port> Enable HTTP transport on specified port\n * - --stdio Enable stdio transport (default if no port)\n * - --log-level=<level> Logging level (default: info)\n * - --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n * - --base-url=<url> Base URL for HTTP file serving (optional)\n *\n * Environment Variables:\n * - GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n * - GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n * - AUTH_MODE Default authentication mode (optional)\n * - HEADLESS Disable browser auto-open (optional)\n * - DCR_MODE DCR mode (optional, same format as --dcr-mode)\n * - DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n * - DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n * - TOKEN_STORE_URI Token storage URI (optional)\n * - PORT Default HTTP port (optional)\n * - LOG_LEVEL Default logging level (optional)\n * - RESOURCE_STORE_URI Resource store URI (optional, file://)\n * - BASE_URL Default base URL for file serving (optional)\n *\n * OAuth Scopes (from constants.ts):\n * openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n */\nexport function parseConfig(args: string[], env: Record<string, string | undefined>): ServerConfig {\n const transportConfig = parseTransportConfig(args, env);\n const oauthConfig = parseOAuthConfig(args, env);\n\n // Parse DCR configuration if DCR mode is enabled\n const dcrConfig = oauthConfig.auth === 'dcr' ? parseDcrConfig(args, env, GOOGLE_SCOPE) : undefined;\n\n // Parse application-level config (LOG_LEVEL, RESOURCE_STORE_URI, BASE_URL)\n const { values } = parseArgs({\n args,\n options: {\n 'log-level': { type: 'string' },\n 'base-url': { type: 'string' },\n 'resource-store-uri': { type: 'string' },\n },\n strict: false, // Allow other arguments\n allowPositionals: true,\n });\n\n const name = pkg.name.replace(/^@[^/]+\\//, '');\n // Parse repository URL from package.json, stripping git+ prefix and .git suffix\n const rawRepoUrl = typeof pkg.repository === 'object' ? pkg.repository.url : pkg.repository;\n const repositoryUrl = rawRepoUrl?.replace(/^git\\+/, '').replace(/\\.git$/, '') ?? `https://github.com/mcp-z/${name}`;\n let rootDir = homedir();\n try {\n const configPath = findConfigPath({ config: '.mcp.json', cwd: process.cwd(), stopDir: homedir() });\n rootDir = path.dirname(configPath);\n } catch {\n rootDir = homedir();\n }\n const baseDir = path.join(rootDir, '.mcp-z');\n const cliLogLevel = typeof values['log-level'] === 'string' ? values['log-level'] : undefined;\n const envLogLevel = env.LOG_LEVEL;\n const logLevel = cliLogLevel ?? envLogLevel ?? 'info';\n\n // Parse storage configuration\n const cliResourceStoreUri = typeof values['resource-store-uri'] === 'string' ? values['resource-store-uri'] : undefined;\n const envResourceStoreUri = env.RESOURCE_STORE_URI;\n const defaultResourceStorePath = path.join(baseDir, name, 'files');\n const resourceStoreUri = normalizeResourceStoreUri(cliResourceStoreUri ?? envResourceStoreUri ?? defaultResourceStorePath);\n\n const cliBaseUrl = typeof values['base-url'] === 'string' ? values['base-url'] : undefined;\n const envBaseUrl = env.BASE_URL;\n const baseUrl = cliBaseUrl ?? envBaseUrl;\n\n // Combine configs\n const result: ServerConfig = {\n ...oauthConfig, // Includes clientId, auth, headless, redirectUri, serviceAccountKeyFile\n transport: transportConfig.transport,\n logLevel,\n baseDir,\n name,\n version: pkg.version,\n repositoryUrl,\n resourceStoreUri,\n };\n if (baseUrl) result.baseUrl = baseUrl;\n if (dcrConfig !== undefined) result.dcrConfig = dcrConfig;\n return result;\n}\n\n/**\n * Build production configuration from process globals.\n * Entry point for production server.\n */\nexport function createConfig(): ServerConfig {\n return parseConfig(process.argv, process.env);\n}\n\nfunction normalizeResourceStoreUri(resourceStoreUri: string): string {\n const filePrefix = 'file://';\n if (resourceStoreUri.startsWith(filePrefix)) {\n const rawPath = resourceStoreUri.slice(filePrefix.length);\n const expandedPath = rawPath.startsWith('~') ? rawPath.replace(/^~/, homedir()) : rawPath;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n }\n\n if (resourceStoreUri.includes('://')) return resourceStoreUri;\n\n const expandedPath = resourceStoreUri.startsWith('~') ? resourceStoreUri.replace(/^~/, homedir()) : resourceStoreUri;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n}\n"],"names":["parseDcrConfig","parseConfig","parseOAuthConfig","findConfigPath","parseTransportConfig","fs","moduleRoot","homedir","path","url","parseArgs","GOOGLE_SCOPE","pkg","JSON","parse","readFileSync","join","fileURLToPath","HELP_TEXT","trim","handleVersionHelp","args","values","options","version","type","help","strict","handled","output","env","cliLogLevel","cliResourceStoreUri","transportConfig","oauthConfig","dcrConfig","auth","undefined","allowPositionals","name","replace","rawRepoUrl","repository","repositoryUrl","rootDir","configPath","config","cwd","process","stopDir","dirname","baseDir","envLogLevel","LOG_LEVEL","logLevel","envResourceStoreUri","RESOURCE_STORE_URI","defaultResourceStorePath","resourceStoreUri","normalizeResourceStoreUri","cliBaseUrl","envBaseUrl","BASE_URL","baseUrl","result","transport","createConfig","argv","filePrefix","startsWith","rawPath","slice","length","expandedPath","resolve","includes"],"mappings":"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"}
1
+ {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/setup/config.ts"],"sourcesContent":["import type * as OAuthGoogle from '@mcp-z/oauth-google';\nimport type * as McpServer from '@mcp-z/server';\nimport { Module } from 'module';\nimport { homedir } from 'os';\nimport * as path from 'path';\nimport { parseArgs } from 'util';\nimport { GOOGLE_SCOPE } from '../constants.ts';\nimport type { ServerConfig } from '../types.ts';\nimport { readPkg } from './version-help.ts';\n\nconst pkg = readPkg();\n\n// @mcp-z/oauth-google and @mcp-z/server are requireable at the >=20 floor; deferred so\n// --version/--help (handled via version-help.ts, never this file) load neither package.\nconst _require = typeof require === 'undefined' ? Module.createRequire(import.meta.url) : require;\n\n/**\n * Parse Gmail server configuration from CLI arguments and environment.\n *\n * CLI Arguments (all optional):\n * - --auth=<mode> Authentication mode (default: loopback-oauth)\n * Modes: loopback-oauth, service-account, dcr\n * - --headless Disable browser auto-open, return auth URL instead\n * - --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n * - --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n * - --dcr-verify-url=<url> External verification endpoint (required for external mode)\n * - --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n * - --port=<port> Enable HTTP transport on specified port\n * - --stdio Enable stdio transport (default if no port)\n * - --log-level=<level> Logging level (default: info)\n * - --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n * - --base-url=<url> Base URL for HTTP file serving (optional)\n *\n * Environment Variables:\n * - GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n * - GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n * - AUTH_MODE Default authentication mode (optional)\n * - HEADLESS Disable browser auto-open (optional)\n * - DCR_MODE DCR mode (optional, same format as --dcr-mode)\n * - DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n * - DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n * - TOKEN_STORE_URI Token storage URI (optional)\n * - PORT Default HTTP port (optional)\n * - LOG_LEVEL Default logging level (optional)\n * - RESOURCE_STORE_URI Resource store URI (optional, file://)\n * - BASE_URL Default base URL for file serving (optional)\n *\n * OAuth Scopes (from constants.ts):\n * openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n */\nexport function parseConfig(args: string[], env: Record<string, string | undefined>): ServerConfig {\n const oauthGoogle = _require('@mcp-z/oauth-google') as typeof OAuthGoogle;\n const mcpServer = _require('@mcp-z/server') as typeof McpServer;\n\n const transportConfig = mcpServer.parseConfig(args, env);\n const oauthConfig = oauthGoogle.parseConfig(args, env);\n\n // Parse DCR configuration if DCR mode is enabled\n const dcrConfig = oauthConfig.auth === 'dcr' ? oauthGoogle.parseDcrConfig(args, env, GOOGLE_SCOPE) : undefined;\n\n // Parse application-level config (LOG_LEVEL, RESOURCE_STORE_URI, BASE_URL)\n const { values } = parseArgs({\n args,\n options: {\n 'log-level': { type: 'string' },\n 'base-url': { type: 'string' },\n 'resource-store-uri': { type: 'string' },\n },\n strict: false, // Allow other arguments\n allowPositionals: true,\n });\n\n const name = pkg.name.replace(/^@[^/]+\\//, '');\n // Parse repository URL from package.json, stripping git+ prefix and .git suffix\n const rawRepoUrl = typeof pkg.repository === 'object' ? pkg.repository.url : pkg.repository;\n const repositoryUrl = rawRepoUrl?.replace(/^git\\+/, '').replace(/\\.git$/, '') ?? `https://github.com/mcp-z/${name}`;\n let rootDir = homedir();\n try {\n const configPath = mcpServer.findConfigPath({ config: '.mcp.json', cwd: process.cwd(), stopDir: homedir() });\n rootDir = path.dirname(configPath);\n } catch {\n rootDir = homedir();\n }\n const baseDir = path.join(rootDir, '.mcp-z');\n const cliLogLevel = typeof values['log-level'] === 'string' ? values['log-level'] : undefined;\n const envLogLevel = env.LOG_LEVEL;\n const logLevel = cliLogLevel ?? envLogLevel ?? 'info';\n\n // Parse storage configuration\n const cliResourceStoreUri = typeof values['resource-store-uri'] === 'string' ? values['resource-store-uri'] : undefined;\n const envResourceStoreUri = env.RESOURCE_STORE_URI;\n const defaultResourceStorePath = path.join(baseDir, name, 'files');\n const resourceStoreUri = normalizeResourceStoreUri(cliResourceStoreUri ?? envResourceStoreUri ?? defaultResourceStorePath);\n\n const cliBaseUrl = typeof values['base-url'] === 'string' ? values['base-url'] : undefined;\n const envBaseUrl = env.BASE_URL;\n const baseUrl = cliBaseUrl ?? envBaseUrl;\n\n // Combine configs\n const result: ServerConfig = {\n ...oauthConfig, // Includes clientId, auth, headless, redirectUri, serviceAccountKeyFile\n transport: transportConfig.transport,\n logLevel,\n baseDir,\n name,\n version: pkg.version,\n repositoryUrl,\n resourceStoreUri,\n };\n if (baseUrl) result.baseUrl = baseUrl;\n if (dcrConfig !== undefined) result.dcrConfig = dcrConfig;\n return result;\n}\n\n/**\n * Build production configuration from process globals.\n * Entry point for production server.\n */\nexport function createConfig(): ServerConfig {\n return parseConfig(process.argv, process.env);\n}\n\nfunction normalizeResourceStoreUri(resourceStoreUri: string): string {\n const filePrefix = 'file://';\n if (resourceStoreUri.startsWith(filePrefix)) {\n const rawPath = resourceStoreUri.slice(filePrefix.length);\n const expandedPath = rawPath.startsWith('~') ? rawPath.replace(/^~/, homedir()) : rawPath;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n }\n\n if (resourceStoreUri.includes('://')) return resourceStoreUri;\n\n const expandedPath = resourceStoreUri.startsWith('~') ? resourceStoreUri.replace(/^~/, homedir()) : resourceStoreUri;\n return `${filePrefix}${path.resolve(expandedPath)}`;\n}\n"],"names":["Module","homedir","path","parseArgs","GOOGLE_SCOPE","readPkg","pkg","_require","require","createRequire","url","parseConfig","args","env","cliLogLevel","cliResourceStoreUri","oauthGoogle","mcpServer","transportConfig","oauthConfig","dcrConfig","auth","parseDcrConfig","undefined","values","options","type","strict","allowPositionals","name","replace","rawRepoUrl","repository","repositoryUrl","rootDir","configPath","findConfigPath","config","cwd","process","stopDir","dirname","baseDir","join","envLogLevel","LOG_LEVEL","logLevel","envResourceStoreUri","RESOURCE_STORE_URI","defaultResourceStorePath","resourceStoreUri","normalizeResourceStoreUri","cliBaseUrl","envBaseUrl","BASE_URL","baseUrl","result","transport","version","createConfig","argv","filePrefix","startsWith","rawPath","slice","length","expandedPath","resolve","includes"],"mappings":"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"}
@@ -0,0 +1,16 @@
1
+ /** Package metadata read from package.json, resolved relative to this file. */
2
+ export declare function readPkg(): {
3
+ name: string;
4
+ version: string;
5
+ repository?: string | {
6
+ url?: string;
7
+ };
8
+ };
9
+ /**
10
+ * Handle --version/--help flags and the `version` subcommand before config parsing.
11
+ * These must work without requiring any configuration or heavy dependency.
12
+ */
13
+ export declare function handleVersionHelp(args: string[]): {
14
+ handled: boolean;
15
+ output?: string;
16
+ };
@@ -0,0 +1,90 @@
1
+ import * as fs from 'fs';
2
+ import moduleRoot from 'module-root-sync';
3
+ import * as path from 'path';
4
+ import * as url from 'url';
5
+ import { parseArgs } from 'util';
6
+ // Kept dependency-free (fs/path/url/module-root-sync only) so `--version`/`--help`/`version`
7
+ // resolve nothing beyond Node startup: config.ts's parseConfig pulls in @mcp-z/oauth-google and
8
+ // @mcp-z/server, which this path must not touch.
9
+ const pkg = JSON.parse(fs.readFileSync(path.join(moduleRoot(url.fileURLToPath(import.meta.url)), 'package.json'), 'utf-8'));
10
+ const HELP_TEXT = `
11
+ Usage: mcp-gmail [options]
12
+
13
+ MCP server for Gmail email management with OAuth authentication.
14
+
15
+ Options:
16
+ --version Show version number
17
+ --help Show this help message
18
+ --auth=<mode> Authentication mode (default: loopback-oauth)
19
+ Modes: loopback-oauth, service-account, dcr
20
+ --headless Disable browser auto-open, return auth URL instead
21
+ --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)
22
+ --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)
23
+ --dcr-verify-url=<url> External verification endpoint (required for external mode)
24
+ --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)
25
+ --port=<port> Enable HTTP transport on specified port
26
+ --stdio Enable stdio transport (default if no port)
27
+ --log-level=<level> Logging level (default: info)
28
+ --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)
29
+ --base-url=<url> Base URL for HTTP file serving (optional)
30
+
31
+ Commands:
32
+ version Show version number
33
+
34
+ Environment Variables:
35
+ GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)
36
+ GOOGLE_CLIENT_SECRET OAuth client secret (optional)
37
+ AUTH_MODE Default authentication mode (optional)
38
+ HEADLESS Disable browser auto-open (optional)
39
+ DCR_MODE DCR mode (optional, same format as --dcr-mode)
40
+ DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)
41
+ DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)
42
+ TOKEN_STORE_URI Token storage URI (optional)
43
+ PORT Default HTTP port (optional)
44
+ LOG_LEVEL Default logging level (optional)
45
+ RESOURCE_STORE_URI Resource store URI (optional, file://)
46
+ BASE_URL Default base URL for file serving (optional)
47
+
48
+ OAuth Scopes:
49
+ openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/
50
+
51
+ Examples:
52
+ mcp-gmail # Use default settings
53
+ mcp-gmail version # Print version number
54
+ mcp-gmail --auth=service-account # Use service account auth
55
+ mcp-gmail --port=3000 # HTTP transport on port 3000
56
+ mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI
57
+ GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var
58
+ `.trim();
59
+ /** Package metadata read from package.json, resolved relative to this file. */ export function readPkg() {
60
+ return pkg;
61
+ }
62
+ /**
63
+ * Handle --version/--help flags and the `version` subcommand before config parsing.
64
+ * These must work without requiring any configuration or heavy dependency.
65
+ */ export function handleVersionHelp(args) {
66
+ const { values, positionals } = parseArgs({
67
+ args,
68
+ options: {
69
+ version: {
70
+ type: 'boolean'
71
+ },
72
+ help: {
73
+ type: 'boolean'
74
+ }
75
+ },
76
+ strict: false,
77
+ allowPositionals: true
78
+ });
79
+ if (values.version || positionals[0] === 'version') return {
80
+ handled: true,
81
+ output: pkg.version
82
+ };
83
+ if (values.help) return {
84
+ handled: true,
85
+ output: HELP_TEXT
86
+ };
87
+ return {
88
+ handled: false
89
+ };
90
+ }
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["/Users/kevin/Dev/OpenSource/ai/mcp-z/mcp-gmail/src/setup/version-help.ts"],"sourcesContent":["import * as fs from 'fs';\nimport moduleRoot from 'module-root-sync';\nimport * as path from 'path';\nimport * as url from 'url';\nimport { parseArgs } from 'util';\n\n// Kept dependency-free (fs/path/url/module-root-sync only) so `--version`/`--help`/`version`\n// resolve nothing beyond Node startup: config.ts's parseConfig pulls in @mcp-z/oauth-google and\n// @mcp-z/server, which this path must not touch.\nconst pkg = JSON.parse(fs.readFileSync(path.join(moduleRoot(url.fileURLToPath(import.meta.url)), 'package.json'), 'utf-8'));\n\nconst HELP_TEXT = `\nUsage: mcp-gmail [options]\n\nMCP server for Gmail email management with OAuth authentication.\n\nOptions:\n --version Show version number\n --help Show this help message\n --auth=<mode> Authentication mode (default: loopback-oauth)\n Modes: loopback-oauth, service-account, dcr\n --headless Disable browser auto-open, return auth URL instead\n --redirect-uri=<uri> OAuth redirect URI (default: ephemeral loopback)\n --dcr-mode=<mode> DCR mode (self-hosted or external, default: self-hosted)\n --dcr-verify-url=<url> External verification endpoint (required for external mode)\n --dcr-store-uri=<uri> DCR client storage URI (required for self-hosted mode)\n --port=<port> Enable HTTP transport on specified port\n --stdio Enable stdio transport (default if no port)\n --log-level=<level> Logging level (default: info)\n --resource-store-uri=<uri> Resource store URI for CSV file storage (default: file://~/.mcp-z/mcp-gmail/files)\n --base-url=<url> Base URL for HTTP file serving (optional)\n\nCommands:\n version Show version number\n\nEnvironment Variables:\n GOOGLE_CLIENT_ID OAuth client ID (REQUIRED)\n GOOGLE_CLIENT_SECRET OAuth client secret (optional)\n AUTH_MODE Default authentication mode (optional)\n HEADLESS Disable browser auto-open (optional)\n DCR_MODE DCR mode (optional, same format as --dcr-mode)\n DCR_VERIFY_URL External verification URL (optional, same as --dcr-verify-url)\n DCR_STORE_URI DCR storage URI (optional, same as --dcr-store-uri)\n TOKEN_STORE_URI Token storage URI (optional)\n PORT Default HTTP port (optional)\n LOG_LEVEL Default logging level (optional)\n RESOURCE_STORE_URI Resource store URI (optional, file://)\n BASE_URL Default base URL for file serving (optional)\n\nOAuth Scopes:\n openid https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email https://mail.google.com/\n\nExamples:\n mcp-gmail # Use default settings\n mcp-gmail version # Print version number\n mcp-gmail --auth=service-account # Use service account auth\n mcp-gmail --port=3000 # HTTP transport on port 3000\n mcp-gmail --resource-store-uri=file:///tmp/emails # Custom resource store URI\n GOOGLE_CLIENT_ID=xxx mcp-gmail # Set client ID via env var\n`.trim();\n\n/** Package metadata read from package.json, resolved relative to this file. */\nexport function readPkg(): { name: string; version: string; repository?: string | { url?: string } } {\n return pkg;\n}\n\n/**\n * Handle --version/--help flags and the `version` subcommand before config parsing.\n * These must work without requiring any configuration or heavy dependency.\n */\nexport function handleVersionHelp(args: string[]): { handled: boolean; output?: string } {\n const { values, positionals } = parseArgs({\n args,\n options: {\n version: { type: 'boolean' },\n help: { type: 'boolean' },\n },\n strict: false,\n allowPositionals: true,\n });\n\n if (values.version || positionals[0] === 'version') return { handled: true, output: pkg.version };\n if (values.help) return { handled: true, output: HELP_TEXT };\n return { handled: false };\n}\n"],"names":["fs","moduleRoot","path","url","parseArgs","pkg","JSON","parse","readFileSync","join","fileURLToPath","HELP_TEXT","trim","readPkg","handleVersionHelp","args","values","positionals","options","version","type","help","strict","allowPositionals","handled","output"],"mappings":"AAAA,YAAYA,QAAQ,KAAK;AACzB,OAAOC,gBAAgB,mBAAmB;AAC1C,YAAYC,UAAU,OAAO;AAC7B,YAAYC,SAAS,MAAM;AAC3B,SAASC,SAAS,QAAQ,OAAO;AAEjC,6FAA6F;AAC7F,gGAAgG;AAChG,iDAAiD;AACjD,MAAMC,MAAMC,KAAKC,KAAK,CAACP,GAAGQ,YAAY,CAACN,KAAKO,IAAI,CAACR,WAAWE,IAAIO,aAAa,CAAC,YAAYP,GAAG,IAAI,iBAAiB;AAElH,MAAMQ,YAAY,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAgDnB,CAAC,CAACC,IAAI;AAEN,6EAA6E,GAC7E,OAAO,SAASC;IACd,OAAOR;AACT;AAEA;;;CAGC,GACD,OAAO,SAASS,kBAAkBC,IAAc;IAC9C,MAAM,EAAEC,MAAM,EAAEC,WAAW,EAAE,GAAGb,UAAU;QACxCW;QACAG,SAAS;YACPC,SAAS;gBAAEC,MAAM;YAAU;YAC3BC,MAAM;gBAAED,MAAM;YAAU;QAC1B;QACAE,QAAQ;QACRC,kBAAkB;IACpB;IAEA,IAAIP,OAAOG,OAAO,IAAIF,WAAW,CAAC,EAAE,KAAK,WAAW,OAAO;QAAEO,SAAS;QAAMC,QAAQpB,IAAIc,OAAO;IAAC;IAChG,IAAIH,OAAOK,IAAI,EAAE,OAAO;QAAEG,SAAS;QAAMC,QAAQd;IAAU;IAC3D,OAAO;QAAEa,SAAS;IAAM;AAC1B"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mcp-z/mcp-gmail",
3
- "version": "1.0.12",
3
+ "version": "1.1.0",
4
4
  "description": "MCP server for Gmail integration with OAuth authentication, message search, batch operations, and Google Sheets export",
5
5
  "keywords": [
6
6
  "gmail",
@@ -61,11 +61,9 @@
61
61
  "format": "tsds format",
62
62
  "prepublish:check": "ncp",
63
63
  "prepublishOnly": "tsds validate",
64
- "test": "npm run test:unit && npm run test:integration",
65
- "test:engines": "nvu engines tsds test:node --no-timeouts 'test/**/*.test.ts'",
66
- "test:integration": "tsds test:node --no-timeouts 'test/integration/**/*.test.ts'",
64
+ "test": "tsds test:node --no-timeouts",
65
+ "test:engines": "nvu engines tsds test:node --no-timeouts",
67
66
  "test:setup": "node scripts/setup-test.ts",
68
- "test:unit": "tsds test:node --no-timeouts 'test/unit/**/*.test.ts'",
69
67
  "version": "tsds version"
70
68
  },
71
69
  "dependencies": {