# Pull Request Capabilities

This package now includes comprehensive pull request (PR) capabilities that support both GitHub and Gerrit platforms. The implementation provides a unified interface for managing pull requests across different code hosting platforms.

## Features

- **Unified Interface**: Same API for both GitHub and Gerrit
- **Full CRUD Operations**: Create, read, update, delete pull requests
- **Advanced Filtering**: List pull requests with various filters
- **Merge Operations**: Support for different merge strategies
- **Error Handling**: Comprehensive error handling with detailed messages
- **Authentication**: Support for token-based and basic authentication

## Supported Platforms

### GitHub
- Uses GitHub REST API v3
- Supports personal access tokens for authentication
- Full support for all pull request operations
- Handles GitHub-specific features like draft PRs, labels, assignees, and reviewers

### Gerrit
- Uses Gerrit REST API
- Supports HTTP password or API token authentication
- Maps Gerrit "changes" to pull requests
- Handles Gerrit-specific features like topics and review workflows

## Quick Start

### GitHub Example

```go
package main

import (
    "context"
    "github.com/iomodo/staff/git"
    "net/http"
    "time"
)

func main() {
    ctx := context.Background()
    
    // Create GitHub configuration
    githubConfig := git.GitHubConfig{
        Token: "your-github-token",
        BaseURL: "https://api.github.com",
        HTTPClient: &http.Client{Timeout: 30 * time.Second},
    }
    
    // Create GitHub provider
    githubProvider := git.NewGitHubPullRequestProvider("owner", "repo", githubConfig)
    
    // Create Git instance with pull request capabilities
    git := git.NewGitWithPullRequests("/path/to/repo", git.GitConfig{}, githubProvider)
    
    // Create a pull request
    prOptions := git.PullRequestOptions{
        Title:       "Add new feature",
        Description: "This PR adds a new feature to the application.",
        BaseBranch:  "main",
        HeadBranch:  "feature/new-feature",
        Labels:      []string{"enhancement", "feature"},
        Assignees:   []string{"username1", "username2"},
        Reviewers:   []string{"reviewer1", "reviewer2"},
        Draft:       false,
    }
    
    pr, err := git.CreatePullRequest(ctx, prOptions)
    if err != nil {
        log.Fatal(err)
    }
    
    fmt.Printf("Created pull request: %s (#%d)\n", pr.Title, pr.Number)
}
```

### Gerrit Example

```go
package main

import (
    "context"
    "github.com/iomodo/staff/git"
    "net/http"
    "time"
)

func main() {
    ctx := context.Background()
    
    // Create Gerrit configuration
    gerritConfig := git.GerritConfig{
        Username: "your-username",
        Password: "your-http-password-or-api-token",
        BaseURL:  "https://gerrit.example.com",
        HTTPClient: &http.Client{Timeout: 30 * time.Second},
    }
    
    // Create Gerrit provider
    gerritProvider := git.NewGerritPullRequestProvider("project-name", gerritConfig)
    
    // Create Git instance with pull request capabilities
    git := git.NewGitWithPullRequests("/path/to/repo", git.GitConfig{}, gerritProvider)
    
    // Create a change (pull request)
    prOptions := git.PullRequestOptions{
        Title:       "Add new feature",
        Description: "This change adds a new feature to the application.",
        BaseBranch:  "master",
        HeadBranch:  "feature/new-feature",
    }
    
    pr, err := git.CreatePullRequest(ctx, prOptions)
    if err != nil {
        log.Fatal(err)
    }
    
    fmt.Printf("Created change: %s (#%d)\n", pr.Title, pr.Number)
}
```

## API Reference

### Types

#### PullRequest
Represents a pull request or merge request across platforms.

```go
type PullRequest struct {
    ID          string
    Number      int
    Title       string
    Description string
    State       string // "open", "closed", "merged"
    Author      Author
    CreatedAt   time.Time
    UpdatedAt   time.Time
    BaseBranch  string
    HeadBranch  string
    BaseRepo    string
    HeadRepo    string
    Labels      []string
    Assignees   []Author
    Reviewers   []Author
    Commits     []Commit
    Comments    []PullRequestComment
}
```

#### PullRequestOptions
Options for creating or updating pull requests.

```go
type PullRequestOptions struct {
    Title       string
    Description string
    BaseBranch  string
    HeadBranch  string
    BaseRepo    string
    HeadRepo    string
    Labels      []string
    Assignees   []string
    Reviewers   []string
    Draft       bool
}
```

#### ListPullRequestOptions
Options for listing pull requests.

```go
type ListPullRequestOptions struct {
    State      string // "open", "closed", "all"
    Author     string
    Assignee   string
    BaseBranch string
    HeadBranch string
    Labels     []string
    Limit      int
}
```

#### MergePullRequestOptions
Options for merging pull requests.

```go
type MergePullRequestOptions struct {
    MergeMethod string // "merge", "squash", "rebase"
    CommitTitle string
    CommitMsg   string
}
```

### Methods

#### CreatePullRequest
Creates a new pull request.

```go
func (g *Git) CreatePullRequest(ctx context.Context, options PullRequestOptions) (*PullRequest, error)
```

#### GetPullRequest
Retrieves a pull request by ID.

```go
func (g *Git) GetPullRequest(ctx context.Context, id string) (*PullRequest, error)
```

#### ListPullRequests
Lists pull requests with optional filtering.

```go
func (g *Git) ListPullRequests(ctx context.Context, options ListPullRequestOptions) ([]PullRequest, error)
```

#### UpdatePullRequest
Updates an existing pull request.

```go
func (g *Git) UpdatePullRequest(ctx context.Context, id string, options PullRequestOptions) (*PullRequest, error)
```

#### ClosePullRequest
Closes a pull request.

```go
func (g *Git) ClosePullRequest(ctx context.Context, id string) error
```

#### MergePullRequest
Merges a pull request.

```go
func (g *Git) MergePullRequest(ctx context.Context, id string, options MergePullRequestOptions) error
```

## Configuration

### GitHub Configuration

```go
type GitHubConfig struct {
    Token      string        // GitHub personal access token
    BaseURL    string        // GitHub API base URL (default: https://api.github.com)
    HTTPClient *http.Client  // Custom HTTP client (optional)
}
```

### Gerrit Configuration

```go
type GerritConfig struct {
    Username    string        // Gerrit username
    Password    string        // HTTP password or API token
    BaseURL     string        // Gerrit instance URL
    HTTPClient  *http.Client  // Custom HTTP client (optional)
}
```

## Error Handling

All pull request operations return detailed error information through the `GitError` type:

```go
type GitError struct {
    Command string
    Output  string
    Err     error
}
```

Common error scenarios:
- Authentication failures
- Invalid repository or project names
- Network connectivity issues
- API rate limiting
- Invalid pull request data

## Platform-Specific Notes

### GitHub
- Requires a personal access token with appropriate permissions
- Supports draft pull requests
- Full support for labels, assignees, and reviewers
- Uses GitHub's REST API v3

### Gerrit
- Requires HTTP password or API token
- Uses "changes" instead of "pull requests"
- Topics are used to group related changes
- Review workflow is more structured
- Uses Gerrit's REST API

## Examples

See `pull_request_example.go` for comprehensive examples of using both GitHub and Gerrit providers.

## Testing

Run the tests to ensure everything works correctly:

```bash
go test ./git/... -v
```

## Contributing

When adding support for new platforms:

1. Implement the `PullRequestProvider` interface
2. Add platform-specific configuration types
3. Create conversion functions to map platform-specific data to our unified types
4. Add comprehensive tests
5. Update this documentation

## License

This code is part of the staff project and follows the same licensing terms. 