Skip to main content
Glama
KUMUDZIMAL

GitHub Repository Assistant

by KUMUDZIMAL
README.md
# GitHub Repository Assistant using MCP

An AI-powered GitHub repository assistant that demonstrates how MCP (Model Context Protocol) allows LLMs to interact with external tools and data through a standardized protocol.

## Project Overview

This project creates an MCP server that exposes GitHub repository operations as tools. When connected to an MCP-compatible LLM client (like Claude Desktop), users can ask natural language questions about any GitHub repository, and the LLM will automatically use the appropriate tools to find and present the information.

**Example interaction:**
```
User: "Give me information about microsoft/vscode"
LLM: → calls get_repo_info("microsoft", "vscode")
LLM: "Visual Studio Code is a source-code editor developed by Microsoft..."

User: "Show me the project structure"
LLM: → calls list_files("microsoft", "vscode")
LLM: "The repository contains the following structure: src/, package.json, README.md..."
```

---

## What is MCP?

**MCP (Model Context Protocol)** is a standardized way for LLMs (Large Language Models) to interact with external tools and data sources.

Think of MCP as a **universal adapter**:
- It defines how an LLM discovers what tools are available
- It defines how the LLM calls those tools
- It defines how results are returned

**Without MCP:**
```
LLM → Custom GitHub Integration → GitHub API
     (You write this for each LLM)
```

**With MCP:**
```
LLM → MCP → MCP Server → GitHub API
     (Write once, works with any MCP-compatible LLM)
```

---

## Why MCP?

Imagine you want to connect an LLM to GitHub, Slack, and a database. Without MCP:

1. You'd write a custom GitHub integration for OpenAI
2. Another custom integration for Claude
3. Another for Google's Gemini
4. And repeat for every new LLM...

**With MCP:**
1. Write one GitHub MCP server
2. Any MCP-compatible LLM can use it
3. Add new tools by just adding new functions
4. No changes needed when new LLMs are released

**Key benefits:**
- **Standardization**: One protocol works everywhere
- **Reusability**: Write once, use with any MCP client
- **Modularity**: Tools are independent and composable
- **Security**: Servers control what data the LLM can access
- **Testability**: Each tool can be tested independently

---

## Architecture

```
┌─────────────────────────────────────────────────────────┐
│                        User                             │
│              "Show me the README"                        │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│                    LLM / AI Model                       │
│         (Claude, GPT-4, or other MCP client)            │
│                                                         │
│  1. Understands user's question                         │
│  2. Decides which tool to use (get_readme)              │
│  3. Calls the tool via MCP protocol                     │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│                  MCP Protocol                           │
│         (Standardized communication layer)              │
│                                                         │
│  - Tool discovery                                       │
│  - Parameter validation                                 │
│  - Request/Response formatting                          │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│              MCP Server (This Project)                   │
│                                                         │
│  Tools:                                                 │
│  - get_repo_info()                                      │
│  - list_files()                                         │
│  - read_file()                                          │
│  - search_code()                                        │
│  - get_readme()                                         │
│                                                         │
│  Uses GitHubClient to make API calls                    │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│                  GitHub API                             │
│         (https://api.github.com)                        │
│                                                         │
│  - Repository metadata                                  │
│  - File contents                                        │
│  - Code search                                          │
└─────────────────────────────────────────────────────────┘
```

---

## Available MCP Tools

| Tool | Purpose | Inputs |
|------|---------|--------|
| `get_repo_info` | Get repository metadata (stars, forks, language, etc.) | `owner`, `repo` |
| `list_files` | List files and directories in the repository | `owner`, `repo`, `branch` (optional), `path` (optional) |
| `read_file` | Read the contents of a specific file | `owner`, `repo`, `path`, `branch` (optional) |
| `search_code` | Search for code matching a query | `owner`, `repo`, `query` |
| `get_readme` | Get the README file content | `owner`, `repo`, `branch` (optional) |

---

## Setup

### Prerequisites

- Python 3.11 or higher
- pip (Python package manager)
- Git
- A GitHub account (optional, but recommended for full functionality)

### Step 1: Clone the Repository

```bash
git clone https://github.com/your-username/github-mcp-assistant.git
cd github-mcp-assistant
```

### Step 2: Create a Virtual Environment

```bash
# Windows
python -m venv venv
venv\Scripts\activate

# macOS/Linux
python3 -m venv venv
source venv/bin/activate
```

### Step 3: Install Dependencies

```bash
pip install -r requirements.txt
```

### Step 4: Configure Environment Variables

1. Copy the example environment file:
   ```bash
   cp .env.example .env
   ```

2. Edit `.env` and add your GitHub token:
   ```
   GITHUB_TOKEN=ghp_your_token_here
   ```

### Step 5: Get a GitHub Token (Optional but Recommended)

1. Go to https://github.com/settings/tokens
2. Click "Generate new token (classic)"
3. Give it a name like "MCP Assistant"
4. Select scopes:
   - `repo` (for private repositories)
   - `read:org` (if accessing organization repos)
5. Click "Generate token"
6. Copy the token and paste it in your `.env` file

**Note:** You can use the server without a token for public repositories, but code search requires authentication.

---

## Running the MCP Server

### Option 1: Direct Python Execution

```bash
python -m server.server
```

The server will start and listen for MCP protocol messages on standard input/output (stdio).

### Option 2: Using Docker

```bash
docker build -t github-mcp-assistant .
docker run -i -e GITHUB_TOKEN=your_token github-mcp-assistant
```

The `-i` flag is important - it keeps stdin open for the MCP protocol communication.

---

## Connecting an MCP Client

### Claude Desktop

1. Open Claude Desktop
2. Go to Settings → Developer
3. Click "Edit Config"
4. Add the server configuration:

```json
{
  "mcpServers": {
    "github-assistant": {
      "command": "python",
      "args": ["-m", "server.server"],
      "cwd": "/path/to/github-mcp-assistant"
    }
  }
}
```

5. Restart Claude Desktop
6. The GitHub tools will be available when you start a new conversation

### Custom MCP Client

If you're building a custom client, connect to the server via stdio and use the MCP protocol to:
1. Send `initialize` to start the connection
2. Send `tools/list` to discover available tools
3. Send `tools/call` to invoke a tool

---

## Example Prompts

Once connected, try these prompts:

1. **Get repository info:**
   "Give me information about microsoft/vscode"

2. **Show project structure:**
   "Show me the project structure of facebook/react"

3. **Read a specific file:**
   "Read the main.py file in fastapi/fastapi"

4. **Search for code:**
   "Where is authentication implemented in django/django?"

5. **Get the README:**
   "Show me the README of torvalds/linux"

6. **Understand a project:**
   "Explain this repository to me: pallets/flask"

7. **Compare files:**
   "What's the difference between requirements.txt and setup.py in requests/requests?"

8. **Find configuration:**
   "Show me the configuration files in kubernetes/kubernetes"

---

## Project Flow

When you ask: "Where is authentication implemented?"

```
┌─────────────────────────────────────────────────────────┐
│ 1. User asks: "Where is authentication implemented?"    │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│ 2. LLM understands the question and decides to          │
│    search for authentication-related code               │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│ 3. LLM calls search_code(owner, repo, "authentication") │
│    via MCP protocol                                     │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│ 4. MCP Server receives the request                      │
│    - Validates parameters                               │
│    - Calls GitHubClient.search_code()                   │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│ 5. GitHubClient makes HTTP request to GitHub API:       │
│    GET /search/code?q=authentication repo:owner/repo    │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│ 6. GitHub API returns search results                    │
│    - List of files containing "authentication"          │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│ 7. MCP Server formats results and returns to LLM        │
└─────────────────────────────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────┐
│ 8. LLM uses the results to answer the user:             │
│    "Authentication is implemented in:                   │
│     - src/auth.py                                       │
│     - src/login.py                                      │
│     - middleware/auth.py"                               │
└─────────────────────────────────────────────────────────┘
```

---

## Security

### Why the GitHub Token Should Never Be Committed

Your GitHub token is like a password - it gives access to your GitHub account. If committed to a public repository:

1. **Anyone can see it** - Even if you delete it later, it's in the git history
2. **Automated bots scan for tokens** - They'll find and use it within minutes
3. **Your account is compromised** - Attackers can access your repositories, create issues, delete code, etc.
4. **You're responsible** - GitHub may hold you accountable for any damage

### Best Practices

- ✅ Store tokens in `.env` files (gitignored)
- ✅ Use environment variables
- ✅ Create tokens with minimal permissions
- ✅ Rotate tokens regularly
- ❌ Never hardcode tokens in source code
- ❌ Never commit `.env` files
- ❌ Never share tokens in chat or documentation

---

## Testing

### Run Unit Tests

```bash
# Activate virtual environment first
python -m pytest tests/ -v
```

### Test Coverage

The tests cover:
- GitHub client initialization
- Repository information retrieval
- File listing
- File reading
- Code search
- README retrieval
- Error handling (404, 401, 403)
- Edge cases (empty results, directories vs files)

---

## Project Structure

```
github-mcp-assistant/
│
├── server/
│   ├── __init__.py          # Package marker
│   ├── server.py            # MCP server with tool definitions
│   └── github_client.py     # GitHub API client (separated for testing)
│
├── tests/
│   ├── __init__.py          # Package marker
│   ├── test_github_client.py # Tests for GitHub API client
│   └── test_tools.py        # Tests for MCP tools
│
├── .env.example             # Environment variable template
├── .gitignore               # Git ignore rules
├── requirements.txt         # Python dependencies
├── Dockerfile               # Docker configuration
└── README.md                # This file
```

---

## Future Improvements

### Feature Enhancements

- **Pull Request Analysis**: Analyze PRs for code quality, review comments
- **Issue Analysis**: Search and analyze issues, track bugs
- **Commit History**: View recent commits, blame information
- **Code Summarization**: Use LLM to summarize code files
- **Dependency Analysis**: Analyze project dependencies
- **Multiple Repository Support**: Compare or analyze multiple repos
- **Branch Comparison**: Compare different branches
- **Release Information**: Get release notes and versions

### Technical Improvements

- **Caching**: Cache GitHub API responses to reduce rate limit usage
- **Pagination**: Handle paginated API responses for large repositories
- **Async Optimization**: Improve async performance
- **Logging**: Add comprehensive logging
- **Configuration**: Add more configuration options
- **Rate Limiting**: Implement client-side rate limiting

### Testing Improvements

- **Integration Tests**: Test against real GitHub API (with token)
- **Performance Tests**: Test with large repositories
- **Edge Case Tests**: More error scenarios

---

## How to Explain This Project in an Interview

### What is MCP?

"MCP stands for Model Context Protocol. It's a standardized way for LLMs to interact with external tools and data sources. Think of it as a universal adapter - instead of writing custom integrations for each LLM, you write one MCP server that works with any MCP-compatible client."

### Why MCP Was Used

"I chose MCP because it solves the N×M problem. Without MCP, connecting N LLMs to M external services requires N×M custom integrations. With MCP, you write M servers and they work with any MCP-compatible LLM. This makes the code more maintainable, testable, and reusable."

### What the MCP Server Does

"The MCP server exposes GitHub repository operations as tools. It has five main tools: get_repo_info, list_files, read_file, search_code, and get_readme. When an LLM needs to interact with GitHub, it calls these tools through the MCP protocol."

### What Tools Were Created

"1. **get_repo_info**: Returns repository metadata like stars, forks, language
2. **list_files**: Shows the project structure by listing files and directories
3. **read_file**: Reads the content of a specific file
4. **search_code**: Searches for code matching a query across the repository
5. **get_readme**: Retrieves the README file content"

### What Happens When a User Asks a Question

"When a user asks 'Where is authentication implemented?', the LLM:
1. Understands the question and decides to search for code
2. Calls the search_code tool via MCP with query='authentication'
3. The MCP server receives the request and calls GitHub's API
4. GitHub returns search results
5. The MCP server formats and returns results to the LLM
6. The LLM uses the results to provide a human-readable answer"

### Why This Architecture Is Better

"This architecture is better than tightly coupled integration because:

1. **Separation of Concerns**: The GitHub logic is separate from the MCP protocol
2. **Testability**: Each component can be tested independently
3. **Reusability**: The MCP server works with any MCP-compatible LLM
4. **Maintainability**: Adding new tools doesn't require changing the LLM
5. **Security**: The server controls what data the LLM can access
6. **Standardization**: Uses a protocol that's becoming an industry standard"

### Key Technical Decisions

- **Separated GitHub client**: Makes the code easier to test and maintain
- **Async/await**: Better performance for I/O-bound operations
- **Type hints**: Improves code readability and enables IDE support
- **Environment variables**: Secure configuration management
- **Error handling**: Graceful degradation with human-readable error messages

---

## Contributing

Contributions are welcome! Please feel free to submit issues or pull requests.

1. Fork the repository
2. Create a feature branch
3. Make your changes
4. Add tests for new functionality
5. Run tests to ensure they pass
6. Submit a pull request

---

## License

This project is open source and available under the MIT License.

---

## Acknowledgments

- [MCP Protocol](https://modelcontextprotocol.io/) - The official MCP documentation
- [FastMCP](https://github.com/jlowin/fastmcp) - The Python MCP SDK used in this project
- [GitHub REST API](https://docs.github.com/en/rest) - The API used for GitHub interactions