Metadata-Version: 2.5
Name: pia-mcp-server-git
Version: 0.2.3
Summary: A Model Context Protocol server providing tools to read, search, and manipulate Git repositories programmatically via LLMs
Author: Anthropic, PBC., PIA Shanghai
Maintainer: PIA Shanghai
License: MIT
License-File: LICENSE
Keywords: automation,git,llm,mcp
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Requires-Python: >=3.10
Requires-Dist: click>=8.1.7
Requires-Dist: gitpython>=3.1.50
Requires-Dist: mcp<2,>=1.29.0
Requires-Dist: pydantic>=2.0.0
Description-Content-Type: text/markdown

# pia-mcp-server-git：用于 Git 仓库交互与自动化的 MCP 服务器

## 概述

一个用于 Git 仓库交互和自动化的模型上下文协议（MCP）服务器。该服务器提供通过大语言模型读取、搜索和操作 Git 仓库的工具。

需要 MCP Python SDK 1.x（`mcp>=1.29.0,<2`）。SDK 2.0 已重命名本服务器使用的 API，目前正在迁移至 v2。

请注意，pia-mcp-server-git 目前仍处于早期开发阶段。随着服务器的持续开发和完善，其功能和可用工具可能会发生变化或扩展。

### 工具

1. `git_status`
   - 显示工作树状态
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
   - 返回：以文本形式返回工作目录的当前状态

2. `git_diff_unstaged`
   - 显示工作目录中尚未暂存的更改
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
     - `context_lines`（数字，可选）：显示的上下文行数（默认值：3）
   - 返回：未暂存更改的差异内容

3. `git_diff_staged`
   - 显示已暂存、等待提交的更改
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
     - `context_lines`（数字，可选）：显示的上下文行数（默认值：3）
   - 返回：已暂存更改的差异内容

4. `git_diff`
   - 显示分支或提交之间的差异
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
     - `target`（字符串）：要比较的目标分支或提交
     - `context_lines`（数字，可选）：显示的上下文行数（默认值：3）
   - 返回：当前状态与目标之间的差异内容

5. `git_commit`
   - 将更改记录到仓库
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
     - `message`（字符串）：提交信息
   - 返回：包含新提交哈希值的确认信息

6. `git_add`
   - 将文件内容添加到暂存区
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
     - `files`（字符串数组）：要暂存的文件路径数组
   - 返回：文件已暂存的确认信息

7. `git_reset`
   - 取消暂存所有已暂存的更改
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
   - 返回：重置操作的确认信息

8. `git_log`
   - 显示提交日志，支持按日期筛选
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
     - `max_count`（数字，可选）：显示的最大提交数量（默认值：10）
     - `start_timestamp`（字符串，可选）：用于筛选提交的起始时间。支持 ISO 8601 格式（例如 `'2024-01-15T14:30:25'`）、相对日期（例如 `'2 weeks ago'`、`'yesterday'`）或绝对日期（例如 `'2024-01-15'`、`'Jan 15 2024'`）
     - `end_timestamp`（字符串，可选）：用于筛选提交的结束时间。支持 ISO 8601 格式（例如 `'2024-01-15T14:30:25'`）、相对日期（例如 `'2 weeks ago'`、`'yesterday'`）或绝对日期（例如 `'2024-01-15'`、`'Jan 15 2024'`）
   - 返回：包含哈希值、作者、日期和提交信息的提交记录数组

9. `git_create_branch`
   - 创建新分支
   - 输入：
     - `repo_path`（字符串）：Git 仓库路径
     - `branch_name`（字符串）：新分支名称
     - `base_branch`（字符串，可选）：创建新分支所基于的分支（默认为当前分支）
   - 返回：分支创建成功的确认信息

10. `git_checkout`
    - 切换分支
    - 输入：
      - `repo_path`（字符串）：Git 仓库路径
      - `branch_name`（字符串）：要切换到的分支名称
    - 返回：分支切换成功的确认信息

11. `git_show`
    - 显示提交内容
    - 输入：
      - `repo_path`（字符串）：Git 仓库路径
      - `revision`（字符串）：要显示的版本标识（提交哈希值、分支名称或标签）
    - 返回：指定提交的内容

12. `git_branch`
    - 列出 Git 分支
    - 输入：
      - `repo_path`（字符串）：Git 仓库路径
      - `branch_type`（字符串）：列出本地分支（`'local'`）、远程分支（`'remote'`）或全部分支（`'all'`）
      - `contains`（字符串，可选）：分支应包含的提交 SHA；未指定提交 SHA 时请勿传入此参数
      - `not_contains`（字符串，可选）：分支不应包含的提交 SHA；未指定提交 SHA 时请勿传入此参数
    - 返回：分支列表

13. `git_clone`
    - 将 HTTPS 或 SSH Git 仓库克隆到指定目标目录
    - 无参数启动时支持任意绝对目标路径；使用 `--workspace-root` 时，目标必须位于工作区根目录内；该工具在 `--repository` 模式下不可用
    - 输入：
      - `repository_url`（字符串）：不含嵌入式凭据的仓库 URL，主机必须在允许列表中
      - `target_path`（字符串）：新克隆目标路径。无参数启动时必须是绝对路径；使用 `--workspace-root` 时可使用根目录内的相对路径或绝对路径。目标目录必须不存在，且其父目录必须已存在
      - `branch`（字符串，可选）：要克隆的分支
      - `depth`（数字，可选）：浅克隆深度，取值范围为 1 到 10000
    - 返回：包含解析后克隆目标路径的确认信息

14. `git_fetch`
    - 获取远程引用，不更改当前工作树
    - 输入：
      - `repo_path`（字符串）：Git 仓库路径
      - `remote`（字符串，可选）：远程仓库名称（默认值：`origin`）
    - 返回：确认信息以及已获取的引用更新

15. `git_pull`
    - 仅使用快进方式将远程分支拉取到当前本地分支
    - 要求工作树无未提交更改，并且当前有活动分支
    - 输入：
      - `repo_path`（字符串）：Git 仓库路径
      - `remote`（字符串，可选）：远程仓库名称（默认值：`origin`）
      - `branch`（字符串，可选）：远程分支；省略时使用当前分支的上游分支
    - 返回：拉取结果及当前仓库状态

16. `git_push`
    - 获取远程更新并检查分支差异后，以非强制方式推送当前本地分支
    - 要求工作树无未提交更改、当前有活动分支，并且已获得用户明确批准
    - 拒绝推送到 `main`、`master`、`release` 以及 `release/` 下的分支
    - 输入：
      - `repo_path`（字符串）：Git 仓库路径
      - `remote`（字符串，可选）：远程仓库名称（默认值：`origin`）
      - `branch`（字符串，可选）：远程目标分支（默认值：当前本地分支）
    - 返回：包含已推送提交数量的确认信息，或已是最新状态的提示信息

`git_clone`、`git_fetch`、`git_pull` 和 `git_push` 使用的远程 URL 必须采用 HTTPS 或 SSH，并通过已配置的 Git 主机允许列表检查。凭据必须通过本地 Git 凭据管理器、SSH 代理或其他 Git 原生凭据机制提供；包含嵌入式凭据的仓库 URL 将被拒绝。

## 安装

### 使用 uv（推荐）

安装 `uv`，然后根据锁文件准备项目环境：

```bash
uv --directory /path/to/pia-mcp-server-git sync --locked
```

### 使用 pip

也可以使用 pip 安装该软件包：

```bash
pip install pia-mcp-server-git
```

## 部署

该服务器通过 stdio 通信。宿主服务必须启动该进程，并将其标准输入和标准输出连接到 MCP 客户端。项目本身不提供 HTTP 端点。

### 使用已安装的软件包

不指定仓库边界启动：

```bash
pia-mcp-server-git
```

等效的模块调用方式如下：

```bash
python -m mcp_server_git
```

无参数模式允许 `git_clone` 克隆到当前用户有权限写入的任意绝对路径，也允许其他 Git 工具访问任意仓库。仅应在可信的 MCP Client 中使用该模式。

如果只允许服务器操作一个已有 Git 仓库，请使用 `--repository`：

```bash
pia-mcp-server-git --repository /path/to/git/repo
```

如果需要启用 `git_clone`，但希望将访问和克隆范围限制在指定目录内，请使用 `--workspace-root`：

```bash
pia-mcp-server-git --workspace-root /path/to/workspace
```

`--repository` 和 `--workspace-root` 不能同时使用。

## 使用 MCP Inspector 测试

该 MCP Server 使用 stdio 通信，可以通过 MCP Inspector 检查 Tools 和 Resources。运行前需要安装 Node.js、`npx` 和 `uv`，并准备一个本地 Git 仓库。

### 测试当前项目源码

在项目根目录执行：

```powershell
npx -y @modelcontextprotocol/inspector uv run pia-mcp-server-git --repository "C:\study\mcp-server-git"
```

该命令通过当前项目的 `.venv` 运行 editable 安装，加载的是 `src/mcp_server_git` 中的本地源码，适合在发布前验证代码修改。

### 测试 PyPI 发布版本

使用 `uvx` 在独立环境中下载并运行 PyPI 上与当前 Python 环境兼容的最新稳定版本：

```powershell
npx -y @modelcontextprotocol/inspector uvx --refresh --from "pia-mcp-server-git" pia-mcp-server-git
```

`--refresh` 会刷新软件包缓存并重新解析版本。`uvx` 不会复用当前项目的 `.venv`，因此可以验证 PyPI 用户实际安装到的最新制品。该命令以无参数模式启动，不限制 Git 仓库或克隆目标范围。

### 测试克隆功能

使用上面的无参数命令启动后，在 Inspector 中调用 `git_clone`，传入远程仓库 URL 和绝对目标路径。目标目录必须尚不存在，且其父目录必须已经存在，例如：

```text
repository_url: https://github.com/example/example.git
target_path: C:\path\to\new-repository
```

无参数模式不会限制克隆位置。需要目录边界保护时，请改用 `--workspace-root /path/to/workspace` 启动，并将 `target_path` 设置为该根目录内的新目录。

### 检查项目

连接成功后，至少检查以下内容：

1. `tools/list` 返回完整的 Git 工具列表。
2. `resources/list` 返回仓库的 `status`、`branches` 和 `HEAD commit` 资源。
3. 调用 `git_status`，确认能够读取指定仓库。
4. 分别读取三个 Resource，确认返回内容与仓库当前状态一致。

当前项目没有实现 Prompts 和 Resource Templates，因此 `prompts/list` 和 `resources/templates/list` 返回不支持属于预期结果。`git_add`、`git_commit`、`git_pull` 和 `git_push` 会修改本地仓库或远程状态，测试前应确认影响范围。

## 发布到 PyPI

发布脚本使用 PyPI 项目级 API Token 进行身份认证，并通过 Windows DPAPI 将凭据加密保存在本地。该流程仅适用于 Windows PowerShell 环境。

### 发布前准备

- 安装并确保 `uv` 命令可用。
- 在 PyPI 中创建仅限 `pia-mcp-server-git` 项目的 API Token。
- 确认 [pyproject.toml](pyproject.toml) 中的 `version` 尚未发布。PyPI 不允许覆盖已经发布的同版本文件。

### 1. 配置 PyPI 凭据

在项目根目录运行：

```powershell
.\scripts\setup-pypi-auth.ps1
```

根据提示输入 PyPI 项目级 API Token。脚本会将加密凭据保存到：

```text
.secrets/pypi-token.clixml
```

### 2. 发布包

确认版本号和待发布内容无误后运行：

```powershell
.\scripts\publish-pypi.ps1
```

发布脚本会依次执行以下操作：

1. 从 Windows 凭据文件中临时读取 PyPI Token。
2. 使用 `uv build` 构建 wheel 和源码分发包。
3. 使用 `uv publish --dry-run` 验证发布参数和制品。
4. 将两个制品正式上传到 PyPI。
5. 清理临时 Token 和临时构建目录。

终端显示以下内容表示发布成功：

```text
PyPI publish completed successfully.
```

发布完成后，可以在以下页面检查版本和制品：

```text
https://pypi.org/project/pia-mcp-server-git/
```
