@markstiles/sitecore-search-mcp 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (88) hide show
  1. package/AUTHENTICATION.md +337 -0
  2. package/LICENSE +21 -0
  3. package/README.md +606 -0
  4. package/dist/client/base-client.d.ts +34 -0
  5. package/dist/client/base-client.d.ts.map +1 -0
  6. package/dist/client/base-client.js +117 -0
  7. package/dist/client/base-client.js.map +1 -0
  8. package/dist/client/events-client.d.ts +77 -0
  9. package/dist/client/events-client.d.ts.map +1 -0
  10. package/dist/client/events-client.js +32 -0
  11. package/dist/client/events-client.js.map +1 -0
  12. package/dist/client/ingestion-client.d.ts +76 -0
  13. package/dist/client/ingestion-client.d.ts.map +1 -0
  14. package/dist/client/ingestion-client.js +73 -0
  15. package/dist/client/ingestion-client.js.map +1 -0
  16. package/dist/client/search-client.d.ts +97 -0
  17. package/dist/client/search-client.d.ts.map +1 -0
  18. package/dist/client/search-client.js +18 -0
  19. package/dist/client/search-client.js.map +1 -0
  20. package/dist/config.d.ts +99 -0
  21. package/dist/config.d.ts.map +1 -0
  22. package/dist/config.js +75 -0
  23. package/dist/config.js.map +1 -0
  24. package/dist/index.d.ts +3 -0
  25. package/dist/index.d.ts.map +1 -0
  26. package/dist/index.js +312 -0
  27. package/dist/index.js.map +1 -0
  28. package/dist/tools/events/track-event.d.ts +394 -0
  29. package/dist/tools/events/track-event.d.ts.map +1 -0
  30. package/dist/tools/events/track-event.js +80 -0
  31. package/dist/tools/events/track-event.js.map +1 -0
  32. package/dist/tools/events/validate-event.d.ts +94 -0
  33. package/dist/tools/events/validate-event.d.ts.map +1 -0
  34. package/dist/tools/events/validate-event.js +51 -0
  35. package/dist/tools/events/validate-event.js.map +1 -0
  36. package/dist/tools/ingestion/check-status.d.ts +50 -0
  37. package/dist/tools/ingestion/check-status.d.ts.map +1 -0
  38. package/dist/tools/ingestion/check-status.js +27 -0
  39. package/dist/tools/ingestion/check-status.js.map +1 -0
  40. package/dist/tools/ingestion/create-document.d.ts +50 -0
  41. package/dist/tools/ingestion/create-document.d.ts.map +1 -0
  42. package/dist/tools/ingestion/create-document.js +27 -0
  43. package/dist/tools/ingestion/create-document.js.map +1 -0
  44. package/dist/tools/ingestion/delete-document.d.ts +50 -0
  45. package/dist/tools/ingestion/delete-document.d.ts.map +1 -0
  46. package/dist/tools/ingestion/delete-document.js +27 -0
  47. package/dist/tools/ingestion/delete-document.js.map +1 -0
  48. package/dist/tools/ingestion/ingest-from-source.d.ts +234 -0
  49. package/dist/tools/ingestion/ingest-from-source.d.ts.map +1 -0
  50. package/dist/tools/ingestion/ingest-from-source.js +48 -0
  51. package/dist/tools/ingestion/ingest-from-source.js.map +1 -0
  52. package/dist/tools/ingestion/update-document.d.ts +62 -0
  53. package/dist/tools/ingestion/update-document.d.ts.map +1 -0
  54. package/dist/tools/ingestion/update-document.js +34 -0
  55. package/dist/tools/ingestion/update-document.js.map +1 -0
  56. package/dist/tools/search/ai-search.d.ts +132 -0
  57. package/dist/tools/search/ai-search.d.ts.map +1 -0
  58. package/dist/tools/search/ai-search.js +65 -0
  59. package/dist/tools/search/ai-search.js.map +1 -0
  60. package/dist/tools/search/basic-search.d.ts +98 -0
  61. package/dist/tools/search/basic-search.d.ts.map +1 -0
  62. package/dist/tools/search/basic-search.js +51 -0
  63. package/dist/tools/search/basic-search.js.map +1 -0
  64. package/dist/tools/search/faceted-search.d.ts +114 -0
  65. package/dist/tools/search/faceted-search.d.ts.map +1 -0
  66. package/dist/tools/search/faceted-search.js +52 -0
  67. package/dist/tools/search/faceted-search.js.map +1 -0
  68. package/dist/tools/search/recommendations.d.ts +62 -0
  69. package/dist/tools/search/recommendations.d.ts.map +1 -0
  70. package/dist/tools/search/recommendations.js +50 -0
  71. package/dist/tools/search/recommendations.js.map +1 -0
  72. package/dist/utils/auth-manager.d.ts +60 -0
  73. package/dist/utils/auth-manager.d.ts.map +1 -0
  74. package/dist/utils/auth-manager.js +184 -0
  75. package/dist/utils/auth-manager.js.map +1 -0
  76. package/dist/utils/errors.d.ts +18 -0
  77. package/dist/utils/errors.d.ts.map +1 -0
  78. package/dist/utils/errors.js +58 -0
  79. package/dist/utils/errors.js.map +1 -0
  80. package/dist/utils/logger.d.ts +12 -0
  81. package/dist/utils/logger.d.ts.map +1 -0
  82. package/dist/utils/logger.js +50 -0
  83. package/dist/utils/logger.js.map +1 -0
  84. package/dist/utils/schema.d.ts +6 -0
  85. package/dist/utils/schema.d.ts.map +1 -0
  86. package/dist/utils/schema.js +14 -0
  87. package/dist/utils/schema.js.map +1 -0
  88. package/package.json +58 -0
@@ -0,0 +1,60 @@
1
+ /**
2
+ * Authentication scopes for Sitecore Search APIs
3
+ */
4
+ export type AuthScope = 'discover' | 'event' | 'ingestion';
5
+ /**
6
+ * Authentication Manager for Sitecore Search APIs
7
+ * Handles API key authentication and token management (generation, refresh, expiry)
8
+ */
9
+ export declare class AuthManager {
10
+ private apiKey?;
11
+ private scopes;
12
+ private accessTokenExpiry;
13
+ private refreshTokenExpiry;
14
+ private logger;
15
+ private authEndpoint;
16
+ private axios;
17
+ private tokenStorage?;
18
+ private tokenRefreshPromise?;
19
+ constructor(apiKey?: string | undefined, scopes?: AuthScope[], accessTokenExpiry?: number, // 1 day default
20
+ refreshTokenExpiry?: number);
21
+ /**
22
+ * Get authentication header for API requests
23
+ * Returns either API key or access token in Authorization header
24
+ */
25
+ getAuthHeader(): Promise<Record<string, string>>;
26
+ /**
27
+ * Get a valid access token (generates new one if needed or refreshes if expired)
28
+ */
29
+ private getAccessToken;
30
+ /**
31
+ * Generate access and refresh tokens from API key
32
+ */
33
+ private generateTokensFromApiKey;
34
+ /**
35
+ * Refresh access token using refresh token
36
+ */
37
+ private refreshAccessToken;
38
+ /**
39
+ * Check if access token is valid (not expired)
40
+ * Returns true if valid, false if expired or about to expire (within 1 minute)
41
+ */
42
+ private isAccessTokenValid;
43
+ /**
44
+ * Check if refresh token is valid (not expired)
45
+ */
46
+ private isRefreshTokenValid;
47
+ /**
48
+ * Force clear stored tokens (useful for testing or manual token invalidation)
49
+ */
50
+ clearTokens(): void;
51
+ /**
52
+ * Get current token status for debugging
53
+ */
54
+ getTokenStatus(): {
55
+ hasTokens: boolean;
56
+ accessTokenValid: boolean;
57
+ refreshTokenValid: boolean;
58
+ };
59
+ }
60
+ //# sourceMappingURL=auth-manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-manager.d.ts","sourceRoot":"","sources":["../../src/utils/auth-manager.ts"],"names":[],"mappings":"AAGA;;GAEG;AACH,MAAM,MAAM,SAAS,GAAG,UAAU,GAAG,OAAO,GAAG,WAAW,CAAC;AA6B3D;;;GAGG;AACH,qBAAa,WAAW;IAQpB,OAAO,CAAC,MAAM,CAAC;IACf,OAAO,CAAC,MAAM;IACd,OAAO,CAAC,iBAAiB;IACzB,OAAO,CAAC,kBAAkB;IAV5B,OAAO,CAAC,MAAM,CAAS;IACvB,OAAO,CAAC,YAAY,CAAmD;IACvE,OAAO,CAAC,KAAK,CAAgB;IAC7B,OAAO,CAAC,YAAY,CAAC,CAAe;IACpC,OAAO,CAAC,mBAAmB,CAAC,CAAkB;gBAGpC,MAAM,CAAC,EAAE,MAAM,YAAA,EACf,MAAM,GAAE,SAAS,EAAuC,EACxD,iBAAiB,GAAE,MAAiB,EAAE,gBAAgB;IACtD,kBAAkB,GAAE,MAAkB;IAWhD;;;OAGG;IACG,aAAa,IAAI,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IA2BtD;;OAEG;YACW,cAAc;IA4B5B;;OAEG;YACW,wBAAwB;IAsCtC;;OAEG;YACW,kBAAkB;IAgChC;;;OAGG;IACH,OAAO,CAAC,kBAAkB;IAQ1B;;OAEG;IACH,OAAO,CAAC,mBAAmB;IAO3B;;OAEG;IACH,WAAW,IAAI,IAAI;IAKnB;;OAEG;IACH,cAAc,IAAI;QAChB,SAAS,EAAE,OAAO,CAAC;QACnB,gBAAgB,EAAE,OAAO,CAAC;QAC1B,iBAAiB,EAAE,OAAO,CAAC;KAC5B;CAOF"}
@@ -0,0 +1,184 @@
1
+ import axios from 'axios';
2
+ import { Logger } from './logger.js';
3
+ /**
4
+ * Authentication Manager for Sitecore Search APIs
5
+ * Handles API key authentication and token management (generation, refresh, expiry)
6
+ */
7
+ export class AuthManager {
8
+ apiKey;
9
+ scopes;
10
+ accessTokenExpiry;
11
+ refreshTokenExpiry;
12
+ logger;
13
+ authEndpoint = 'https://api.rfksrv.com/account/1/access-token';
14
+ axios;
15
+ tokenStorage;
16
+ tokenRefreshPromise;
17
+ constructor(apiKey, scopes = ['discover', 'event', 'ingestion'], accessTokenExpiry = 86400000, // 1 day default
18
+ refreshTokenExpiry = 604800000 // 7 days default
19
+ ) {
20
+ this.apiKey = apiKey;
21
+ this.scopes = scopes;
22
+ this.accessTokenExpiry = accessTokenExpiry;
23
+ this.refreshTokenExpiry = refreshTokenExpiry;
24
+ this.logger = new Logger('AuthManager');
25
+ this.axios = axios.create({
26
+ timeout: 10000,
27
+ headers: {
28
+ 'Content-Type': 'application/json',
29
+ },
30
+ });
31
+ }
32
+ /**
33
+ * Get authentication header for API requests
34
+ * Returns either API key or access token in Authorization header
35
+ */
36
+ async getAuthHeader() {
37
+ // If no API key configured, return empty headers (subdomain authentication)
38
+ if (!this.apiKey) {
39
+ return {};
40
+ }
41
+ // For Ingestion API, always use API key (per documentation)
42
+ if (this.scopes.includes('ingestion') && this.scopes.length === 1) {
43
+ return {
44
+ Authorization: this.apiKey,
45
+ };
46
+ }
47
+ // Try to use access token for other APIs
48
+ const accessToken = await this.getAccessToken();
49
+ if (accessToken) {
50
+ return {
51
+ Authorization: `Bearer ${accessToken}`,
52
+ };
53
+ }
54
+ // Fallback to API key
55
+ return {
56
+ Authorization: this.apiKey,
57
+ };
58
+ }
59
+ /**
60
+ * Get a valid access token (generates new one if needed or refreshes if expired)
61
+ */
62
+ async getAccessToken() {
63
+ // If we're already refreshing, wait for that operation
64
+ if (this.tokenRefreshPromise) {
65
+ return this.tokenRefreshPromise;
66
+ }
67
+ // Check if we have a valid access token
68
+ if (this.tokenStorage && this.isAccessTokenValid()) {
69
+ return this.tokenStorage.accessToken;
70
+ }
71
+ // Check if we have a valid refresh token
72
+ if (this.tokenStorage && this.isRefreshTokenValid()) {
73
+ this.tokenRefreshPromise = this.refreshAccessToken()
74
+ .finally(() => {
75
+ this.tokenRefreshPromise = undefined;
76
+ });
77
+ return this.tokenRefreshPromise;
78
+ }
79
+ // Generate new tokens from API key
80
+ this.tokenRefreshPromise = this.generateTokensFromApiKey()
81
+ .finally(() => {
82
+ this.tokenRefreshPromise = undefined;
83
+ });
84
+ return this.tokenRefreshPromise;
85
+ }
86
+ /**
87
+ * Generate access and refresh tokens from API key
88
+ */
89
+ async generateTokensFromApiKey() {
90
+ if (!this.apiKey) {
91
+ throw new Error('API key is required to generate tokens');
92
+ }
93
+ this.logger.debug('Generating new access token from API key');
94
+ try {
95
+ const response = await this.axios.post(this.authEndpoint, {
96
+ scope: this.scopes,
97
+ accessExpiry: this.accessTokenExpiry,
98
+ refreshExpiry: this.refreshTokenExpiry,
99
+ }, {
100
+ headers: {
101
+ 'x-api-key': this.apiKey,
102
+ },
103
+ });
104
+ const now = Date.now();
105
+ this.tokenStorage = {
106
+ accessToken: response.data.accessToken,
107
+ refreshToken: response.data.refreshToken,
108
+ accessTokenExpiresAt: now + response.data.accessTokenExpiry,
109
+ refreshTokenExpiresAt: now + response.data.refreshTokenExpiry,
110
+ };
111
+ this.logger.info('Successfully generated new access token');
112
+ return this.tokenStorage.accessToken;
113
+ }
114
+ catch (error) {
115
+ this.logger.error('Failed to generate access token from API key', error);
116
+ throw error;
117
+ }
118
+ }
119
+ /**
120
+ * Refresh access token using refresh token
121
+ */
122
+ async refreshAccessToken() {
123
+ if (!this.tokenStorage) {
124
+ throw new Error('No token storage available for refresh');
125
+ }
126
+ this.logger.debug('Refreshing access token using refresh token');
127
+ try {
128
+ const response = await this.axios.put(this.authEndpoint, {}, {
129
+ headers: {
130
+ Authorization: `Bearer ${this.tokenStorage.refreshToken}`,
131
+ },
132
+ });
133
+ // Update only the access token, keep the refresh token
134
+ this.tokenStorage.accessToken = response.data.accessToken;
135
+ this.tokenStorage.accessTokenExpiresAt = Date.now() + this.accessTokenExpiry;
136
+ this.logger.info('Successfully refreshed access token');
137
+ return this.tokenStorage.accessToken;
138
+ }
139
+ catch (error) {
140
+ this.logger.error('Failed to refresh access token', error);
141
+ // Clear token storage to force re-authentication
142
+ this.tokenStorage = undefined;
143
+ throw error;
144
+ }
145
+ }
146
+ /**
147
+ * Check if access token is valid (not expired)
148
+ * Returns true if valid, false if expired or about to expire (within 1 minute)
149
+ */
150
+ isAccessTokenValid() {
151
+ if (!this.tokenStorage) {
152
+ return false;
153
+ }
154
+ // Add 1 minute buffer before expiry
155
+ return Date.now() < this.tokenStorage.accessTokenExpiresAt - 60000;
156
+ }
157
+ /**
158
+ * Check if refresh token is valid (not expired)
159
+ */
160
+ isRefreshTokenValid() {
161
+ if (!this.tokenStorage) {
162
+ return false;
163
+ }
164
+ return Date.now() < this.tokenStorage.refreshTokenExpiresAt;
165
+ }
166
+ /**
167
+ * Force clear stored tokens (useful for testing or manual token invalidation)
168
+ */
169
+ clearTokens() {
170
+ this.tokenStorage = undefined;
171
+ this.logger.info('Cleared stored tokens');
172
+ }
173
+ /**
174
+ * Get current token status for debugging
175
+ */
176
+ getTokenStatus() {
177
+ return {
178
+ hasTokens: !!this.tokenStorage,
179
+ accessTokenValid: this.isAccessTokenValid(),
180
+ refreshTokenValid: this.isRefreshTokenValid(),
181
+ };
182
+ }
183
+ }
184
+ //# sourceMappingURL=auth-manager.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-manager.js","sourceRoot":"","sources":["../../src/utils/auth-manager.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,18 @@
1
+ import { z } from 'zod';
2
+ /**
3
+ * Base error class for Sitecore API errors
4
+ */
5
+ export declare class SitecoreApiError extends Error {
6
+ statusCode?: number | undefined;
7
+ response?: unknown | undefined;
8
+ constructor(message: string, statusCode?: number | undefined, response?: unknown | undefined);
9
+ }
10
+ /**
11
+ * Error handling utility for API responses
12
+ */
13
+ export declare function handleApiError(error: unknown): never;
14
+ /**
15
+ * Validate input against a Zod schema
16
+ */
17
+ export declare function validateInput<T>(schema: z.ZodSchema<T>, input: unknown): T;
18
+ //# sourceMappingURL=errors.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/utils/errors.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB;;GAEG;AACH,qBAAa,gBAAiB,SAAQ,KAAK;IAGhC,UAAU,CAAC,EAAE,MAAM;IACnB,QAAQ,CAAC,EAAE,OAAO;gBAFzB,OAAO,EAAE,MAAM,EACR,UAAU,CAAC,EAAE,MAAM,YAAA,EACnB,QAAQ,CAAC,EAAE,OAAO,YAAA;CAK5B;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,CA6BpD;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,GAAG,CAAC,CAY1E"}
@@ -0,0 +1,58 @@
1
+ import { z } from 'zod';
2
+ /**
3
+ * Base error class for Sitecore API errors
4
+ */
5
+ export class SitecoreApiError extends Error {
6
+ statusCode;
7
+ response;
8
+ constructor(message, statusCode, response) {
9
+ super(message);
10
+ this.statusCode = statusCode;
11
+ this.response = response;
12
+ this.name = 'SitecoreApiError';
13
+ }
14
+ }
15
+ /**
16
+ * Error handling utility for API responses
17
+ */
18
+ export function handleApiError(error) {
19
+ if (error instanceof SitecoreApiError) {
20
+ throw error;
21
+ }
22
+ if (typeof error === 'object' && error !== null) {
23
+ const err = error;
24
+ if (err.response) {
25
+ // Axios error with response
26
+ const statusCode = err.response.status;
27
+ const data = err.response.data;
28
+ let message = `API request failed with status ${statusCode}`;
29
+ if (data?.message) {
30
+ message = data.message;
31
+ }
32
+ else if (typeof data === 'string') {
33
+ message = data;
34
+ }
35
+ throw new SitecoreApiError(message, statusCode, data);
36
+ }
37
+ if (err.message) {
38
+ throw new SitecoreApiError(err.message);
39
+ }
40
+ }
41
+ throw new SitecoreApiError('Unknown error occurred');
42
+ }
43
+ /**
44
+ * Validate input against a Zod schema
45
+ */
46
+ export function validateInput(schema, input) {
47
+ try {
48
+ return schema.parse(input);
49
+ }
50
+ catch (error) {
51
+ if (error instanceof z.ZodError) {
52
+ const formattedErrors = error.errors.map(err => `${err.path.join('.')}: ${err.message}`).join(', ');
53
+ throw new Error(`Validation error: ${formattedErrors}`);
54
+ }
55
+ throw error;
56
+ }
57
+ }
58
+ //# sourceMappingURL=errors.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errors.js","sourceRoot":"","sources":["../../src/utils/errors.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB;;GAEG;AACH,MAAM,OAAO,gBAAiB,SAAQ,KAAK;IAGhC;IACA;IAHT,YACE,OAAe,EACR,UAAmB,EACnB,QAAkB;QAEzB,KAAK,CAAC,OAAO,CAAC,CAAC;QAHR,eAAU,GAAV,UAAU,CAAS;QACnB,aAAQ,GAAR,QAAQ,CAAU;QAGzB,IAAI,CAAC,IAAI,GAAG,kBAAkB,CAAC;IACjC,CAAC;CACF;AAED;;GAEG;AACH,MAAM,UAAU,cAAc,CAAC,KAAc;IAC3C,IAAI,KAAK,YAAY,gBAAgB,EAAE,CAAC;QACtC,MAAM,KAAK,CAAC;IACd,CAAC;IAED,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;QAChD,MAAM,GAAG,GAAG,KAAY,CAAC;QAEzB,IAAI,GAAG,CAAC,QAAQ,EAAE,CAAC;YACjB,4BAA4B;YAC5B,MAAM,UAAU,GAAG,GAAG,CAAC,QAAQ,CAAC,MAAM,CAAC;YACvC,MAAM,IAAI,GAAG,GAAG,CAAC,QAAQ,CAAC,IAAI,CAAC;YAE/B,IAAI,OAAO,GAAG,kCAAkC,UAAU,EAAE,CAAC;YAC7D,IAAI,IAAI,EAAE,OAAO,EAAE,CAAC;gBAClB,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC;YACzB,CAAC;iBAAM,IAAI,OAAO,IAAI,KAAK,QAAQ,EAAE,CAAC;gBACpC,OAAO,GAAG,IAAI,CAAC;YACjB,CAAC;YAED,MAAM,IAAI,gBAAgB,CAAC,OAAO,EAAE,UAAU,EAAE,IAAI,CAAC,CAAC;QACxD,CAAC;QAED,IAAI,GAAG,CAAC,OAAO,EAAE,CAAC;YAChB,MAAM,IAAI,gBAAgB,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;QAC1C,CAAC;IACH,CAAC;IAED,MAAM,IAAI,gBAAgB,CAAC,wBAAwB,CAAC,CAAC;AACvD,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,aAAa,CAAI,MAAsB,EAAE,KAAc;IACrE,IAAI,CAAC;QACH,OAAO,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;IAC7B,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IAAI,KAAK,YAAY,CAAC,CAAC,QAAQ,EAAE,CAAC;YAChC,MAAM,eAAe,GAAG,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,CAC7C,GAAG,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,KAAK,GAAG,CAAC,OAAO,EAAE,CACxC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACb,MAAM,IAAI,KAAK,CAAC,qBAAqB,eAAe,EAAE,CAAC,CAAC;QAC1D,CAAC;QACD,MAAM,KAAK,CAAC;IACd,CAAC;AACH,CAAC"}
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Logger utility for structured logging
3
+ */
4
+ export declare class Logger {
5
+ private context;
6
+ constructor(context: string);
7
+ info(message: string, meta?: Record<string, unknown>): void;
8
+ error(message: string, error?: Error, meta?: Record<string, unknown>): void;
9
+ warn(message: string, meta?: Record<string, unknown>): void;
10
+ debug(message: string, meta?: Record<string, unknown>): void;
11
+ }
12
+ //# sourceMappingURL=logger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../../src/utils/logger.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,qBAAa,MAAM;IACL,OAAO,CAAC,OAAO;gBAAP,OAAO,EAAE,MAAM;IAEnC,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;IAU3D,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,CAAC,EAAE,KAAK,EAAE,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;IAY3E,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;IAU3D,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;CAW7D"}
@@ -0,0 +1,50 @@
1
+ /**
2
+ * Logger utility for structured logging
3
+ */
4
+ export class Logger {
5
+ context;
6
+ constructor(context) {
7
+ this.context = context;
8
+ }
9
+ info(message, meta) {
10
+ console.log(JSON.stringify({
11
+ level: 'info',
12
+ context: this.context,
13
+ message,
14
+ timestamp: new Date().toISOString(),
15
+ ...meta,
16
+ }));
17
+ }
18
+ error(message, error, meta) {
19
+ console.error(JSON.stringify({
20
+ level: 'error',
21
+ context: this.context,
22
+ message,
23
+ error: error?.message,
24
+ stack: error?.stack,
25
+ timestamp: new Date().toISOString(),
26
+ ...meta,
27
+ }));
28
+ }
29
+ warn(message, meta) {
30
+ console.warn(JSON.stringify({
31
+ level: 'warn',
32
+ context: this.context,
33
+ message,
34
+ timestamp: new Date().toISOString(),
35
+ ...meta,
36
+ }));
37
+ }
38
+ debug(message, meta) {
39
+ if (process.env.DEBUG) {
40
+ console.debug(JSON.stringify({
41
+ level: 'debug',
42
+ context: this.context,
43
+ message,
44
+ timestamp: new Date().toISOString(),
45
+ ...meta,
46
+ }));
47
+ }
48
+ }
49
+ }
50
+ //# sourceMappingURL=logger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../../src/utils/logger.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,MAAM,OAAO,MAAM;IACG;IAApB,YAAoB,OAAe;QAAf,YAAO,GAAP,OAAO,CAAQ;IAAG,CAAC;IAEvC,IAAI,CAAC,OAAe,EAAE,IAA8B;QAClD,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC;YACzB,KAAK,EAAE,MAAM;YACb,OAAO,EAAE,IAAI,CAAC,OAAO;YACrB,OAAO;YACP,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,GAAG,IAAI;SACR,CAAC,CAAC,CAAC;IACN,CAAC;IAED,KAAK,CAAC,OAAe,EAAE,KAAa,EAAE,IAA8B;QAClE,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC;YAC3B,KAAK,EAAE,OAAO;YACd,OAAO,EAAE,IAAI,CAAC,OAAO;YACrB,OAAO;YACP,KAAK,EAAE,KAAK,EAAE,OAAO;YACrB,KAAK,EAAE,KAAK,EAAE,KAAK;YACnB,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,GAAG,IAAI;SACR,CAAC,CAAC,CAAC;IACN,CAAC;IAED,IAAI,CAAC,OAAe,EAAE,IAA8B;QAClD,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC;YAC1B,KAAK,EAAE,MAAM;YACb,OAAO,EAAE,IAAI,CAAC,OAAO;YACrB,OAAO;YACP,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,GAAG,IAAI;SACR,CAAC,CAAC,CAAC;IACN,CAAC;IAED,KAAK,CAAC,OAAe,EAAE,IAA8B;QACnD,IAAI,OAAO,CAAC,GAAG,CAAC,KAAK,EAAE,CAAC;YACtB,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC;gBAC3B,KAAK,EAAE,OAAO;gBACd,OAAO,EAAE,IAAI,CAAC,OAAO;gBACrB,OAAO;gBACP,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;gBACnC,GAAG,IAAI;aACR,CAAC,CAAC,CAAC;QACN,CAAC;IACH,CAAC;CACF"}
@@ -0,0 +1,6 @@
1
+ import { z } from 'zod';
2
+ /**
3
+ * Convert a Zod schema to JSON Schema format for MCP
4
+ */
5
+ export declare function toJsonSchema(zodSchema: z.ZodType<any>): any;
6
+ //# sourceMappingURL=schema.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"schema.d.ts","sourceRoot":"","sources":["../../src/utils/schema.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB;;GAEG;AACH,wBAAgB,YAAY,CAAC,SAAS,EAAE,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,OAUrD"}
@@ -0,0 +1,14 @@
1
+ import { zodToJsonSchema } from 'zod-to-json-schema';
2
+ /**
3
+ * Convert a Zod schema to JSON Schema format for MCP
4
+ */
5
+ export function toJsonSchema(zodSchema) {
6
+ const jsonSchema = zodToJsonSchema(zodSchema, {
7
+ target: 'jsonSchema7',
8
+ $refStrategy: 'none'
9
+ });
10
+ // Remove $schema field as MCP doesn't expect it
11
+ const { $schema, ...rest } = jsonSchema;
12
+ return rest;
13
+ }
14
+ //# sourceMappingURL=schema.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"schema.js","sourceRoot":"","sources":["../../src/utils/schema.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AAGrD;;GAEG;AACH,MAAM,UAAU,YAAY,CAAC,SAAyB;IACpD,MAAM,UAAU,GAAG,eAAe,CAAC,SAAS,EAAE;QAC5C,MAAM,EAAE,aAAa;QACrB,YAAY,EAAE,MAAM;KACrB,CAAC,CAAC;IAEH,gDAAgD;IAChD,MAAM,EAAE,OAAO,EAAE,GAAG,IAAI,EAAE,GAAG,UAAiB,CAAC;IAE/C,OAAO,IAAI,CAAC;AACd,CAAC"}
package/package.json ADDED
@@ -0,0 +1,58 @@
1
+ {
2
+ "name": "@markstiles/sitecore-search-mcp",
3
+ "version": "1.0.0",
4
+ "description": "Model Context Protocol server for Sitecore Search APIs (Search, Ingestion, and Events)",
5
+ "type": "module",
6
+ "main": "dist/index.js",
7
+ "bin": {
8
+ "mcp-sitecore-search-server": "dist/index.js"
9
+ },
10
+ "files": [
11
+ "dist/**/*",
12
+ "README.md",
13
+ "LICENSE",
14
+ "AUTHENTICATION.md"
15
+ ],
16
+ "scripts": {
17
+ "build": "tsc",
18
+ "dev": "tsc --watch",
19
+ "prepare": "npm run build",
20
+ "prepublishOnly": "npm run build",
21
+ "test": "echo \"Error: no test specified\" && exit 1"
22
+ },
23
+ "keywords": [
24
+ "mcp",
25
+ "model-context-protocol",
26
+ "sitecore",
27
+ "sitecore-search",
28
+ "search",
29
+ "api",
30
+ "search-api",
31
+ "ingestion",
32
+ "events",
33
+ "analytics"
34
+ ],
35
+ "author": "Your Name <your.email@example.com>",
36
+ "license": "MIT",
37
+ "repository": {
38
+ "type": "git",
39
+ "url": "https://github.com/markstiles/mcp-sitecore-search-server.git"
40
+ },
41
+ "bugs": {
42
+ "url": "https://github.com/markstiles/mcp-sitecore-search-server/issues"
43
+ },
44
+ "homepage": "https://github.com/markstiles/mcp-sitecore-search-server#readme",
45
+ "dependencies": {
46
+ "@modelcontextprotocol/sdk": "^1.0.0",
47
+ "axios": "^1.6.0",
48
+ "zod": "^3.23.0",
49
+ "zod-to-json-schema": "^3.25.0"
50
+ },
51
+ "devDependencies": {
52
+ "@types/node": "^20.0.0",
53
+ "typescript": "^5.3.0"
54
+ },
55
+ "engines": {
56
+ "node": ">=18.0.0"
57
+ }
58
+ }