Metadata-Version: 2.4
Name: bb-mcp-server
Version: 1.3.0
Summary: Bitbucket MCP (Model Context Protocol) server built with FastMCP that provides programmatic access to Bitbucket API v2.0
Author-email: Jason Schulz <jason@schulz.studio>
License: MIT
Project-URL: Homepage, https://github.com/your-username/bb-mcp-server
Project-URL: Repository, https://github.com/your-username/bb-mcp-server
Project-URL: Issues, https://github.com/your-username/bb-mcp-server/issues
Keywords: mcp,bitbucket,api,fastmcp,model-context-protocol
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Operating System :: OS Independent
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.8
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Topic :: Software Development :: Libraries :: Python Modules
Classifier: Topic :: Internet :: WWW/HTTP :: Dynamic Content
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: fastmcp<3,>=2.12.1
Requires-Dist: httpx>=0.25.0
Requires-Dist: pydantic>=2.11.10
Requires-Dist: pytest>=8.4.2
Requires-Dist: python-dotenv>=1.0.0
Dynamic: license-file

# Unified Tool Server

This directory contains an alternative Bitbucket MCP server implementation that exposes all functionality through a **single unified tool** backed by comprehensive server instructions, following the patterns outlined in the [MCP Server Instructions blog post](https://blog.modelcontextprotocol.io/posts/2025-11-03-using-server-instructions/).

## Overview

Instead of providing 10 separate tools (`pr_list`, `pr_overview`, `pr_review`, etc.), the unified server exposes a single `bitbucket` tool with an `action` parameter. The server instructions (~200 lines) provide:

- **Recommended workflows** for common tasks (PR review, creation, pipeline debugging, workspace discovery)
- **Action-specific guidance** with parameter requirements and usage patterns
- **Performance optimization** tips (batching, pagination, auto-reviewers)
- **Rate limits and constraints** to prevent API abuse
- **Error handling** guidance for common issues
- **Security notes** for credential management

## Architecture

```
unified_server.py                    # Main entry point
├─ src/modules/tools/unified.py     # Single tool implementation
└─ Uses same infrastructure as server.py:
   ├─ src/modules/resources/         # MCP resources (unchanged)
   ├─ src/modules/prompts/           # MCP prompts (unchanged)
   ├─ src/modules/middleware/        # Auth middleware (unchanged)
   └─ src/utils/                     # Shared utilities (unchanged)
```

## Running the Unified Server

```bash
# Direct execution
python unified_server.py --host 0.0.0.0 --port 8000

# With environment variables
FASTMCP_HOST=localhost FASTMCP_PORT=8000 python unified_server.py
```

## Tool Interface

### Single Tool: `bitbucket`

All Bitbucket operations are performed through this one tool by specifying the `action` parameter.

**Available Actions:**
- `pr_list` - List pull requests with filtering
- `pr_overview` - Get PR digest with blockers, comments, diffstat
- `pr_review` - Generate structured review summary
- `pr_comment_add` - Add PR comments (inline or general)
- `pr_comments_list` - List comments on a pull request
- `pr_tasks_list` - List PR tasks with details
- `pr_tasks_sync` - Create/resolve PR tasks in batch
- `pr_upsert` - Create or update pull requests
- `pipe_fail_summary` - Analyze failing pipeline steps
- `workspace_list` - List repos, members, projects, or reviewers
- `repo_get` - Get repository basics with PR sample
- `me_whoami` - Get authenticated user identity

### Example Usage

```python
# List open PRs for current user
{
  "action": "pr_list",
  "author": "me",
  "state": "OPEN",
  "limit": 10
}

# Get PR overview
{
  "action": "pr_overview",
  "pr": "123"
}

# Create PR with auto-reviewers
{
  "action": "pr_upsert",
  "title": "Add new feature",
  "source": "feature/my-branch",
  "destination": "main",
  "auto_reviewers": "default"
}

# Add inline comment
{
  "action": "pr_comment_add",
  "pr": "123",
  "text": "Consider extracting this to a helper function",
  "file": "src/main.py",
  "line": 42
}
```

## Command-Line Interface (`bb-cli`)

The same action-based surface is available from the terminal via `bb-cli`. It runs a
single action and prints the JSON result to stdout — clean to pipe into `jq` or consume
from an agent with bash access. Diagnostic logs go to stderr (silence with `--quiet`),
and the exit code is `0` on success, `1` on error (errors are emitted as parseable JSON).

```bash
# After `pip install -e .` the console script is on PATH:
bb-cli pr_list --author me --state OPEN --limit 5 --quiet | jq '.items'

# Or run the module directly without installing:
python cli.py pr_list --author me --state OPEN --limit 5 --quiet
```

### Examples

```bash
# List open PRs for the current user
bb-cli pr_list --author me --state OPEN --limit 10

# PR overview / review
bb-cli pr_overview --pr 123
bb-cli pr_review --pr 123 --repo workspace/repo

# Add an inline comment (writes to Bitbucket)
bb-cli pr_comment_add --pr 123 --text "Extract this to a helper" --file src/main.py --line 42

# Batch create / resolve PR tasks
bb-cli pr_tasks_sync --pr 123 \
  --create '[{"text":"fix typo","file":"a.py","line":3}]' \
  --resolve 456,789

# Create a PR with auto-assigned reviewers
bb-cli pr_upsert --title "Add feature" --source feature/my-branch \
  --destination main --auto-reviewers default

# Workspace discovery and repo basics
bb-cli workspace_list --kind repos --limit 20
bb-cli repo_get --slug workspace/repo --pretty

# Summarize the latest failing pipeline (with log excerpts)
bb-cli pipe_fail_summary --include-logs
```

List-valued flags (`--create`, `--resolve`, `--reviewers`) accept either a JSON array or
a comma-separated string. `--state`, `--verbosity`, `--task-state`, `--kind`, and
`--auto-reviewers` are restricted to the choices shown in `--help`.

### `-h, --help`

```text
usage: bb-cli [-h] [--quiet] [--pretty] [--repo REPO] [--limit LIMIT]
              [--cursor CURSOR] [--verbosity {ids,summary,full}]
              [--author AUTHOR]
              [--state {OPEN,MERGED,DECLINED,SUPERSEDED,ALL}] [--pr PR]
              [--text TEXT] [--file FILE] [--line LINE]
              [--task-state {OPEN,RESOLVED,ALL}] [--create CREATE]
              [--resolve RESOLVE] [--title TITLE] [--source SOURCE]
              [--destination DESTINATION] [--summary SUMMARY]
              [--reviewers REVIEWERS] [--auto-reviewers {default,all,none}]
              [--close-source] [--draft]
              [--kind {repos,members,projects,reviewers}]
              [--workspace WORKSPACE] [--slug SLUG] [--pipeline PIPELINE]
              [--include-logs]
              {pr_list,pr_overview,pr_review,pr_comment_add,pr_comments_list,pr_tasks_list,pr_tasks_sync,pr_upsert,pipe_fail_summary,workspace_list,repo_get,me_whoami}

Run a single Bitbucket action and print its JSON result.

positional arguments:
  {pr_list,pr_overview,pr_review,pr_comment_add,pr_comments_list,pr_tasks_list,pr_tasks_sync,pr_upsert,pipe_fail_summary,workspace_list,repo_get,me_whoami}
                        Operation to perform.

options:
  -h, --help            show this help message and exit
  --quiet, -q           Suppress diagnostic logs on stderr.
  --pretty              Pretty-print the JSON result.
  --repo REPO           'workspace/repo' slug; falls back to configured
                        default.
  --limit LIMIT         Max items to return (1-50).
  --cursor CURSOR       Pagination cursor.
  --verbosity {ids,summary,full}
                        Response detail level.
  --author AUTHOR       Filter PRs by author nickname; 'me' for current user.
  --state {OPEN,MERGED,DECLINED,SUPERSEDED,ALL}
                        PR state filter.
  --pr PR               PR identifier, e.g. '123' or '#123'.
  --text TEXT           Comment text.
  --file FILE           File path for inline anchoring.
  --line LINE           Line number for inline anchoring.
  --task-state {OPEN,RESOLVED,ALL}
                        Filter tasks by state.
  --create CREATE       Tasks to create: JSON array of {text,file,line}.
  --resolve RESOLVE     Task IDs to resolve: JSON array or comma-separated.
  --title TITLE         PR title.
  --source SOURCE       Source branch.
  --destination DESTINATION
                        Destination branch.
  --summary SUMMARY     PR description/summary.
  --reviewers REVIEWERS
                        Reviewer identifiers: JSON array or comma-separated.
  --auto-reviewers {default,all,none}
                        Auto-assign reviewers.
  --close-source        Close source branch on merge.
  --draft               Create/update as draft.
  --kind {repos,members,projects,reviewers}
                        Item type to list.
  --workspace WORKSPACE
                        Workspace slug.
  --slug SLUG           Repository slug or 'workspace/repo'.
  --pipeline PIPELINE   Specific pipeline ID/number to analyze.
  --include-logs        Include full log excerpts.

Each action uses a subset of the flags below; unused flags are ignored. Run a
destructive action (pr_comment_add, pr_tasks_sync, pr_upsert) only when you
mean it — they write to Bitbucket.
```

## Server Instructions

The unified server includes comprehensive instructions that are automatically injected into the LLM's context. These instructions guide the LLM to:

1. **Follow optimal workflows**
   - Example: Use `pr_overview` before `pr_review` to gather context
   - Example: Use `pr_tasks_sync` for batch task operations instead of individual calls

2. **Understand cross-action relationships**
   - How `pr_upsert` with `auto_reviewers="default"` automatically fetches and assigns reviewers
   - When to use `pipe_fail_summary` after `pr_overview` shows failing checks

3. **Optimize performance**
   - Prefer `pr_overview` over multiple separate API calls
   - Use batching with `pr_tasks_sync` for multiple tasks
   - Leverage pagination with appropriate limits

4. **Handle edge cases**
   - Required vs optional parameters for each action
   - Parameter format variations (e.g., repo as "workspace/slug" or just "slug")
   - Error messages and resolutions

## Comparison: Multi-Tool vs Unified

### Multi-Tool Server (`server.py`)

```python
# Three separate tool calls
response1 = call_tool("pr_overview", {"pr": "123"})
response2 = call_tool("pr_review", {"pr": "123"})
response3 = call_tool("pr_comment_add", {
    "pr": "123",
    "text": "LGTM",
})
```

**Pros:**
- Fine-grained tool selection
- Familiar pattern for traditional MCP clients
- Can filter specific tools via `ALLOWED_TOOLS`

**Cons:**
- Limited guidance on workflows
- LLM must infer optimal sequences
- Tool descriptions have space constraints

### Unified Tool Server (`unified_server.py`)

```python
# Same functionality, one tool interface
response1 = call_tool("bitbucket", {"action": "pr_overview", "pr": "123"})
response2 = call_tool("bitbucket", {"action": "pr_review", "pr": "123"})
response3 = call_tool("bitbucket", {
    "action": "pr_comment_add",
    "pr": "123",
    "text": "LGTM"
})
```

**Pros:**
- Comprehensive server instructions guide optimal usage
- Documented workflows (PR review, creation, debugging)
- Performance optimization tips built-in
- Cross-action relationships explained
- Better for LLMs that benefit from detailed guidance

**Cons:**
- Single tool interface (action-based)
- Cannot selectively disable specific actions
- Server instructions increase context size (~200 lines)

## When to Use Unified Server

Choose the unified server when:

- ✅ Your LLM client benefits from detailed contextual guidance
- ✅ You want optimized workflows documented in server instructions
- ✅ You prefer action-based tool invocation
- ✅ You want to follow MCP server instructions best practices
- ✅ You're working with LLMs that struggle with complex multi-tool orchestration

Choose the multi-tool server when:

- ✅ You need fine-grained tool filtering
- ✅ Your client has strict context size limits
- ✅ You prefer traditional tool-per-operation pattern
- ✅ You're integrating with existing MCP tooling

## Implementation Details

The unified tool (`src/modules/tools/unified.py`) is a thin wrapper that:

1. Accepts an `action` parameter and action-specific arguments
2. Validates required parameters based on the action
3. Routes to the underlying implementation functions
4. Returns the same response format as the individual tools

**Key point:** The unified server doesn't duplicate code. It uses the exact same tool implementations as the multi-tool server, just exposed through a different interface.

```python
# unified.py routes to existing implementations
match action:
    case BitbucketAction.PR_LIST:
        return await pr_list(...)  # Same function as multi-tool server
    case BitbucketAction.PR_OVERVIEW:
        return await pr_overview(...)
    # ... etc
```

## Configuration

The unified server uses the same configuration system as the multi-tool server:

**Environment Variables:**
```env
BITBUCKET_USERNAME=your_username
BITBUCKET_APP_PASSWORD=your_app_password
BITBUCKET_WORKSPACE=workspace-name
BITBUCKET_REPO=repo-slug
FASTMCP_PORT=8000
FASTMCP_HOST=localhost
```

**HTTP Headers (per-request):**
```
X-BITBUCKET-WORKSPACE: override-workspace
X-BITBUCKET-REPO: override-repo
Authorization: Bearer <token>
```

## Resources and Prompts

The unified server mounts the same resources and prompts as the multi-tool server:

**Resources:**
- Repository information
- Recent pipeline runs
- Open pull requests
- Workspace members
- Available branches
- Workspace projects

**Prompts:**
- All prompts from the resources server are available

## Testing

```bash
# Syntax validation
python -m py_compile unified_server.py
python -m py_compile src/modules/tools/unified.py

# Type checking (with mypy installed)
mypy unified_server.py --ignore-missing-imports

# Runtime test (requires dependencies)
python unified_server.py --help
```

## Migration from Multi-Tool Server

If you're currently using the multi-tool server and want to migrate:

1. **Update your tool calls:**
   ```python
   # Before
   call_tool("pr_list", {"author": "me"})

   # After
   call_tool("bitbucket", {"action": "pr_list", "author": "me"})
   ```

2. **Update your server startup:**
   ```bash
   # Before
   python server.py --port 8000

   # After
   python unified_server.py --port 8000
   ```

3. **No changes needed for:**
   - Environment variables
   - HTTP headers
   - Resources
   - Prompts
   - Authentication

## Benefits of Server Instructions Pattern

Following the [MCP blog post recommendations](https://blog.modelcontextprotocol.io/posts/2025-11-03-using-server-instructions/):

✅ **Cross-feature relationships** - Documents how actions interact
✅ **Operational patterns** - Specifies performance-optimized sequences
✅ **Constraints and limitations** - Clarifies rate limits and boundaries
✅ **Model-agnostic language** - Factual guidance without assumptions

The blog post testing showed **60% improvement** in GPT models following optimal workflows when instructions were present.

## Changelog

### 1.2.4

- Fix `me_whoami` and workspace auto-discovery hitting `GET /2.0/workspaces`,
  which Atlassian removed in [CHANGE-2770](https://developer.atlassian.com/cloud/bitbucket/changelog/)
  (returns `410 Gone`). Both now use the user-scoped replacement
  `GET /2.0/user/workspaces`.

### 1.2.3

- Add `bb-cli`, a command-line wrapper over the unified tool surface.
- Remove hardcoded credentials from `config.py`.

## License

Same as the main project.
