Skip to content
Back to skills

Gen Taskfiles

FSecurity

Generate mise.toml, Taskfile.yml, Taskfile_dev.yml, and .pre-commit-config.yaml for Go projects with comprehensive task automation

  • 16 stars
  • 0 votes
  • 0 copies
  • 0 views
  • Added September 25, 2026
developmentgoshellbashdockertestinggitapidocumentation

Works with

  • claude code
  • api

Security analysis

F34/100
  • criticalPipes output to a shell interpreter
  • mediumUses curl or wget to download content
  • criticalDownloads and executes remote scripts — classic supply chain attack
  • mediumInstalls packages at runtime which could introduce malicious dependencies

Pro shows the line behind each finding and how to fix it

Scanned September 25, 2026

npx -y skills add sgaunet/claude-plugins --skill gen-taskfiles --agent claude-code

Installs into .claude/skills of the current project.

Are you the author of Gen Taskfiles?

Add the live security badge to your README. It updates with every re-scan.

Security grade badge for Gen Taskfiles
[![Security: F — Skills Directory](https://www.skillsdirectory.com/api/skills/sgaunet-gen-taskfiles/badge)](https://www.skillsdirectory.com/skills/sgaunet-gen-taskfiles)

More formats (shields.io, HTML) on the badges page. Keep it an A: scan every change in CI with Pro.

Download with Pro
SKILL.md
---
name: gen-taskfiles
description: Generate mise.toml, Taskfile.yml, Taskfile_dev.yml, and .pre-commit-config.yaml for Go projects with comprehensive task automation
argument-hint: "[--force] [--dry-run]"
user-invocable: true
disable-model-invocation: true
allowed-tools: Read, Write, Bash(git:*), Bash(test:*), AskUserQuestion
---

# Generate Taskfiles

Instantly create a complete Task automation setup for Go projects including a `mise.toml` (development tool versions), the main Taskfile, development tasks, and pre-commit hooks configuration. This skill provides a comprehensive task runner setup with linting, testing, building, and release automation — and pins the tool versions so local development and CI stay in sync.

## Why This Skill Exists

**Problem**: Setting up task automation for Go projects requires manually creating Taskfile configuration, understanding Task syntax, pinning tool versions, and configuring pre-commit hooks - a 20-30 minute process.

**Solution**: One-command generation that:
- Creates complete dev setup (4 files): `mise.toml`, `Taskfile.yml`, `Taskfile_dev.yml`, `.pre-commit-config.yaml`
- Pins tool versions in `mise.toml` (go, task, golangci-lint, goreleaser) so local dev and CI use identical versions
- Includes tasks: lint, test, build, snapshot, release, image, doc
- Configures pre-commit hooks for automated quality checks
- Integrates with golangci-lint and goreleaser

**mise.toml** is the single source of truth for tool versions. It is consumed by the CI generators (`/gen-github-dir`, `/gen-forgejo-dir`, `/gen-gitlab-ci`), whose workflows install tools via mise and then run `task …`. See https://mise.jdx.dev.

## Content Generation Rules

**CRITICAL**: When generating any content (taskfiles, commit messages, or any other output):
- **NEVER** add Claude Code attribution or co-authorship
- **NEVER** include phrases like "Generated by Claude", "Created with Claude Code", or similar
- **NEVER** add "Co-Authored-By: Claude" in commit messages or documentation
- All generated content should appear as if written by a human developer
- Focus on technical accuracy and providing working templates

## Process (6 Phases)

### Phase 1: Prerequisites Validation

**Critical checks before proceeding:**

1. **Validate Git repository:**
   ```bash
   git rev-parse --git-dir
   ```
   - If fails: Exit with error "Not a git repository. Run 'git init' first."

2. **Validate Go project:**
   ```bash
   test -f go.mod
   ```
   - If fails: Exit with error "go.mod not found. This skill is for Go projects only."

3. **Check existing taskfiles:**
   ```bash
   test -f mise.toml
   test -f Taskfile.yml
   test -f Taskfile_dev.yml
   test -f .pre-commit-config.yaml
   ```
   - Store which files exist: `existingFiles = []`
   - If any exist: Store `hasExistingFiles = true`
   - Note `mise.toml` separately as `existingMise = true|false` (a pre-existing
     `mise.toml` already pins tool versions; default to preserving it unless `--force`).

4. **Verify skill assets directory:**
   - Use Read tool to verify `${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/Taskfile.yml` exists
   - Use Read tool to verify `${CLAUDE_PLUGIN_ROOT}/assets/mise/mise.toml` exists
   - If either fails: Exit with error "Skill assets directory not found at ${CLAUDE_PLUGIN_ROOT}/assets/. Plugin may be corrupted. Reinstall the go-specialist plugin."

5. **Check for supporting configs (non-blocking):**
   ```bash
   test -f .golangci.yml
   test -f .goreleaser.yml
   ```
   - If .golangci.yml missing: Store `linterMissing = true` (warn in Phase 6)
   - If .goreleaser.yml missing: Store `goreleaserMissing = true` (warn in Phase 6)

### Phase 2: Argument Parsing

Parse skill arguments from `$argument` string:

**Supported flags:**
- `--force`: Skip confirmation for existing files
- `--dry-run`: Show preview without writing files

**Parsing logic:**
```
arguments = split($argument by space)
for each arg in arguments:
  if arg == "--force": set forceMode = true
  if arg == "--dry-run": set dryRunMode = true
```

### Phase 3: Template Reading

**Read all template files** from skill assets directory:

**Files to read:**

1. **mise.toml**
   - Path: `${CLAUDE_PLUGIN_ROOT}/assets/mise/mise.toml`
   - Target: `mise.toml` (project root)

2. **Taskfile.yml** (66 lines)
   - Path: `${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/Taskfile.yml`
   - Target: `Taskfile.yml` (project root)

3. **Taskfile_dev.yml** (14 lines)
   - Path: `${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/Taskfile_dev.yml`
   - Target: `Taskfile_dev.yml` (project root)

4. **.pre-commit-config.yaml** (25 lines)
   - Path: `${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/.pre-commit-config.yaml`
   - Target: `.pre-commit-config.yaml` (project root)

**Template handling:**
- Store content in memory for Phase 3.5 substitution
- All substitutions handled in Phase 3.5 (not inline)

**Error handling:**
- If any Read fails: Exit with error "Failed to read template file: {filename}. Plugin may be corrupted. Ensure ${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/ directory exists."

### Phase 3.5: Auto-Detection & Substitution

**Detection Function Library:** Use the shared detection functions from `${CLAUDE_PLUGIN_ROOT}/assets/detection-functions.md`. Read that file to get all bash detection functions (`detect_project_name`, `detect_git_owner`, `detect_main_dir`, `detect_registry`, `detect_go_version`, `detect_golangci_lint_version`, `detect_goreleaser_version`, `strip_leading_v`, `substitute_placeholders`, `substitute_version_placeholders`).

**Detection Workflow:**

1. **Detect all values:**
   ```bash
   PROJECT_NAME=$(detect_project_name)
   OWNER=$(detect_git_owner)
   REGISTRY=$(detect_registry)
   MAIN_DIR=$(detect_main_dir)
   ```

0. **Detect tool versions for mise.toml:**
   ```bash
   GO_VERSION=$(detect_go_version)
   GOLANGCI_LINT_VERSION=$(detect_golangci_lint_version)
   GORELEASER_VERSION=$(detect_goreleaser_version)
   GOLANGCI_LINT_VERSION_BARE=$(strip_leading_v "${GOLANGCI_LINT_VERSION:-v2.2.2}")

   mise_template=$(substitute_version_placeholders "$mise_template" \
       "GO_VERSION=${GO_VERSION:-1.25}" \
       "GOLANGCI_LINT_VERSION_BARE=${GOLANGCI_LINT_VERSION_BARE:-2.2.2}" \
       "GORELEASER_VERSION=${GORELEASER_VERSION:-v2.12.0}")
   ```
   - `mise.toml` uses the bare golangci-lint version (no leading `v`), the
     v-prefixed goreleaser tag, and `major.minor` Go from go.mod.

2. **Handle missing critical values:**
   - If `PROJECT_NAME` is empty: Use "app" as default
   - If `OWNER` is empty: Preserve `[OWNER]` placeholder
   - Non-critical values have sensible defaults

3. **Substitute placeholders in Taskfile.yml template:**
   ```bash
   taskfile_template=$(substitute_placeholders "$taskfile_template" \
       "$PROJECT_NAME" "$OWNER" "$REGISTRY" "$MAIN_DIR")
   ```

4. **Detect pre-commit-hooks version:**
   ```bash
   PRE_COMMIT_HOOKS_VERSION=$(detect_pre_commit_hooks_version)
   ```
   - If empty (gh not available or API failure): Use fallback `v4.3.0`

5. **Substitute version placeholders in .pre-commit-config.yaml template:**
   ```bash
   precommit_template=$(substitute_version_placeholders "$precommit_template" \
       "PRE_COMMIT_HOOKS_VERSION=${PRE_COMMIT_HOOKS_VERSION:-v4.3.0}")
   ```

   Note: Taskfile_dev.yml has no placeholders

### Phase 4: User Confirmation

**Build preview summary:**

```
Files to be created:
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
✅ mise.toml - Pinned dev tool versions (go, task, golangci-lint, goreleaser)
✅ Taskfile.yml (66 lines) - Main task definitions
✅ Taskfile_dev.yml (14 lines) - Development tasks
✅ .pre-commit-config.yaml (25 lines) - Git pre-commit hooks

Total: 4 files

[If existingMise == true and not --force:]
ℹ️  mise.toml already exists — it will be PRESERVED (your tool pins are kept).

✅ Auto-detected Configuration
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

Project Settings:
  • Project name: <PROJECT_NAME> (from go.mod)
  • Binary name: <PROJECT_NAME>
  • Main directory: <MAIN_DIR>

Tool Versions (mise.toml):
  • Go: <GO_VERSION> (from go.mod)
  • golangci-lint: <GOLANGCI_LINT_VERSION_BARE>
  • goreleaser: <GORELEASER_VERSION>
  • task: latest

Repository Settings:
  • Owner: <OWNER> (from git remote)
  • Registry: <REGISTRY>

Task Categories:
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
🔧 Development:
   - default: List all available tasks
   - check-before-commit: Run all quality checks
   - lint: Run golangci-lint
   - test: Run unit tests with race detection
   - build: Build project binaries

📦 Release:
   - snapshot: Create snapshot release (goreleaser)
   - release: Create production release (goreleaser)
   - image: Build and push Docker image

📚 Documentation:
   - doc: Start godoc server

🛠️  Dev Tools (Taskfile_dev.yml):
   - dev:install-pre-commit: Install pre-commit hooks
   - dev:pre-commit: Run all pre-commit hooks manually

🎯 Pre-commit Hooks:
   - check-yaml: Validate YAML syntax
   - check-added-large-files: Prevent large files
   - unit-tests: Run tests before commit
   - lint: Run linter before commit
   - build: Test build before commit

[If hasExistingFiles == true:]
⚠️  WARNING: Some files already exist and will be overwritten:
[List existing files]
```

**Dry run mode:**
If `dryRunMode == true`:
- Show preview summary above
- Display first 20 lines of each file
- Show customization requirements
- Display next steps guide
- Exit without creating files

**Confirmation logic:**

1. **If `--force` flag provided:** Skip confirmation, proceed to Phase 5

2. **If existing files without `--force`:**
   ```
   Use AskUserQuestion:
   Question: "Task configuration files already exist. Overwrite?"
   Options:
   1. "Yes, overwrite files" [Recommended if upgrading]
   2. "Show full preview first"
   3. "Cancel"

   If option 2: Display full content preview, then re-ask confirmation
   If option 3: Exit gracefully
   ```

3. **If no existing files:**
   ```
   Use AskUserQuestion:
   Question: "Create task configuration files (3 files)?"
   Options:
   1. "Yes, create files"
   2. "Show preview first"
   3. "Cancel"
   ```

### Phase 5: File Creation

**File writing sequence:**

Write files in order:

1. `mise.toml`
   - Write the version-substituted template to project root
   - **Preserve-if-exists:** if `existingMise == true` and `--force` was NOT
     given, skip writing (keep the project's existing tool pins) and note it in
     the report. With `--force`, overwrite like the other files.

2. `Taskfile.yml`
   - Replace `BINFILE: gitlab-backup` with detected binary name
   - Write to project root

3. `Taskfile_dev.yml`
   - Write as-is to project root

4. `.pre-commit-config.yaml`
   - Write as-is to project root

**For each file:**
- Use Write tool with full file path
- Write content from Phase 3 templates
- Track success/failure status
- Continue with remaining files if one fails (partial success acceptable)

**Error handling:**
- If individual file write fails: Log error, continue with next file
- If all writes fail: Report failure with details
- If partial success: Report which files succeeded/failed

**Track results:**
```
successfulFiles = []
failedFiles = []

for each file:
  try write:
    if success: add to successfulFiles
    if failure: add to failedFiles
```

### Phase 6: Validation & Success Report

**Post-creation validation:** for each file in `successfulFiles`, confirm it exists and is
non-zero; move any failure to `failedFiles`.

**Report to the user** — cover these facts; no fixed layout required:

- **Files written:** each path with its line count, and a total. Mark `mise.toml` as
  created vs. preserved (an existing one is never overwritten).
- **Detected values:** project name and binary name (from go.mod), main directory, owner
  (from git remote), registry, the Go / golangci-lint / goreleaser versions pinned in
  `mise.toml`, and the pre-commit hooks version.
- **Key tasks:** `task` or `task -a` lists everything; highlight `task check-before-commit`,
  `task lint`, `task test`, `task build`, `task snapshot`, `task release`, `task doc`,
  `task dev:install-pre-commit`, `task dev:pre-commit`.
- **Prerequisites:** tool versions are pinned in `mise.toml`, so mise is installed once per
  machine (`brew install mise`, or `curl https://mise.run | sh` —
  https://mise.jdx.dev/getting-started.html) and then provides go, task, golangci-lint and
  goreleaser at the exact CI versions. Follow with `mise install`, plus either
  `mise activate <shell>` in the shell rc or one-offs via `mise exec -- task lint`.
  pre-commit installs separately (`brew install pre-commit` or `pip install pre-commit`),
  then `task dev:install-pre-commit`.
- **Missing configs:** if `linterMissing`, warn that `.golangci.yml` is absent and point at
  `/gen-linter`; if `goreleaserMissing`, same for `.goreleaser.yml` and `/gen-goreleaser`.
  Note that mise supplies both binaries either way — only the config is missing.
- **Optional customizations:** multi-binary projects need the build task extended; the
  commented-out `trailing-whitespace` and `end-of-file-fixer` hooks can be enabled; the
  Docker image is already wired to `<REGISTRY>/<OWNER>/<PROJECT_NAME>:latest` and worth a
  check.
- **Pre-commit hooks:** installed with `task dev:install-pre-commit`, tested with
  `task dev:pre-commit`, then run on every `git commit` — checking YAML syntax, large
  files, unit tests, the linter and a snapshot build. `git commit --no-verify` bypasses
  them in an emergency.
- **Next steps:** install mise and run `mise install`, review `mise.toml` and
  `Taskfile.yml`, install the hooks, generate any missing config, run `task lint`,
  `task test` and `task build`, then `git add mise.toml Taskfile*.yml .pre-commit-config.yaml`
  and `git commit -m "build: add mise, task automation and pre-commit hooks"`.
- **Docs:** https://taskfile.dev · https://pre-commit.com · `task -a` for the task list.

**On failure:** report which files were written, which failed and why, and that `--force`
retries. Partial success is a warning, total failure an error — for a total failure also
name the likely causes (permissions, disk space, filesystem restrictions).

## Arguments

Arguments are parsed from the `argument` string parameter:

- **`--force`**: Skip confirmation prompt and overwrite existing files
  - Use when: Upgrading existing task configuration
  - Behavior: Overwrites files directly without confirmation

- **`--dry-run`**: Preview files without writing to disk
  - Shows: File list, line counts, preview of content
  - Writes: Nothing
  - Use when: Reviewing what will be created before committing

**Parsing example:**
```
argument = "--force"
Split by space, check for each flag:
- forceMode = true
- dryRunMode = false
```

## Error Handling

### Critical Errors (Exit Immediately)

**Not a Git repository:**
```
❌ Error: Not a git repository

This skill requires a Git repository. Initialize one:
  git init
  git add .
  git commit -m "Initial commit"
```

**Not a Go project:**
```
❌ Error: go.mod not found

This skill is for Go projects only. Initialize a Go module:
  go mod init github.com/username/project
```

**Skill assets missing:**
```
❌ Error: Skill assets directory not found

The go-specialist plugin may be corrupted. Try:
1. Reinstalling the plugin
2. Updating Claude Code to latest version
3. Reporting issue at: https://github.com/sgaunet/claude-plugins/issues
```

### Warning Errors (Continue with Warnings)

**Existing task files:**
- Without `--force`: Request user confirmation
- With `--force`: Overwrite silently

**Missing .golangci.yml or .goreleaser.yml:**
- Don't block creation
- Warn in success report
- Suggest using the `/gen-linter` or `/gen-goreleaser` skills

### Recovery Actions

**If file write fails:**
```
❌ Error: Failed to write [filename]

Check:
1. Current directory is writable
2. Sufficient disk space
3. No file system restrictions

Current permissions: [show with ls -ld .]
```

## File Mapping

| Source Path | Target (Relative to CWD) | Lines | Purpose |
|-------------|--------------------------|-------|---------|
| `${CLAUDE_PLUGIN_ROOT}/assets/mise/mise.toml` | `mise.toml` | ~35 | Pinned dev tool versions (preserve-if-exists) |
| `${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/Taskfile.yml` | `Taskfile.yml` | 66 | Main task definitions |
| `${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/Taskfile_dev.yml` | `Taskfile_dev.yml` | 14 | Development tasks |
| `${CLAUDE_PLUGIN_ROOT}/assets/taskfiles/.pre-commit-config.yaml` | `.pre-commit-config.yaml` | 25 | Git pre-commit hooks |

## Integration with Other Skills

**Works with:**
- `/commit`: Commit generated taskfiles
- `/gen-linter`: Generate .golangci.yml (required for lint task)
- `/gen-goreleaser`: Generate .goreleaser.yml (required for snapshot/release tasks)
- `/gen-github-dir`: GitHub workflows can call task commands
- `/gen-gitlab-ci`: GitLab CI can call task commands

**Typical Workflow:**
```bash
# 1. Generate task configuration (also writes mise.toml)
/gen-taskfiles

# 2. Generate supporting configs
/gen-linter          # Creates .golangci.yml
/gen-goreleaser      # Creates .goreleaser.yml

# 3. Install tools (one mise install pins everything) and hooks
brew install mise pre-commit   # or: curl https://mise.run | sh
mise install                   # installs go, task, golangci-lint, goreleaser
task dev:install-pre-commit

# 4. Test tasks
task lint
task test
task build

# 5. Commit everything
git add mise.toml Taskfile*.yml .pre-commit-config.yaml .golangci.yml .goreleaser.yml
git commit -m "build: add mise, task automation and pre-commit hooks"

# 6. Verify hooks work
# Make a test change, try to commit - hooks should run
```

## Task Descriptions

### Main Tasks (Taskfile.yml)

**default**: List all available tasks
- Dependencies: Checks for pre-commit hooks installed
- Command: `task -a`

**check-before-commit**: Run complete quality check suite
- Dependencies: test, snapshot, lint (in order)
- Use: Before pushing code or creating PR

**lint**: Run golangci-lint
- Command: `golangci-lint run`
- Requirements: .golangci.yml file

**test**: Run unit tests with race detection
- Command: `go test -count=2 -race ./...`
- Runs tests twice to catch flaky tests
- Race detector finds concurrency issues

**build**: Build project binaries
- Command: CGO-disabled builds for static binaries
- Customize: Update for your binary names

**image**: Build and push Docker image
- Dependencies: build task
- Customize: Update registry and image name

**doc**: Start godoc documentation server
- Command: `godoc -http=:6060`
- Access: http://localhost:6060

**snapshot**: Create snapshot release
- Command: `goreleaser --clean --snapshot`
- Requirements: .goreleaser.yml file
- Use: Test release process without publishing

**release**: Create production release
- Command: `goreleaser --clean`
- Requirements: .goreleaser.yml file, git tag
- Use: On tagged commits to publish release

### Development Tasks (Taskfile_dev.yml)

**dev:install-pre-commit**: Install pre-commit hooks
- Command: `pre-commit install`
- Run once: After cloning repository

**dev:pre-commit**: Run all pre-commit hooks manually
- Command: `pre-commit run --all-files`
- Use: Test hooks before committing

## Pre-commit Hooks Configuration

**.pre-commit-config.yaml** configures automatic quality checks:

**Standard hooks** (from pre-commit/pre-commit-hooks):
- `check-yaml`: Validate YAML syntax (enabled)
- `check-added-large-files`: Prevent commits of large files (enabled)
- `trailing-whitespace`: Remove trailing whitespace (commented, can enable)
- `end-of-file-fixer`: Ensure files end with newline (commented, can enable)

**Local hooks** (run task commands):
- `unit-tests`: Run `task test` before commit
- `lint`: Run `task lint` before commit
- `build`: Run `task snapshot` before commit

All local hooks use `pass_filenames: false` to run full checks, not per-file.

## Best Practices

**Before running this skill:**
1. Ensure git repository initialized
2. Have go.mod configured
3. Review task documentation: https://taskfile.dev

**After generation:**
1. Review and customize Taskfile.yml
2. Generate .golangci.yml and .goreleaser.yml if missing
3. Install Task runner if not already installed
4. Install pre-commit: `task dev:install-pre-commit`
5. Test all tasks: `task lint`, `task test`, `task build`
6. Commit with meaningful message

**Ongoing usage:**
1. Run `task check-before-commit` before pushing code
2. Let pre-commit hooks catch issues automatically
3. Use `task snapshot` to test releases locally
4. Keep Task and pre-commit tools updated
5. Add custom tasks as project needs evolve

## Limitations

**This skill does NOT:**
- Generate .golangci.yml (use `/gen-linter` skill)
- Generate .goreleaser.yml (use `/gen-goreleaser` skill)
- Install Task runner or pre-commit tools (manual installation required)
- Modify existing taskfiles intelligently (use `--force` to overwrite)
- Install pre-commit hooks automatically (run `task dev:install-pre-commit`)
- Customize binary names automatically (detects from go.mod, may need manual adjustment)

**Scope boundaries:**
- Only handles task and pre-commit configuration files
- Templates are opinionated (aligned with gitlab-backup project patterns)
- Assumes standard Go project structure
- Requires manual customization for multi-binary projects
- Docker image task requires customization for your registry

## Examples

```bash
# Standard generation (3 files)
/gen-taskfiles

# Preview before creating
/gen-taskfiles --dry-run

# Overwrite existing configuration
/gen-taskfiles --force

# Force with dry run
/gen-taskfiles --force --dry-run
```

## Output Summary

**Standard mode (default):**
- 4 files created (mise.toml + 3 task files)
- Complete task automation setup with pinned tool versions and pre-commit hooks

**Dry run mode (`--dry-run`):**
- 0 files created
- Preview shown
- Safe exploration

## Task vs Make

**Why Task instead of Make?**
- YAML syntax (easier than Makefile)
- Cross-platform (Windows, macOS, Linux)
- Built-in parallel execution
- Better dependency management
- Includes from other taskfiles
- Modern tool designed for development workflows

**Migration from Make:**
If you have a Makefile, you can:
1. Keep both (Task can call make targets)
2. Gradually migrate targets to Taskfile.yml
3. Use Task as the primary interface, delegate to make when needed

Attribution

Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.

Comments

Loading comments…

Newsletter

Get the weekly list of safe new skills, and the ones we pulled.