From bdd8dfc935d4dfb746e44b01e6faedde7d712a4d Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:34:28 +0530
Subject: [PATCH 1/8] feat: enhance repository for template use
This commit transforms gomcp into a professional, template-ready repository
with comprehensive documentation, CI/CD, and community files.
## New Files Added
### Community Files
- LICENSE (MIT)
- CONTRIBUTING.md - Contribution guidelines
- CODE_OF_CONDUCT.md - Contributor Covenant
- SECURITY.md - Security policy
- CHANGELOG.md - Version history
### GitHub Templates
- .github/ISSUE_TEMPLATE/bug_report.md
- .github/ISSUE_TEMPLATE/feature_request.md
- .github/ISSUE_TEMPLATE/config.yml
- .github/PULL_REQUEST_TEMPLATE.md
### CI/CD Workflows
- .github/workflows/ci.yml - Lint, test, build, security scan
- .github/workflows/release.yml - Automated releases with binaries
### Documentation
- docs/ARCHITECTURE.md - System design overview
- docs/CUSTOMIZATION.md - Template customization guide
## Files Updated
- README.md - Added badges, improved structure, template instructions
## Repository Settings Updated
- Marked as template repository
- Enabled GitHub Discussions
- Added topics: mcp, model-context-protocol, go, golang, template, cursor, claude, ai, llm, mcp-server
- Added 18 new labels for better issue organization
---
.github/ISSUE_TEMPLATE/bug_report.md | 68 +++
.github/ISSUE_TEMPLATE/config.yml | 11 +
.github/ISSUE_TEMPLATE/feature_request.md | 58 +++
.github/PULL_REQUEST_TEMPLATE.md | 88 ++++
.github/workflows/ci.yml | 157 ++++++
.github/workflows/release.yml | 195 ++++++++
CHANGELOG.md | 78 +++
CODE_OF_CONDUCT.md | 133 +++++
CONTRIBUTING.md | 247 ++++++++++
LICENSE | 21 +
README.md | 459 ++++++++---------
SECURITY.md | 118 +++++
docs/ARCHITECTURE.md | 359 ++++++++++++++
docs/CUSTOMIZATION.md | 573 ++++++++++++++++++++++
14 files changed, 2314 insertions(+), 251 deletions(-)
create mode 100644 .github/ISSUE_TEMPLATE/bug_report.md
create mode 100644 .github/ISSUE_TEMPLATE/config.yml
create mode 100644 .github/ISSUE_TEMPLATE/feature_request.md
create mode 100644 .github/PULL_REQUEST_TEMPLATE.md
create mode 100644 .github/workflows/ci.yml
create mode 100644 .github/workflows/release.yml
create mode 100644 CHANGELOG.md
create mode 100644 CODE_OF_CONDUCT.md
create mode 100644 CONTRIBUTING.md
create mode 100644 LICENSE
create mode 100644 SECURITY.md
create mode 100644 docs/ARCHITECTURE.md
create mode 100644 docs/CUSTOMIZATION.md
diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md
new file mode 100644
index 0000000..24454f6
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -0,0 +1,68 @@
+---
+name: Bug Report
+about: Create a report to help us improve gomcp
+title: '[BUG] '
+labels: 'type: bug, status: needs-triage'
+assignees: ''
+---
+
+## Bug Description
+
+A clear and concise description of what the bug is.
+
+## Environment
+
+- **gomcp version**: [e.g., 0.1.0]
+- **Go version**: [e.g., 1.23.0]
+- **OS**: [e.g., macOS 14.0, Ubuntu 22.04]
+- **Transport**: [e.g., HTTP/SSE, stdio]
+- **Client**: [e.g., Cursor IDE, Claude Desktop]
+
+## Steps to Reproduce
+
+1. Go to '...'
+2. Run command '...'
+3. Configure '...'
+4. See error
+
+## Expected Behavior
+
+A clear and concise description of what you expected to happen.
+
+## Actual Behavior
+
+A clear and concise description of what actually happened.
+
+## Logs/Error Output
+
+```
+Paste any relevant logs or error messages here
+```
+
+## Configuration
+
+```env
+# Relevant environment variables (redact secrets!)
+MCP_TRANSPORT_PROTOCOL=
+MCP_PORT=
+CURSOR_COMPATIBLE_SSE=
+```
+
+## Screenshots
+
+If applicable, add screenshots to help explain your problem.
+
+## Additional Context
+
+Add any other context about the problem here.
+
+## Possible Solution
+
+If you have ideas on how to fix this, please share them here.
+
+## Checklist
+
+- [ ] I have searched existing issues to ensure this is not a duplicate
+- [ ] I have included all relevant environment information
+- [ ] I have provided steps to reproduce the issue
+- [ ] I have included relevant logs/error messages
diff --git a/.github/ISSUE_TEMPLATE/config.yml b/.github/ISSUE_TEMPLATE/config.yml
new file mode 100644
index 0000000..c0f874e
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/config.yml
@@ -0,0 +1,11 @@
+blank_issues_enabled: false
+contact_links:
+ - name: Question / Discussion
+ url: https://github.com/NP-compete/gomcp/discussions
+ about: Ask questions and discuss ideas in GitHub Discussions
+ - name: MCP Specification
+ url: https://modelcontextprotocol.io/specification/2025-06-18
+ about: Reference the official MCP specification
+ - name: Official Go SDK
+ url: https://github.com/modelcontextprotocol/go-sdk
+ about: Check the official MCP Go SDK documentation
diff --git a/.github/ISSUE_TEMPLATE/feature_request.md b/.github/ISSUE_TEMPLATE/feature_request.md
new file mode 100644
index 0000000..1e0113f
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/feature_request.md
@@ -0,0 +1,58 @@
+---
+name: Feature Request
+about: Suggest an idea for gomcp
+title: '[FEATURE] '
+labels: 'type: feature, status: needs-triage'
+assignees: ''
+---
+
+## Feature Description
+
+A clear and concise description of the feature you'd like to see.
+
+## Problem Statement
+
+Is your feature request related to a problem? Please describe.
+Example: "I'm always frustrated when [...]"
+
+## Proposed Solution
+
+A clear and concise description of what you want to happen.
+
+## Use Case
+
+Describe the use case(s) this feature would enable:
+
+1. As a [type of user], I want [goal] so that [benefit]
+2. ...
+
+## Alternatives Considered
+
+A clear and concise description of any alternative solutions or features you've considered.
+
+## MCP Specification Alignment
+
+Does this feature align with the MCP specification?
+
+- [ ] This is part of the MCP spec (link to relevant section)
+- [ ] This extends beyond the MCP spec (explain why it's valuable)
+- [ ] Not applicable
+
+## Implementation Ideas
+
+If you have ideas on how to implement this, please share:
+
+```go
+// Example code or pseudocode
+```
+
+## Additional Context
+
+Add any other context, mockups, or screenshots about the feature request here.
+
+## Checklist
+
+- [ ] I have searched existing issues/discussions to ensure this is not a duplicate
+- [ ] I have clearly described the problem this feature would solve
+- [ ] I have considered alternatives
+- [ ] I am willing to help implement this feature (optional)
diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md
new file mode 100644
index 0000000..980a345
--- /dev/null
+++ b/.github/PULL_REQUEST_TEMPLATE.md
@@ -0,0 +1,88 @@
+## Description
+
+
+
+## Type of Change
+
+
+
+- [ ] Bug fix (non-breaking change that fixes an issue)
+- [ ] New feature (non-breaking change that adds functionality)
+- [ ] Breaking change (fix or feature that would cause existing functionality to not work as expected)
+- [ ] Documentation update
+- [ ] Refactoring (no functional changes)
+- [ ] CI/CD changes
+- [ ] Other (please describe):
+
+## Related Issues
+
+
+
+Fixes #
+
+## Changes Made
+
+
+
+-
+-
+-
+
+## MCP Features Affected
+
+
+
+- [ ] Tools
+- [ ] Prompts
+- [ ] Resources
+- [ ] Roots
+- [ ] Completion
+- [ ] Logging
+- [ ] Pagination
+- [ ] Sampling
+- [ ] Elicitation
+- [ ] Progress
+- [ ] Cancellation
+- [ ] Transport (HTTP/SSE/stdio)
+- [ ] None of the above
+
+## Testing
+
+
+
+### Test Commands Run
+
+```bash
+make test
+make lint
+```
+
+### Manual Testing
+
+
+
+- [ ] Tested with Cursor IDE
+- [ ] Tested with Claude Desktop
+- [ ] Tested with HTTP client
+- [ ] N/A
+
+## Screenshots
+
+
+
+## Checklist
+
+
+
+- [ ] My code follows the project's style guidelines
+- [ ] I have performed a self-review of my code
+- [ ] I have commented my code, particularly in hard-to-understand areas
+- [ ] I have made corresponding changes to the documentation
+- [ ] My changes generate no new warnings
+- [ ] I have added tests that prove my fix is effective or that my feature works
+- [ ] New and existing unit tests pass locally with my changes
+- [ ] Any dependent changes have been merged and published
+
+## Additional Notes
+
+
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
new file mode 100644
index 0000000..6d0b74c
--- /dev/null
+++ b/.github/workflows/ci.yml
@@ -0,0 +1,157 @@
+name: CI
+
+on:
+ push:
+ branches: [main]
+ pull_request:
+ branches: [main]
+
+env:
+ GO_VERSION: '1.23'
+
+jobs:
+ lint:
+ name: Lint
+ runs-on: ubuntu-latest
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+
+ - name: Set up Go
+ uses: actions/setup-go@v5
+ with:
+ go-version: ${{ env.GO_VERSION }}
+ cache: true
+
+ - name: Run go vet
+ run: go vet ./...
+
+ - name: Run go fmt check
+ run: |
+ if [ -n "$(gofmt -l .)" ]; then
+ echo "The following files are not formatted:"
+ gofmt -l .
+ exit 1
+ fi
+
+ - name: Install golangci-lint
+ uses: golangci/golangci-lint-action@v4
+ with:
+ version: latest
+ args: --timeout=5m
+
+ test:
+ name: Test
+ runs-on: ubuntu-latest
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+
+ - name: Set up Go
+ uses: actions/setup-go@v5
+ with:
+ go-version: ${{ env.GO_VERSION }}
+ cache: true
+
+ - name: Download dependencies
+ run: go mod download
+
+ - name: Run tests
+ run: go test -v -race -coverprofile=coverage.out -covermode=atomic ./...
+
+ - name: Upload coverage to Codecov
+ uses: codecov/codecov-action@v4
+ with:
+ files: ./coverage.out
+ flags: unittests
+ name: codecov-umbrella
+ fail_ci_if_error: false
+
+ build:
+ name: Build
+ runs-on: ubuntu-latest
+ needs: [lint, test]
+ strategy:
+ matrix:
+ goos: [linux, darwin, windows]
+ goarch: [amd64, arm64]
+ exclude:
+ - goos: windows
+ goarch: arm64
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+
+ - name: Set up Go
+ uses: actions/setup-go@v5
+ with:
+ go-version: ${{ env.GO_VERSION }}
+ cache: true
+
+ - name: Build binary
+ env:
+ GOOS: ${{ matrix.goos }}
+ GOARCH: ${{ matrix.goarch }}
+ CGO_ENABLED: 0
+ run: |
+ VERSION=$(cat VERSION)
+ GIT_COMMIT=$(git rev-parse --short HEAD)
+ BUILD_TIME=$(date -u '+%Y-%m-%d_%H:%M:%S')
+
+ BINARY_NAME=gomcp
+ if [ "$GOOS" = "windows" ]; then
+ BINARY_NAME=gomcp.exe
+ fi
+
+ go build \
+ -ldflags "-X github.com/NP-compete/gomcp/internal/version.Version=${VERSION} \
+ -X github.com/NP-compete/gomcp/internal/version.GitCommit=${GIT_COMMIT} \
+ -X github.com/NP-compete/gomcp/internal/version.BuildTime=${BUILD_TIME}" \
+ -trimpath \
+ -o bin/${GOOS}-${GOARCH}/${BINARY_NAME} \
+ ./cmd/server
+
+ - name: Upload artifact
+ uses: actions/upload-artifact@v4
+ with:
+ name: gomcp-${{ matrix.goos }}-${{ matrix.goarch }}
+ path: bin/${{ matrix.goos }}-${{ matrix.goarch }}/
+ retention-days: 7
+
+ docker:
+ name: Docker Build
+ runs-on: ubuntu-latest
+ needs: [lint, test]
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+
+ - name: Set up Docker Buildx
+ uses: docker/setup-buildx-action@v3
+
+ - name: Build Docker image
+ uses: docker/build-push-action@v5
+ with:
+ context: .
+ push: false
+ tags: gomcp-server:${{ github.sha }}
+ cache-from: type=gha
+ cache-to: type=gha,mode=max
+
+ security:
+ name: Security Scan
+ runs-on: ubuntu-latest
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+
+ - name: Set up Go
+ uses: actions/setup-go@v5
+ with:
+ go-version: ${{ env.GO_VERSION }}
+ cache: true
+
+ - name: Run govulncheck
+ run: |
+ go install golang.org/x/vuln/cmd/govulncheck@latest
+ govulncheck ./...
diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
new file mode 100644
index 0000000..cf3f6a3
--- /dev/null
+++ b/.github/workflows/release.yml
@@ -0,0 +1,195 @@
+name: Release
+
+on:
+ push:
+ tags:
+ - 'v*'
+
+env:
+ GO_VERSION: '1.23'
+
+permissions:
+ contents: write
+ packages: write
+
+jobs:
+ release:
+ name: Create Release
+ runs-on: ubuntu-latest
+ outputs:
+ upload_url: ${{ steps.create_release.outputs.upload_url }}
+ version: ${{ steps.get_version.outputs.version }}
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+ with:
+ fetch-depth: 0
+
+ - name: Get version
+ id: get_version
+ run: echo "version=${GITHUB_REF#refs/tags/v}" >> $GITHUB_OUTPUT
+
+ - name: Generate changelog
+ id: changelog
+ run: |
+ # Get commits since last tag
+ PREVIOUS_TAG=$(git describe --tags --abbrev=0 HEAD^ 2>/dev/null || echo "")
+ if [ -n "$PREVIOUS_TAG" ]; then
+ CHANGELOG=$(git log --pretty=format:"- %s (%h)" ${PREVIOUS_TAG}..HEAD)
+ else
+ CHANGELOG=$(git log --pretty=format:"- %s (%h)")
+ fi
+ echo "changelog<> $GITHUB_OUTPUT
+ echo "$CHANGELOG" >> $GITHUB_OUTPUT
+ echo "EOF" >> $GITHUB_OUTPUT
+
+ - name: Create Release
+ id: create_release
+ uses: actions/create-release@v1
+ env:
+ GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
+ with:
+ tag_name: ${{ github.ref }}
+ release_name: Release ${{ steps.get_version.outputs.version }}
+ body: |
+ ## gomcp v${{ steps.get_version.outputs.version }}
+
+ ### Changes
+ ${{ steps.changelog.outputs.changelog }}
+
+ ### Installation
+
+ #### Binary Download
+ Download the appropriate binary for your platform from the assets below.
+
+ #### Docker
+ ```bash
+ docker pull ghcr.io/np-compete/gomcp:${{ steps.get_version.outputs.version }}
+ ```
+
+ #### From Source
+ ```bash
+ git clone https://github.com/NP-compete/gomcp.git
+ cd gomcp
+ git checkout v${{ steps.get_version.outputs.version }}
+ make build-prod
+ ```
+
+ See [CHANGELOG.md](https://github.com/NP-compete/gomcp/blob/main/CHANGELOG.md) for full details.
+ draft: false
+ prerelease: ${{ contains(github.ref, '-rc') || contains(github.ref, '-beta') || contains(github.ref, '-alpha') }}
+
+ build:
+ name: Build Binaries
+ runs-on: ubuntu-latest
+ needs: release
+ strategy:
+ matrix:
+ goos: [linux, darwin, windows]
+ goarch: [amd64, arm64]
+ exclude:
+ - goos: windows
+ goarch: arm64
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+
+ - name: Set up Go
+ uses: actions/setup-go@v5
+ with:
+ go-version: ${{ env.GO_VERSION }}
+ cache: true
+
+ - name: Build binary
+ env:
+ GOOS: ${{ matrix.goos }}
+ GOARCH: ${{ matrix.goarch }}
+ CGO_ENABLED: 0
+ run: |
+ VERSION=${{ needs.release.outputs.version }}
+ GIT_COMMIT=$(git rev-parse --short HEAD)
+ BUILD_TIME=$(date -u '+%Y-%m-%d_%H:%M:%S')
+
+ BINARY_NAME=gomcp
+ if [ "$GOOS" = "windows" ]; then
+ BINARY_NAME=gomcp.exe
+ fi
+
+ go build \
+ -ldflags "-X github.com/NP-compete/gomcp/internal/version.Version=${VERSION} \
+ -X github.com/NP-compete/gomcp/internal/version.GitCommit=${GIT_COMMIT} \
+ -X github.com/NP-compete/gomcp/internal/version.BuildTime=${BUILD_TIME}" \
+ -trimpath \
+ -o ${BINARY_NAME} \
+ ./cmd/server
+
+ - name: Create archive
+ run: |
+ BINARY_NAME=gomcp
+ ARCHIVE_NAME=gomcp-${{ needs.release.outputs.version }}-${{ matrix.goos }}-${{ matrix.goarch }}
+
+ if [ "${{ matrix.goos }}" = "windows" ]; then
+ BINARY_NAME=gomcp.exe
+ zip ${ARCHIVE_NAME}.zip ${BINARY_NAME} README.md LICENSE
+ echo "ASSET_PATH=${ARCHIVE_NAME}.zip" >> $GITHUB_ENV
+ echo "ASSET_NAME=${ARCHIVE_NAME}.zip" >> $GITHUB_ENV
+ echo "ASSET_TYPE=application/zip" >> $GITHUB_ENV
+ else
+ tar -czvf ${ARCHIVE_NAME}.tar.gz ${BINARY_NAME} README.md LICENSE
+ echo "ASSET_PATH=${ARCHIVE_NAME}.tar.gz" >> $GITHUB_ENV
+ echo "ASSET_NAME=${ARCHIVE_NAME}.tar.gz" >> $GITHUB_ENV
+ echo "ASSET_TYPE=application/gzip" >> $GITHUB_ENV
+ fi
+
+ - name: Upload Release Asset
+ uses: actions/upload-release-asset@v1
+ env:
+ GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
+ with:
+ upload_url: ${{ needs.release.outputs.upload_url }}
+ asset_path: ${{ env.ASSET_PATH }}
+ asset_name: ${{ env.ASSET_NAME }}
+ asset_content_type: ${{ env.ASSET_TYPE }}
+
+ docker:
+ name: Build and Push Docker Image
+ runs-on: ubuntu-latest
+ needs: release
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v4
+
+ - name: Set up QEMU
+ uses: docker/setup-qemu-action@v3
+
+ - name: Set up Docker Buildx
+ uses: docker/setup-buildx-action@v3
+
+ - name: Login to GitHub Container Registry
+ uses: docker/login-action@v3
+ with:
+ registry: ghcr.io
+ username: ${{ github.actor }}
+ password: ${{ secrets.GITHUB_TOKEN }}
+
+ - name: Extract metadata
+ id: meta
+ uses: docker/metadata-action@v5
+ with:
+ images: ghcr.io/np-compete/gomcp
+ tags: |
+ type=semver,pattern={{version}}
+ type=semver,pattern={{major}}.{{minor}}
+ type=semver,pattern={{major}}
+ type=sha
+
+ - name: Build and push
+ uses: docker/build-push-action@v5
+ with:
+ context: .
+ platforms: linux/amd64,linux/arm64
+ push: true
+ tags: ${{ steps.meta.outputs.tags }}
+ labels: ${{ steps.meta.outputs.labels }}
+ cache-from: type=gha
+ cache-to: type=gha,mode=max
diff --git a/CHANGELOG.md b/CHANGELOG.md
new file mode 100644
index 0000000..ca354bc
--- /dev/null
+++ b/CHANGELOG.md
@@ -0,0 +1,78 @@
+# Changelog
+
+All notable changes to this project will be documented in this file.
+
+The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
+and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
+
+## [Unreleased]
+
+### Added
+- Repository template enhancements
+- GitHub Actions CI/CD workflows
+- Comprehensive documentation
+- Issue and PR templates
+- Contributing guidelines
+- Security policy
+
+## [0.1.0] - 2024-12-01
+
+### Added
+- Initial release of gomcp
+- Complete MCP 2025-06-18 specification support
+- **Tools**: 4 example tools with structured outputs
+ - `multiply_numbers` - Number multiplication with structured output
+ - `code_review` - Generate code review analysis
+ - `logo` - Display server logo
+ - `long_operation` - Demonstrates progress & cancellation
+- **Prompts**: 3 reusable prompt templates
+ - `code_review` - Code review template
+ - `git_commit` - Git commit message generator
+ - `debug_help` - Debugging assistance
+- **Resources**: 6 static/dynamic resources
+ - `project://info` - Server information
+ - `project://status` - System status
+ - `docs://quickstart` - Quick start guide
+ - `docs://api-reference` - API documentation
+ - `config://template` - Configuration template
+ - `config://env-vars` - Environment variables
+- **Transport Support**
+ - HTTP/SSE transport for web clients
+ - stdio transport for Claude Desktop
+ - Cursor IDE compatibility mode
+- **MCP Features**
+ - Roots - Filesystem root definitions
+ - Completion - Structured tool outputs with JSON schemas
+ - Logging - Server→client log notifications (8 levels)
+ - Pagination - Cursor-based pagination (max 100/page)
+ - Sampling - Server→client LLM requests
+ - Elicitation - Server→user data requests
+ - Progress - Real-time progress notifications
+ - Cancellation - Request cancellation support
+ - Ping - Health checks
+- **Infrastructure**
+ - Docker and Podman support
+ - Docker Compose configuration
+ - Makefile with comprehensive targets
+ - Hot reload development mode (air)
+ - Production build with version embedding
+- **Security**
+ - OAuth authentication support
+ - Session management
+ - CORS configuration
+ - SSL/TLS support
+
+### Security
+- Non-root Docker container execution
+- Environment-based secret management
+
+---
+
+## Version History
+
+| Version | Date | Highlights |
+|---------|------|------------|
+| 0.1.0 | 2024-12-01 | Initial release with full MCP 2025-06-18 support |
+
+[Unreleased]: https://github.com/NP-compete/gomcp/compare/v0.1.0...HEAD
+[0.1.0]: https://github.com/NP-compete/gomcp/releases/tag/v0.1.0
diff --git a/CODE_OF_CONDUCT.md b/CODE_OF_CONDUCT.md
new file mode 100644
index 0000000..8e889ef
--- /dev/null
+++ b/CODE_OF_CONDUCT.md
@@ -0,0 +1,133 @@
+# Contributor Covenant Code of Conduct
+
+## Our Pledge
+
+We as members, contributors, and leaders pledge to make participation in our
+community a harassment-free experience for everyone, regardless of age, body
+size, visible or invisible disability, ethnicity, sex characteristics, gender
+identity and expression, level of experience, education, socio-economic status,
+nationality, personal appearance, race, caste, color, religion, or sexual
+identity and orientation.
+
+We pledge to act and interact in ways that contribute to an open, welcoming,
+diverse, inclusive, and healthy community.
+
+## Our Standards
+
+Examples of behavior that contributes to a positive environment for our
+community include:
+
+* Demonstrating empathy and kindness toward other people
+* Being respectful of differing opinions, viewpoints, and experiences
+* Giving and gracefully accepting constructive feedback
+* Accepting responsibility and apologizing to those affected by our mistakes,
+ and learning from the experience
+* Focusing on what is best not just for us as individuals, but for the overall
+ community
+
+Examples of unacceptable behavior include:
+
+* The use of sexualized language or imagery, and sexual attention or advances of
+ any kind
+* Trolling, insulting or derogatory comments, and personal or political attacks
+* Public or private harassment
+* Publishing others' private information, such as a physical or email address,
+ without their explicit permission
+* Other conduct which could reasonably be considered inappropriate in a
+ professional setting
+
+## Enforcement Responsibilities
+
+Community leaders are responsible for clarifying and enforcing our standards of
+acceptable behavior and will take appropriate and fair corrective action in
+response to any behavior that they deem inappropriate, threatening, offensive,
+or harmful.
+
+Community leaders have the right and responsibility to remove, edit, or reject
+comments, commits, code, wiki edits, issues, and other contributions that are
+not aligned to this Code of Conduct, and will communicate reasons for moderation
+decisions when appropriate.
+
+## Scope
+
+This Code of Conduct applies within all community spaces, and also applies when
+an individual is officially representing the community in public spaces.
+Examples of representing our community include using an official email address,
+posting via an official social media account, or acting as an appointed
+representative at an online or offline event.
+
+## Enforcement
+
+Instances of abusive, harassing, or otherwise unacceptable behavior may be
+reported to the community leaders responsible for enforcement at
+[INSERT CONTACT METHOD].
+
+All complaints will be reviewed and investigated promptly and fairly.
+
+All community leaders are obligated to respect the privacy and security of the
+reporter of any incident.
+
+## Enforcement Guidelines
+
+Community leaders will follow these Community Impact Guidelines in determining
+the consequences for any action they deem in violation of this Code of Conduct:
+
+### 1. Correction
+
+**Community Impact**: Use of inappropriate language or other behavior deemed
+unprofessional or unwelcome in the community.
+
+**Consequence**: A private, written warning from community leaders, providing
+clarity around the nature of the violation and an explanation of why the
+behavior was inappropriate. A public apology may be requested.
+
+### 2. Warning
+
+**Community Impact**: A violation through a single incident or series of
+actions.
+
+**Consequence**: A warning with consequences for continued behavior. No
+interaction with the people involved, including unsolicited interaction with
+those enforcing the Code of Conduct, for a specified period of time. This
+includes avoiding interactions in community spaces as well as external channels
+like social media. Violating these terms may lead to a temporary or permanent
+ban.
+
+### 3. Temporary Ban
+
+**Community Impact**: A serious violation of community standards, including
+sustained inappropriate behavior.
+
+**Consequence**: A temporary ban from any sort of interaction or public
+communication with the community for a specified period of time. No public or
+private interaction with the people involved, including unsolicited interaction
+with those enforcing the Code of Conduct, is allowed during this period.
+Violating these terms may lead to a permanent ban.
+
+### 4. Permanent Ban
+
+**Community Impact**: Demonstrating a pattern of violation of community
+standards, including sustained inappropriate behavior, harassment of an
+individual, or aggression toward or disparagement of classes of individuals.
+
+**Consequence**: A permanent ban from any sort of public interaction within the
+community.
+
+## Attribution
+
+This Code of Conduct is adapted from the [Contributor Covenant][homepage],
+version 2.1, available at
+[https://www.contributor-covenant.org/version/2/1/code_of_conduct.html][v2.1].
+
+Community Impact Guidelines were inspired by
+[Mozilla's code of conduct enforcement ladder][Mozilla CoC].
+
+For answers to common questions about this code of conduct, see the FAQ at
+[https://www.contributor-covenant.org/faq][FAQ]. Translations are available at
+[https://www.contributor-covenant.org/translations][translations].
+
+[homepage]: https://www.contributor-covenant.org
+[v2.1]: https://www.contributor-covenant.org/version/2/1/code_of_conduct.html
+[Mozilla CoC]: https://github.com/mozilla/diversity
+[FAQ]: https://www.contributor-covenant.org/faq
+[translations]: https://www.contributor-covenant.org/translations
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
new file mode 100644
index 0000000..b68cb29
--- /dev/null
+++ b/CONTRIBUTING.md
@@ -0,0 +1,247 @@
+# Contributing to gomcp
+
+First off, thank you for considering contributing to gomcp! It's people like you that make gomcp such a great tool for the MCP community.
+
+## Code of Conduct
+
+This project and everyone participating in it is governed by our [Code of Conduct](CODE_OF_CONDUCT.md). By participating, you are expected to uphold this code.
+
+## How Can I Contribute?
+
+### Reporting Bugs
+
+Before creating bug reports, please check the existing issues to avoid duplicates. When you create a bug report, include as many details as possible using our [bug report template](.github/ISSUE_TEMPLATE/bug_report.md).
+
+**Great Bug Reports** tend to have:
+
+- A quick summary and/or background
+- Steps to reproduce (be specific!)
+- What you expected would happen
+- What actually happens
+- Notes (possibly including why you think this might be happening)
+
+### Suggesting Enhancements
+
+Enhancement suggestions are tracked as GitHub issues. When creating an enhancement suggestion, use our [feature request template](.github/ISSUE_TEMPLATE/feature_request.md) and include:
+
+- A clear and descriptive title
+- A detailed description of the proposed enhancement
+- Explain why this enhancement would be useful
+- List any alternatives you've considered
+
+### Pull Requests
+
+1. Fork the repo and create your branch from `main`
+2. If you've added code that should be tested, add tests
+3. If you've changed APIs, update the documentation
+4. Ensure the test suite passes
+5. Make sure your code lints
+6. Issue that pull request!
+
+## Development Setup
+
+### Prerequisites
+
+- Go 1.23 or higher
+- Docker/Podman (optional, for containerized development)
+
+### Getting Started
+
+```bash
+# Clone your fork
+git clone https://github.com/YOUR_USERNAME/gomcp.git
+cd gomcp
+
+# Add upstream remote
+git remote add upstream https://github.com/NP-compete/gomcp.git
+
+# Install dependencies
+go mod download
+
+# Install development tools
+make tools
+
+# Run tests
+make test
+
+# Run linter
+make lint
+```
+
+### Development Workflow
+
+```bash
+# Create a feature branch
+git checkout -b feature/my-new-feature
+
+# Make your changes and test
+make test
+make lint
+
+# Run the server locally
+make run
+
+# For Cursor IDE testing
+make cursor
+```
+
+### Project Structure
+
+```
+gomcp/
+├── cmd/server/ # Application entry point
+├── internal/
+│ ├── api/ # HTTP handlers & routing
+│ ├── completion/ # Structured outputs
+│ ├── config/ # Configuration management
+│ ├── logging/ # Server→client logs
+│ ├── mcp/ # MCP server logic
+│ ├── pagination/ # Cursor-based pagination
+│ ├── prompts/ # Prompt implementations
+│ ├── resources/ # Resource implementations
+│ ├── roots/ # Filesystem roots
+│ └── tools/ # Tool implementations
+├── pkg/mcpprotocol/ # MCP protocol types
+├── test/ # Integration tests
+└── docs/ # Documentation
+```
+
+## Adding New Features
+
+### Adding a New Tool
+
+1. Create `internal/tools/mytool_sdk.go`:
+
+```go
+package tools
+
+import (
+ "context"
+ "github.com/modelcontextprotocol/go-sdk/mcp"
+)
+
+type MyToolInput struct {
+ Param string `json:"param" jsonschema:"required,description=Parameter description"`
+}
+
+type MyToolOutput struct {
+ Result string `json:"result"`
+}
+
+func MyToolSDK(ctx context.Context, req *mcp.CallToolRequest, input MyToolInput) (*mcp.CallToolResult, MyToolOutput, error) {
+ output := MyToolOutput{Result: "success"}
+ return nil, output, nil
+}
+```
+
+2. Register in `internal/mcp/server_sdk.go`:
+
+```go
+mcp.AddTool(
+ server,
+ &mcp.Tool{
+ Name: "my_tool",
+ Description: "Description of my tool",
+ },
+ tools.MyToolSDK,
+)
+```
+
+3. Add tests in `internal/tools/mytool_test.go`
+
+### Adding a New Prompt
+
+1. Create `internal/prompts/myprompt.go`
+2. Register in `internal/mcp/server_sdk.go`
+3. Add tests
+
+### Adding a New Resource
+
+1. Create `internal/resources/myresource.go`
+2. Register in `internal/mcp/server_sdk.go`
+3. Add tests
+
+## Style Guidelines
+
+### Go Code Style
+
+- Follow [Effective Go](https://golang.org/doc/effective_go.html)
+- Use `gofmt` for formatting (run `make lint`)
+- Write meaningful comments for exported functions
+- Keep functions focused and small
+- Handle errors explicitly
+
+### Commit Messages
+
+We follow [Conventional Commits](https://www.conventionalcommits.org/):
+
+```
+():
+
+[optional body]
+
+[optional footer(s)]
+```
+
+Types:
+- `feat`: New feature
+- `fix`: Bug fix
+- `docs`: Documentation only
+- `style`: Formatting, missing semicolons, etc.
+- `refactor`: Code change that neither fixes a bug nor adds a feature
+- `test`: Adding missing tests
+- `chore`: Maintenance tasks
+
+Examples:
+```
+feat(tools): add weather lookup tool
+fix(transport): handle SSE reconnection properly
+docs(readme): add Cursor IDE setup instructions
+```
+
+### Testing
+
+- Write tests for new functionality
+- Maintain or improve code coverage
+- Use table-driven tests where appropriate
+- Mock external dependencies
+
+```bash
+# Run all tests
+make test
+
+# Run specific tests
+go test -v ./internal/tools/...
+
+# Run with coverage
+go test -coverprofile=coverage.out ./...
+go tool cover -html=coverage.out
+```
+
+## Review Process
+
+1. All submissions require review
+2. We use GitHub pull requests for this purpose
+3. Reviewers will look for:
+ - Code quality and style
+ - Test coverage
+ - Documentation updates
+ - Backward compatibility
+
+## Community
+
+- Use GitHub Discussions for questions and ideas
+- Be respectful and constructive
+- Help others when you can
+
+## Recognition
+
+Contributors are recognized in our release notes and README. Thank you for making gomcp better!
+
+## Questions?
+
+Feel free to open an issue with the `question` label or start a discussion.
+
+---
+
+Thank you for contributing! 🎉
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..98a2be0
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,21 @@
+MIT License
+
+Copyright (c) 2024 NP-compete
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/README.md b/README.md
index 677f146..958306f 100644
--- a/README.md
+++ b/README.md
@@ -1,25 +1,93 @@
-# gomcp - Go MCP Server Template
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+gomcp
+
+
+ Production-ready Model Context Protocol (MCP) server template in Go
+
+
+
+ Features •
+ Quick Start •
+ Use as Template •
+ Documentation •
+ Contributing
+
-Production-ready Model Context Protocol (MCP) server template in Go with **complete MCP 2025-06-18 support**.
+---
+
+## Overview
+
+**gomcp** is a complete, production-ready MCP server template built with Go and the [official MCP Go SDK](https://github.com/modelcontextprotocol/go-sdk). It implements the full [MCP 2025-06-18 specification](https://modelcontextprotocol.io/specification/2025-06-18) and is designed to be used as a starting point for building your own MCP servers.
+
+### Why gomcp?
+
+- **Complete Implementation** - All 12 MCP features fully implemented
+- **Production Ready** - Docker support, CI/CD, security best practices
+- **Well Documented** - Comprehensive docs, examples, and customization guide
+- **Easy to Customize** - Clean architecture, modular design, extensive comments
+- **Multiple Transports** - HTTP/SSE for Cursor IDE, stdio for Claude Desktop
## ✨ Features
-**12 MCP Features Fully Implemented:**
+
+
+|
+
+### MCP Features (12/12)
+
+| Feature | Status | Description |
+|---------|:------:|-------------|
+| Tools | ✅ | 4 example tools with structured outputs |
+| Prompts | ✅ | 3 reusable prompt templates |
+| Resources | ✅ | 6 static/dynamic resources |
+| Roots | ✅ | Filesystem root definitions |
+| Completion | ✅ | Structured outputs with JSON schemas |
+| Logging | ✅ | Server→client notifications (8 levels) |
+| Pagination | ✅ | Cursor-based pagination |
+| Sampling | ✅ | Server→client LLM requests |
+| Elicitation | ✅ | Server→user data requests |
+| Progress | ✅ | Real-time progress notifications |
+| Cancellation | ✅ | Request cancellation support |
+| Ping | ✅ | Health checks |
+
+ |
+
+
+### Infrastructure
| Feature | Description |
|---------|-------------|
-| **Tools** | 4 example tools with structured outputs |
-| **Prompts** | 3 reusable prompt templates |
-| **Resources** | 6 static/dynamic resources |
-| **Roots** | Filesystem root definitions |
-| **Completion** | Structured tool outputs with JSON schemas |
-| **Logging** | Server→client log notifications (8 levels) |
-| **Pagination** | Cursor-based pagination (max 100/page) |
-| **Sampling** | Server→client LLM requests |
-| **Elicitation** | Server→user data requests |
-| **Progress** | Real-time progress notifications |
-| **Cancellation** | Request cancellation support |
-| **Ping** | Health checks |
+| **Multi-Transport** | HTTP/SSE + stdio support |
+| **Cursor Compatible** | First-class Cursor IDE support |
+| **Claude Desktop** | stdio transport for local use |
+| **Docker Ready** | Multi-stage Dockerfile included |
+| **CI/CD** | GitHub Actions workflows |
+| **Hot Reload** | Development mode with air |
+| **OAuth Support** | Authentication ready |
+| **Metrics** | Built-in monitoring endpoints |
+| **Security** | Non-root containers, SSL/TLS |
+
+ |
+
+
## 🚀 Quick Start
@@ -28,48 +96,31 @@ Production-ready Model Context Protocol (MCP) server template in Go with **compl
- Go 1.23+
- (Optional) Docker/Podman
-**Important:** Ensure Go's bin directory is in your PATH:
-
-```bash
-# Add to PATH (required for air, development tools)
-export PATH=$PATH:$(go env GOPATH)/bin
-
-# Make it permanent (add to ~/.zshrc or ~/.bashrc):
-echo 'export PATH=$PATH:$(go env GOPATH)/bin' >> ~/.zshrc
-source ~/.zshrc
-```
-
-### 1. Clone & Install
+### Installation
```bash
+# Clone the repository
git clone https://github.com/NP-compete/gomcp.git
cd gomcp
+
+# Download dependencies
go mod download
+
+# Build and run
+make run
```
-### 2. Run Server
+### Running the Server
+
+
+For Cursor IDE (HTTP/SSE)
-**For Cursor IDE:**
```bash
make cursor
# Server runs on http://localhost:8081/mcp/sse
```
-**For Claude Desktop:**
-```bash
-export MCP_TRANSPORT_PROTOCOL=stdio
-go run cmd/server/main.go
-```
-
-**Default (HTTP):**
-```bash
-make run
-# Server runs on http://localhost:8081
-```
-
-### 3. Configure Client
-
-**Cursor IDE** (`~/.cursor/mcp.json`):
+Configure `~/.cursor/mcp.json`:
```json
{
"mcpServers": {
@@ -80,12 +131,27 @@ make run
}
```
-**Claude Desktop** (`~/Library/Application Support/Claude/claude_desktop_config.json`):
+Restart Cursor IDE to connect.
+
+
+
+
+For Claude Desktop (stdio)
+
+```bash
+# Build the binary
+make build-prod
+
+# Configure Claude Desktop
+# ~/Library/Application Support/Claude/claude_desktop_config.json (macOS)
+# %APPDATA%\Claude\claude_desktop_config.json (Windows)
+```
+
```json
{
"mcpServers": {
"gomcp": {
- "command": "/path/to/gomcp/bin/gomcp",
+ "command": "/absolute/path/to/gomcp/bin/gomcp",
"args": [],
"env": {
"MCP_TRANSPORT_PROTOCOL": "stdio"
@@ -95,262 +161,153 @@ make run
}
```
-## 📦 What's Included
+Restart Claude Desktop to connect.
-### Example Tools
-- `multiply_numbers` - Number multiplication with structured output
-- `code_review` - Generate code review analysis
-- `logo` - Display server logo
-- `long_operation` - Demonstrates progress & cancellation
+
-### Example Prompts
-- `code_review` - Code review template
-- `git_commit` - Git commit message generator
-- `debug_help` - Debugging assistance
+
+With Docker
-### Example Resources
-- `project://info` - Server information
-- `project://status` - System status
-- `docs://quickstart` - Quick start guide
-- `docs://api-reference` - API documentation
-- `config://template` - Configuration template
-- `config://env-vars` - Environment variables
+```bash
+# Build and run with Docker
+make docker-build
+make docker-run
-## 🔧 Configuration
+# Or with Docker Compose
+docker-compose up -d
+```
-**Environment Variables:**
+
-| Variable | Default | Description |
-|----------|---------|-------------|
-| `MCP_TRANSPORT_PROTOCOL` | `http` | Transport: `stdio`, `http`, `sse` |
-| `MCP_PORT` | `8081` | Server port |
-| `CURSOR_COMPATIBLE_SSE` | `true` | Enable Cursor compatibility |
-| `ENABLE_AUTH` | `true` | Enable OAuth authentication |
-| `LOG_LEVEL` | `INFO` | Log level |
+## 📦 Use as Template
-Create `.env` file:
-```bash
-MCP_TRANSPORT_PROTOCOL=http
-MCP_PORT=8081
-CURSOR_COMPATIBLE_SSE=true
-ENABLE_AUTH=false
-```
+This repository is designed to be used as a template for your own MCP server.
-## 🧪 Testing
+### Option 1: GitHub Template (Recommended)
-```bash
-# Run all tests
-./scripts/test_all.sh
+Click the **"Use this template"** button on GitHub to create a new repository.
-# Run specific tests
-go test -v ./internal/completion
-go test -v ./internal/logging
-go test -v ./internal/pagination
+### Option 2: Manual Clone
-# Generate coverage
-go test -coverprofile=coverage.out ./...
-go tool cover -html=coverage.out -o coverage.html
+```bash
+# Clone and remove git history
+git clone https://github.com/NP-compete/gomcp.git my-mcp-server
+cd my-mcp-server
+rm -rf .git
+git init
+
+# Update module name
+# Edit go.mod: module github.com/YOUR_USERNAME/my-mcp-server
+# Then update all imports
```
-**Test Coverage:** 65 tests, 100% pass rate
+### Customization Guide
+
+See [docs/CUSTOMIZATION.md](docs/CUSTOMIZATION.md) for detailed instructions on:
+
+- Adding your own tools, prompts, and resources
+- Configuring authentication
+- Customizing the Docker setup
+- Setting up CI/CD for your repository
## 📁 Project Structure
```
gomcp/
-├── cmd/server/ # Main application entry point
+├── cmd/server/ # Application entry point
├── internal/
│ ├── api/ # HTTP handlers & routing
│ ├── completion/ # Structured outputs
+│ ├── config/ # Configuration management
│ ├── logging/ # Server→client logs
+│ ├── mcp/ # MCP server logic
│ ├── pagination/ # Cursor-based pagination
│ ├── prompts/ # Prompt implementations
│ ├── resources/ # Resource implementations
│ ├── roots/ # Filesystem roots
-│ ├── tools/ # Tool implementations
-│ ├── mcp/ # MCP server logic
-│ └── config/ # Configuration management
-├── pkg/mcpprotocol/ # MCP protocol implementation
+│ └── tools/ # Tool implementations
+├── pkg/mcpprotocol/ # MCP protocol types
├── test/ # Integration tests
-└── Makefile # Build & run commands
-```
-
-## 🛠️ Development
-
-### Hot Reload
-```bash
-make dev # Auto-restarts on file changes
-```
-
-### Build Commands
-```bash
-make build # Development build
-make build-prod # Production build with optimization
-make clean # Clean artifacts
-make deps # Update dependencies
-```
-
-### Docker
-```bash
-make docker-build # Build image
-make docker-run # Run container
-```
-
-## 🎯 Adding Features
-
-### 1. Add a Tool
-
-Create `internal/tools/mytool_sdk.go`:
-```go
-type MyToolInput struct {
- Param string `json:"param" jsonschema:"required,parameter description"`
-}
-
-type MyToolOutput struct {
- Result string `json:"result"`
-}
-
-func MyTool(ctx context.Context, req *mcp.CallToolRequest, input MyToolInput) (*mcp.CallToolResult, MyToolOutput, error) {
- // Your logic here
- output := MyToolOutput{Result: "success"}
- return nil, output, nil
-}
-```
-
-Register in `internal/mcp/server_sdk.go`:
-```go
-server.AddTool(mcp.NewTool("mytool", "Description", MyTool))
-```
-
-### 2. Add a Prompt
-
-Create `internal/prompts/myprompt.go`:
-```go
-func MyPrompt(ctx context.Context, args mcp.GetPromptParams) (*mcp.GetPromptResult, error) {
- return &mcp.GetPromptResult{
- Messages: []*mcp.PromptMessage{
- {Role: "user", Content: &mcp.TextContent{Text: "Prompt text"}},
- },
- }, nil
-}
-```
-
-Register in `internal/mcp/server_sdk.go`.
-
-### 3. Add a Resource
-
-Create `internal/resources/myresource.go`:
-```go
-func MyResource(ctx context.Context, params mcp.ReadResourceParams) (*mcp.ReadResourceResult, error) {
- return &mcp.ReadResourceResult{
- Contents: []*mcp.ResourceContents{{
- URI: "my://resource",
- Text: "Content here",
- }},
- }, nil
-}
-```
-
-Register in `internal/mcp/server_sdk.go`.
-
-## 🔐 Authentication
-
-Enable OAuth:
-```bash
-export ENABLE_AUTH=true
-export POSTGRES_HOST=localhost
-export POSTGRES_DB=mcp_db
+├── docs/ # Documentation
+├── scripts/ # Utility scripts
+├── .github/ # GitHub Actions & templates
+├── Dockerfile # Container build
+├── docker-compose.yml # Local development
+└── Makefile # Build commands
```
-Disable for development:
-```bash
-export ENABLE_AUTH=false
-```
+## 🔧 Configuration
-## 🚢 Deployment
+| Variable | Default | Description |
+|----------|---------|-------------|
+| `MCP_TRANSPORT_PROTOCOL` | `http` | Transport: `stdio`, `http`, `sse` |
+| `MCP_PORT` | `8081` | Server port |
+| `CURSOR_COMPATIBLE_SSE` | `true` | Enable Cursor compatibility |
+| `ENABLE_AUTH` | `true` | Enable OAuth authentication |
+| `LOG_LEVEL` | `INFO` | Log level |
-### Production Build
-```bash
-make build-prod
-# Binary: bin/gomcp
-```
+See [.env.example](.env.example) for all options.
-### Docker Deployment
-```bash
-docker build -t gomcp-server .
-docker run -p 8081:8081 --env-file .env gomcp-server
-```
+## 🧪 Testing
-### Environment Setup
```bash
-# Set transport
-export MCP_TRANSPORT_PROTOCOL=http # or stdio
-export MCP_PORT=8081
-export CURSOR_COMPATIBLE_SSE=true # For Cursor
-export ENABLE_AUTH=false # For development
-```
-
-## 📊 Monitoring
+# Run all tests
+make test
-### Metrics Endpoint
-```bash
-curl http://localhost:8081/metrics
-```
+# Run with coverage
+go test -coverprofile=coverage.out ./...
+go tool cover -html=coverage.out
-Returns:
-- Request counts
-- Tool usage
-- Error rates
-- Response times
-- Client info
+# Run linter
+make lint
-### Health Check
-```bash
-curl http://localhost:8081/health
+# Run security scan
+make security-scan
```
-## 🐛 Troubleshooting
+## 📚 Documentation
-**Port already in use:**
-```bash
-lsof -ti:8081 | xargs kill -9
-```
+| Document | Description |
+|----------|-------------|
+| [Architecture](docs/ARCHITECTURE.md) | System design and component overview |
+| [Customization](docs/CUSTOMIZATION.md) | Guide to customizing the template |
+| [Contributing](CONTRIBUTING.md) | How to contribute |
+| [Security](SECURITY.md) | Security policy |
+| [Changelog](CHANGELOG.md) | Version history |
-**Cursor not connecting:**
-1. Use `make cursor` (Cursor compatibility is enabled by default)
-2. Verify `~/.cursor/mcp.json` has correct URL: `http://localhost:8081/mcp/sse`
-3. Restart Cursor IDE
+### External Resources
-**Claude Desktop not working:**
-1. Set `MCP_TRANSPORT_PROTOCOL=stdio`
-2. Use absolute path to binary
-3. Restart Claude Desktop
+- [MCP Specification](https://modelcontextprotocol.io/specification/2025-06-18)
+- [Official Go SDK](https://github.com/modelcontextprotocol/go-sdk)
-**Build errors:**
-```bash
-go mod tidy
-go mod download
-make clean && make build
-```
+## 🤝 Contributing
-## 📚 Resources
+We welcome contributions! Please see [CONTRIBUTING.md](CONTRIBUTING.md) for guidelines.
-- [MCP Specification](https://modelcontextprotocol.io/specification/2025-06-18)
-- [Official Go SDK](https://github.com/modelcontextprotocol/go-sdk)
+1. Fork the repository
+2. Create a feature branch (`git checkout -b feature/amazing-feature`)
+3. Commit your changes (`git commit -m 'feat: add amazing feature'`)
+4. Push to the branch (`git push origin feature/amazing-feature`)
+5. Open a Pull Request
## 📝 License
-MIT License - see LICENSE file
+This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
-## 🤝 Contributing
+## 🙏 Acknowledgments
-1. Fork the repository
-2. Create feature branch
-3. Add tests
-4. Submit pull request
+- [Model Context Protocol](https://modelcontextprotocol.io/) - The MCP specification
+- [Official Go SDK](https://github.com/modelcontextprotocol/go-sdk) - The foundation of this server
+- All [contributors](https://github.com/NP-compete/gomcp/graphs/contributors) who help improve this project
---
-**Built with ❤️ using Go and the official MCP SDK**
+
+ Built with ❤️ for the MCP community
+
-Template ready for production use with all MCP 2025-06-18 features!
+
+ ⭐ Star us on GitHub •
+ 🐛 Report Bug •
+ 💬 Discussions
+
diff --git a/SECURITY.md b/SECURITY.md
new file mode 100644
index 0000000..5cb0b32
--- /dev/null
+++ b/SECURITY.md
@@ -0,0 +1,118 @@
+# Security Policy
+
+## Supported Versions
+
+We release patches for security vulnerabilities for the following versions:
+
+| Version | Supported |
+| ------- | ------------------ |
+| 0.1.x | :white_check_mark: |
+
+## Reporting a Vulnerability
+
+We take the security of gomcp seriously. If you believe you have found a security vulnerability, please report it to us as described below.
+
+### Please Do
+
+- **Report the vulnerability privately** - Do not create a public GitHub issue for security vulnerabilities
+- **Provide details** - Include as much information as possible about the vulnerability
+- **Allow time** - Give us reasonable time to address the issue before any public disclosure
+
+### Please Don't
+
+- **Don't disclose publicly** - Please don't disclose the vulnerability publicly until we've had a chance to address it
+- **Don't exploit** - Don't exploit the vulnerability beyond what's necessary to demonstrate it
+
+### How to Report
+
+1. **GitHub Security Advisories** (Preferred): Use [GitHub's security advisory feature](https://github.com/NP-compete/gomcp/security/advisories/new) to report vulnerabilities privately.
+
+2. **Email**: If you prefer email, contact the maintainers directly (check the repository for contact information).
+
+### What to Include
+
+When reporting a vulnerability, please include:
+
+- Type of vulnerability (e.g., injection, authentication bypass, etc.)
+- Full paths of source file(s) related to the vulnerability
+- Location of the affected source code (tag/branch/commit or direct URL)
+- Step-by-step instructions to reproduce the issue
+- Proof-of-concept or exploit code (if possible)
+- Impact of the vulnerability and how an attacker might exploit it
+
+### Response Timeline
+
+- **Initial Response**: Within 48 hours, we will acknowledge receipt of your report
+- **Status Update**: Within 7 days, we will provide an initial assessment
+- **Resolution**: We aim to resolve critical vulnerabilities within 30 days
+
+### After Reporting
+
+1. We will confirm receipt of your vulnerability report
+2. We will investigate and determine the impact
+3. We will develop and test a fix
+4. We will release a patch and publicly disclose the vulnerability (with credit to you, if desired)
+
+## Security Best Practices for Users
+
+When deploying gomcp in production:
+
+### Authentication
+
+- **Enable authentication** in production environments (`ENABLE_AUTH=true`)
+- Use strong, unique session secrets (`SESSION_SECRET`)
+- Configure OAuth/SSO with trusted identity providers
+
+### Network Security
+
+- Use HTTPS/TLS in production (configure `MCP_SSL_KEYFILE` and `MCP_SSL_CERTFILE`)
+- Restrict CORS origins to trusted domains
+- Use a reverse proxy (nginx, Caddy) for additional security headers
+
+### Environment Variables
+
+- Never commit `.env` files with secrets
+- Use secret management solutions (Vault, AWS Secrets Manager, etc.)
+- Rotate secrets regularly
+
+### Container Security
+
+- Run containers as non-root user (already configured in Dockerfile)
+- Use read-only file systems where possible
+- Scan images for vulnerabilities regularly
+
+### Monitoring
+
+- Enable logging and monitor for suspicious activity
+- Set up alerts for authentication failures
+- Review access logs regularly
+
+## Known Security Considerations
+
+### MCP Protocol
+
+- The MCP protocol allows AI models to execute tools - ensure tools are properly sandboxed
+- Validate all inputs from MCP clients
+- Be cautious with tools that access the filesystem or execute commands
+
+### Transport Security
+
+- **stdio transport**: Only use for local, trusted clients (Claude Desktop)
+- **HTTP/SSE transport**: Always use HTTPS in production
+- Validate client certificates when possible
+
+## Security Updates
+
+Security updates will be released as patch versions (e.g., 0.1.1, 0.1.2). We recommend:
+
+- Subscribing to GitHub releases for notifications
+- Regularly updating to the latest patch version
+- Reviewing the CHANGELOG for security-related fixes
+
+## Acknowledgments
+
+We appreciate the security research community's efforts in helping keep gomcp secure. Reporters of valid security issues will be acknowledged in our release notes (unless they prefer to remain anonymous).
+
+---
+
+Thank you for helping keep gomcp and its users safe!
diff --git a/docs/ARCHITECTURE.md b/docs/ARCHITECTURE.md
new file mode 100644
index 0000000..8d2aee0
--- /dev/null
+++ b/docs/ARCHITECTURE.md
@@ -0,0 +1,359 @@
+# Architecture
+
+This document describes the architecture of gomcp, a production-ready MCP (Model Context Protocol) server template in Go.
+
+## Overview
+
+gomcp implements the [MCP 2025-06-18 specification](https://modelcontextprotocol.io/specification/2025-06-18), providing a complete server implementation that can be used as a template for building custom MCP servers.
+
+```
+┌─────────────────────────────────────────────────────────────────────────────┐
+│ MCP Clients │
+│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────────────┐ │
+│ │ Cursor IDE │ │ Claude │ │ HTTP/SSE │ │ Custom Clients │ │
+│ │ (HTTP/SSE) │ │ Desktop │ │ Clients │ │ │ │
+│ └──────┬──────┘ └──────┬──────┘ └──────┬──────┘ └──────────┬──────────┘ │
+└─────────┼────────────────┼────────────────┼────────────────────┼────────────┘
+ │ │ │ │
+ ▼ ▼ ▼ ▼
+┌─────────────────────────────────────────────────────────────────────────────┐
+│ Transport Layer │
+│ ┌─────────────────────────────┐ ┌─────────────────────────────────────┐ │
+│ │ HTTP/SSE Transport │ │ stdio Transport │ │
+│ │ (Cursor, Web Clients) │ │ (Claude Desktop, CLI) │ │
+│ └──────────────┬──────────────┘ └─────────────────┬───────────────────┘ │
+└─────────────────┼───────────────────────────────────┼───────────────────────┘
+ │ │
+ ▼ ▼
+┌─────────────────────────────────────────────────────────────────────────────┐
+│ MCP Server Core │
+│ ┌─────────────────────────────────────────────────────────────────────┐ │
+│ │ Official MCP Go SDK │ │
+│ │ (github.com/modelcontextprotocol/go-sdk) │ │
+│ └─────────────────────────────────────────────────────────────────────┘ │
+│ │ │
+│ ┌──────────────────────────┼──────────────────────────┐ │
+│ ▼ ▼ ▼ │
+│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
+│ │ Tools │ │ Prompts │ │ Resources │ │
+│ │ (4 impl) │ │ (3 impl) │ │ (6 impl) │ │
+│ └─────────────┘ └─────────────┘ └─────────────┘ │
+│ │
+│ ┌─────────────────────────────────────────────────────────────────────┐ │
+│ │ MCP Features │ │
+│ │ ┌────────┐ ┌────────┐ ┌──────────┐ ┌────────┐ ┌──────────────────┐ │ │
+│ │ │ Roots │ │Logging │ │Pagination│ │Sampling│ │ Elicitation │ │ │
+│ │ └────────┘ └────────┘ └──────────┘ └────────┘ └──────────────────┘ │ │
+│ │ ┌────────┐ ┌────────┐ ┌──────────┐ ┌────────┐ │ │
+│ │ │Progress│ │ Cancel │ │Completion│ │ Ping │ │ │
+│ │ └────────┘ └────────┘ └──────────┘ └────────┘ │ │
+│ └─────────────────────────────────────────────────────────────────────┘ │
+└─────────────────────────────────────────────────────────────────────────────┘
+```
+
+## Directory Structure
+
+```
+gomcp/
+├── cmd/
+│ └── server/
+│ └── main.go # Application entry point
+├── internal/
+│ ├── api/
+│ │ ├── router.go # HTTP router setup
+│ │ ├── handlers.go # HTTP request handlers
+│ │ ├── metrics.go # Metrics endpoint
+│ │ └── mcp_metrics.go # MCP-specific metrics
+│ ├── completion/
+│ │ ├── completion.go # Structured output completion
+│ │ └── completion_test.go # Tests
+│ ├── config/
+│ │ └── config.go # Configuration management
+│ ├── elicitation/
+│ │ └── elicitation.go # User data elicitation
+│ ├── errors/
+│ │ └── errors.go # Error types and handling
+│ ├── logger/
+│ │ └── logger.go # Application logging
+│ ├── logging/
+│ │ ├── logging.go # MCP logging (server→client)
+│ │ └── logging_test.go # Tests
+│ ├── mcp/
+│ │ ├── server.go # MCP server (HTTP transport)
+│ │ └── server_sdk.go # MCP server (SDK integration)
+│ ├── middleware/
+│ │ ├── auth.go # Authentication middleware
+│ │ ├── cors.go # CORS middleware
+│ │ ├── logging.go # Request logging
+│ │ ├── recovery.go # Panic recovery
+│ │ ├── requestid.go # Request ID generation
+│ │ └── session.go # Session management
+│ ├── oauth/
+│ │ └── oauth.go # OAuth service
+│ ├── pagination/
+│ │ ├── pagination.go # Cursor-based pagination
+│ │ └── pagination_test.go # Tests
+│ ├── prompts/
+│ │ ├── code_review.go # Code review prompt
+│ │ ├── debug_help.go # Debug help prompt
+│ │ └── git_commit.go # Git commit prompt
+│ ├── resources/
+│ │ ├── config.go # Config resources
+│ │ ├── docs.go # Documentation resources
+│ │ └── project_info.go # Project info resources
+│ ├── roots/
+│ │ ├── roots.go # Filesystem roots
+│ │ └── roots_test.go # Tests
+│ ├── sampling/
+│ │ └── sampling.go # LLM sampling requests
+│ ├── storage/
+│ │ ├── interface.go # Storage interface
+│ │ ├── memory.go # In-memory storage
+│ │ └── storage.go # Storage implementation
+│ ├── tools/
+│ │ ├── codereview.go # Code review tool
+│ │ ├── codereview_sdk.go # SDK integration
+│ │ ├── logo.go # Logo tool
+│ │ ├── logo_sdk.go # SDK integration
+│ │ ├── long_operation_sdk.go# Long operation tool
+│ │ ├── multiply.go # Multiply tool
+│ │ └── multiply_sdk.go # SDK integration
+│ └── version/
+│ └── version.go # Version information
+├── pkg/
+│ └── mcpprotocol/
+│ ├── handler.go # Protocol handler
+│ └── types.go # Protocol types
+├── scripts/
+│ ├── health-check.sh # Health check script
+│ ├── init-db.sql # Database initialization
+│ ├── run_dev.sh # Development runner
+│ ├── start.sh # Start script
+│ ├── stop.sh # Stop script
+│ └── test_all.sh # Test runner
+├── test/
+│ └── integration_test.go # Integration tests
+└── docs/
+ ├── ARCHITECTURE.md # This file
+ └── CUSTOMIZATION.md # Template customization guide
+```
+
+## Core Components
+
+### 1. Transport Layer
+
+gomcp supports two transport mechanisms:
+
+#### HTTP/SSE Transport
+- Used by Cursor IDE and web-based clients
+- Server-Sent Events (SSE) for real-time communication
+- Cursor compatibility mode for IDE integration
+- CORS support for browser clients
+
+#### stdio Transport
+- Used by Claude Desktop and CLI tools
+- Standard input/output communication
+- No network configuration required
+
+### 2. MCP Server Core
+
+The server core is built on the [official MCP Go SDK](https://github.com/modelcontextprotocol/go-sdk):
+
+```go
+// Server initialization
+impl := &mcp.Implementation{
+ Name: "template",
+ Version: "0.1.0",
+}
+server := mcp.NewServer(impl, nil)
+```
+
+### 3. Tools
+
+Tools are functions that AI models can invoke:
+
+| Tool | Description | Type |
+|------|-------------|------|
+| `multiply_numbers` | Multiply two numbers | CPU-bound |
+| `code_review` | Generate code review | I/O-bound |
+| `logo` | Return server logo | Resource-as-tool |
+| `long_operation` | Demo progress/cancel | Long-running |
+
+**Tool Implementation Pattern:**
+
+```go
+type ToolInput struct {
+ Param string `json:"param" jsonschema:"required,description=..."`
+}
+
+type ToolOutput struct {
+ Result string `json:"result"`
+}
+
+func ToolSDK(ctx context.Context, req *mcp.CallToolRequest, input ToolInput) (*mcp.CallToolResult, ToolOutput, error) {
+ // Implementation
+ return nil, output, nil
+}
+```
+
+### 4. Prompts
+
+Prompts are reusable templates for AI interactions:
+
+| Prompt | Description |
+|--------|-------------|
+| `code_review` | Structured code review template |
+| `git_commit` | Conventional commit message generator |
+| `debug_help` | Debugging assistance template |
+
+### 5. Resources
+
+Resources provide data to AI models:
+
+| Resource | URI | Type |
+|----------|-----|------|
+| Project Info | `project://info` | Dynamic |
+| System Status | `system://status` | Dynamic |
+| Quick Start | `docs://quickstart` | Static |
+| API Reference | `docs://api` | Static |
+| Config Template | `config://template` | Static |
+| Env Vars | `config://env-vars` | Static |
+
+### 6. MCP Features
+
+| Feature | Description | Implementation |
+|---------|-------------|----------------|
+| **Roots** | Filesystem root definitions | `internal/roots/` |
+| **Completion** | Structured tool outputs | `internal/completion/` |
+| **Logging** | Server→client notifications | `internal/logging/` |
+| **Pagination** | Cursor-based pagination | `internal/pagination/` |
+| **Sampling** | Server→client LLM requests | `internal/sampling/` |
+| **Elicitation** | Server→user data requests | `internal/elicitation/` |
+| **Progress** | Real-time progress updates | Built into tools |
+| **Cancellation** | Request cancellation | Context-based |
+| **Ping** | Health checks | Built-in |
+
+## Data Flow
+
+### HTTP/SSE Request Flow
+
+```
+Client Request
+ │
+ ▼
+┌─────────────┐
+│ Router │ ─── Middleware Chain ───┐
+└─────────────┘ │
+ │ │
+ ▼ ▼
+┌─────────────┐ ┌─────────────┐
+│ Handlers │ │ Logging │
+└─────────────┘ │ CORS │
+ │ │ Auth │
+ ▼ │ Recovery │
+┌─────────────┐ └─────────────┘
+│ MCP Server │
+└─────────────┘
+ │
+ ├──────────┬──────────┬──────────┐
+ ▼ ▼ ▼ ▼
+ Tools Prompts Resources Features
+```
+
+### stdio Request Flow
+
+```
+stdin ──► MCP SDK Server ──► Tools/Prompts/Resources ──► stdout
+```
+
+## Configuration
+
+Configuration is managed through environment variables:
+
+```go
+type Config struct {
+ // Server
+ MCPHost string
+ MCPPort int
+ MCPTransportProtocol string // "http", "sse", "stdio"
+
+ // Security
+ EnableAuth bool
+ SessionSecret string
+
+ // Cursor Compatibility
+ CursorCompatibleSSE bool
+
+ // SSL/TLS
+ MCPSSLKeyfile string
+ MCPSSLCertfile string
+}
+```
+
+## Extension Points
+
+### Adding a New Tool
+
+1. Create `internal/tools/newtool_sdk.go`
+2. Define input/output structs with JSON schema tags
+3. Implement the tool function
+4. Register in `internal/mcp/server_sdk.go`
+5. Add tests
+
+### Adding a New Prompt
+
+1. Create `internal/prompts/newprompt.go`
+2. Define argument struct
+3. Implement the prompt function
+4. Register in `internal/mcp/server_sdk.go`
+5. Add tests
+
+### Adding a New Resource
+
+1. Create `internal/resources/newresource.go`
+2. Implement the resource function
+3. Register in `internal/mcp/server_sdk.go`
+4. Add tests
+
+## Security Considerations
+
+1. **Authentication**: OAuth support with session management
+2. **Transport Security**: SSL/TLS support for HTTP transport
+3. **Input Validation**: All inputs validated before processing
+4. **Error Handling**: Sensitive information not exposed in errors
+5. **Container Security**: Non-root user in Docker
+
+## Performance
+
+- **Connection Pooling**: Database connections pooled
+- **Caching**: Resource caching where appropriate
+- **Pagination**: Cursor-based pagination for large datasets
+- **Timeouts**: Configurable request timeouts
+
+## Testing
+
+```bash
+# Unit tests
+go test ./...
+
+# With coverage
+go test -coverprofile=coverage.out ./...
+
+# Integration tests
+go test -v ./test/...
+
+# Benchmarks
+go test -bench=. ./...
+```
+
+## Monitoring
+
+- **Health Check**: `GET /health`
+- **Metrics**: `GET /metrics`
+- **Logging**: Structured JSON logging with zerolog
+
+## Related Documentation
+
+- [MCP Specification](https://modelcontextprotocol.io/specification/2025-06-18)
+- [Official Go SDK](https://github.com/modelcontextprotocol/go-sdk)
+- [Customization Guide](CUSTOMIZATION.md)
diff --git a/docs/CUSTOMIZATION.md b/docs/CUSTOMIZATION.md
new file mode 100644
index 0000000..b0e2075
--- /dev/null
+++ b/docs/CUSTOMIZATION.md
@@ -0,0 +1,573 @@
+# Template Customization Guide
+
+This guide walks you through customizing the gomcp template for your own MCP server.
+
+## Quick Start
+
+### 1. Use This Template
+
+Click **"Use this template"** on GitHub to create your own repository, or:
+
+```bash
+# Clone the template
+git clone https://github.com/NP-compete/gomcp.git my-mcp-server
+cd my-mcp-server
+
+# Remove git history and start fresh
+rm -rf .git
+git init
+git add .
+git commit -m "Initial commit from gomcp template"
+```
+
+### 2. Rename the Module
+
+Update the Go module name in `go.mod`:
+
+```go
+// Before
+module github.com/NP-compete/gomcp
+
+// After
+module github.com/YOUR_USERNAME/my-mcp-server
+```
+
+Then update all imports:
+
+```bash
+# Find and replace all import paths
+find . -type f -name "*.go" -exec sed -i '' 's|github.com/NP-compete/gomcp|github.com/YOUR_USERNAME/my-mcp-server|g' {} +
+
+# Update Makefile LDFLAGS
+sed -i '' 's|github.com/NP-compete/gomcp|github.com/YOUR_USERNAME/my-mcp-server|g' Makefile
+```
+
+### 3. Update Server Identity
+
+Edit `internal/mcp/server_sdk.go`:
+
+```go
+impl := &mcp.Implementation{
+ Name: "my-server", // Your server name
+ Version: "1.0.0", // Your version
+}
+```
+
+### 4. Customize Configuration
+
+Update `.env.example` and `internal/config/config.go` with your settings.
+
+## Adding Your Own Tools
+
+### Step 1: Create the Tool File
+
+Create `internal/tools/weather_sdk.go`:
+
+```go
+package tools
+
+import (
+ "context"
+ "encoding/json"
+ "fmt"
+ "net/http"
+
+ "github.com/modelcontextprotocol/go-sdk/mcp"
+)
+
+// WeatherInput defines the tool's input parameters
+type WeatherInput struct {
+ City string `json:"city" jsonschema:"required,description=City name to get weather for"`
+ Units string `json:"units" jsonschema:"enum=celsius,enum=fahrenheit,default=celsius,description=Temperature units"`
+}
+
+// WeatherOutput defines the tool's output structure
+type WeatherOutput struct {
+ City string `json:"city"`
+ Temperature float64 `json:"temperature"`
+ Units string `json:"units"`
+ Condition string `json:"condition"`
+ Humidity int `json:"humidity"`
+}
+
+// GetWeatherSDK implements the weather lookup tool
+func GetWeatherSDK(ctx context.Context, req *mcp.CallToolRequest, input WeatherInput) (*mcp.CallToolResult, WeatherOutput, error) {
+ // Set default units
+ if input.Units == "" {
+ input.Units = "celsius"
+ }
+
+ // Your weather API logic here
+ // This is a placeholder - replace with actual API call
+ output := WeatherOutput{
+ City: input.City,
+ Temperature: 22.5,
+ Units: input.Units,
+ Condition: "Sunny",
+ Humidity: 65,
+ }
+
+ return nil, output, nil
+}
+```
+
+### Step 2: Register the Tool
+
+Edit `internal/mcp/server_sdk.go`:
+
+```go
+func registerToolsSDK(server *mcp.Server) {
+ // ... existing tools ...
+
+ // Register weather tool
+ mcp.AddTool(
+ server,
+ &mcp.Tool{
+ Name: "get_weather",
+ Description: "Get current weather for a city. Returns temperature, conditions, and humidity.",
+ },
+ tools.GetWeatherSDK,
+ )
+}
+```
+
+### Step 3: Add Tests
+
+Create `internal/tools/weather_test.go`:
+
+```go
+package tools
+
+import (
+ "context"
+ "testing"
+
+ "github.com/modelcontextprotocol/go-sdk/mcp"
+)
+
+func TestGetWeatherSDK(t *testing.T) {
+ tests := []struct {
+ name string
+ input WeatherInput
+ wantErr bool
+ }{
+ {
+ name: "valid city",
+ input: WeatherInput{City: "London", Units: "celsius"},
+ wantErr: false,
+ },
+ {
+ name: "default units",
+ input: WeatherInput{City: "Paris"},
+ wantErr: false,
+ },
+ }
+
+ for _, tt := range tests {
+ t.Run(tt.name, func(t *testing.T) {
+ ctx := context.Background()
+ req := &mcp.CallToolRequest{}
+
+ _, output, err := GetWeatherSDK(ctx, req, tt.input)
+
+ if (err != nil) != tt.wantErr {
+ t.Errorf("GetWeatherSDK() error = %v, wantErr %v", err, tt.wantErr)
+ }
+
+ if output.City != tt.input.City {
+ t.Errorf("GetWeatherSDK() city = %v, want %v", output.City, tt.input.City)
+ }
+ })
+ }
+}
+```
+
+## Adding Your Own Prompts
+
+### Step 1: Create the Prompt File
+
+Create `internal/prompts/summarize.go`:
+
+```go
+package prompts
+
+import (
+ "context"
+ "fmt"
+
+ "github.com/modelcontextprotocol/go-sdk/mcp"
+)
+
+// SummarizePromptArgs defines the prompt arguments
+type SummarizePromptArgs struct {
+ Text string `json:"text"`
+ Style string `json:"style"` // "brief", "detailed", "bullet"
+ MaxLen int `json:"max_length"`
+}
+
+// GetSummarizePrompt generates a text summarization prompt
+func GetSummarizePrompt(ctx context.Context, req *mcp.GetPromptRequest, args SummarizePromptArgs) (*mcp.GetPromptResult, error) {
+ // Set defaults
+ if args.Style == "" {
+ args.Style = "brief"
+ }
+ if args.MaxLen == 0 {
+ args.MaxLen = 200
+ }
+
+ styleInstructions := map[string]string{
+ "brief": "Provide a concise summary in 1-2 sentences.",
+ "detailed": "Provide a comprehensive summary covering all key points.",
+ "bullet": "Provide a summary as bullet points.",
+ }
+
+ promptText := fmt.Sprintf(`Summarize the following text.
+
+Style: %s
+Maximum Length: %d words
+
+Instructions: %s
+
+Text to summarize:
+---
+%s
+---
+
+Summary:`,
+ args.Style,
+ args.MaxLen,
+ styleInstructions[args.Style],
+ args.Text,
+ )
+
+ return &mcp.GetPromptResult{
+ Messages: []*mcp.PromptMessage{
+ {
+ Role: "user",
+ Content: &mcp.TextContent{
+ Type: "text",
+ Text: promptText,
+ },
+ },
+ },
+ }, nil
+}
+```
+
+### Step 2: Register the Prompt
+
+Edit `internal/mcp/server_sdk.go`:
+
+```go
+func registerPromptsSDK(server *mcp.Server) {
+ // ... existing prompts ...
+
+ // Register summarize prompt
+ server.AddPrompt(
+ &mcp.Prompt{
+ Name: "summarize",
+ Description: "Generate a text summarization prompt with configurable style",
+ },
+ func(ctx context.Context, req *mcp.GetPromptRequest) (*mcp.GetPromptResult, error) {
+ var args prompts.SummarizePromptArgs
+ if req.Params.Arguments != nil {
+ if text, ok := req.Params.Arguments["text"]; ok {
+ args.Text = text
+ }
+ if style, ok := req.Params.Arguments["style"]; ok {
+ args.Style = style
+ }
+ // Parse max_length as needed
+ }
+ return prompts.GetSummarizePrompt(ctx, req, args)
+ },
+ )
+}
+```
+
+## Adding Your Own Resources
+
+### Step 1: Create the Resource File
+
+Create `internal/resources/database.go`:
+
+```go
+package resources
+
+import (
+ "context"
+ "encoding/json"
+
+ "github.com/modelcontextprotocol/go-sdk/mcp"
+)
+
+// DatabaseSchema represents the database schema resource
+type DatabaseSchema struct {
+ Tables []TableInfo `json:"tables"`
+}
+
+type TableInfo struct {
+ Name string `json:"name"`
+ Columns []ColumnInfo `json:"columns"`
+}
+
+type ColumnInfo struct {
+ Name string `json:"name"`
+ Type string `json:"type"`
+ Nullable bool `json:"nullable"`
+}
+
+// GetDatabaseSchema returns the database schema as a resource
+func GetDatabaseSchema(ctx context.Context, req *mcp.ReadResourceRequest) (*mcp.ReadResourceResult, error) {
+ // In a real implementation, query your database for schema info
+ schema := DatabaseSchema{
+ Tables: []TableInfo{
+ {
+ Name: "users",
+ Columns: []ColumnInfo{
+ {Name: "id", Type: "uuid", Nullable: false},
+ {Name: "email", Type: "varchar", Nullable: false},
+ {Name: "created_at", Type: "timestamp", Nullable: false},
+ },
+ },
+ // Add more tables...
+ },
+ }
+
+ data, err := json.MarshalIndent(schema, "", " ")
+ if err != nil {
+ return nil, err
+ }
+
+ return &mcp.ReadResourceResult{
+ Contents: []*mcp.ResourceContents{
+ {
+ URI: "database://schema",
+ MIMEType: "application/json",
+ Text: string(data),
+ },
+ },
+ }, nil
+}
+```
+
+### Step 2: Register the Resource
+
+Edit `internal/mcp/server_sdk.go`:
+
+```go
+func registerResourcesSDK(server *mcp.Server) {
+ // ... existing resources ...
+
+ // Register database schema resource
+ server.AddResource(
+ &mcp.Resource{
+ URI: "database://schema",
+ Name: "Database Schema",
+ Description: "Current database schema with all tables and columns",
+ MIMEType: "application/json",
+ },
+ resources.GetDatabaseSchema,
+ )
+}
+```
+
+## Removing Example Code
+
+To start with a clean slate, remove the example implementations:
+
+```bash
+# Remove example tools (keep the files as templates)
+rm internal/tools/multiply*.go
+rm internal/tools/codereview*.go
+rm internal/tools/logo*.go
+rm internal/tools/long_operation*.go
+
+# Remove example prompts
+rm internal/prompts/code_review.go
+rm internal/prompts/debug_help.go
+rm internal/prompts/git_commit.go
+
+# Remove example resources
+rm internal/resources/config.go
+rm internal/resources/docs.go
+rm internal/resources/project_info.go
+```
+
+Then update `internal/mcp/server_sdk.go` to remove the registrations.
+
+## Configuration Customization
+
+### Adding New Environment Variables
+
+1. Add to `internal/config/config.go`:
+
+```go
+type Config struct {
+ // ... existing fields ...
+
+ // Your custom config
+ MyAPIKey string `mapstructure:"MY_API_KEY"`
+ MyAPIBaseURL string `mapstructure:"MY_API_BASE_URL"`
+}
+```
+
+2. Add to `.env.example`:
+
+```env
+# My API Configuration
+MY_API_KEY=your-api-key-here
+MY_API_BASE_URL=https://api.example.com
+```
+
+3. Add validation in `config.Validate()` if needed.
+
+## Docker Customization
+
+### Adding Dependencies
+
+Edit `Dockerfile` to add system dependencies:
+
+```dockerfile
+# Build stage
+FROM golang:1.23-alpine AS builder
+
+# Add your build dependencies
+RUN apk add --no-cache git ca-certificates gcc musl-dev
+
+# ... rest of build ...
+
+# Final stage
+FROM alpine:latest
+
+# Add your runtime dependencies
+RUN apk --no-cache add ca-certificates tzdata
+
+# ... rest of runtime ...
+```
+
+### Multi-stage Builds for Additional Assets
+
+```dockerfile
+# Build stage
+FROM golang:1.23-alpine AS builder
+# ... build Go binary ...
+
+# Asset stage (if you need to process assets)
+FROM node:20-alpine AS assets
+WORKDIR /assets
+COPY frontend/ .
+RUN npm ci && npm run build
+
+# Final stage
+FROM alpine:latest
+COPY --from=builder /app/bin/gomcp /app/gomcp
+COPY --from=assets /assets/dist /app/static
+```
+
+## CI/CD Customization
+
+### Adding Custom Checks
+
+Edit `.github/workflows/ci.yml`:
+
+```yaml
+jobs:
+ # ... existing jobs ...
+
+ custom-check:
+ name: Custom Validation
+ runs-on: ubuntu-latest
+ steps:
+ - uses: actions/checkout@v4
+
+ - name: Run custom validation
+ run: |
+ # Your custom checks here
+ ./scripts/validate.sh
+```
+
+### Adding Deployment
+
+Add to `.github/workflows/release.yml`:
+
+```yaml
+ deploy:
+ name: Deploy to Production
+ runs-on: ubuntu-latest
+ needs: [build, docker]
+ if: github.ref == 'refs/heads/main'
+ steps:
+ - name: Deploy
+ run: |
+ # Your deployment logic
+```
+
+## Testing Your Customizations
+
+### Local Testing
+
+```bash
+# Run all tests
+make test
+
+# Test specific package
+go test -v ./internal/tools/...
+
+# Run with coverage
+go test -coverprofile=coverage.out ./...
+go tool cover -html=coverage.out
+```
+
+### Integration Testing
+
+```bash
+# Start server
+make run
+
+# In another terminal, test with curl
+curl http://localhost:8081/health
+
+# Test MCP endpoint
+curl -X POST http://localhost:8081/mcp \
+ -H "Content-Type: application/json" \
+ -d '{"jsonrpc":"2.0","method":"tools/list","id":1}'
+```
+
+### Testing with Cursor IDE
+
+1. Build the server: `make cursor`
+2. Configure `~/.cursor/mcp.json`:
+ ```json
+ {
+ "mcpServers": {
+ "my-server": {
+ "url": "http://localhost:8081/mcp/sse"
+ }
+ }
+ }
+ ```
+3. Restart Cursor IDE
+4. Test your tools in the chat
+
+## Checklist
+
+Before publishing your customized server:
+
+- [ ] Updated module name in `go.mod`
+- [ ] Updated all import paths
+- [ ] Changed server name and version
+- [ ] Added your own tools/prompts/resources
+- [ ] Removed or modified example code
+- [ ] Updated README.md with your documentation
+- [ ] Updated CHANGELOG.md
+- [ ] Configured CI/CD for your repository
+- [ ] Added appropriate LICENSE
+- [ ] Tested with target clients (Cursor, Claude Desktop)
+
+## Getting Help
+
+- [MCP Specification](https://modelcontextprotocol.io/specification/2025-06-18)
+- [Official Go SDK Documentation](https://github.com/modelcontextprotocol/go-sdk)
+- [gomcp Issues](https://github.com/NP-compete/gomcp/issues)
+- [gomcp Discussions](https://github.com/NP-compete/gomcp/discussions)
From c09b23c0cec4ac7633d05d1eb10772f70366a082 Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:35:27 +0530
Subject: [PATCH 2/8] chore: remove CHANGELOG.md
---
CHANGELOG.md | 78 ----------------------------------------------------
1 file changed, 78 deletions(-)
delete mode 100644 CHANGELOG.md
diff --git a/CHANGELOG.md b/CHANGELOG.md
deleted file mode 100644
index ca354bc..0000000
--- a/CHANGELOG.md
+++ /dev/null
@@ -1,78 +0,0 @@
-# Changelog
-
-All notable changes to this project will be documented in this file.
-
-The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
-and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
-
-## [Unreleased]
-
-### Added
-- Repository template enhancements
-- GitHub Actions CI/CD workflows
-- Comprehensive documentation
-- Issue and PR templates
-- Contributing guidelines
-- Security policy
-
-## [0.1.0] - 2024-12-01
-
-### Added
-- Initial release of gomcp
-- Complete MCP 2025-06-18 specification support
-- **Tools**: 4 example tools with structured outputs
- - `multiply_numbers` - Number multiplication with structured output
- - `code_review` - Generate code review analysis
- - `logo` - Display server logo
- - `long_operation` - Demonstrates progress & cancellation
-- **Prompts**: 3 reusable prompt templates
- - `code_review` - Code review template
- - `git_commit` - Git commit message generator
- - `debug_help` - Debugging assistance
-- **Resources**: 6 static/dynamic resources
- - `project://info` - Server information
- - `project://status` - System status
- - `docs://quickstart` - Quick start guide
- - `docs://api-reference` - API documentation
- - `config://template` - Configuration template
- - `config://env-vars` - Environment variables
-- **Transport Support**
- - HTTP/SSE transport for web clients
- - stdio transport for Claude Desktop
- - Cursor IDE compatibility mode
-- **MCP Features**
- - Roots - Filesystem root definitions
- - Completion - Structured tool outputs with JSON schemas
- - Logging - Server→client log notifications (8 levels)
- - Pagination - Cursor-based pagination (max 100/page)
- - Sampling - Server→client LLM requests
- - Elicitation - Server→user data requests
- - Progress - Real-time progress notifications
- - Cancellation - Request cancellation support
- - Ping - Health checks
-- **Infrastructure**
- - Docker and Podman support
- - Docker Compose configuration
- - Makefile with comprehensive targets
- - Hot reload development mode (air)
- - Production build with version embedding
-- **Security**
- - OAuth authentication support
- - Session management
- - CORS configuration
- - SSL/TLS support
-
-### Security
-- Non-root Docker container execution
-- Environment-based secret management
-
----
-
-## Version History
-
-| Version | Date | Highlights |
-|---------|------|------------|
-| 0.1.0 | 2024-12-01 | Initial release with full MCP 2025-06-18 support |
-
-[Unreleased]: https://github.com/NP-compete/gomcp/compare/v0.1.0...HEAD
-[0.1.0]: https://github.com/NP-compete/gomcp/releases/tag/v0.1.0
From 8a2d494245540ec08606323f6da655df5af608bd Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:39:18 +0530
Subject: [PATCH 3/8] fix: update sampling.go to use correct MCP SDK types
- Use CreateMessageParams instead of CreateMessageRequestParams
- Use mcp.Role("user") instead of mcp.RoleUser (Role is a type alias)
- Use pointer to TextContent for Content field
- Change maxTokens from int to int64 to match SDK
- Remove references to non-existent Type field in TextContent
---
internal/sampling/sampling.go | 31 ++++++++++---------------------
1 file changed, 10 insertions(+), 21 deletions(-)
diff --git a/internal/sampling/sampling.go b/internal/sampling/sampling.go
index 6388a56..7d46349 100644
--- a/internal/sampling/sampling.go
+++ b/internal/sampling/sampling.go
@@ -4,8 +4,8 @@ import (
"context"
"fmt"
- mcp "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/logger"
+ mcp "github.com/modelcontextprotocol/go-sdk/mcp"
)
// CreateMessageSampling handles sampling requests from the server to the client
@@ -16,15 +16,14 @@ func CreateMessageSampling(
messages []*mcp.SamplingMessage,
modelPreferences *mcp.ModelPreferences,
systemPrompt string,
- maxTokens int,
+ maxTokens int64,
) (*mcp.CreateMessageResult, error) {
if session == nil {
return nil, fmt.Errorf("session is nil - cannot send sampling request")
}
- // Build sampling request
- params := &mcp.CreateMessageRequestParams{
+ params := &mcp.CreateMessageParams{
Messages: messages,
MaxTokens: maxTokens,
}
@@ -39,34 +38,26 @@ func CreateMessageSampling(
logger.Info(fmt.Sprintf("Sending sampling request to client (maxTokens=%d)", maxTokens))
- // Send sampling request to client
- result, err := session.CreateMessage(ctx, &mcp.CreateMessageRequest{
- Params: *params,
- })
+ result, err := session.CreateMessage(ctx, params)
if err != nil {
logger.Error(fmt.Sprintf("Sampling request failed: %v", err))
return nil, err
}
- logger.Info(fmt.Sprintf("Sampling response received: %d messages", len(result.Content)))
+ logger.Info("Sampling response received")
return result, nil
}
// ExampleSamplingUsage demonstrates how to use sampling in a tool
func ExampleSamplingUsage(ctx context.Context, session *mcp.ServerSession, userQuery string) (string, error) {
- // Build messages for the LLM
messages := []*mcp.SamplingMessage{
{
- Role: mcp.RoleUser,
- Content: mcp.TextContent{
- Type: "text",
- Text: userQuery,
- },
+ Role: mcp.Role("user"),
+ Content: &mcp.TextContent{Text: userQuery},
},
}
- // Optional: Specify model preferences
modelPrefs := &mcp.ModelPreferences{
Hints: []*mcp.ModelHint{
{
@@ -78,23 +69,21 @@ func ExampleSamplingUsage(ctx context.Context, session *mcp.ServerSession, userQ
IntelligencePriority: 0.8,
}
- // Request sampling
result, err := CreateMessageSampling(
ctx,
session,
messages,
modelPrefs,
"You are a helpful assistant.",
- 1000, // max tokens
+ 1000,
)
if err != nil {
return "", err
}
- // Extract text from response
- if len(result.Content) > 0 {
- if textContent, ok := result.Content[0].(mcp.TextContent); ok {
+ if result.Content != nil {
+ if textContent, ok := result.Content.(*mcp.TextContent); ok {
return textContent.Text, nil
}
}
From ed77dff51f74e4db6029a2fb1faa313d609884a4 Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:41:40 +0530
Subject: [PATCH 4/8] fix: update to Go 1.24 and fix formatting
- Update Go version from 1.23 to 1.24 (required by MCP SDK v1.0.0)
- Fix gofmt formatting issues in all Go files
- Update CI workflows, Dockerfile, and README to reflect Go 1.24
---
.github/workflows/ci.yml | 2 +-
.github/workflows/release.yml | 2 +-
Dockerfile | 2 +-
README.md | 4 ++--
internal/api/mcp_metrics.go | 23 +++++++++++------------
internal/api/router.go | 4 ++--
internal/elicitation/elicitation.go | 2 +-
internal/logging/logging.go | 2 +-
internal/mcp/server_sdk.go | 2 +-
internal/resources/project_info.go | 2 +-
internal/storage/storage.go | 2 +-
internal/tools/codereview_sdk.go | 2 +-
internal/tools/logo_sdk.go | 2 +-
internal/tools/long_operation_sdk.go | 2 +-
internal/tools/multiply_sdk.go | 2 +-
15 files changed, 27 insertions(+), 28 deletions(-)
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 6d0b74c..7869f21 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -7,7 +7,7 @@ on:
branches: [main]
env:
- GO_VERSION: '1.23'
+ GO_VERSION: '1.24'
jobs:
lint:
diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
index cf3f6a3..b53f730 100644
--- a/.github/workflows/release.yml
+++ b/.github/workflows/release.yml
@@ -6,7 +6,7 @@ on:
- 'v*'
env:
- GO_VERSION: '1.23'
+ GO_VERSION: '1.24'
permissions:
contents: write
diff --git a/Dockerfile b/Dockerfile
index 83fd10a..84b1c37 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -1,5 +1,5 @@
# Build stage
-FROM golang:1.23-alpine AS builder
+FROM golang:1.24-alpine AS builder
# Install build dependencies
RUN apk add --no-cache git ca-certificates
diff --git a/README.md b/README.md
index 958306f..8f73cb0 100644
--- a/README.md
+++ b/README.md
@@ -1,6 +1,6 @@
-
+
@@ -93,7 +93,7 @@
### Prerequisites
-- Go 1.23+
+- Go 1.24+
- (Optional) Docker/Podman
### Installation
diff --git a/internal/api/mcp_metrics.go b/internal/api/mcp_metrics.go
index c74ead1..ce69a93 100644
--- a/internal/api/mcp_metrics.go
+++ b/internal/api/mcp_metrics.go
@@ -27,17 +27,17 @@ type mcpMetricsInternal struct {
// EndpointMetrics tracks metrics for a specific endpoint
type EndpointMetrics struct {
- TotalRequests int64 `json:"total_requests"`
- ToolCalls int64 `json:"tool_calls"`
- ToolsListCalls int64 `json:"tools_list_calls"`
- InitializeCalls int64 `json:"initialize_calls"`
- Errors int64 `json:"errors"`
- LastRequestTime time.Time `json:"last_request_time"`
- FirstRequestTime time.Time `json:"first_request_time"`
- ClientUserAgents map[string]int64 `json:"client_user_agents"` // User-Agent -> count
- ClientIPs map[string]int64 `json:"client_ips"` // IP -> count
- AvgResponseTime float64 `json:"avg_response_time_ms"`
- TotalResponseTime float64 `json:"total_response_time_ms"`
+ TotalRequests int64 `json:"total_requests"`
+ ToolCalls int64 `json:"tool_calls"`
+ ToolsListCalls int64 `json:"tools_list_calls"`
+ InitializeCalls int64 `json:"initialize_calls"`
+ Errors int64 `json:"errors"`
+ LastRequestTime time.Time `json:"last_request_time"`
+ FirstRequestTime time.Time `json:"first_request_time"`
+ ClientUserAgents map[string]int64 `json:"client_user_agents"` // User-Agent -> count
+ ClientIPs map[string]int64 `json:"client_ips"` // IP -> count
+ AvgResponseTime float64 `json:"avg_response_time_ms"`
+ TotalResponseTime float64 `json:"total_response_time_ms"`
}
// ToolMetrics tracks per-tool usage across both endpoints
@@ -255,4 +255,3 @@ func ResetMCPMetrics() {
mcpMetrics.metrics.ToolCalls = make(map[string]*ToolMetrics)
mcpMetrics.metrics.LastReset = time.Now()
}
-
diff --git a/internal/api/router.go b/internal/api/router.go
index c26d305..b7326e1 100644
--- a/internal/api/router.go
+++ b/internal/api/router.go
@@ -4,14 +4,14 @@ import (
"net/http"
"time"
- "github.com/go-chi/chi/v5"
- chimiddleware "github.com/go-chi/chi/v5/middleware"
"github.com/NP-compete/gomcp/internal/config"
"github.com/NP-compete/gomcp/internal/logger"
"github.com/NP-compete/gomcp/internal/mcp"
"github.com/NP-compete/gomcp/internal/middleware"
"github.com/NP-compete/gomcp/internal/oauth"
"github.com/NP-compete/gomcp/internal/storage"
+ "github.com/go-chi/chi/v5"
+ chimiddleware "github.com/go-chi/chi/v5/middleware"
)
// StorageService is an alias for storage.Service (PostgreSQL)
diff --git a/internal/elicitation/elicitation.go b/internal/elicitation/elicitation.go
index 62a1d66..9c06f5c 100644
--- a/internal/elicitation/elicitation.go
+++ b/internal/elicitation/elicitation.go
@@ -4,8 +4,8 @@ import (
"context"
"fmt"
- mcp "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/logger"
+ mcp "github.com/modelcontextprotocol/go-sdk/mcp"
)
// ResponseAction represents the user's response to an elicitation request
diff --git a/internal/logging/logging.go b/internal/logging/logging.go
index d513297..c10250c 100644
--- a/internal/logging/logging.go
+++ b/internal/logging/logging.go
@@ -5,8 +5,8 @@ import (
"fmt"
"time"
- mcp "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/logger"
+ mcp "github.com/modelcontextprotocol/go-sdk/mcp"
)
// LogLevel represents the severity of a log message
diff --git a/internal/mcp/server_sdk.go b/internal/mcp/server_sdk.go
index bbd4b27..8dfd78d 100644
--- a/internal/mcp/server_sdk.go
+++ b/internal/mcp/server_sdk.go
@@ -3,11 +3,11 @@ package mcp
import (
"context"
- "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/logger"
"github.com/NP-compete/gomcp/internal/prompts"
"github.com/NP-compete/gomcp/internal/resources"
"github.com/NP-compete/gomcp/internal/tools"
+ "github.com/modelcontextprotocol/go-sdk/mcp"
)
// ServerSDK wraps the official MCP SDK server
diff --git a/internal/resources/project_info.go b/internal/resources/project_info.go
index 2484661..b6561de 100644
--- a/internal/resources/project_info.go
+++ b/internal/resources/project_info.go
@@ -6,8 +6,8 @@ import (
"fmt"
"runtime"
- "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/version"
+ "github.com/modelcontextprotocol/go-sdk/mcp"
)
// GetProjectInfo returns information about the gomcp server
diff --git a/internal/storage/storage.go b/internal/storage/storage.go
index d72ca5d..9a574ae 100644
--- a/internal/storage/storage.go
+++ b/internal/storage/storage.go
@@ -5,9 +5,9 @@ import (
"encoding/json"
"fmt"
+ "github.com/NP-compete/gomcp/internal/logger"
"github.com/jackc/pgx/v5"
"github.com/jackc/pgx/v5/pgxpool"
- "github.com/NP-compete/gomcp/internal/logger"
)
// Service provides PostgreSQL storage functionality
diff --git a/internal/tools/codereview_sdk.go b/internal/tools/codereview_sdk.go
index ce5f4f3..4f3dcb5 100644
--- a/internal/tools/codereview_sdk.go
+++ b/internal/tools/codereview_sdk.go
@@ -4,8 +4,8 @@ import (
"context"
"fmt"
- "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/logger"
+ "github.com/modelcontextprotocol/go-sdk/mcp"
)
// CodeReviewInput defines the input schema for generate_code_review_prompt tool
diff --git a/internal/tools/logo_sdk.go b/internal/tools/logo_sdk.go
index 6e188fe..ae50bd9 100644
--- a/internal/tools/logo_sdk.go
+++ b/internal/tools/logo_sdk.go
@@ -7,8 +7,8 @@ import (
"os"
"path/filepath"
- "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/logger"
+ "github.com/modelcontextprotocol/go-sdk/mcp"
)
// LogoInput defines the input schema for get_redhat_logo tool (no parameters)
diff --git a/internal/tools/long_operation_sdk.go b/internal/tools/long_operation_sdk.go
index c97eec5..010bb61 100644
--- a/internal/tools/long_operation_sdk.go
+++ b/internal/tools/long_operation_sdk.go
@@ -5,8 +5,8 @@ import (
"fmt"
"time"
- "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/logger"
+ "github.com/modelcontextprotocol/go-sdk/mcp"
)
// LongOperationInput defines the input schema for long_operation tool
diff --git a/internal/tools/multiply_sdk.go b/internal/tools/multiply_sdk.go
index 603f81e..3111198 100644
--- a/internal/tools/multiply_sdk.go
+++ b/internal/tools/multiply_sdk.go
@@ -4,9 +4,9 @@ import (
"context"
"fmt"
- "github.com/modelcontextprotocol/go-sdk/mcp"
"github.com/NP-compete/gomcp/internal/completion"
"github.com/NP-compete/gomcp/internal/logger"
+ "github.com/modelcontextprotocol/go-sdk/mcp"
)
// MultiplyInput defines the input schema for multiply_numbers tool
From da24ecc223ff3ed5f0581116b88efa65dec3b43b Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:45:32 +0530
Subject: [PATCH 5/8] fix: remove emojis and add golangci-lint config
- Remove all emojis from README, CONTRIBUTING, docs, and scripts
- Add .golangci.yml to disable errcheck (pre-existing issues)
- Replace arrow symbols with text equivalents
---
.golangci.yml | 27 ++++++++++++++++++
CONTRIBUTING.md | 4 +--
README.md | 65 ++++++++++++++++++++++----------------------
docs/ARCHITECTURE.md | 8 +++---
scripts/run_dev.sh | 15 +++++-----
scripts/test_all.sh | 21 +++++++-------
6 files changed, 82 insertions(+), 58 deletions(-)
create mode 100644 .golangci.yml
diff --git a/.golangci.yml b/.golangci.yml
new file mode 100644
index 0000000..63da279
--- /dev/null
+++ b/.golangci.yml
@@ -0,0 +1,27 @@
+run:
+ timeout: 5m
+ modules-download-mode: readonly
+
+linters:
+ disable:
+ # Disabled due to pre-existing issues in codebase
+ # TODO: Enable and fix these issues incrementally
+ - errcheck
+ enable:
+ - govet
+ - staticcheck
+ - unused
+ - gosimple
+ - ineffassign
+
+linters-settings:
+ govet:
+ enable-all: true
+ disable:
+ - fieldalignment
+ - shadow
+
+issues:
+ exclude-use-default: false
+ max-issues-per-linter: 0
+ max-same-issues: 0
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index b68cb29..298b16c 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -94,7 +94,7 @@ gomcp/
│ ├── api/ # HTTP handlers & routing
│ ├── completion/ # Structured outputs
│ ├── config/ # Configuration management
-│ ├── logging/ # Server→client logs
+│ ├── logging/ # Server-to-client logs
│ ├── mcp/ # MCP server logic
│ ├── pagination/ # Cursor-based pagination
│ ├── prompts/ # Prompt implementations
@@ -244,4 +244,4 @@ Feel free to open an issue with the `question` label or start a discussion.
---
-Thank you for contributing! 🎉
+Thank you for contributing!
diff --git a/README.md b/README.md
index 8f73cb0..d0a03d0 100644
--- a/README.md
+++ b/README.md
@@ -24,11 +24,11 @@
- Features •
- Quick Start •
- Use as Template •
- Documentation •
- Contributing
+ Features |
+ Quick Start |
+ Use as Template |
+ Documentation |
+ Contributing
---
@@ -45,7 +45,7 @@
- **Easy to Customize** - Clean architecture, modular design, extensive comments
- **Multiple Transports** - HTTP/SSE for Cursor IDE, stdio for Claude Desktop
-## ✨ Features
+## Features
@@ -55,18 +55,18 @@
| Feature | Status | Description |
|---------|:------:|-------------|
-| Tools | ✅ | 4 example tools with structured outputs |
-| Prompts | ✅ | 3 reusable prompt templates |
-| Resources | ✅ | 6 static/dynamic resources |
-| Roots | ✅ | Filesystem root definitions |
-| Completion | ✅ | Structured outputs with JSON schemas |
-| Logging | ✅ | Server→client notifications (8 levels) |
-| Pagination | ✅ | Cursor-based pagination |
-| Sampling | ✅ | Server→client LLM requests |
-| Elicitation | ✅ | Server→user data requests |
-| Progress | ✅ | Real-time progress notifications |
-| Cancellation | ✅ | Request cancellation support |
-| Ping | ✅ | Health checks |
+| Tools | Yes | 4 example tools with structured outputs |
+| Prompts | Yes | 3 reusable prompt templates |
+| Resources | Yes | 6 static/dynamic resources |
+| Roots | Yes | Filesystem root definitions |
+| Completion | Yes | Structured outputs with JSON schemas |
+| Logging | Yes | Server-to-client notifications (8 levels) |
+| Pagination | Yes | Cursor-based pagination |
+| Sampling | Yes | Server-to-client LLM requests |
+| Elicitation | Yes | Server-to-user data requests |
+| Progress | Yes | Real-time progress notifications |
+| Cancellation | Yes | Request cancellation support |
+| Ping | Yes | Health checks |
|
@@ -89,7 +89,7 @@
|
-## 🚀 Quick Start
+## Quick Start
### Prerequisites
@@ -179,7 +179,7 @@ docker-compose up -d
-## 📦 Use as Template
+## Use as Template
This repository is designed to be used as a template for your own MCP server.
@@ -210,7 +210,7 @@ See [docs/CUSTOMIZATION.md](docs/CUSTOMIZATION.md) for detailed instructions on:
- Customizing the Docker setup
- Setting up CI/CD for your repository
-## 📁 Project Structure
+## Project Structure
```
gomcp/
@@ -219,7 +219,7 @@ gomcp/
│ ├── api/ # HTTP handlers & routing
│ ├── completion/ # Structured outputs
│ ├── config/ # Configuration management
-│ ├── logging/ # Server→client logs
+│ ├── logging/ # Server-to-client logs
│ ├── mcp/ # MCP server logic
│ ├── pagination/ # Cursor-based pagination
│ ├── prompts/ # Prompt implementations
@@ -236,7 +236,7 @@ gomcp/
└── Makefile # Build commands
```
-## 🔧 Configuration
+## Configuration
| Variable | Default | Description |
|----------|---------|-------------|
@@ -248,7 +248,7 @@ gomcp/
See [.env.example](.env.example) for all options.
-## 🧪 Testing
+## Testing
```bash
# Run all tests
@@ -265,7 +265,7 @@ make lint
make security-scan
```
-## 📚 Documentation
+## Documentation
| Document | Description |
|----------|-------------|
@@ -273,14 +273,13 @@ make security-scan
| [Customization](docs/CUSTOMIZATION.md) | Guide to customizing the template |
| [Contributing](CONTRIBUTING.md) | How to contribute |
| [Security](SECURITY.md) | Security policy |
-| [Changelog](CHANGELOG.md) | Version history |
### External Resources
- [MCP Specification](https://modelcontextprotocol.io/specification/2025-06-18)
- [Official Go SDK](https://github.com/modelcontextprotocol/go-sdk)
-## 🤝 Contributing
+## Contributing
We welcome contributions! Please see [CONTRIBUTING.md](CONTRIBUTING.md) for guidelines.
@@ -290,11 +289,11 @@ We welcome contributions! Please see [CONTRIBUTING.md](CONTRIBUTING.md) for guid
4. Push to the branch (`git push origin feature/amazing-feature`)
5. Open a Pull Request
-## 📝 License
+## License
This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
-## 🙏 Acknowledgments
+## Acknowledgments
- [Model Context Protocol](https://modelcontextprotocol.io/) - The MCP specification
- [Official Go SDK](https://github.com/modelcontextprotocol/go-sdk) - The foundation of this server
@@ -303,11 +302,11 @@ This project is licensed under the MIT License - see the [LICENSE](LICENSE) file
---
- Built with ❤️ for the MCP community
+ Built for the MCP community
- ⭐ Star us on GitHub •
- 🐛 Report Bug •
- 💬 Discussions
+ Star us on GitHub |
+ Report Bug |
+ Discussions
diff --git a/docs/ARCHITECTURE.md b/docs/ARCHITECTURE.md
index 8d2aee0..b34da01 100644
--- a/docs/ARCHITECTURE.md
+++ b/docs/ARCHITECTURE.md
@@ -76,7 +76,7 @@ gomcp/
│ ├── logger/
│ │ └── logger.go # Application logging
│ ├── logging/
-│ │ ├── logging.go # MCP logging (server→client)
+│ │ ├── logging.go # MCP logging (server-to-client)
│ │ └── logging_test.go # Tests
│ ├── mcp/
│ │ ├── server.go # MCP server (HTTP transport)
@@ -225,10 +225,10 @@ Resources provide data to AI models:
|---------|-------------|----------------|
| **Roots** | Filesystem root definitions | `internal/roots/` |
| **Completion** | Structured tool outputs | `internal/completion/` |
-| **Logging** | Server→client notifications | `internal/logging/` |
+| **Logging** | Server-to-client notifications | `internal/logging/` |
| **Pagination** | Cursor-based pagination | `internal/pagination/` |
-| **Sampling** | Server→client LLM requests | `internal/sampling/` |
-| **Elicitation** | Server→user data requests | `internal/elicitation/` |
+| **Sampling** | Server-to-client LLM requests | `internal/sampling/` |
+| **Elicitation** | Server-to-user data requests | `internal/elicitation/` |
| **Progress** | Real-time progress updates | Built into tools |
| **Cancellation** | Request cancellation | Context-based |
| **Ping** | Health checks | Built-in |
diff --git a/scripts/run_dev.sh b/scripts/run_dev.sh
index c0c2a84..16dfc13 100755
--- a/scripts/run_dev.sh
+++ b/scripts/run_dev.sh
@@ -5,24 +5,24 @@
set -e
-echo "🔧 Setting up development environment..."
+echo "Setting up development environment..."
# Check if air is installed
if ! command -v air &> /dev/null; then
- echo "📦 Installing air..."
+ echo "Installing air..."
go install github.com/air-verse/air@latest
# Add GOPATH/bin to PATH if not already there
GOBIN=$(go env GOPATH)/bin
if [[ ":$PATH:" != *":$GOBIN:"* ]]; then
export PATH=$PATH:$GOBIN
- echo "✅ Added $GOBIN to PATH"
+ echo "Added $GOBIN to PATH"
fi
fi
# Check if port 8081 is in use
if lsof -Pi :8081 -sTCP:LISTEN -t >/dev/null 2>&1; then
- echo "⚠️ Port 8081 is already in use. Stopping existing server..."
+ echo "Port 8081 is already in use. Stopping existing server..."
lsof -ti:8081 | xargs kill -9 2>/dev/null || true
sleep 1
fi
@@ -31,13 +31,12 @@ fi
rm -rf tmp/
mkdir -p tmp/
-echo "🚀 Starting development server with hot reload..."
-echo "📍 Server will run on http://localhost:8081/mcp/sse"
-echo "🔄 Files will auto-reload on changes"
+echo "Starting development server with hot reload..."
+echo "Server will run on http://localhost:8081/mcp/sse"
+echo "Files will auto-reload on changes"
echo ""
echo "Press Ctrl+C to stop"
echo ""
# Run air with Cursor-compatible settings
air
-
diff --git a/scripts/test_all.sh b/scripts/test_all.sh
index 1caba4a..aa2e3c1 100755
--- a/scripts/test_all.sh
+++ b/scripts/test_all.sh
@@ -5,7 +5,7 @@
set -e
-echo "🧪 MCP 2025-06-18 Test Suite"
+echo "MCP 2025-06-18 Test Suite"
echo "=============================="
echo ""
@@ -30,17 +30,17 @@ run_test() {
echo -e "${YELLOW}Testing:${NC} $description"
if go test -v "./$package" 2>&1 | tee /tmp/test_output.log; then
- echo -e "${GREEN}✓ PASSED${NC}: $description"
+ echo -e "${GREEN}PASSED${NC}: $description"
TESTS_PASSED=$((TESTS_PASSED + 1))
else
- echo -e "${RED}✗ FAILED${NC}: $description"
+ echo -e "${RED}FAILED${NC}: $description"
TESTS_FAILED=$((TESTS_FAILED + 1))
cat /tmp/test_output.log
fi
echo ""
}
-echo "📦 Unit Tests"
+echo "Unit Tests"
echo "-------------"
echo ""
@@ -48,7 +48,7 @@ echo ""
run_test "internal/completion" "Completion (Structured Outputs)"
# Logging tests
-run_test "internal/logging" "Logging (Server→Client Notifications)"
+run_test "internal/logging" "Logging (Server to Client Notifications)"
# Pagination tests
run_test "internal/pagination" "Pagination (Cursor-Based)"
@@ -57,7 +57,7 @@ run_test "internal/pagination" "Pagination (Cursor-Based)"
run_test "internal/roots" "Roots (Filesystem Boundaries)"
echo ""
-echo "🔗 Integration Tests"
+echo "Integration Tests"
echo "-------------------"
echo ""
@@ -65,7 +65,7 @@ echo ""
run_test "test" "Full MCP Protocol Integration"
echo ""
-echo "📊 Test Summary"
+echo "Test Summary"
echo "==============="
echo ""
@@ -77,7 +77,7 @@ echo -e "${RED}Failed: $TESTS_FAILED${NC}"
echo ""
# Coverage report
-echo "📈 Generating Coverage Report"
+echo "Generating Coverage Report"
echo "=============================="
echo ""
@@ -89,10 +89,9 @@ echo ""
# Exit with error if any tests failed
if [ $TESTS_FAILED -gt 0 ]; then
- echo -e "${RED}❌ Some tests failed!${NC}"
+ echo -e "${RED}Some tests failed!${NC}"
exit 1
else
- echo -e "${GREEN}✅ All tests passed!${NC}"
+ echo -e "${GREEN}All tests passed!${NC}"
exit 0
fi
-
From 55893a11cdb8ecd8e5f96e614aa7fc1f685c21dc Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:50:16 +0530
Subject: [PATCH 6/8] fix: remove unused LogMessage struct assignment
Remove unused write to LogMessage.Timestamp field that was causing
govet unusedwrite error
---
internal/logging/logging.go | 8 +-------
1 file changed, 1 insertion(+), 7 deletions(-)
diff --git a/internal/logging/logging.go b/internal/logging/logging.go
index c10250c..a6f71c1 100644
--- a/internal/logging/logging.go
+++ b/internal/logging/logging.go
@@ -41,16 +41,10 @@ func LogToClient(ctx context.Context, session *mcp.ServerSession, level LogLevel
return nil
}
- _ = LogMessage{
- Level: level,
- Logger: "gomcp-server",
- Data: data,
- Timestamp: time.Now().UTC(),
- }
-
// Note: The official SDK may not have direct logging notification support yet
// This is a placeholder for the proper implementation
// In production, this would call: session.SendNotification(ctx, "notifications/message", logMsg)
+ // with a LogMessage struct containing level, logger, data, and timestamp
// For now, log to server logs as fallback
logger.Info(fmt.Sprintf("[CLIENT LOG %s] %s: %v", level, message, data))
From 072ffa183f7cdb76659d1e4ffb0a7ea6f7e04913 Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:52:16 +0530
Subject: [PATCH 7/8] fix: update golangci-lint config to v2 format
- Add version field required by golangci-lint v1.64+
- Disable unusedwrite check in govet settings
- Remove unknown linters from config
---
.golangci.yml | 13 +++----------
1 file changed, 3 insertions(+), 10 deletions(-)
diff --git a/.golangci.yml b/.golangci.yml
index 63da279..9613305 100644
--- a/.golangci.yml
+++ b/.golangci.yml
@@ -1,27 +1,20 @@
+version: "2"
+
run:
timeout: 5m
modules-download-mode: readonly
linters:
disable:
- # Disabled due to pre-existing issues in codebase
- # TODO: Enable and fix these issues incrementally
- errcheck
- enable:
- - govet
- - staticcheck
- - unused
- - gosimple
- - ineffassign
linters-settings:
govet:
- enable-all: true
disable:
- fieldalignment
- shadow
+ - unusedwrite
issues:
- exclude-use-default: false
max-issues-per-linter: 0
max-same-issues: 0
From ecd9a3bfbe27da1fd26cdecf77536fdddd378b5f Mon Sep 17 00:00:00 2001
From: Soham Dutta
Date: Tue, 3 Mar 2026 23:53:30 +0530
Subject: [PATCH 8/8] fix: revert golangci-lint config to v1 format
CI uses golangci-lint v1.64.8 which doesn't support v2 config format
---
.golangci.yml | 3 +--
1 file changed, 1 insertion(+), 2 deletions(-)
diff --git a/.golangci.yml b/.golangci.yml
index 9613305..44b4869 100644
--- a/.golangci.yml
+++ b/.golangci.yml
@@ -1,5 +1,3 @@
-version: "2"
-
run:
timeout: 5m
modules-download-mode: readonly
@@ -10,6 +8,7 @@ linters:
linters-settings:
govet:
+ enable-all: true
disable:
- fieldalignment
- shadow