Skip to main content
Welcome! We appreciate your interest in contributing to CoW Protocol Services. This guide will help you make high-quality contributions.

Before You Start

For Bug Reports or Feature Requests

1

Check existing issues

Search existing issues to see if your bug or feature has already been reported.
2

Open an issue

Create a new issue with:
  • Clear description
  • Steps to reproduce (for bugs)
  • Use cases and impact (for features)
3

Get feedback

Wait for maintainer feedback before starting major work.
For serious security bugs, follow the security policy instead of opening an issue.

For Code Contributions

Non-trivial changes must be discussed first. Only very minor changes (typos, comments, small refactors) are accepted without prior discussion.
Look for issues labeled “help wanted” for good starting points.

Code Formatting

Proper formatting is enforced by CI. Run formatters before committing.

Rust Code Formatting

Always use the nightly toolchain for formatting. Never use stable cargo fmt.
just fmt
Why nightly? The project uses nightly rustfmt features for consistent formatting.

TOML File Formatting

The project uses Tombi for TOML formatting.
just fmt-toml
Install Tombi:
cargo install tombi
Editor extensions:

Linting

Run Clippy before submitting your PR.
just clippy
The -D warnings flag treats warnings as errors. Fix all warnings before submitting.

Testing Requirements

All PRs must pass the test suite.

Run Tests Locally

1

Unit tests

just test-unit
2

Database tests

Start PostgreSQL first:
docker compose up -d
just test-db
3

E2E tests (if relevant)

# Local node tests
just test-e2e-local

# Forked network tests (requires RPC URLs)
export FORK_URL_MAINNET="..."
export FORK_URL_GNOSIS="..."
just test-e2e-forked
Always use cargo nextest run, never cargo test. The CI uses nextest and handles global state differently.

Add Tests for New Code

  • New features: Add unit tests and integration tests
  • Bug fixes: Add regression tests that would have caught the bug
  • Refactors: Ensure existing tests still pass
See the Testing Guide for details.

Pull Request Guidelines

Creating a PR

1

Fork the repository

Click “Fork” on GitHub and clone your fork:
git clone https://github.com/YOUR_USERNAME/services.git
cd services
2

Create a feature branch

git checkout -b feature/my-feature
Use descriptive branch names:
  • feature/add-order-validation
  • fix/orderbook-race-condition
  • refactor/simplify-driver-logic
3

Make your changes

  • Write code
  • Add tests
  • Run formatters and linters
  • Test locally
4

Commit your changes

5

Push and create PR

git push origin feature/my-feature
Then create a PR on GitHub.

PR Checklist

Before submitting, ensure:
  • Code is formatted with just fmt and just fmt-toml
  • Clippy passes with just clippy
  • Tests pass locally
  • New code has tests
  • PR description clearly explains the change
  • Related issue is linked (if applicable)

PR Description Template

When you create a PR, GitHub will show a template. Fill it out completely:
## Description
Brief description of what this PR does.

## Related Issue
Closes #123

## Changes
- List key changes
- Made in this PR

## Testing
Describe how you tested the changes:
- Ran unit tests
- Tested in playground
- Manual testing steps

## Checklist
- [ ] Tests added/updated
- [ ] Documentation updated (if needed)
- [ ] Formatted with `just fmt` and `just fmt-toml`
- [ ] Clippy passes

Commit Message Style

Write clear, descriptive commit messages.

Format

brief summary of change (50 chars or less)

More detailed explanation if needed. Explain WHY you made the change,
not just WHAT changed. The code shows what changed.

- Can use bullet points
- To list multiple aspects

References #123

Good Examples

Fix race condition in orderbook insertion

Orders could be inserted with outdated validation state if another
order was processed concurrently. Added proper locking around the
validation + insertion sequence.

Fixes #456
Add support for ERC-1271 signature validation

Enables smart contract wallets to place orders by implementing
ERC-1271 signature verification. Required for CoW Swap smart
wallet support.

References #789

Bad Examples

fixed bug  ❌  (too vague)
Updated orderbook.rs  ❌  (doesn't explain why)
refactor  ❌  (no details)

Code Review Process

1

Initial review

A maintainer will review your PR within a few days.
2

Address feedback

  • Respond to comments
  • Make requested changes
  • Push new commits (don’t force-push during review)
3

Approval

Once approved, a maintainer will merge your PR.

Review Expectations

For contributors:
  • Be responsive to feedback
  • Be open to suggestions
  • Ask questions if something is unclear
From maintainers:
  • Constructive feedback
  • Clear explanations for requested changes
  • Timely responses

Code Style Guidelines

Import Organization

Group imports logically:
// External crates
use anyhow::Result;
use tokio::sync::Mutex;

// Internal crates
use crate::database::Db;
use crate::orderbook::Order;

// Local modules
use super::validation;

Prefer Type Imports

Import types at the module level instead of using full paths:
// Good ✓
use shared::arguments::TokenBucketFeeOverride;

fn process(overrides: Vec<TokenBucketFeeOverride>) {
    // ...
}

// Bad ✗
fn process(overrides: Vec<shared::arguments::TokenBucketFeeOverride>) {
    // ...
}

Comments

Use comments sparingly:
  • Don’t comment obvious code
  • Do comment complex algorithms or non-obvious logic
  • Do comment “why”, not “what”
  • Do document public APIs
// Bad ✗
// Increment counter
counter += 1;

// Good ✓
// We need to delay here to avoid overwhelming the RPC node with requests.
// The rate limit is 10 requests per second.
tokio::time::sleep(Duration::from_millis(100)).await;

Error Handling

Use anyhow::Result for functions that can fail:
use anyhow::{Context, Result};

fn process_order(order: Order) -> Result<()> {
    validate_order(&order)
        .context("failed to validate order")?;
    
    store_order(&order)
        .context("failed to store order")?;
    
    Ok(())
}

Rewards for Contributors

Earn 100 DAI for merged PRs that solve “help wanted” issues!
To receive your reward:
  1. Ensure your PR is merged
  2. Include a Gnosis Chain address in your PR description or DM mastercow.eth on Discord

Getting Help

Community Support

Development Questions

If you’re stuck:
  1. Check the documentation
  2. Search existing issues and discussions
  3. Ask in Discord (be specific about your problem)

What to Contribute

High-Impact Contributions

Bug Fixes

Fix reported issues, especially those affecting users

Performance

Optimize slow code paths or reduce resource usage

Tests

Improve test coverage for critical code

Documentation

Clarify confusing docs or add missing examples

Areas Needing Help

Check issues labeled:

Summary: Pre-PR Checklist

Before submitting your PR:
# 1. Format code
just fmt
just fmt-toml

# 2. Lint
just clippy

# 3. Test
just test-unit
docker compose up -d && just test-db

# 4. Verify formatting
just fmt --check
just fmt-toml --check
Then:
  • Write clear commit messages
  • Fill out PR template completely
  • Link related issues
  • Respond to review feedback

Next Steps

Setup Guide

Set up your development environment

Testing Guide

Learn how to test your changes

Playground

Test in a full local environment

GitHub Issues

Find issues to work on
Thank you for contributing to CoW Protocol!

Build docs developers (and LLMs) love