@zonuexe/techbook-mcp 0.2.4 → 0.3.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.
Files changed (92) hide show
  1. package/CHANGELOG.md +38 -1
  2. package/README.md +15 -2
  3. package/dist/adapters/http/fetch-client.d.ts.map +1 -1
  4. package/dist/adapters/http/fetch-client.js +18 -1
  5. package/dist/adapters/http/fetch-client.js.map +1 -1
  6. package/dist/adapters/openbd.d.ts.map +1 -1
  7. package/dist/adapters/openbd.js +18 -5
  8. package/dist/adapters/openbd.js.map +1 -1
  9. package/dist/adapters/publishers/base.d.ts +2 -1
  10. package/dist/adapters/publishers/base.d.ts.map +1 -1
  11. package/dist/adapters/publishers/base.js +8 -3
  12. package/dist/adapters/publishers/base.js.map +1 -1
  13. package/dist/adapters/publishers/cq-publishing.d.ts +3 -0
  14. package/dist/adapters/publishers/cq-publishing.d.ts.map +1 -0
  15. package/dist/adapters/publishers/cq-publishing.js +120 -0
  16. package/dist/adapters/publishers/cq-publishing.js.map +1 -0
  17. package/dist/adapters/publishers/google-books.d.ts.map +1 -1
  18. package/dist/adapters/publishers/google-books.js +1 -0
  19. package/dist/adapters/publishers/google-books.js.map +1 -1
  20. package/dist/adapters/publishers/isbn-publisher-codes.js +1 -1
  21. package/dist/adapters/publishers/isbn-publisher-codes.js.map +1 -1
  22. package/dist/adapters/publishers/juse-p.js +2 -2
  23. package/dist/adapters/publishers/juse-p.js.map +1 -1
  24. package/dist/adapters/publishers/leanpub.d.ts +3 -0
  25. package/dist/adapters/publishers/leanpub.d.ts.map +1 -0
  26. package/dist/adapters/publishers/leanpub.js +96 -0
  27. package/dist/adapters/publishers/leanpub.js.map +1 -0
  28. package/dist/adapters/publishers/oreilly-japan.d.ts.map +1 -1
  29. package/dist/adapters/publishers/oreilly-japan.js +8 -2
  30. package/dist/adapters/publishers/oreilly-japan.js.map +1 -1
  31. package/dist/adapters/publishers/peaks.d.ts.map +1 -1
  32. package/dist/adapters/publishers/peaks.js +3 -2
  33. package/dist/adapters/publishers/peaks.js.map +1 -1
  34. package/dist/adapters/publishers/personal-media.d.ts.map +1 -1
  35. package/dist/adapters/publishers/personal-media.js +3 -2
  36. package/dist/adapters/publishers/personal-media.js.map +1 -1
  37. package/dist/adapters/publishers/pragprog.d.ts +3 -0
  38. package/dist/adapters/publishers/pragprog.d.ts.map +1 -0
  39. package/dist/adapters/publishers/pragprog.js +120 -0
  40. package/dist/adapters/publishers/pragprog.js.map +1 -0
  41. package/dist/adapters/publishers/registry.d.ts.map +1 -1
  42. package/dist/adapters/publishers/registry.js +6 -0
  43. package/dist/adapters/publishers/registry.js.map +1 -1
  44. package/dist/adapters/publishers/techbookfest.d.ts.map +1 -1
  45. package/dist/adapters/publishers/techbookfest.js +2 -1
  46. package/dist/adapters/publishers/techbookfest.js.map +1 -1
  47. package/dist/application/concurrency.d.ts +16 -0
  48. package/dist/application/concurrency.d.ts.map +1 -0
  49. package/dist/application/concurrency.js +42 -0
  50. package/dist/application/concurrency.js.map +1 -0
  51. package/dist/application/get-book-by-isbn.d.ts +0 -9
  52. package/dist/application/get-book-by-isbn.d.ts.map +1 -1
  53. package/dist/application/get-book-by-isbn.js +44 -6
  54. package/dist/application/get-book-by-isbn.js.map +1 -1
  55. package/dist/application/get-book-detail.d.ts.map +1 -1
  56. package/dist/application/get-book-detail.js +3 -0
  57. package/dist/application/get-book-detail.js.map +1 -1
  58. package/dist/application/search-books.d.ts +16 -5
  59. package/dist/application/search-books.d.ts.map +1 -1
  60. package/dist/application/search-books.js +46 -9
  61. package/dist/application/search-books.js.map +1 -1
  62. package/dist/domain/authors.d.ts +7 -0
  63. package/dist/domain/authors.d.ts.map +1 -0
  64. package/dist/domain/authors.js +22 -0
  65. package/dist/domain/authors.js.map +1 -0
  66. package/dist/domain/book.d.ts +2 -0
  67. package/dist/domain/book.d.ts.map +1 -1
  68. package/dist/domain/isbn.d.ts +8 -0
  69. package/dist/domain/isbn.d.ts.map +1 -0
  70. package/dist/domain/isbn.js +16 -0
  71. package/dist/domain/isbn.js.map +1 -0
  72. package/dist/domain/publisher.d.ts +16 -0
  73. package/dist/domain/publisher.d.ts.map +1 -1
  74. package/dist/domain/text-match.d.ts +32 -0
  75. package/dist/domain/text-match.d.ts.map +1 -0
  76. package/dist/domain/text-match.js +84 -0
  77. package/dist/domain/text-match.js.map +1 -0
  78. package/dist/main.js +0 -0
  79. package/dist/mcp/server.d.ts +6 -0
  80. package/dist/mcp/server.d.ts.map +1 -1
  81. package/dist/mcp/server.js +40 -4
  82. package/dist/mcp/server.js.map +1 -1
  83. package/dist/mcp/tools.d.ts.map +1 -1
  84. package/dist/mcp/tools.js +9 -1
  85. package/dist/mcp/tools.js.map +1 -1
  86. package/dist/version.d.ts +9 -0
  87. package/dist/version.d.ts.map +1 -0
  88. package/dist/version.js +9 -0
  89. package/dist/version.js.map +1 -0
  90. package/docs/design-doc.md +127 -7
  91. package/package.json +14 -15
  92. package/flake.lock +0 -61
@@ -1 +1 @@
1
- {"version":3,"file":"server.js","sourceRoot":"","sources":["../../src/mcp/server.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"server.js","sourceRoot":"","sources":["../../src/mcp/server.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"tools.d.ts","sourceRoot":"","sources":["../../src/mcp/tools.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,KAAK;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAsER,CAAC"}
1
+ {"version":3,"file":"tools.d.ts","sourceRoot":"","sources":["../../src/mcp/tools.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,KAAK;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EA8ER,CAAC"}
package/dist/mcp/tools.js CHANGED
@@ -2,7 +2,15 @@ export const TOOLS = [
2
2
  {
3
3
  name: "search_books",
4
4
  description: "書名・著者名から日本語技術書を検索し、書誌情報の一覧を返します。" +
5
- "複数の出版社を横断して検索します。",
5
+ "複数の出版社を横断して検索します。" +
6
+ "各書籍の publishedAt は YYYY-MM-DD 形式(riida の release_date に対応)、" +
7
+ "language は ISO 639-1(省略時は \"ja\")です。" +
8
+ "結果はクエリとの一致度 matchScore(0〜1、1が完全一致)の降順で並んでおり、" +
9
+ "先頭ほど本命候補です。一致する書籍がなければ空配列を返します" +
10
+ "(無関係な新着本でフォールバックしません)。" +
11
+ "検索語は ASCII 語・正確なフルタイトルが最も当たりやすく、" +
12
+ "日本語の部分語は空白区切りの複数トークンにすると拾われやすくなります。" +
13
+ "版違いを厳密に当てたい場合は title に ISBN を渡すと ISBN 検索に切り替わります。",
6
14
  inputSchema: {
7
15
  type: "object",
8
16
  properties: {
@@ -1 +1 @@
1
- {"version":3,"file":"tools.js","sourceRoot":"","sources":["../../src/mcp/tools.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,KAAK,GAAG;IACnB;QACE,IAAI,EAAE,cAAc;QACpB,WAAW,EACT,kCAAkC;YAClC,mBAAmB;QACrB,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,UAAU,EAAE;gBACV,KAAK,EAAE;oBACL,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,UAAU;iBACxB;gBACD,MAAM,EAAE;oBACN,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,WAAW;iBACzB;gBACD,SAAS,EAAE;oBACT,IAAI,EAAE,QAAQ;oBACd,WAAW,EACT,uCAAuC;wBACvC,mCAAmC;iBACtC;gBACD,KAAK,EAAE;oBACL,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,kCAAkC;oBAC/C,OAAO,EAAE,EAAE;iBACZ;aACF;SACF;KACF;IACD;QACE,IAAI,EAAE,iBAAiB;QACvB,WAAW,EAAE,6BAA6B;QAC1C,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,KAAK,CAAC;YACjB,UAAU,EAAE;gBACV,GAAG,EAAE;oBACH,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,yBAAyB;iBACvC;aACF;SACF;KACF;IACD;QACE,IAAI,EAAE,iBAAiB;QACvB,WAAW,EAAE,uBAAuB;QACpC,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,UAAU,EAAE,EAAE;SACf;KACF;IACD;QACE,IAAI,EAAE,kBAAkB;QACxB,WAAW,EACT,mBAAmB;YACnB,0CAA0C;YAC1C,mCAAmC;QACrC,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,MAAM,CAAC;YAClB,UAAU,EAAE;gBACV,IAAI,EAAE;oBACJ,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,4CAA4C;iBAC1D;aACF;SACF;KACF;CACO,CAAC"}
1
+ {"version":3,"file":"tools.js","sourceRoot":"","sources":["../../src/mcp/tools.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,KAAK,GAAG;IACnB;QACE,IAAI,EAAE,cAAc;QACpB,WAAW,EACT,kCAAkC;YAClC,mBAAmB;YACnB,6DAA6D;YAC7D,sCAAsC;YACtC,8CAA8C;YAC9C,gCAAgC;YAChC,wBAAwB;YACxB,kCAAkC;YAClC,qCAAqC;YACrC,mDAAmD;QACrD,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,UAAU,EAAE;gBACV,KAAK,EAAE;oBACL,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,UAAU;iBACxB;gBACD,MAAM,EAAE;oBACN,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,WAAW;iBACzB;gBACD,SAAS,EAAE;oBACT,IAAI,EAAE,QAAQ;oBACd,WAAW,EACT,uCAAuC;wBACvC,mCAAmC;iBACtC;gBACD,KAAK,EAAE;oBACL,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,kCAAkC;oBAC/C,OAAO,EAAE,EAAE;iBACZ;aACF;SACF;KACF;IACD;QACE,IAAI,EAAE,iBAAiB;QACvB,WAAW,EAAE,6BAA6B;QAC1C,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,KAAK,CAAC;YACjB,UAAU,EAAE;gBACV,GAAG,EAAE;oBACH,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,yBAAyB;iBACvC;aACF;SACF;KACF;IACD;QACE,IAAI,EAAE,iBAAiB;QACvB,WAAW,EAAE,uBAAuB;QACpC,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,UAAU,EAAE,EAAE;SACf;KACF;IACD;QACE,IAAI,EAAE,kBAAkB;QACxB,WAAW,EACT,mBAAmB;YACnB,0CAA0C;YAC1C,mCAAmC;QACrC,WAAW,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,CAAC,MAAM,CAAC;YAClB,UAAU,EAAE;gBACV,IAAI,EAAE;oBACJ,IAAI,EAAE,QAAQ;oBACd,WAAW,EAAE,4CAA4C;iBAC1D;aACF;SACF;KACF;CACO,CAAC"}
@@ -0,0 +1,9 @@
1
+ /**
2
+ * パッケージのバージョン(単一の真実の源)。
3
+ *
4
+ * MCP サーバーの申告バージョンと HTTP User-Agent はここを参照する。
5
+ * リリース時は package.json / package-lock.json / CHANGELOG.md と揃えて更新すること
6
+ * ([[.codex/skills/techbook-mcp-release-prep]] の更新対象ファイルに含まれる)。
7
+ */
8
+ export declare const VERSION = "0.3.1";
9
+ //# sourceMappingURL=version.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"version.d.ts","sourceRoot":"","sources":["../src/version.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,eAAO,MAAM,OAAO,UAAU,CAAC"}
@@ -0,0 +1,9 @@
1
+ /**
2
+ * パッケージのバージョン(単一の真実の源)。
3
+ *
4
+ * MCP サーバーの申告バージョンと HTTP User-Agent はここを参照する。
5
+ * リリース時は package.json / package-lock.json / CHANGELOG.md と揃えて更新すること
6
+ * ([[.codex/skills/techbook-mcp-release-prep]] の更新対象ファイルに含まれる)。
7
+ */
8
+ export const VERSION = "0.3.1";
9
+ //# sourceMappingURL=version.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"version.js","sourceRoot":"","sources":["../src/version.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC"}
@@ -5,8 +5,14 @@
5
5
 
6
6
  ## 概要
7
7
 
8
- 日本語技術書の書誌情報を出版社公式サイト・APIから取得するMCPサーバー。
8
+ 日本語技術書(および一部の海外技術書)の書誌情報を出版社公式サイト・APIから取得するMCPサーバー。
9
9
  書名・著者名での検索と、URLからの詳細情報取得を提供する。
10
+ 価格は原則 税込円(整数)だが、海外出版社は当該通貨の数値と `BookRecord.currency`(ISO 4217)で表す。
11
+ 言語は `BookRecord.language`(ISO 639-1、省略時 `"ja"`)で表す。
12
+
13
+ 書籍管理アプリ [Riida](https://github.com/zonuexe/riida) の `riida-mcp` とシームレスに連携することを目標とし、
14
+ 利用エージェント側の試行錯誤を減らしてスムーズに書誌を取得できることを重視する。
15
+ `publishedAt`(YYYY-MM-DD)は riida の `release_date` に対応する。
10
16
 
11
17
  ## アーキテクチャ
12
18
 
@@ -49,20 +55,21 @@ techbook-mcp/
49
55
  ├── flake.nix # Nix flake (devShell + package build)
50
56
  ├── package.json
51
57
  ├── tsconfig.json
52
- ├── vitest.config.ts
53
58
  ├── docs/
54
59
  │ └── design-doc.md # 本ドキュメント
55
60
  ├── src/
56
61
  │ ├── domain/
57
62
  │ │ ├── book.ts # BookRecord, SearchQuery, DrmType 型定義
58
- │ │ └── publisher.ts # PublisherAdapter インターフェース
63
+ │ │ ├── publisher.ts # PublisherAdapter インターフェース (language, scale)
64
+ │ │ ├── text-match.ts # 照合用テキスト正規化・matchScore 算出
65
+ │ │ └── isbn.ts # ISBN 正規化・looksLikeIsbn 判定
59
66
  │ ├── ports/
60
67
  │ │ ├── http.ts # HttpClient インターフェース
61
68
  │ │ ├── html-parser.ts # HtmlParser インターフェース
62
69
  │ │ └── cache.ts # CacheStore インターフェース
63
70
  │ ├── adapters/
64
71
  │ │ ├── http/
65
- │ │ │ ├── fetch-client.ts # fetch() ベース実装
72
+ │ │ │ ├── fetch-client.ts # fetch() ベース実装 (charset を見て EUC-JP/Shift_JIS をデコード)
66
73
  │ │ │ └── mock-client.ts # テスト用モック
67
74
  │ │ ├── html/
68
75
  │ │ │ └── cheerio-parser.ts
@@ -74,14 +81,17 @@ techbook-mcp/
74
81
  │ │ ├── book-tech.ts # BOOK TECH
75
82
  │ │ ├── born-digital.ts # ボーンデジタル
76
83
  │ │ ├── coronasha.ts # コロナ社
84
+ │ │ ├── cq-publishing.ts # CQ出版社 (Tech Village 書庫&販売)
77
85
  │ │ ├── gihyo.ts # 技術評論社
78
86
  │ │ ├── lambdanote.ts # ラムダノート
87
+ │ │ ├── leanpub.ts # Leanpub (海外・セルフ出版・DRM-free)
79
88
  │ │ ├── manatee.ts # マナティ (マイナビ出版直販)
80
89
  │ │ ├── maruzen-publishing.ts # 丸善出版
81
90
  │ │ ├── optronics.ts # オプトロニクス社
82
91
  │ │ ├── oreilly-japan.ts # オライリー・ジャパン
83
92
  │ │ ├── peaks.ts # PEAKS
84
93
  │ │ ├── personal-media.ts # パーソナルメディア
94
+ │ │ ├── pragprog.ts # Pragmatic Bookshelf (海外・DRM-free)
85
95
  │ │ ├── rutles.ts # ラトルズ
86
96
  │ │ ├── saiensu.ts # サイエンス社
87
97
  │ │ ├── seshop.ts # SEshop (翔泳社)
@@ -89,8 +99,10 @@ techbook-mcp/
89
99
  │ │ ├── techbookfest.ts # 技術書典
90
100
  │ │ └── registry.ts # 出版社リスト (DEFAULT_PUBLISHERS)
91
101
  │ ├── application/
92
- │ │ ├── search-books.ts
93
- │ │ └── get-book-detail.ts
102
+ │ │ ├── search-books.ts # 横断検索・スケジューリング・matchScore 付与
103
+ │ │ ├── get-book-detail.ts
104
+ │ │ ├── get-book-by-isbn.ts
105
+ │ │ └── concurrency.ts # mapWithConcurrency / withTimeout
94
106
  │ ├── mcp/
95
107
  │ │ ├── server.ts
96
108
  │ │ └── tools.ts
@@ -105,11 +117,14 @@ techbook-mcp/
105
117
 
106
118
  ## 対応出版社
107
119
 
120
+ ### 国内出版社
121
+
108
122
  | ID | 名称 | 取得方式 | 備考 |
109
123
  |----|------|---------|------|
110
124
  | `book-tech` | BOOK TECH | HTML scraping | カラーミーショップ |
111
125
  | `born-digital` | ボーンデジタル | HTML scraping | カラーミーショップ・EUC-JP エンコード必須 |
112
126
  | `coronasha` | コロナ社 | HTML scraping | 電子版フラグで絞り込み・外部ストアへ委託販売 |
127
+ | `cq-publishing` | CQ出版社 | HTML scraping | 電子書籍直販サイト「Tech Village」・検索キーワードはパスに埋め込む |
113
128
  | `gihyo` | 技術評論社 | JSON API | `/api_gh/site/search` |
114
129
  | `lambdanote` | ラムダノート | HTML scraping | Shopify ストア |
115
130
  | `manatee` | マナティ (マイナビ出版直販) | HTML scraping | 複数出版社を委託販売 |
@@ -124,6 +139,15 @@ techbook-mcp/
124
139
  | `tatsu-zine` | 達人出版会 | HTML scraping | 複数出版社を委託販売 |
125
140
  | `techbookfest` | 技術書典オンラインマーケット | GraphQL POST API | XSRF-TOKEN 必須 |
126
141
 
142
+ ### 海外出版社
143
+
144
+ 価格は USD(`BookRecord.currency: "USD"`)、`language: "en"`。
145
+
146
+ | ID | 名称 | 取得方式 | 備考 |
147
+ |----|------|---------|------|
148
+ | `pragprog` | Pragmatic Bookshelf | JSON index | 米国・`/search/index.json` をローカルフィルタ・DRM-free |
149
+ | `leanpub` | Leanpub | HTML scraping | 米国・セルフ出版・DRM-free・価格/日付は埋め込みJSONストリームから取得 |
150
+
127
151
  ### 各アダプターの実装メモ
128
152
 
129
153
  **BOOK TECH (book-tech)** — カラーミーショップ
@@ -158,6 +182,17 @@ GET https://www.coronasha.co.jp/np/result.html?q={keyword}
158
182
  - 電子書籍ストアは `extractEbookStoresFromDoc()` で自動検出(Kindle, Kinoppy, VarsityWave eBooks 等)
159
183
  - Knowledge Worker (`kw.maruzen.co.jp`) はパターン未登録のため自動除外
160
184
 
185
+ **CQ出版社 (cq-publishing)** — Tech Village 書庫&販売
186
+ ```
187
+ GET https://cc.cqpub.co.jp/lib/system/doclib_search/q={UTF-8 percent-encoded keyword}/
188
+ ```
189
+ - CQ出版の電子書籍直販サイト(`cc.cqpub.co.jp/lib/`)。物販サイト `shop.cqpub.co.jp` とは別ドメインで、後者は紙の書籍・雑誌のみ・ネイティブ検索なし
190
+ - 検索キーワードは CakePHP の名前付きパラメータとして**パスに埋め込む**(`?q=` ではない)。複数語はスペース区切り(OR検索)
191
+ - 検索結果: `ul.itemList.books04 li` の `.mainTitle a`(タイトル・リンク)・`.subTitle`・`.price span`・`dt img`
192
+ - 詳細ページ: `/lib/system/doclib_item/{id}/`。`table[summary='商品詳細']` の th/td から著者・発行元・価格(ライセンス料金)・発行日を取得。**ISBN は持たず**コンテンツコード(例 `DP45551`)のみ
193
+ - タイトル末尾の形式マーカー `【PDF版】`(重複表記あり)・`【EPUB版】` 等を除去
194
+ - DRM: `"social"`(2017年導入の電子透かしで購入者情報を埋め込み、標準PDFビューアで閲覧可)
195
+
161
196
  **技術評論社 (gihyo)** — JSON API
162
197
  ```
163
198
  GET https://gihyo.jp/api_gh/site/search?search={keyword}&limit={n}
@@ -247,6 +282,29 @@ GET https://tatsu-zine.com/books/?search={keyword}
247
282
  ```
248
283
  複数出版社の電子書籍を委託販売。全書籍ソーシャルDRM。
249
284
 
285
+ **Pragmatic Bookshelf (pragprog)** — 海外(米国)・JSONインデックス
286
+ ```
287
+ GET https://pragprog.com/search/index.json # 全書籍インデックス(lunr.js 用)
288
+ ```
289
+ - 唯一の海外(英語)出版社。サイト内検索は lunr.js のクライアントサイド検索なので、インデックス JSON を取得して**ローカルフィルタ**する
290
+ - インデックスの各レコード: `record_type`(`"book"`/`"errata"`)・`href`・`title`・`subtitle`・`author`・`keywords[]`・`code`・`image`。`"book"` のみ対象
291
+ - 検索: タイトル語は title+subtitle+keywords に全トークン一致、著者は `author` 部分一致。インデックスに価格・ISBN・発行日はない
292
+ - 詳細: `/titles/{code}/{slug}/`。`<meta property="book:isbn|book:author|og:*">` と `.book-about-text`("Published: July 2026" → `2026-07-01`)・`.buybox`("$39.95 (USD)")から取得
293
+ - 著者: "A with B, C, and D" を `with`/`and`/カンマで分割(オックスフォードカンマの "and" 残りも除去)
294
+ - 価格は **USD** なので `price` に数値・`currency: "USD"` を付与
295
+ - DRM: `"free"`(PDF/epub/mobi 全フォーマット提供・技術的DRMなし)
296
+
297
+ **Leanpub (leanpub)** — 海外(米国)・セルフ出版プラットフォーム
298
+ ```
299
+ GET https://leanpub.com/store?search={keyword} # サーバーレンダリングのストア検索
300
+ ```
301
+ - 海外のセルフパブリッシング・プラットフォーム。React Router (Remix系) アプリだが、ストア検索結果は静的HTMLでレンダリングされる
302
+ - 検索結果: 書影付き `<li>`(書影 `cloudfront.net/{slug}/s_featured`)を走査。slug は書影URLから取得し、`a[href="/{slug}"]` のテキストをタイトル、`.text-neutral-500` を著者、`.italic` をサブタイトルとして取得
303
+ - 詳細 `/{slug}`: タイトル・著者・説明・書影は `<meta property="og:*">`・`<meta name="author">` から取得
304
+ - **価格・更新日は埋め込み React Router ストリーム(`<script>`内)から正規表現で取得**: `minimumPaidPrice\",{数値}`(最低価格)・`lastPublishedAt\",\"{YYYY-MM-DD}`。静的HTMLの表示テキスト("Last updated on ..." 等)は CDN/SSR 状態で揺れて不安定なため使わない
305
+ - 価格は pay-what-you-want の**最低価格**・**USD**(`currency: "USD"`)。ISBN は持たない
306
+ - DRM: `"free"`(PDF/EPUB、技術的DRMなし)。`publisher` はセルフ出版のため `"Leanpub"`
307
+
250
308
  **技術書典 (techbookfest)** — GraphQL
251
309
  ```
252
310
  POST https://techbookfest.org/api/graphql
@@ -278,10 +336,12 @@ type DrmType = "free" | "social" | "password_pdf" | "drm";
278
336
  | ラトルズ | `free` | 購入・確認済み |
279
337
  | PEAKS | `free` | 利用規約に明記 |
280
338
  | オプトロニクス社 | `free` | 購入・確認済み |
339
+ | Pragmatic Bookshelf | `free` | PDF/epub/mobi 全フォーマット提供・DRMなし |
281
340
  | Gihyo Digital Publishing | `social` | 公式方針 |
282
341
  | SEshop (翔泳社) | `social` | メールアドレス埋め込み透かし |
283
342
  | BOOK TECH | `social` | 購入者情報透かし |
284
343
  | ボーンデジタル | `social` | PDFにメールアドレス印字 |
344
+ | CQ出版 Tech Village | `social` | 2017年導入の電子透かしで購入者情報を埋め込み |
285
345
  | マナティ | `social` | 公式 about ページに明記 |
286
346
  | ラムダノート | `social` | 公式方針 |
287
347
  | 達人出版会 | `social` | 公式方針 |
@@ -303,13 +363,73 @@ type DrmType = "free" | "social" | "password_pdf" | "drm";
303
363
  |---------|------|---------|
304
364
  | `search_books` | 書名・著者名で検索 | `title?`, `author?`, `publisher?`, `limit?` |
305
365
  | `get_book_detail` | URLから詳細情報取得 | `url` |
366
+ | `get_book_by_isbn` | ISBNから書誌情報取得(openBD→出版社サイト→カーリル) | `isbn` |
306
367
  | `list_publishers` | 対応出版社一覧 | なし |
307
368
 
369
+ ## 検索の挙動
370
+
371
+ 利用エージェント側の試行錯誤を減らすため、`search_books` は以下の前処理・後処理を行う。
372
+
373
+ - **ベストマッチ順ソート**: 各候補にクエリとの一致度 `matchScore`(0〜1、1が完全一致)を付与し降順に並べる。
374
+ 先頭ほど本命候補なので、PDF奥付から推定した曖昧な title/author でも候補選びに迷わない。
375
+ スコアは `src/domain/text-match.ts` の `normalizeForMatch()`(NFKC で全半角統一・装飾括弧/長音/約物/空白を除去)+
376
+ 書名はクエリを空白でトークン分割して候補書名への包含割合で算出する(純日本語の部分語が助詞を跨いでも拾える)。
377
+ `matchScore` はクエリ相対値のためドメインの `BookRecord` には載せず、検索結果境界の `ScoredBook` 型に限定する
378
+ - **ゼロ関連度のフォールバックを除外**: クエリ語があるのに `matchScore` が 0 の候補(検索サイトが「該当なし」時に返す新着順の無関係本)は除外する。
379
+ 「該当なし」を空配列で表し、「該当なし」と「誤ヒット」を呼び出し側が区別できるようにする(誤メタデータ混入を防ぐ)
380
+ - **著者の重複排除**: `src/domain/authors.ts` の `dedupeAuthors()` で著者配列の重複を除く(`normalizeForMatch` をキーに表記ゆれも同一視)。search/detail/isbn の全経路に適用
381
+ - **openBD による欠損補完**: ISBN を持つ結果は `enrichWithOpenBD()` で `authors`(空のとき)・`publishedAt`・`price`・`coverImageUrl`・`description` を補完する。出版社の検索APIが著者や紹介文を返さない場合の救済(アダプタ間の取得項目の不揃いを平準化)
382
+ - **大規模出版社を優先スケジュール**: `PublisherAdapter.scale === "minor"` の小規模・専門/ローカルフィルタ型サイトは大規模出版社の後に回す。
383
+ 小規模サイトのカタログは変動が少ないため `CATALOG_CACHE_TTL_SECONDS`(24時間)で全キャッシュし、ライブ負荷を抑える
384
+ - **並列度制限・タイムアウト**: `src/application/concurrency.ts` の `mapWithConcurrency`(`SEARCH_CONCURRENCY = 6`)と
385
+ `withTimeout`(`SEARCH_TIMEOUT_MS = 12s`)で、遅い1社が全体をブロックしないようにする(部分結果を返す)
386
+ - **errors の集約**: 失敗理由を `type`(`robots` / `timeout` / `http` / `other`)に分類し、MCP 層で種別×出版社に集約して静音化する
387
+ - **ISBN ショートカット**: `title` が ISBN 形式(`src/domain/isbn.ts` の `looksLikeIsbn`)かつ `author` 未指定なら、
388
+ 全社横断をやめて `get_book_by_isbn` 経路に振り分ける
389
+
390
+ ## カバレッジの制約
391
+
392
+ 各アダプターは出版社の**現行ストアの生カタログ**(検索結果ページ・電子書籍一覧・JSON索引)をスクレイプする。
393
+ このため、出版社がストアから**販売終了・取り下げした旧刊**は構造的に `search_books` でヒットしない。
394
+ 共通パターンは2008〜2013年頃の短編・電子書籍専売タイトル。書籍自体は実在するが、現行の検索可能な索引のどこにも載っていない。
395
+
396
+ riida-mcp フィードバック「現象9」で報告された未ヒット例の調査結果(2026-06-02 確認):
397
+
398
+ - **オライリー・ジャパン(旧刊 Ebook版のみタイトル)**: `CSS3の値、単位、色`(9784873116266)・`セレクタ、詳細度、カスケード`(9784873116037)・
399
+ `D3をはじめよう`(9784873115979)・`Web Workers`(9784873115962)・`OAuth 2.0をはじめよう`(9784873115580)・
400
+ `PHP開発者のためのJavaScript`(9784873116433)等。
401
+ これらは `/books/{isbn}/` の詳細ページは生きている(HTTP 200)が、`oreilly-japan` がフィルタする `/ebook/` 一覧
402
+ (現行ストアで販売中の約580冊)にも `/catalog/`・カテゴリページ(`/books/{topic}/`)にも載っていない。
403
+ 詳細ページの `buying-options` は空(=現行ストアで購入導線なし。og:description に「本書はEbook版のみの販売となります」と残るが実売は終了)。
404
+ `sitemap.xml` も無く(404)、旧刊を網羅する代替の生インデックスは存在しない → **一覧ソースの差し替えでは救済不能**。
405
+ さらにこれら電子書籍専売 ISBN は openBD にも未登録(紙流通前提の JPRO/openBD に載らない)なため、
406
+ `search_books` だけでなく `get_book_by_isbn` の通常経路(openBD → カーリル)でも失敗する。
407
+ - **翔泳社 / SEshop(旧刊)**: `レガシーソフトウェア改善ガイド`・`実用Common Lisp`・`初めての人のためのLISP[増補改訂版]`・
408
+ `エンジニアのための文章術 再入門講座 新版` 等。SEshop 検索(全カテゴリ)でそもそも 0 件=**ストアに商品ページ自体が残っていない**
409
+ (O'Reilly と違い詳細ページも消えている)。電子版が存在しないか取り下げ済みで、`seshop` アダプタの取りこぼしではない。
410
+
411
+ ### 旧刊救済: ISBN からの詳細ページ直引き(`detailUrlForIsbn`)
412
+
413
+ 部分的な救済余地があるのはオライリーのみ。詳細ページ `/books/{isbn}/` が生きているため、以下を実装済み:
414
+
415
+ - `PublisherAdapter.detailUrlForIsbn?(isbn)`(任意メソッド)— ISBN ベースの安定 URL を持つサイトが詳細ページ URL を構成する。
416
+ `oreilly-japan` が `/books/{isbn}/` を返す。
417
+ - `isbn-publisher-codes.ts` の `oreilly-japan` に旧記号 `87311` を追加(従来は新記号 `8144` のみ)。
418
+ - `get_book_by_isbn` は openBD ミス時、カーリルより先に `detailUrlForIsbn` 経路(robots.txt 確認 → `getDetail`)を試みる
419
+ (`fetchDetailByIsbnCode`)。これで `CSS3の値、単位、色`(9784873116266)等は**価格を除く書誌**(書名・著者・発行日・説明・書影)が回収できる。
420
+ 価格は詳細ページの `buying-options` が空のため取得不可。
421
+
422
+ ただし `search_books`(横断検索)では依然ヒットしない(`/ebook/` 一覧に無いため)。回収には ISBN が分かっている必要がある。
423
+ SEshop 旧刊は詳細ページごと消えているため `detailUrlForIsbn` でも回収不能。
424
+
308
425
  ## 新しいアダプターの追加手順
309
426
 
310
427
  1. `src/adapters/publishers/{id}.ts` を作成し `PublisherAdapter` を実装
311
428
  - `search()`: 検索APIまたはHTMLスクレイピングで `BookRecord[]` を返す
312
429
  - `getDetail()`: 詳細ページをスクレイピングして `BookRecord` を返す
430
+ - 海外出版社など日本語以外なら `language`(ISO 639-1)を宣言する(省略時はアプリ層で `"ja"` とみなす)
431
+ - ラインナップが小さい/検索APIがなく全カタログをローカルフィルタするサイトは `scale: "minor"` を宣言し、
432
+ カタログ取得を `fetchText(url, deps, undefined, CATALOG_CACHE_TTL_SECONDS)` で長期キャッシュする
313
433
  2. `tests/fixtures/{id}-search.html` (または `.json`) を作成
314
434
  3. `tests/fixtures/{id}-detail.html` を作成
315
435
  4. `tests/unit/adapters/publishers/{id}.test.ts` を作成
@@ -317,7 +437,7 @@ type DrmType = "free" | "social" | "password_pdf" | "drm";
317
437
  6. `src/adapters/publishers/registry.ts` に登録
318
438
 
319
439
  よく使う共通ユーティリティ (`base.ts`):
320
- - `fetchText(url, deps, extraHeaders?)` — キャッシュ付きHTTP GET
440
+ - `fetchText(url, deps, extraHeaders?, ttlSeconds?)` — キャッシュ付きHTTP GET(`ttlSeconds` 省略時 1時間、小規模カタログは `CATALOG_CACHE_TTL_SECONDS`)
321
441
  - `parseJapanesePrice(text)` — "3,740円(税込)" → 3740
322
442
  - `resolveUrl(base, path)` — 相対URLを絶対URLに解決
323
443
  - `extractEbookStoresFromDoc(doc)` — ページ内リンクから電子書籍ストアを自動検出
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@zonuexe/techbook-mcp",
3
- "version": "0.2.4",
3
+ "version": "0.3.1",
4
4
  "description": "MCP server for searching Japanese technical book bibliographic information",
5
5
  "license": "AGPL-3.0-or-later",
6
6
  "type": "module",
@@ -10,23 +10,22 @@
10
10
  "bin": {
11
11
  "techbook-mcp": "dist/main.js"
12
12
  },
13
+ "dependencies": {
14
+ "@modelcontextprotocol/sdk": "^1.29.0",
15
+ "cheerio": "^1.2.0",
16
+ "iconv-lite": "^0.7.2",
17
+ "zod": "^4.4.3"
18
+ },
19
+ "devDependencies": {
20
+ "@types/node": "^25.9.1",
21
+ "oxlint": "^1.68.0",
22
+ "tsx": "^4.22.4",
23
+ "typescript": "^6.0.3"
24
+ },
13
25
  "scripts": {
14
26
  "build": "tsc",
15
27
  "lint": "oxlint --config .oxlintrc.json src/",
16
- "prepublishOnly": "npm run build",
17
28
  "test": "node --import tsx/esm --test 'tests/**/*.test.ts'",
18
29
  "test:watch": "node --import tsx/esm --test --watch 'tests/**/*.test.ts'"
19
- },
20
- "dependencies": {
21
- "@modelcontextprotocol/sdk": "^1.11.0",
22
- "cheerio": "^1.0.0",
23
- "iconv-lite": "^0.6.0",
24
- "zod": "^3.24.0"
25
- },
26
- "devDependencies": {
27
- "@types/node": "^22.0.0",
28
- "oxlint": "^1.59.0",
29
- "tsx": "^4.0.0",
30
- "typescript": "^5.8.0"
31
30
  }
32
- }
31
+ }
package/flake.lock DELETED
@@ -1,61 +0,0 @@
1
- {
2
- "nodes": {
3
- "flake-utils": {
4
- "inputs": {
5
- "systems": "systems"
6
- },
7
- "locked": {
8
- "lastModified": 1731533236,
9
- "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=",
10
- "owner": "numtide",
11
- "repo": "flake-utils",
12
- "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b",
13
- "type": "github"
14
- },
15
- "original": {
16
- "owner": "numtide",
17
- "repo": "flake-utils",
18
- "type": "github"
19
- }
20
- },
21
- "nixpkgs": {
22
- "locked": {
23
- "lastModified": 1776169885,
24
- "narHash": "sha256-l/iNYDZ4bGOAFQY2q8y5OAfBBtrDAaPuRQqWaFHVRXM=",
25
- "owner": "NixOS",
26
- "repo": "nixpkgs",
27
- "rev": "4bd9165a9165d7b5e33ae57f3eecbcb28fb231c9",
28
- "type": "github"
29
- },
30
- "original": {
31
- "owner": "NixOS",
32
- "ref": "nixos-unstable",
33
- "repo": "nixpkgs",
34
- "type": "github"
35
- }
36
- },
37
- "root": {
38
- "inputs": {
39
- "flake-utils": "flake-utils",
40
- "nixpkgs": "nixpkgs"
41
- }
42
- },
43
- "systems": {
44
- "locked": {
45
- "lastModified": 1681028828,
46
- "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
47
- "owner": "nix-systems",
48
- "repo": "default",
49
- "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
50
- "type": "github"
51
- },
52
- "original": {
53
- "owner": "nix-systems",
54
- "repo": "default",
55
- "type": "github"
56
- }
57
- }
58
- },
59
- "root": "root",
60
- "version": 7
61
- }