›
›
›
  1. docs
  2. ›
  3. byrcsc/laravel-approval
1.x
Browse documentationOpenClose

Getting started

  • Introduction
  • Installation and setup
  • Quick start

Core concepts

  • Workflows and stages
  • Choosing the workflow
  • Approvers and resolvers
  • Requests and state
  • Conditional stages

Approval flow

  • Submitting for approval
  • Recording decisions
  • Attribute drafts
  • Returns and resubmission
  • Bulk decisions

Assignments and deadlines

  • Delegation and reassignment
  • SLAs and escalation

Reading and authorization

  • Eligibility and authorization
  • Queries and timelines
  • Events and listeners
  • Notifications
  • Notification content

Operations

  • Workflow definitions
  • Audit trail and evidence
  • Console commands
  • Testing
  • Troubleshooting

Getting started

  • Introduction
  • Installation and setup
  • Quick start

Core concepts

  • Workflows and stages
  • Choosing the workflow
  • Approvers and resolvers
  • Requests and state
  • Conditional stages

Approval flow

  • Submitting for approval
  • Recording decisions
  • Attribute drafts
  • Returns and resubmission
  • Bulk decisions

Assignments and deadlines

  • Delegation and reassignment
  • SLAs and escalation

Reading and authorization

  • Eligibility and authorization
  • Queries and timelines
  • Events and listeners
  • Notifications
  • Notification content

Operations

  • Workflow definitions
  • Audit trail and evidence
  • Console commands
  • Testing
  • Troubleshooting

byrcsc/laravel-approval · 1.x

Console commands.

Inspect, repair, escalate, verify, and maintain approvals through Artisan.

Every command that takes a request accepts its public ULID or its numeric key. People copy the ULID from a URL and the key from a query, so both forms work.

CommandPurposeSchedule
approval:escalateApply each overdue stage's escalation policyRequired
approval:delegationsMove assignments as delegation windows open and closeRequired for future windows
approval:verifyWalk the audit trail's hash chainsRecommended
approval:doctorFind stranded stagesRecommended
approval:statusSummarize state and list what needs attentionOn demand
approval:syncReconcile version-controlled workflow definitionsOn deploy
approval:resyncRebuild a live request's approver assignmentsOn demand

approval:escalate

php artisan approval:escalate

Finds stages whose deadline has passed and applies each stage's escalation policy. Nothing escalates unless this command runs, so schedule it:

Schedule::command('approval:escalate')->everyFifteenMinutes();

The sweep is idempotent. The interval sets how soon after a deadline the command notices it, and does not affect correctness. Each stage runs in its own transaction, so one misconfigured stage cannot stop the others. If a stage's strategy throws, that stage rolls back entirely and the next run retries it.

Reports escalations, reminders, newly stranded stages, and failures. Exits non-zero if any stage's strategy threw, so a scheduler that watches exit codes reports the failure. See SLAs and escalation.

approval:delegations

php artisan approval:delegations

Moves assignments to delegates when a standing delegation window opens, and back to approvers when it closes. Granting, revoking, and stage activation already move assignments, so this command only matters for windows that open or close later:

Schedule::command('approval:delegations')->everyFifteenMinutes();

The command is idempotent. The interval sets how soon after a window opens or closes the command moves assignments. Each stage runs in its own transaction.

Reports how many assignments moved. When the delegations migration has not run, it prints a warning and exits zero.

approval:verify

php artisan approval:verify
php artisan approval:verify 01JBK7QK5X8ZW2F0T3D9M4NA6E
ArgumentOptionalMeaning
requestyesVerify one request, by ULID or id

Walks each request's hash chain and reports any action or attachment that fails verification. Reports findings and never repairs them. Exits non-zero when it finds anything, or when the named request does not exist.

See audit trail and evidence.

approval:doctor

php artisan approval:doctor --limit=50
OptionDefaultMeaning
--limit50Maximum stranded stages to list

Finds pending stages whose living assignment holders can no longer meet the required approvals. Nobody can finish these stages, and no other part of the engine reports them. Exits non-zero when it finds any.

  Found 1 stranded approval stage.
  01JBK7QK5X8ZW2F0T3D9M4NA6E ... Directors: 1 living / 2 required

Fix them with delegation, reassignment, or a resync.

approval:status

php artisan approval:status --limit=10
OptionDefaultMeaning
--limit10How many requests to list under each heading

Prints a count per request state, then lists the requests that need attention under these headings:

  • Overdue requests wait on an approver past the deadline.
  • Stranded requests have living holders who cannot meet the required approvals.
  • Conflicted requests passed every stage, then found the record had changed.

Always exits zero. It is a report, not a check.

  State ............................ Requests
  pending .................................. 7
  approved ................................ 41
  …

  Overdue
  01JBK7QK5X… ......... Finance, due 3 hours ago

  Conflicted, waiting on a person
  01JBK2M9YB… ......................... 2 days ago

Nothing in the package resolves conflicted requests automatically. They stay open until an administrator reapplies or discards the draft.

approval:sync

php artisan approval:sync --dry-run
php artisan approval:sync
OptionMeaning
--dry-runPreview changes without writing them

Creates and reconciles the workflows declared in approval.definitions. The command applies additive and supported configuration changes. It refuses to remove or reorder existing stages or approvers. A refusal aborts the whole sync before it writes anything.

Exits non-zero when anything was refused. See workflow definitions.

approval:resync

php artisan approval:resync 01JBK7QK5X8ZW2F0T3D9M4NA6E --operator=42
php artisan approval:resync 91 --operator="App\Models\Staff:7" --prune
Argument / optionRequiredMeaning
requestyesThe request ULID, or its numeric id
--operatoryesA key of the configured user model, or type:id
--prunenoAlso drop approvers the workflow no longer names

Re-runs a pending request's approver rules against the current workflow. Use it when an approver has left and their requests are stuck.

Resync never runs automatically, because rebuilding a live request's assignments is a decision a person makes. --operator is required, and the command records the operator on the audit trail. Shell history does not record who ran a command. --operator accepts a morph alias or a class name in the type:id form.

Prints the change per stage. Exits non-zero when the request or operator cannot be resolved:

  Stage 1 .................................. +1 / -0
    + App\Models\User:9

See delegation and reassignment.

A workable schedule

use Illuminate\Support\Facades\Schedule;

Schedule::command('approval:escalate')->everyFifteenMinutes();
Schedule::command('approval:delegations')->everyFifteenMinutes();
Schedule::command('approval:doctor')->hourly();
Schedule::command('approval:verify')->dailyAt('03:00');

approval:escalate is required for deadlines to have any effect. approval:delegations is required when standing delegations start or end in the future. approval:doctor and approval:verify are checks that signal a problem with a non-zero exit. Send their failures to the same place as your other scheduler failures.

What to read next

  • SLAs and escalation to schedule overdue processing.
  • Delegation and reassignment to grant standing delegations.
  • Audit trail and evidence to understand verification results.
  • Troubleshooting to diagnose non-zero command exits.
PreviousAudit trail and evidenceNextTesting
View source

On this page

  1. approval:escalate
  2. approval:delegations
  3. approval:verify
  4. approval:doctor
  5. approval:status
  6. approval:sync
  7. approval:resync
  8. A workable schedule
  9. What to read next