codewiki-mcp 1.0.1 → 1.1.1
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/LICENSE +21 -0
- package/dist/cli.js +7 -2
- package/dist/cli.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/lib/extractKeyword.js +30 -0
- package/dist/lib/extractKeyword.js.map +1 -1
- package/dist/lib/repo.js +4 -1
- package/dist/lib/repo.js.map +1 -1
- package/dist/server.d.ts +2 -1
- package/dist/server.js +17 -6
- package/dist/server.js.map +1 -1
- package/package.json +23 -1
- package/.claude/skills/codewiki.md +0 -186
- package/.cursor/mcp.json +0 -9
- package/.dockerignore +0 -10
- package/.github/dependabot.yml +0 -33
- package/.github/workflows/ci.yml +0 -42
- package/.github/workflows/release.yml +0 -36
- package/.releaserc.json +0 -16
- package/CHANGELOG.md +0 -13
- package/Dockerfile +0 -15
- package/src/cli.ts +0 -67
- package/src/index.ts +0 -32
- package/src/lib/batchexecute.ts +0 -72
- package/src/lib/codewikiClient.ts +0 -294
- package/src/lib/config.ts +0 -30
- package/src/lib/errors.ts +0 -57
- package/src/lib/extractKeyword.ts +0 -47
- package/src/lib/repo.ts +0 -70
- package/src/lib/resolveRepo.ts +0 -60
- package/src/schemas.ts +0 -22
- package/src/server.ts +0 -120
- package/src/tools/askRepo.ts +0 -38
- package/src/tools/fetchRepo.ts +0 -74
- package/src/tools/searchRepos.ts +0 -40
- package/tests/batchexecute.test.ts +0 -42
- package/tests/client.test.ts +0 -129
- package/tests/errors.test.ts +0 -122
- package/tests/extractKeyword.test.ts +0 -34
- package/tests/resolveRepo.test.ts +0 -79
- package/tsconfig.json +0 -18
- package/vitest.config.ts +0 -10
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 codewiki-mcp contributors
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/dist/cli.js
CHANGED
|
@@ -43,14 +43,19 @@ async function main() {
|
|
|
43
43
|
const port = Number.parseInt(values.port, 10) || 3000;
|
|
44
44
|
const endpoint = values.endpoint;
|
|
45
45
|
const config = loadConfig();
|
|
46
|
-
const mcp = createMcpServer(config);
|
|
47
46
|
const shutdown = async () => {
|
|
48
47
|
await stopServer();
|
|
49
48
|
process.exit(0);
|
|
50
49
|
};
|
|
51
50
|
process.on('SIGTERM', shutdown);
|
|
52
51
|
process.on('SIGINT', shutdown);
|
|
53
|
-
|
|
52
|
+
if (transport === 'sse') {
|
|
53
|
+
await startServer(() => createMcpServer(config), { transport, port, endpoint });
|
|
54
|
+
}
|
|
55
|
+
else {
|
|
56
|
+
const mcp = createMcpServer(config);
|
|
57
|
+
await startServer(mcp, { transport, port, endpoint });
|
|
58
|
+
}
|
|
54
59
|
}
|
|
55
60
|
main().catch((error) => {
|
|
56
61
|
console.error(error);
|
package/dist/cli.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AAEA,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAA;AACrC,OAAO,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAA;AAC5C,OAAO,EAAE,eAAe,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,aAAa,CAAA;AAEtE,MAAM,IAAI,GAAG;;;;;;;;;;;;;;;;;;;;;CAqBZ,CAAC,IAAI,EAAE,CAAA;AAER,KAAK,UAAU,IAAI;IACjB,MAAM,EAAE,MAAM,EAAE,GAAG,SAAS,CAAC;QAC3B,OAAO,EAAE;YACP,IAAI,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,KAAK,EAAE;YACzC,GAAG,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,KAAK,EAAE;YACxC,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE;YACzC,QAAQ,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE;YAC7C,IAAI,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,KAAK,EAAE,GAAG,EAAE,OAAO,EAAE,KAAK,EAAE;SACtD;QACD,MAAM,EAAE,IAAI;KACb,CAAC,CAAA;IAEF,IAAI,MAAM,CAAC,IAAI,EAAE,CAAC;QAChB,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,CAAA;QACjB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,MAAM,SAAS,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAA;IACrE,MAAM,IAAI,GAAG,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,IAAK,EAAE,EAAE,CAAC,IAAI,IAAI,CAAA;IACtD,MAAM,QAAQ,GAAG,MAAM,CAAC,QAAS,CAAA;IAEjC,MAAM,MAAM,GAAG,UAAU,EAAE,CAAA;
|
|
1
|
+
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AAEA,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAA;AACrC,OAAO,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAA;AAC5C,OAAO,EAAE,eAAe,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,aAAa,CAAA;AAEtE,MAAM,IAAI,GAAG;;;;;;;;;;;;;;;;;;;;;CAqBZ,CAAC,IAAI,EAAE,CAAA;AAER,KAAK,UAAU,IAAI;IACjB,MAAM,EAAE,MAAM,EAAE,GAAG,SAAS,CAAC;QAC3B,OAAO,EAAE;YACP,IAAI,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,KAAK,EAAE;YACzC,GAAG,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,KAAK,EAAE;YACxC,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE;YACzC,QAAQ,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE;YAC7C,IAAI,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,KAAK,EAAE,GAAG,EAAE,OAAO,EAAE,KAAK,EAAE;SACtD;QACD,MAAM,EAAE,IAAI;KACb,CAAC,CAAA;IAEF,IAAI,MAAM,CAAC,IAAI,EAAE,CAAC;QAChB,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,CAAA;QACjB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,MAAM,SAAS,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAA;IACrE,MAAM,IAAI,GAAG,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,IAAK,EAAE,EAAE,CAAC,IAAI,IAAI,CAAA;IACtD,MAAM,QAAQ,GAAG,MAAM,CAAC,QAAS,CAAA;IAEjC,MAAM,MAAM,GAAG,UAAU,EAAE,CAAA;IAE3B,MAAM,QAAQ,GAAG,KAAK,IAAI,EAAE;QAC1B,MAAM,UAAU,EAAE,CAAA;QAClB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC,CAAA;IACD,OAAO,CAAC,EAAE,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAA;IAC/B,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAA;IAE9B,IAAI,SAAS,KAAK,KAAK,EAAE,CAAC;QACxB,MAAM,WAAW,CAAC,GAAG,EAAE,CAAC,eAAe,CAAC,MAAM,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,QAAQ,EAAE,CAAC,CAAA;IACjF,CAAC;SAAM,CAAC;QACN,MAAM,GAAG,GAAG,eAAe,CAAC,MAAM,CAAC,CAAA;QACnC,MAAM,WAAW,CAAC,GAAG,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,QAAQ,EAAE,CAAC,CAAA;IACvD,CAAC;AACH,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;IACrB,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,CAAA;IACpB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;AACjB,CAAC,CAAC,CAAA"}
|
package/dist/index.d.ts
CHANGED
|
@@ -9,7 +9,7 @@ export type { NormalizedRepo } from './lib/repo.js';
|
|
|
9
9
|
export { extractKeyword } from './lib/extractKeyword.js';
|
|
10
10
|
export { resolveRepoFromGitHub } from './lib/resolveRepo.js';
|
|
11
11
|
export { createMcpServer, startServer, stopServer } from './server.js';
|
|
12
|
-
export type { ServerOptions } from './server.js';
|
|
12
|
+
export type { ServerOptions, McpServerFactory } from './server.js';
|
|
13
13
|
export { SearchReposInput, FetchRepoInput, AskRepoInput } from './schemas.js';
|
|
14
14
|
export { registerSearchReposTool } from './tools/searchRepos.js';
|
|
15
15
|
export { registerFetchRepoTool } from './tools/fetchRepo.js';
|
|
@@ -13,8 +13,38 @@ const STOP_WORDS = new Set([
|
|
|
13
13
|
'have', 'has', 'had', 'do', 'did', 'will', 'shall',
|
|
14
14
|
'of', 'in', 'to', 'on', 'at', 'by', 'up', 'it', 'its',
|
|
15
15
|
]);
|
|
16
|
+
const STOP_WORDS_RU = new Set([
|
|
17
|
+
'репозиторий', 'репо', 'библиотека', 'библиотеки', 'фреймворк', 'пакет', 'модуль',
|
|
18
|
+
'проект', 'инструмент', 'код', 'исходник', 'открытый',
|
|
19
|
+
'как', 'что', 'где', 'какой', 'какая', 'какие', 'какого', 'кто', 'когда', 'зачем', 'почему',
|
|
20
|
+
'такое', 'такой', 'такая', 'такие', 'таких', 'такого',
|
|
21
|
+
'покажи', 'расскажи', 'найди', 'найти', 'ищи', 'искать', 'получи', 'посмотри', 'дай',
|
|
22
|
+
'пожалуйста', 'можно', 'можешь', 'нужно', 'нужна', 'нужен', 'нужны',
|
|
23
|
+
'это', 'этот', 'эта', 'эти', 'этого', 'тот', 'та', 'те',
|
|
24
|
+
'для', 'про', 'при', 'или', 'его', 'её', 'мне', 'меня', 'себя',
|
|
25
|
+
'есть', 'был', 'была', 'были', 'быть', 'будет',
|
|
26
|
+
'все', 'всё', 'весь', 'вся', 'всех',
|
|
27
|
+
'из', 'на', 'по', 'за', 'от', 'до', 'об',
|
|
28
|
+
'не', 'ни', 'но', 'да', 'же', 'ли', 'бы',
|
|
29
|
+
'управления', 'управление', 'состоянием', 'состояние',
|
|
30
|
+
'работы', 'работа', 'устроен', 'устроена', 'работает',
|
|
31
|
+
'лучшая', 'лучший', 'лучшие', 'лучше', 'самый', 'самая', 'самые',
|
|
32
|
+
]);
|
|
16
33
|
const SKIP_POS = new Set(['PUNCT', 'SPACE', 'DET', 'ADP', 'CCONJ', 'SCONJ', 'AUX', 'PART', 'INTJ']);
|
|
34
|
+
const HAS_NON_LATIN = /[^\u0000-\u007F]/;
|
|
35
|
+
function extractKeywordSimple(text) {
|
|
36
|
+
const tokens = text
|
|
37
|
+
.split(/[\s,.:;!?()[\]{}"'«»]+/)
|
|
38
|
+
.filter((t) => t.length > 1)
|
|
39
|
+
.filter((t) => !STOP_WORDS.has(t.toLowerCase()) && !STOP_WORDS_RU.has(t.toLowerCase()));
|
|
40
|
+
// Prefer Latin/mixed tokens (likely project names) over pure-Cyrillic tokens
|
|
41
|
+
const latin = tokens.filter((t) => /[a-zA-Z0-9]/.test(t));
|
|
42
|
+
return latin[0] ?? tokens[0] ?? null;
|
|
43
|
+
}
|
|
17
44
|
export function extractKeyword(text) {
|
|
45
|
+
if (HAS_NON_LATIN.test(text)) {
|
|
46
|
+
return extractKeywordSimple(text);
|
|
47
|
+
}
|
|
18
48
|
const doc = nlp.readDoc(text);
|
|
19
49
|
const tokens = doc.tokens();
|
|
20
50
|
// First pass: look for NOUN/PROPN that aren't stop words
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"extractKeyword.js","sourceRoot":"","sources":["../../src/lib/extractKeyword.ts"],"names":[],"mappings":"AAAA,OAAO,OAAO,MAAM,UAAU,CAAA;AAC9B,OAAO,KAAK,MAAM,yBAAyB,CAAA;AAE3C,MAAM,GAAG,GAAG,OAAO,CAAC,KAAK,CAAC,CAAA;AAC1B,MAAM,GAAG,GAAG,GAAG,CAAC,GAAG,CAAA;AAEnB,MAAM,UAAU,GAAG,IAAI,GAAG,CAAC;IACzB,MAAM,EAAE,YAAY,EAAE,SAAS,EAAE,WAAW,EAAE,SAAS,EAAE,QAAQ;IACjE,SAAS,EAAE,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,QAAQ;IAC/D,KAAK,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM;IAChE,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM;IAC7D,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM;IAC9D,QAAQ,EAAE,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,KAAK,EAAE,OAAO;IAC3D,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,OAAO;IACjD,MAAM,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,KAAK,EAAE,MAAM,EAAE,OAAO;IAClD,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK;CACtD,CAAC,CAAA;AAEF,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC,CAAC,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,CAAC,CAAA;AAEnG,MAAM,UAAU,cAAc,CAAC,IAAY;IACzC,MAAM,GAAG,GAAG,GAAG,CAAC,OAAO,CAAC,IAAI,CAAC,CAAA;IAC7B,MAAM,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE,CAAA;IAE3B,yDAAyD;IACzD,MAAM,KAAK,GAAa,EAAE,CAAA;IAC1B,MAAM,QAAQ,GAAa,EAAE,CAAA;IAE7B,MAAM,CAAC,IAAI,CAAC,CAAC,KAAU,EAAE,EAAE;QACzB,MAAM,GAAG,GAAG,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAW,CAAA;QACxC,MAAM,KAAK,GAAG,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,KAAK,CAAW,CAAA;QAC5C,MAAM,KAAK,GAAG,KAAK,CAAC,WAAW,EAAE,CAAA;QAEjC,IAAI,QAAQ,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,KAAK,CAAC,MAAM,IAAI,CAAC;YAAE,OAAM;QAElD,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE,CAAC;YAC3B,IAAI,GAAG,KAAK,MAAM,IAAI,GAAG,KAAK,OAAO,EAAE,CAAC;gBACtC,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAA;YACnB,CAAC;iBAAM,CAAC;gBACN,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAA;YACtB,CAAC;QACH,CAAC;IACH,CAAC,CAAC,CAAA;IAEF,0DAA0D;IAC1D,OAAO,KAAK,CAAC,CAAC,CAAC,IAAI,QAAQ,CAAC,CAAC,CAAC,IAAI,IAAI,CAAA;AACxC,CAAC"}
|
|
1
|
+
{"version":3,"file":"extractKeyword.js","sourceRoot":"","sources":["../../src/lib/extractKeyword.ts"],"names":[],"mappings":"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"}
|
package/dist/lib/repo.js
CHANGED
|
@@ -7,10 +7,13 @@ export function normalizeRepoInput(input) {
|
|
|
7
7
|
}
|
|
8
8
|
if (/^https?:\/\//i.test(raw)) {
|
|
9
9
|
const url = new URL(raw);
|
|
10
|
+
if (url.hostname !== 'github.com') {
|
|
11
|
+
throw new Error(`Only GitHub repositories are supported, got host: ${url.hostname}`);
|
|
12
|
+
}
|
|
10
13
|
const repoPath = url.pathname.replace(/^\/+|\/+$/g, '');
|
|
11
14
|
const parts = repoPath.split('/').filter(Boolean);
|
|
12
15
|
if (parts.length < 2) {
|
|
13
|
-
throw new Error('Expected repository URL in the format https://
|
|
16
|
+
throw new Error('Expected repository URL in the format https://github.com/owner/repo');
|
|
14
17
|
}
|
|
15
18
|
const normalizedPath = `${parts[0]}/${parts[1]}`;
|
|
16
19
|
return {
|
package/dist/lib/repo.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"repo.js","sourceRoot":"","sources":["../../src/lib/repo.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAA;AACpD,OAAO,EAAE,qBAAqB,EAAE,MAAM,kBAAkB,CAAA;AASxD,MAAM,UAAU,kBAAkB,CAAC,KAAa;IAC9C,MAAM,GAAG,GAAG,KAAK,CAAC,IAAI,EAAE,CAAA;IACxB,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,MAAM,IAAI,KAAK,CAAC,2BAA2B,CAAC,CAAA;IAC9C,CAAC;IAED,IAAI,eAAe,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;QAC9B,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,GAAG,CAAC,CAAA;QACxB,MAAM,QAAQ,GAAG,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,YAAY,EAAE,EAAE,CAAC,CAAA;QACvD,MAAM,KAAK,GAAG,QAAQ,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAA;QACjD,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACrB,MAAM,IAAI,KAAK,CAAC
|
|
1
|
+
{"version":3,"file":"repo.js","sourceRoot":"","sources":["../../src/lib/repo.ts"],"names":[],"mappings":"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"}
|
package/dist/server.d.ts
CHANGED
|
@@ -5,6 +5,7 @@ export interface ServerOptions {
|
|
|
5
5
|
port?: number;
|
|
6
6
|
endpoint?: string;
|
|
7
7
|
}
|
|
8
|
+
export type McpServerFactory = () => McpServer;
|
|
8
9
|
export declare function createMcpServer(config: CodeWikiConfig): McpServer;
|
|
9
|
-
export declare function startServer(
|
|
10
|
+
export declare function startServer(mcpOrFactory: McpServer | McpServerFactory, options: ServerOptions): Promise<void>;
|
|
10
11
|
export declare function stopServer(): Promise<void>;
|
package/dist/server.js
CHANGED
|
@@ -4,15 +4,19 @@ import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
|
4
4
|
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
|
|
5
5
|
import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js';
|
|
6
6
|
import { SSEServerTransport } from '@modelcontextprotocol/sdk/server/sse.js';
|
|
7
|
+
import { readFileSync } from 'node:fs';
|
|
8
|
+
import { fileURLToPath } from 'node:url';
|
|
9
|
+
import { dirname, resolve } from 'node:path';
|
|
7
10
|
import { CodeWikiClient } from './lib/codewikiClient.js';
|
|
8
11
|
import { registerSearchReposTool } from './tools/searchRepos.js';
|
|
9
12
|
import { registerFetchRepoTool } from './tools/fetchRepo.js';
|
|
10
13
|
import { registerAskRepoTool } from './tools/askRepo.js';
|
|
11
|
-
const
|
|
14
|
+
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
15
|
+
const pkg = JSON.parse(readFileSync(resolve(__dirname, '..', 'package.json'), 'utf-8'));
|
|
12
16
|
export function createMcpServer(config) {
|
|
13
17
|
const mcp = new McpServer({
|
|
14
18
|
name: 'codewiki-mcp',
|
|
15
|
-
version:
|
|
19
|
+
version: pkg.version,
|
|
16
20
|
});
|
|
17
21
|
const client = CodeWikiClient.fromConfig(config);
|
|
18
22
|
registerSearchReposTool(mcp, client);
|
|
@@ -21,11 +25,12 @@ export function createMcpServer(config) {
|
|
|
21
25
|
return mcp;
|
|
22
26
|
}
|
|
23
27
|
let httpServer;
|
|
24
|
-
export async function startServer(
|
|
28
|
+
export async function startServer(mcpOrFactory, options) {
|
|
25
29
|
const { transport, port = 3000, endpoint = '/mcp' } = options;
|
|
30
|
+
const getMcp = typeof mcpOrFactory === 'function' ? mcpOrFactory : () => mcpOrFactory;
|
|
26
31
|
if (transport === 'stdio') {
|
|
27
32
|
const stdioTransport = new StdioServerTransport();
|
|
28
|
-
await
|
|
33
|
+
await getMcp().connect(stdioTransport);
|
|
29
34
|
return;
|
|
30
35
|
}
|
|
31
36
|
if (transport === 'http') {
|
|
@@ -40,7 +45,7 @@ export async function startServer(mcp, options) {
|
|
|
40
45
|
res.writeHead(404).end('Not Found');
|
|
41
46
|
}
|
|
42
47
|
});
|
|
43
|
-
await
|
|
48
|
+
await getMcp().connect(httpTransport);
|
|
44
49
|
await new Promise((resolve) => {
|
|
45
50
|
httpServer.listen(port, () => {
|
|
46
51
|
console.error(`codewiki-mcp HTTP server listening on http://localhost:${port}${endpoint}`);
|
|
@@ -50,6 +55,11 @@ export async function startServer(mcp, options) {
|
|
|
50
55
|
return;
|
|
51
56
|
}
|
|
52
57
|
if (transport === 'sse') {
|
|
58
|
+
if (typeof mcpOrFactory !== 'function') {
|
|
59
|
+
throw new Error('SSE transport requires a McpServerFactory (a function returning a new McpServer) ' +
|
|
60
|
+
'because each SSE client needs its own McpServer instance. ' +
|
|
61
|
+
'Pass () => createMcpServer(config) instead of a single McpServer.');
|
|
62
|
+
}
|
|
53
63
|
const sessions = new Map();
|
|
54
64
|
httpServer = createServer(async (req, res) => {
|
|
55
65
|
const url = new URL(req.url ?? '/', `http://localhost:${port}`);
|
|
@@ -59,7 +69,8 @@ export async function startServer(mcp, options) {
|
|
|
59
69
|
sseTransport.onclose = () => {
|
|
60
70
|
sessions.delete(sseTransport.sessionId);
|
|
61
71
|
};
|
|
62
|
-
|
|
72
|
+
const sessionMcp = mcpOrFactory();
|
|
73
|
+
await sessionMcp.connect(sseTransport);
|
|
63
74
|
return;
|
|
64
75
|
}
|
|
65
76
|
if (url.pathname === `${endpoint}/message` && req.method === 'POST') {
|
package/dist/server.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAe,MAAM,WAAW,CAAA;AACrD,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAA;AACxC,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AACnE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAA;AAChF,OAAO,EAAE,6BAA6B,EAAE,MAAM,oDAAoD,CAAA;AAClG,OAAO,EAAE,kBAAkB,EAAE,MAAM,yCAAyC,CAAA;
|
|
1
|
+
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,11 +1,33 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "codewiki-mcp",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.1.1",
|
|
4
|
+
"mcpName": "io.github.izzzzzi/codewiki-mcp",
|
|
4
5
|
"description": "MCP server for codewiki.google",
|
|
5
6
|
"type": "module",
|
|
7
|
+
"main": "dist/index.js",
|
|
6
8
|
"bin": {
|
|
7
9
|
"codewiki-mcp": "dist/cli.js"
|
|
8
10
|
},
|
|
11
|
+
"files": [
|
|
12
|
+
"dist",
|
|
13
|
+
"README.md",
|
|
14
|
+
"LICENSE"
|
|
15
|
+
],
|
|
16
|
+
"keywords": [
|
|
17
|
+
"mcp",
|
|
18
|
+
"mcp-server",
|
|
19
|
+
"codewiki",
|
|
20
|
+
"documentation",
|
|
21
|
+
"github",
|
|
22
|
+
"ai",
|
|
23
|
+
"model-context-protocol"
|
|
24
|
+
],
|
|
25
|
+
"repository": {
|
|
26
|
+
"type": "git",
|
|
27
|
+
"url": "https://github.com/izzzzzi/codewiki-mcp.git"
|
|
28
|
+
},
|
|
29
|
+
"license": "MIT",
|
|
30
|
+
"homepage": "https://github.com/izzzzzi/codewiki-mcp",
|
|
9
31
|
"scripts": {
|
|
10
32
|
"build": "tsc -p tsconfig.json",
|
|
11
33
|
"dev": "tsx src/cli.ts",
|
|
@@ -1,186 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: codewiki
|
|
3
|
-
description: Research any open-source repository via codewiki.google — search, fetch wiki docs, ask questions
|
|
4
|
-
tools: ["codewiki_search_repos", "codewiki_fetch_repo", "codewiki_ask_repo"]
|
|
5
|
-
---
|
|
6
|
-
|
|
7
|
-
# CodeWiki MCP — Skill Guide
|
|
8
|
-
|
|
9
|
-
## Available Tools
|
|
10
|
-
|
|
11
|
-
### codewiki_search_repos
|
|
12
|
-
Search repositories indexed by codewiki.google.
|
|
13
|
-
|
|
14
|
-
| Parameter | Type | Required | Description |
|
|
15
|
-
|-----------|------|----------|-------------|
|
|
16
|
-
| `query` | string | yes | Search query (library name, keyword, description) |
|
|
17
|
-
| `limit` | number | no | Max results (1-50, default 10) |
|
|
18
|
-
|
|
19
|
-
**Returns**: JSON with `query`, `count`, `items[]` (each with `fullName`, `url`, `description`, `avatarUrl`, `extraScore`), and `meta` (totalBytes, totalElapsedMs).
|
|
20
|
-
|
|
21
|
-
### codewiki_fetch_repo
|
|
22
|
-
Fetch generated wiki content for a repository.
|
|
23
|
-
|
|
24
|
-
| Parameter | Type | Required | Description |
|
|
25
|
-
|-----------|------|----------|-------------|
|
|
26
|
-
| `repo` | string | yes | Repository identifier: `owner/repo`, full GitHub URL, or natural-language query (NLP resolved) |
|
|
27
|
-
| `mode` | string | no | `"aggregate"` (default) — full markdown; `"pages"` — structured JSON per section |
|
|
28
|
-
|
|
29
|
-
**Returns**:
|
|
30
|
-
- **aggregate mode**: Markdown text with preface (repo, commit, canonical URL, response meta)
|
|
31
|
-
- **pages mode**: JSON with `repo`, `commit`, `canonicalUrl`, `pages[]` (title, level, anchor, markdown, diagramCount), and `meta`
|
|
32
|
-
|
|
33
|
-
### codewiki_ask_repo
|
|
34
|
-
Ask a natural-language question about a repository.
|
|
35
|
-
|
|
36
|
-
| Parameter | Type | Required | Description |
|
|
37
|
-
|-----------|------|----------|-------------|
|
|
38
|
-
| `repo` | string | yes | Repository identifier (same formats as fetch) |
|
|
39
|
-
| `question` | string | yes | Natural-language question about the repo |
|
|
40
|
-
| `history` | array | no | Conversation history: `[{role: "user"|"assistant", content: "..."}]` (max 20) |
|
|
41
|
-
|
|
42
|
-
**Returns**: JSON with `answer` (string) and `meta` (totalBytes, totalElapsedMs).
|
|
43
|
-
|
|
44
|
-
---
|
|
45
|
-
|
|
46
|
-
## Prompt Templates
|
|
47
|
-
|
|
48
|
-
### Study a project's architecture
|
|
49
|
-
```
|
|
50
|
-
1. codewiki_search_repos(query: "<project name>")
|
|
51
|
-
→ find the exact owner/repo
|
|
52
|
-
2. codewiki_fetch_repo(repo: "<owner/repo>", mode: "aggregate")
|
|
53
|
-
→ read the full wiki to understand architecture
|
|
54
|
-
3. codewiki_ask_repo(repo: "<owner/repo>", question: "What are the main architectural patterns and components?")
|
|
55
|
-
→ deep-dive into architecture
|
|
56
|
-
```
|
|
57
|
-
|
|
58
|
-
### Find how a feature is implemented
|
|
59
|
-
```
|
|
60
|
-
codewiki_ask_repo(
|
|
61
|
-
repo: "<owner/repo>",
|
|
62
|
-
question: "How is <feature X> implemented? Show the key modules and data flow."
|
|
63
|
-
)
|
|
64
|
-
```
|
|
65
|
-
|
|
66
|
-
### Compare approaches in two repos
|
|
67
|
-
```
|
|
68
|
-
1. codewiki_fetch_repo(repo: "<owner1/repo1>", mode: "pages")
|
|
69
|
-
2. codewiki_fetch_repo(repo: "<owner2/repo2>", mode: "pages")
|
|
70
|
-
3. Compare the architectural approaches, patterns, and trade-offs
|
|
71
|
-
```
|
|
72
|
-
|
|
73
|
-
### Quick library overview
|
|
74
|
-
```
|
|
75
|
-
1. codewiki_search_repos(query: "<library>")
|
|
76
|
-
→ confirm the right repo
|
|
77
|
-
2. codewiki_fetch_repo(repo: "<owner/repo>", mode: "pages")
|
|
78
|
-
→ get structured sections
|
|
79
|
-
3. Summarize: purpose, key features, getting started, API surface
|
|
80
|
-
```
|
|
81
|
-
|
|
82
|
-
### Explore a topic across repos
|
|
83
|
-
```
|
|
84
|
-
1. codewiki_search_repos(query: "<topic>", limit: 5)
|
|
85
|
-
→ find top repos for the topic
|
|
86
|
-
2. For each interesting repo:
|
|
87
|
-
codewiki_ask_repo(repo: "<repo>", question: "Summarize the approach to <topic>")
|
|
88
|
-
3. Synthesize findings across repos
|
|
89
|
-
```
|
|
90
|
-
|
|
91
|
-
---
|
|
92
|
-
|
|
93
|
-
## Workflow Chains
|
|
94
|
-
|
|
95
|
-
### Deep Research Chain
|
|
96
|
-
**Goal**: Thorough understanding of a project
|
|
97
|
-
|
|
98
|
-
1. **Search** → `codewiki_search_repos` to find the repo and confirm its full name
|
|
99
|
-
2. **Fetch overview** → `codewiki_fetch_repo(mode: "aggregate")` to read the full wiki
|
|
100
|
-
3. **Ask specific questions** → `codewiki_ask_repo` for deep-dives into specific areas
|
|
101
|
-
4. **Follow up** → Use `history` parameter to maintain context across questions
|
|
102
|
-
|
|
103
|
-
### Comparison Chain
|
|
104
|
-
**Goal**: Compare two or more implementations
|
|
105
|
-
|
|
106
|
-
1. **Fetch all** → `codewiki_fetch_repo(mode: "pages")` for each repo
|
|
107
|
-
2. **Identify patterns** → Extract architectural sections from each
|
|
108
|
-
3. **Ask targeted questions** → `codewiki_ask_repo` about specific differences
|
|
109
|
-
|
|
110
|
-
### Migration Research Chain
|
|
111
|
-
**Goal**: Understand a library for migration
|
|
112
|
-
|
|
113
|
-
1. **Search** → Find source and target libraries
|
|
114
|
-
2. **Fetch both** → Get wiki content for both
|
|
115
|
-
3. **Ask migration questions** → "What are the key API differences between X and Y?"
|
|
116
|
-
4. **Ask compatibility** → "What breaking changes should I watch for?"
|
|
117
|
-
|
|
118
|
-
---
|
|
119
|
-
|
|
120
|
-
## Error Handling
|
|
121
|
-
|
|
122
|
-
| Error Code | Meaning | Action |
|
|
123
|
-
|------------|---------|--------|
|
|
124
|
-
| `VALIDATION` | Invalid input parameters | Check parameter types and required fields |
|
|
125
|
-
| `RPC_FAIL` | CodeWiki API call failed | Retry with different query; check if repo exists on codewiki.google |
|
|
126
|
-
| `TIMEOUT` | Request timed out | Try again; for large repos, use `mode: "pages"` to get structured data |
|
|
127
|
-
| `NLP_RESOLVE_FAIL` | Could not resolve natural-language input to a repo | Use explicit `owner/repo` format instead |
|
|
128
|
-
|
|
129
|
-
When you receive an error:
|
|
130
|
-
1. Parse the error envelope: `{ error: { code, message, rpcId?, statusCode? } }`
|
|
131
|
-
2. If `RPC_FAIL` with `statusCode: 404` → repo not indexed, suggest searching first
|
|
132
|
-
3. If `TIMEOUT` → simplify query or try mode: "pages" for fetch
|
|
133
|
-
4. If `NLP_RESOLVE_FAIL` → ask user for the exact repo name
|
|
134
|
-
|
|
135
|
-
---
|
|
136
|
-
|
|
137
|
-
## Conversation History Tips
|
|
138
|
-
|
|
139
|
-
The `history` parameter in `codewiki_ask_repo` enables multi-turn conversations:
|
|
140
|
-
|
|
141
|
-
```json
|
|
142
|
-
{
|
|
143
|
-
"repo": "facebook/react",
|
|
144
|
-
"question": "How does the fiber reconciler differ?",
|
|
145
|
-
"history": [
|
|
146
|
-
{"role": "user", "content": "What is the rendering pipeline?"},
|
|
147
|
-
{"role": "assistant", "content": "React's rendering pipeline consists of..."}
|
|
148
|
-
]
|
|
149
|
-
}
|
|
150
|
-
```
|
|
151
|
-
|
|
152
|
-
**Best practices**:
|
|
153
|
-
- Keep history under 20 entries for optimal performance
|
|
154
|
-
- Include only relevant prior Q&A pairs
|
|
155
|
-
- Summarize long assistant responses in history to save tokens
|
|
156
|
-
- Start a new conversation (no history) when changing topics
|
|
157
|
-
|
|
158
|
-
---
|
|
159
|
-
|
|
160
|
-
## Examples
|
|
161
|
-
|
|
162
|
-
### Example 1: Quick repo lookup
|
|
163
|
-
**User**: "What does the fastify framework do?"
|
|
164
|
-
```
|
|
165
|
-
codewiki_search_repos(query: "fastify")
|
|
166
|
-
→ finds fastify/fastify
|
|
167
|
-
codewiki_ask_repo(repo: "fastify/fastify", question: "What is Fastify and what are its key features?")
|
|
168
|
-
→ comprehensive answer
|
|
169
|
-
```
|
|
170
|
-
|
|
171
|
-
### Example 2: Architecture deep-dive
|
|
172
|
-
**User**: "Explain how Next.js handles server-side rendering"
|
|
173
|
-
```
|
|
174
|
-
codewiki_fetch_repo(repo: "vercel/next.js", mode: "aggregate")
|
|
175
|
-
→ full wiki content
|
|
176
|
-
codewiki_ask_repo(repo: "vercel/next.js", question: "How does Next.js implement server-side rendering? Describe the request lifecycle.")
|
|
177
|
-
→ detailed SSR explanation
|
|
178
|
-
```
|
|
179
|
-
|
|
180
|
-
### Example 3: Library comparison
|
|
181
|
-
**User**: "Compare Express and Fastify"
|
|
182
|
-
```
|
|
183
|
-
codewiki_fetch_repo(repo: "expressjs/express", mode: "pages")
|
|
184
|
-
codewiki_fetch_repo(repo: "fastify/fastify", mode: "pages")
|
|
185
|
-
→ compare architectures, middleware patterns, performance approaches
|
|
186
|
-
```
|
package/.cursor/mcp.json
DELETED
package/.dockerignore
DELETED
package/.github/dependabot.yml
DELETED
|
@@ -1,33 +0,0 @@
|
|
|
1
|
-
version: 2
|
|
2
|
-
|
|
3
|
-
updates:
|
|
4
|
-
- package-ecosystem: npm
|
|
5
|
-
directory: /
|
|
6
|
-
schedule:
|
|
7
|
-
interval: weekly
|
|
8
|
-
day: monday
|
|
9
|
-
open-pull-requests-limit: 10
|
|
10
|
-
labels:
|
|
11
|
-
- dependencies
|
|
12
|
-
commit-message:
|
|
13
|
-
prefix: "chore(deps):"
|
|
14
|
-
groups:
|
|
15
|
-
dev-dependencies:
|
|
16
|
-
dependency-type: development
|
|
17
|
-
update-types:
|
|
18
|
-
- minor
|
|
19
|
-
- patch
|
|
20
|
-
production-dependencies:
|
|
21
|
-
dependency-type: production
|
|
22
|
-
update-types:
|
|
23
|
-
- patch
|
|
24
|
-
|
|
25
|
-
- package-ecosystem: github-actions
|
|
26
|
-
directory: /
|
|
27
|
-
schedule:
|
|
28
|
-
interval: weekly
|
|
29
|
-
day: monday
|
|
30
|
-
labels:
|
|
31
|
-
- ci
|
|
32
|
-
commit-message:
|
|
33
|
-
prefix: "ci:"
|
package/.github/workflows/ci.yml
DELETED
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
name: CI
|
|
2
|
-
|
|
3
|
-
on:
|
|
4
|
-
push:
|
|
5
|
-
branches: [main]
|
|
6
|
-
pull_request:
|
|
7
|
-
branches: [main]
|
|
8
|
-
|
|
9
|
-
permissions:
|
|
10
|
-
contents: read
|
|
11
|
-
|
|
12
|
-
jobs:
|
|
13
|
-
test:
|
|
14
|
-
runs-on: ubuntu-latest
|
|
15
|
-
strategy:
|
|
16
|
-
matrix:
|
|
17
|
-
node-version: [18, 20, 22]
|
|
18
|
-
steps:
|
|
19
|
-
- uses: actions/checkout@v6
|
|
20
|
-
|
|
21
|
-
- uses: actions/setup-node@v6
|
|
22
|
-
with:
|
|
23
|
-
node-version: ${{ matrix.node-version }}
|
|
24
|
-
cache: npm
|
|
25
|
-
|
|
26
|
-
- run: npm ci
|
|
27
|
-
- run: npm run typecheck
|
|
28
|
-
- run: npm run build
|
|
29
|
-
- run: npm run test
|
|
30
|
-
|
|
31
|
-
docker:
|
|
32
|
-
runs-on: ubuntu-latest
|
|
33
|
-
needs: test
|
|
34
|
-
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
|
|
35
|
-
steps:
|
|
36
|
-
- uses: actions/checkout@v6
|
|
37
|
-
|
|
38
|
-
- name: Build Docker image
|
|
39
|
-
run: docker build -t codewiki-mcp .
|
|
40
|
-
|
|
41
|
-
- name: Verify CLI starts
|
|
42
|
-
run: docker run --rm codewiki-mcp --help
|
|
@@ -1,36 +0,0 @@
|
|
|
1
|
-
name: Release
|
|
2
|
-
|
|
3
|
-
on:
|
|
4
|
-
push:
|
|
5
|
-
branches: [main]
|
|
6
|
-
|
|
7
|
-
permissions:
|
|
8
|
-
contents: write
|
|
9
|
-
issues: write
|
|
10
|
-
pull-requests: write
|
|
11
|
-
id-token: write
|
|
12
|
-
|
|
13
|
-
jobs:
|
|
14
|
-
release:
|
|
15
|
-
runs-on: ubuntu-latest
|
|
16
|
-
steps:
|
|
17
|
-
- uses: actions/checkout@v6
|
|
18
|
-
with:
|
|
19
|
-
fetch-depth: 0
|
|
20
|
-
persist-credentials: false
|
|
21
|
-
|
|
22
|
-
- uses: actions/setup-node@v6
|
|
23
|
-
with:
|
|
24
|
-
node-version: 22
|
|
25
|
-
cache: npm
|
|
26
|
-
|
|
27
|
-
- run: npm ci
|
|
28
|
-
- run: npm run typecheck
|
|
29
|
-
- run: npm run build
|
|
30
|
-
- run: npm run test
|
|
31
|
-
|
|
32
|
-
- name: Semantic Release
|
|
33
|
-
env:
|
|
34
|
-
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
35
|
-
NPM_TOKEN: ${{ secrets.NPM_TOKEN }}
|
|
36
|
-
run: npx semantic-release
|
package/.releaserc.json
DELETED
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"branches": ["main"],
|
|
3
|
-
"plugins": [
|
|
4
|
-
"@semantic-release/commit-analyzer",
|
|
5
|
-
"@semantic-release/release-notes-generator",
|
|
6
|
-
"@semantic-release/changelog",
|
|
7
|
-
["@semantic-release/npm", {
|
|
8
|
-
"npmPublish": true
|
|
9
|
-
}],
|
|
10
|
-
["@semantic-release/git", {
|
|
11
|
-
"assets": ["CHANGELOG.md", "package.json", "package-lock.json"],
|
|
12
|
-
"message": "chore(release): ${nextRelease.version} [skip ci]\n\n${nextRelease.notes}"
|
|
13
|
-
}],
|
|
14
|
-
"@semantic-release/github"
|
|
15
|
-
]
|
|
16
|
-
}
|
package/CHANGELOG.md
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
## [1.0.1](https://github.com/izzzzzi/codewiki-mcp/compare/v1.0.0...v1.0.1) (2026-02-16)
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
### Bug Fixes
|
|
5
|
-
|
|
6
|
-
* **docs:** correct GitHub owner in badge URLs and clone links ([dbcaa48](https://github.com/izzzzzi/codewiki-mcp/commit/dbcaa48a8b3ebc99274fa8919ff1ee10ef89d4ac))
|
|
7
|
-
|
|
8
|
-
# 1.0.0 (2026-02-16)
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
### Features
|
|
12
|
-
|
|
13
|
-
* codewiki-mcp v0.2.0 — full MCP server for codewiki.google ([4f4dec7](https://github.com/izzzzzi/codewiki-mcp/commit/4f4dec74e48821e8fe8193b73341fcad1e61449f))
|
package/Dockerfile
DELETED
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
FROM node:22-alpine AS builder
|
|
2
|
-
WORKDIR /app
|
|
3
|
-
COPY package.json package-lock.json ./
|
|
4
|
-
RUN npm ci
|
|
5
|
-
COPY tsconfig.json ./
|
|
6
|
-
COPY src/ src/
|
|
7
|
-
RUN npm run build
|
|
8
|
-
|
|
9
|
-
FROM node:22-alpine
|
|
10
|
-
WORKDIR /app
|
|
11
|
-
COPY --from=builder /app/package.json /app/package-lock.json ./
|
|
12
|
-
RUN npm ci --omit=dev
|
|
13
|
-
COPY --from=builder /app/dist/ dist/
|
|
14
|
-
EXPOSE 3000
|
|
15
|
-
ENTRYPOINT ["node", "dist/cli.js"]
|