Communityライティング&編集github.com

AlexXPZhu/save-papers-to-zotero

CodeX調査で見つけた論文を、Zoteroライブラリに簡単にインポートするスキル 🦐 検証済みPDFを保存し、適切なコレクションに整理します。

save-papers-to-zotero とは?

このスキルは、CodexやClaude CodeなどのAIエージェントが、調査中に発見した論文をZoteroデスクトップアプリのローカルConnectorサーバー(127.0.0.1:23119)経由で直接インポートするためのものです。ユーザーにブラウザ拡張機能を呼び出すよう求めず、代わりにPythonスクリプト(単一論文用とバッチ用の2種類)を使用して、Zoteroのコレクションへの書き込み、メタデータの保存、PDFの添付を自動化します。重複チェック(DOI、arXiv ID、タイトルの正規化)、タグ付け(#status/to-read や #priority/high など)、arXivのCommentsフィールドの保持など、堅牢な機能を備えています。バッチインポートはシリアル実行され、中断後の再開をサポートし、ロック機構で競合を防ぎます。特に、常に新しいアイテムを作成し、既存の一致候補を削除・統合することはありません。

対応✓Claude Code✓Codex CLI~Cursor
npx skills add AlexXPZhu/save-papers-to-zotero

Installed? Explore more ライティング&編集 skills: steipete/notion, langchain-ai/langchain, bytedance/podcast-generation · View all 6 →

お気に入りのAIに質問する

このエージェントスキルを事前に読み込んだ状態で新しいチャットを開きます。

ドキュメント

論文をZoteroに保存

デスクトップアプリのローカルConnectorサーバー(127.0.0.1:23119)を介して、明示的なZoteroインポートリクエストを完了します。ユーザーにZotero Connectorブラウザ拡張機能の呼び出しを要求しないでください。ユーザーがドライランを要求しない限り、検証済みの保存PDFがない親アイテムは不完全として扱ってください。

バンドルパスの解決

インポーターを実行する前に、このSKILL.mdを含むディレクトリを解決してください。Claude Codeでは${CLAUDE_SKILL_DIR}を使用します。Codexでは、ロードされたスキルとともに提供されるインストール済みスキルディレクトリを使用します。以下の<skill-dir>をその絶対パスに置き換え、結果のスクリプトパスを引用符で囲み、カレントワーキングディレクトリがスキルディレクトリであると決して想定しないでください。利用可能なPython 3.10+の実行可能ファイルを使用してください。例ではpythonを使用しています。

インポーターの選択

  • 1件の論文には<skill-dir>/scripts/zotero_connector_import.pyを使用します。
  • 2件以上の論文、DOI/記事リスト、文献レビューの出力には<skill-dir>/scripts/zotero_batch_import.pyを使用します。
  • バッチマニフェストを準備する前に<skill-dir>/references/batch-manifest.mdを読んでください。

両方のインポーターは以下を行います:

  1. Zoteroの接続性と正確なターゲットコレクションを検証します。
  2. DOI、arXiv ID、正規化されたタイトルの順で既存の一致候補を特定します。
  3. それらの一致候補を報告しますが、要求された新しいアイテムは引き続き作成します。
  4. 翻訳スタイルのメタデータと、arXiv Comments を含むオプションの子ノートを保存します。
  5. 要求されたコレクション、通常のタグ、デフォルトの#status/to-read、およびオプションの優先度タグを割り当てます。
  6. PDFバイトを保存された子添付としてアップロードします。
  7. 新しく作成された親アイテム(既存の一致候補ではない)が、保存されたPDFとともにコレクション内にあることを検証します。

一致候補が存在するという理由だけで、アイテムを自動的に削除、マージ、置換、または抑制しないでください。possible_duplicate_count と possible_duplicate_keys を返して、ユーザーがZoteroを検査し、何を削除するかを決定できるようにします。

信頼できる入力を準備する

各論文を正規のランディングページに解決します。出版社のページ、DOIレコード、PubMed Central、リポジトリ、またはユーザーが正当にアクセスできるプレプリントページを優先します。ソースが公開するすべての信頼できるメタデータ(抄録、出版物、巻号、ページ、言語、DOI、arXiv識別子、完全な著者リストを含む)を入力します。欠落している値を創作しないでください。

arXiv論文の場合、ソースのCommentsフィールドを空白の正規化以外はそのままコピーします。その値のみを渡します。インポーターはComment: で始まる別の子ノートを作成します。そこに含まれる発表場所、コード、プロジェクト、出版情報を保持します。抄録、引用、または自身の分析からarXivコメントを合成せず、ソースにCommentsフィールドがない場合は省略します。

Ethereal Styleプラグインで認識される#status/...および#priority/...形式の通常のZoteroタグを使用します。特別なZoteroフィールドやタグタイプは必要ありません。別のステータスまたは明示的なオプトアウトが提供されない限り、新しくインポートされたすべての論文のデフォルトは#status/to-readです:

  • reading_status: to-read は #status/to-read になります。
  • reading_status: reading は #status/reading になります。
  • reading_status: none は自動ステータス割り当てを無効にします。
  • priority: high、medium、または low は #priority/high、#priority/medium、または #priority/low になります。

アイテムまたは要求されたタグにすでに存在する明示的な#status/...タグをデフォルトに置き換えるのではなく保持します。提供されたセマンティックステータスは、競合するステータスタグを上書きします。論文の内容から優先度を推測しないでください。ユーザーからの値またはユーザー定義の階層などの明示的なマッピングからのみ追加します。

Zotero翻訳スタイルのアイテムオブジェクトを使用します:

{
  "itemType": "preprint",
  "title": "Example Paper",
  "creators": [
    {"firstName": "Ada", "lastName": "Lovelace", "creatorType": "author"}
  ],
  "date": "2026",
  "url": "https://example.org/paper",
  "DOI": "10.0000/example",
  "archiveID": "arXiv:2601.00001"
}

各PDFは次の2つの方法のいずれかで取得します:

  • 公開された直接PDF URLとそのランディングページをリファラーとして渡します。
  • ユーザーのサインイン済みChromeセッションでのみ利用可能なPDFの場合、ホストのブラウザ統合を使用します:CodexではChrome制御スキル、またはclaude --chrome(またはChromeがデフォルトで有効になっている状態)で起動されたClaude CodeセッションからClaude in Chromeを使用します。表示されている正当なPDFを一時ファイルにダウンロードし、--pdf-fileでそのファイルを渡します。クッキーやセッションストレージを検査、エクスポート、保持しないでください。

ブラウザ統合が利用できない場合、権限が拒否された場合、またはダウンロードがローカルの有効なPDFを生成しない場合は、Zotero書き込みの前に停止し、ユーザーに正当に取得したローカルPDFの提供を依頼してください。信頼できないミラーにフォールバックしないでください。

ペイウォール、CAPTCHA、アクセス制御、またはライセンス制限を回避しないでください。

1件の論文をインポートする

公開PDF URLの場合:

python -X utf8 "<skill-dir>/scripts/zotero_connector_import.py" \
  --item-json <item.json> \
  --collection <完全なコレクション名> \
  --source-url <ランディングページURL> \
  --pdf-url <直接PDF URL> \
  --referrer <ランディングページURL>

ダウンロードしたPDFの場合は、--pdf-urlを--pdf-file <path>に置き換えます。添付ファイルの記録されたソースがダウンロードURLと異なる必要がある場合は、--pdf-fileまたは--pdf-urlとともに--pdf-source-url <URL>を使用します。

ソースのarXiv Comments値には--arxiv-comment <text>を使用します。インポーターはComment: を正確に1回追加します。他の子ノートには--noteを、通常のタグには--tagを繰り返します。読書ステータスはデフォルトでto-readです。上書きするには--reading-status readingを、オプトアウトするには--reading-status noneを使用します。明示的に要求された場合、またはユーザー提供の階層からマッピングされた場合にのみ--priority high|medium|lowを使用します。書き込み可能なConnectorターゲットが複数あり、要求された正確な名前を持つ場合にのみ--target-id <id>を追加します。書き込みを行わずに接続、コレクション、入力、および重複チェックを行うには--dry-runを使用します。

バッチをインポートする

書き込みを開始する前に、すべてのマニフェストエントリを準備して検証します。次に実行します:

python -X utf8 "<skill-dir>/scripts/zotero_batch_import.py" \
  --manifest <papers.json> \
  --collection <完全なコレクション名> \
  --target-id <id> \
  --ledger <results.jsonl> \
  --summary-json <summary.json>

同名のConnectorターゲットが曖昧でない限り、例の--target-id行は省略します。すべてのマニフェストエントリはデフォルトで#status/to-readになります。readingまたはnoneを選択する場合にのみ、共有または論文ごとのreading_statusを使用します。マニフェストに共有および論文ごとのtags、notes、priorityを設定します。各論文のarxiv_commentは、自身のarXivソースから設定します。バッチCLIには意図的に--tagや--noteオプションはありません。最初の不完全なエントリの後に後続の論文を試行しない場合は、--stop-on-errorを追加します。

バッチインポーターはシリアルでなければなりません。各書き込みの直前に正確なターゲットを再検証し、各論文の後に1つのledgerレコードを追加してフラッシュし、デフォルトでは論文固有の障害後も続行し、Zotero接続またはコレクションの障害では停止します。再開はデフォルトで有効です:同じマニフェストとledgerを再実行すると、以前のsaved_with_pdfレコードをスキップします。ユーザーが以前の完了したリクエストを再度書き込むことを明示的に希望する場合にのみ、--no-resumeを使用します。

書き込みを並列化したり、同じledgerに対して2つのプロセスを実行したりしないでください。インポーターはオペレーティングシステムのアドバイザリロックを使用します。その.lockファイルは実行後またはクラッシュ後にディスクに残る可能性がありますが、ファイル自体は将来のバッチをブロックしません。

バッチの終了コードは、すべてのリクエストが完了したか安全にスキップされた場合は0、不完全なエントリで実行が終了した場合は3、致命的なマニフェスト、ロック、接続、またはコレクションエラーの場合はその他の非ゼロコードです。単一インポーターは成功時に0、失敗時に非ゼロコードを返します。

結果を解釈する

インポーターのJSONを信頼できるものとして扱います:

  • saved_with_pdf:新しい親と保存されたPDFが検証されました。
  • skipped_completed:再開中に以前の成功したledgerレコードが保持されました。
  • skipped_duplicate_in_manifest:重複したマニフェストエントリが2回目の書き込みなしでスキップされました。
  • invalid_pdf、http_error、またはその他の論文固有のステータス:バッチを続行し、ソースと理由を報告します。
  • verification_failed:メタデータは保存された可能性がありますが、新しく作成されたアイテムまたはその保存されたPDFを検証できませんでした。盲目的に再実行しないでください。
  • not_attempted:致命的なバッチレベルの障害により、後続のエントリが停止されました。

possible_duplicate_count と possible_duplicate_keys は情報提供用です。これらはこのリクエストの前に存在していたアイテムのみを参照します。インポーターは新しい親を書き込み、検証します。手動レビューのために提示し、明示的なユーザーの決定なしにアイテムを削除しないでください。

提供された場合、arxiv_commentは正規化された子ノートのテキストを報告します。workflow_tagsは、適用されたデフォルトまたは明示的な#status/...タグと、要求された#priority/...タグを報告します。これらを完了報告に含めて、ユーザーがすべてのアイテムを開かなくてもワークフローメタデータを確認できるようにします。

バッチを報告する

以下を報告します:

  • 要求された総数。
  • 検証済みPDFで新しく保存された数。
  • 再開スキップおよびマニフェスト重複スキップの数。
  • 可能性のある既存の一致があった新しく保存されたアイテムとそのキー。
  • ユーザーのアクションが必要なもの。
  • 失敗または未試行のもの。
  • 不完全な各論文のタイトル、ソース、ステータス、および理由。

添付ファイルの行やURLが表示されているという理由で成功を主張しないでください。インポーターの保存ファイル検証が必要です。

関連スキル