diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000..d04ce5d --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,29 @@ +name: Release + +on: + workflow_dispatch: + inputs: + version: + description: 'Version to release (e.g., v1.2.3)' + required: true + type: string + +jobs: + release: + name: Create Release + runs-on: ubuntu-latest + permissions: + contents: write + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - name: Setup mise + uses: jdx/mise-action@v2 + + - name: Create release + run: mise run release -- ${{ inputs.version }} + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} \ No newline at end of file diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 274d6f5..ec0190b 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -8,7 +8,7 @@ on: workflow_dispatch: env: - VALID_CDEVENT: '{"context":{"version":"0.3.0","id":"test-${{ github.run_id }}","source":"github-action-test","type":"dev.cdevents.build.started.0.1.1","timestamp":"2024-01-01T00:00:00Z"},"subject":{"id":"test-subject","source":"https://github.com/test/repo"}}' + VALID_CDEVENT: '{"context":{"version":"0.4.1","source":"github-action-test","type":"dev.cdevents.taskrun.started.0.2.0"},"subject":{"id":"test-task-${{ github.run_id }}","source":"github-action-test","type":"taskRun","content":{"taskName":"ci-test","url":"${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}"}}}' INVALID_CDEVENT: '{"invalid": "missing required fields"}' jobs: diff --git a/.mise.toml b/.mise.toml index 126ca18..067694f 100644 --- a/.mise.toml +++ b/.mise.toml @@ -1,6 +1,7 @@ [tools] dprint = "latest" bun = "latest" +github-cli = "latest" [tasks.format] description = "Format code using dprint" @@ -18,4 +19,87 @@ run = [ [tasks.ci] description = "Run all CI checks locally" -alias = "check" \ No newline at end of file +alias = "check" + +[tasks.release] +description = "Create a new release with version tag (usage: mise run release -- v1.2.3)" +depends = ["check"] +run = ''' + if [ -z "$1" ]; then + echo 'Error: Please provide version (e.g., mise run release -- v1.2.3)' + exit 1 + fi + + VERSION="$1" + MAJOR_VERSION=$(echo $VERSION | cut -d. -f1) + + echo "=== Creating GitHub Action release ===" + echo "Version: $VERSION (major: $MAJOR_VERSION)" + + # Ensure we're on main branch and up to date + git checkout main + git pull origin main + + # Create and push version tag + echo "Creating tag: $VERSION" + git tag -a "$VERSION" -m "Release $VERSION" + git push origin "$VERSION" + + # Create GitHub release using gh CLI + echo "Creating GitHub release" + gh release create "$VERSION" \ + --title "Release $VERSION" \ + --notes "## Changes + +See [CHANGELOG.md](https://github.com/cdviz-dev/send-cdevents/blob/main/CHANGELOG.md) for details. + +## Usage + +\`\`\`yaml +- name: Send CDEvent + uses: cdviz-dev/send-cdevents@$VERSION + with: + data: | + { + \"context\": { + \"version\": \"0.4.1\", + \"source\": \"github-actions\", + \"type\": \"dev.cdevents.taskrun.started.0.2.0\" + }, + \"subject\": { + \"id\": \"\${{ github.run_id }}\", + \"type\": \"taskRun\", + \"content\": { + \"taskName\": \"ci-build\" + } + } + } + url: \"https://your-webhook-endpoint.com/cdevents\" +\`\`\`" + + # Update major version tag (e.g., v1) + echo "Updating major version tag: $MAJOR_VERSION" + git tag -f -a "$MAJOR_VERSION" -m "Release $MAJOR_VERSION (latest: $VERSION)" + git push origin "$MAJOR_VERSION" --force + + echo "=== Release completed! ===" + echo "✅ Created version tag: $VERSION" + echo "✅ Created GitHub release: $VERSION" + echo "✅ Updated major tag: $MAJOR_VERSION" + echo "📦 GitHub Marketplace will auto-update from the major version tag" +''' + +[tasks.release-check] +description = "Check current release status and tags" +depends = ["check"] +run = ''' + echo "=== Current Release Status ===" + echo "Latest tags:" + git tag --sort=-version:refname | head -5 + + echo "Current branch:" + git branch --show-current + + echo "Uncommitted changes:" + git status --porcelain || echo "Working tree clean" +''' \ No newline at end of file diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..9306c81 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,184 @@ +# Contributing to send-cdevents + +Thank you for your interest in contributing to the send-cdevents GitHub Action! + +## Development Setup + +This project uses [mise](https://mise.jdx.dev/) for tool management and task automation. + +### Prerequisites + +1. Install [mise](https://mise.jdx.dev/getting-started.html) +2. Clone the repository +3. Install tools and dependencies: + +```bash +mise install +``` + +This will automatically install: +- `dprint` - for code formatting +- `bun` - for JavaScript tooling +- `github-cli` - for GitHub operations + +## Development Workflow + +### Code Quality Checks + +Before submitting any changes, ensure your code passes all quality checks: + +```bash +# Format code +mise run format + +# Run all checks (formatting, validation, linting) +mise run check +``` + +The `check` task runs: +- `dprint check` - validates code formatting +- `bunx @action-validator/core action.yml` - validates GitHub Action schema + +### Testing Changes + +Test your changes using the test workflow: + +```bash +# Push changes to trigger test workflow +git push origin feature-branch + +# Or run tests manually via GitHub UI: +# Actions → Test Send CDEvents Action → Run workflow +``` + +The test workflow validates: +- Basic CDEvent sending +- HTTP endpoint integration +- Custom headers +- Configuration files +- Environment variables +- File input +- Error handling +- Config cleanup + +## Making Changes + +### Code Style + +- Use consistent formatting (enforced by dprint) +- Follow existing patterns in the codebase +- Use proper CDEvents format (see conformance examples) +- Use multiline YAML strings (`|`) for JSON data in examples + +### Documentation + +- Update README.md if you change functionality +- Use proper CDEvent examples from the conformance spec +- Include GitHub-flavored markdown callouts where helpful +- Update this CONTRIBUTING.md if you change the development process + +### Commit Messages + +Use conventional commit format: +``` +type: description + +Examples: +feat: add support for custom timeout configuration +fix: resolve config file permission issues +docs: update README with new environment variables +ci: improve test workflow performance +``` + +## Release Process + +### Preferred: GitHub Workflow (Recommended) + +1. Ensure all changes are merged to `main` +2. Go to **Actions** → **Release** → **Run workflow** +3. Enter the version (e.g., `v1.2.3`) following [semantic versioning](https://semver.org/) +4. Click **Run workflow** + +The workflow will: +- Run all quality checks +- Create and push version tag +- Create GitHub release with usage examples +- Update major version tag (e.g., `v1`) for GitHub Marketplace + +### Alternative: Local Release + +If you have the necessary permissions and tools set up locally: + +```bash +# Check release status first +mise run release-check + +# Create release +mise run release -- v1.2.3 +``` + +> **⚠️ Note**: Local releases require: +> - Write access to the repository +> - GitHub CLI authenticated (`gh auth login`) +> - Clean working directory on `main` branch + +### Version Guidelines + +Follow [semantic versioning](https://semver.org/): + +- **Patch** (`v1.0.1`): Bug fixes, documentation updates +- **Minor** (`v1.1.0`): New features, backward-compatible changes +- **Major** (`v2.0.0`): Breaking changes, incompatible API changes + +### Release Checklist + +- [ ] All tests pass +- [ ] Documentation is updated +- [ ] CHANGELOG.md is updated (if exists) +- [ ] Version follows semantic versioning +- [ ] Release notes are meaningful + +## Project Structure + +``` +. +├── action.yml # GitHub Action definition +├── README.md # User documentation +├── CONTRIBUTING.md # This file +├── .mise.toml # Tool management and tasks +├── dprint.json # Code formatting configuration +├── .github/ +│ ├── workflows/ +│ │ ├── ci.yml # Code quality checks +│ │ ├── test.yml # Action functionality tests +│ │ └── release.yml # Release automation +│ ├── dependabot.yml # Dependency updates +│ └── markdownlint.json # Markdown linting config +└── test-data/ # Sample CDEvent files +``` + +## Available Tasks + +```bash +# Show all available tasks +mise tasks + +# Key tasks: +mise run format # Format all code +mise run check # Run all quality checks +mise run release-check # Check current release status +mise run release -- v1.2.3 # Create new release +``` + +## Getting Help + +- Check existing [Issues](https://github.com/cdviz-dev/send-cdevents/issues) +- Review the [cdviz-collector documentation](https://github.com/cdviz-dev/cdviz-collector) +- Look at [CDEvents specification](https://cdevents.dev/) +- Open a new issue for bugs or feature requests + +## Code of Conduct + +This project follows the [Contributor Covenant Code of Conduct](https://www.contributor-covenant.org/version/2/1/code_of_conduct/). By participating, you agree to uphold this code. + +Thank you for contributing! 🎉 \ No newline at end of file diff --git a/README.md b/README.md index 62a888a..a197da7 100644 --- a/README.md +++ b/README.md @@ -19,7 +19,21 @@ jobs: - name: Send CDEvent uses: cdviz-dev/send-cdevents@v1 with: - data: '{"type": "dev.cdevents.build.started.0.1.1", "source": "github-action"}' + data: | + { + "context": { + "version": "0.4.1", + "source": "github-actions", + "type": "dev.cdevents.taskrun.started.0.2.0" + }, + "subject": { + "id": "${{ github.run_id }}", + "type": "taskRun", + "content": { + "taskName": "ci-build" + } + } + } url: "https://your-webhook-endpoint.com/cdevents" ``` @@ -38,7 +52,23 @@ jobs: - name: Send CDEvent uses: cdviz-dev/send-cdevents@v1 with: - data: '{"type": "dev.cdevents.build.started.0.1.1", "source": "github-action"}' + data: | + { + "context": { + "version": "0.4.1", + "source": "github-actions", + "type": "dev.cdevents.service.deployed.0.2.0" + }, + "subject": { + "id": "${{ github.repository }}", + "type": "service", + "content": { + "environment": { + "id": "production" + } + } + } + } url: "https://your-webhook-endpoint.com/cdevents" headers: | Authorization: Bearer ${{ secrets.API_TOKEN }} @@ -60,7 +90,24 @@ jobs: - name: Send CDEvent with HMAC signature uses: cdviz-dev/send-cdevents@v1 with: - data: '{"type": "dev.cdevents.build.started.0.1.1", "source": "github-action"}' + data: | + { + "context": { + "version": "0.4.1", + "source": "github-actions", + "type": "dev.cdevents.testcaserun.started.0.2.0" + }, + "subject": { + "id": "${{ github.run_id }}-test", + "type": "testCaseRun", + "content": { + "testCase": { + "name": "Integration Tests", + "type": "integration" + } + } + } + } url: "https://your-webhook-endpoint.com/cdevents" config: | [sinks.http.headers.x-signature-256] @@ -150,9 +197,45 @@ Examples: ```yaml with: - data: '{"type": "dev.cdevents.build.started.0.1.1", "source": "github-action"}' + data: | + { + "context": { + "version": "0.4.1", + "source": "github-actions", + "type": "dev.cdevents.taskrun.started.0.2.0" + }, + "subject": { + "id": "${{ github.run_id }}", + "type": "taskRun", + "content": { + "taskName": "ci-build" + } + } + } ``` +> [!TIP] +> The `context.id` and `context.timestamp` fields can be automatically generated by cdviz-collector if missing from your CDEvent. You can provide minimal CDEvents and let the collector handle the required metadata: +> +> ```yaml +> with: +> data: | +> { +> "context": { +> "version": "0.4.1", +> "source": "github-actions", +> "type": "dev.cdevents.taskrun.started.0.2.0" +> }, +> "subject": { +> "id": "${{ github.run_id }}", +> "type": "taskRun", +> "content": { +> "taskName": "ci-build" +> } +> } +> } +> ``` + ### From File ```yaml