Skip to content
Back to skills

Acc Create Command

ASecurity

Generates CQRS Commands and Handlers for PHP 8.5. Creates immutable command DTOs with handlers that modify state. Includes unit tests.

  • 666 stars
  • 0 votes
  • 0 copies
  • 0 views
  • Added September 2, 2026
ai-agentsphp

Security analysis

A100/100

Scanned September 2, 2026

npx -y skills add majiayu000/claude-skill-registry --skill acc-create-command --agent claude-code

Installs into .claude/skills of the current project.

Are you the author of Acc Create Command?

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

Security grade badge for Acc Create Command
[![Security: A — Skills Directory](https://www.skillsdirectory.com/api/skills/majiayu000-acc-create-command-claude-skill-registry/badge)](https://www.skillsdirectory.com/skills/majiayu000-acc-create-command-claude-skill-registry)

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: acc-create-command
description: Generates CQRS Commands and Handlers for PHP 8.5. Creates immutable command DTOs with handlers that modify state. Includes unit tests.
---

# Command Generator

Generate CQRS-compliant Commands and Command Handlers with tests.

## Command Characteristics

- **Immutable**: `final readonly class`
- **Imperative naming**: Verb + noun (CreateOrder, ConfirmPayment)
- **Self-validating**: Validates invariants in constructor
- **Intent-revealing**: Name describes what should happen
- **Returns void or ID**: Never returns data

---

## Generation Process

### Step 1: Generate Command

**Path:** `src/Application/{BoundedContext}/Command/`

1. `{Name}Command.php` — Immutable command DTO

### Step 2: Generate Handler

**Path:** `src/Application/{BoundedContext}/Handler/`

1. `{Name}Handler.php` — Command processor

### Step 3: Generate Tests

**Path:** `tests/Unit/Application/{BoundedContext}/`

---

## File Placement

| Component | Path |
|-----------|------|
| Command | `src/Application/{BoundedContext}/Command/` |
| Handler | `src/Application/{BoundedContext}/Handler/` |
| Unit Tests | `tests/Unit/Application/{BoundedContext}/` |

---

## Command Naming Conventions

| Action | Command Name | Returns |
|--------|--------------|---------|
| Create new | `CreateOrderCommand` | ID |
| Confirm/Approve | `ConfirmOrderCommand` | void |
| Cancel/Reject | `CancelOrderCommand` | void |
| Update property | `UpdateShippingAddressCommand` | void |
| Add child | `AddOrderLineCommand` | void |
| Remove child | `RemoveOrderLineCommand` | void |

---

## Quick Template Reference

### Command

```php
final readonly class {Name}Command
{
    public function __construct(
        public {ValueObject} $id,
        public string $data
    ) {
        if (empty($data)) {
            throw new \InvalidArgumentException('Data is required');
        }
    }

    public static function fromArray(array $data): self
    {
        return new self(
            id: new {ValueObject}($data['id']),
            data: $data['data']
        );
    }
}
```

### Handler (Update Flow)

```php
final readonly class {Name}Handler
{
    public function __construct(
        private {Repository}Interface $repository,
        private EventDispatcherInterface $events
    ) {}

    public function __invoke({Name}Command $command): void
    {
        $aggregate = $this->repository->findById($command->id);

        if ($aggregate === null) {
            throw new NotFoundException($command->id);
        }

        $aggregate->doSomething($command->data);

        $this->repository->save($aggregate);

        foreach ($aggregate->releaseEvents() as $event) {
            $this->events->dispatch($event);
        }
    }
}
```

### Handler (Create Flow)

```php
public function __invoke(CreateCommand $command): AggregateId
{
    $aggregate = Aggregate::create(
        id: $this->repository->nextIdentity(),
        ...
    );

    $this->repository->save($aggregate);

    foreach ($aggregate->releaseEvents() as $event) {
        $this->events->dispatch($event);
    }

    return $aggregate->id();
}
```

---

## Anti-patterns to Avoid

| Anti-pattern | Problem | Solution |
|--------------|---------|----------|
| Returning Data | Query through command | Use Query for reads |
| No Validation | Invalid commands | Validate in constructor |
| Business Logic | Handler has decisions | Delegate to aggregate |
| Missing Events | Events not dispatched | Always dispatch after save |
| Direct Persistence | Bypassing aggregate | Always use aggregate methods |

---

## References

For complete PHP templates and examples, see:
- `references/templates.md` — Command, Handler, Test templates with patterns
- `references/examples.md` — CreateOrder, ConfirmOrder, CancelOrder examples and tests

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.