Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 13 additions & 21 deletions .env.example
Original file line number Diff line number Diff line change
@@ -1,17 +1,15 @@
# ==============================================================================
# FILAMENT ACTIONGUARD - ENTERPRISE ENVIRONMENT CONFIGURATION
# ==============================================================================
# Compliant with Laravel 11.x, 12.x, and Laravel 13.x Enterprise Architecture
# Includes OWASP Session Hardening, Hyphenated Cache Prefixes,
# Request Forgery Protection, and First-Party AI SDK Primitives.
# Local-development example only. Do not copy it to production unchanged.
# ==============================================================================

# ------------------------------------------------------------------------------
# 1. APPLICATION & GENERAL SECURITY
# ------------------------------------------------------------------------------
APP_NAME="Filament ActionGuard"
APP_ENV=local
APP_KEY=base64:mwI8+tv+nFBfp+UiEtskdA471cijww4UZEwfIW/znbQ=
APP_KEY=
APP_DEBUG=true
APP_URL=http://localhost:8000
APP_TIMEZONE=UTC
Expand Down Expand Up @@ -55,7 +53,7 @@ DB_FOREIGN_KEYS=true
# DB_PASSWORD=your_secure_password

# ------------------------------------------------------------------------------
# 4. SESSION & COOKIE SECURITY HARDENING (Laravel 13 & OWASP Standards)
# 4. SESSION & COOKIE SETTINGS
# ------------------------------------------------------------------------------
SESSION_DRIVER=file
SESSION_LIFETIME=120
Expand All @@ -64,6 +62,7 @@ SESSION_ENCRYPT=true
SESSION_SERIALIZATION=json
SESSION_PATH=/
SESSION_DOMAIN=null
# Set true in every HTTPS deployment.
SESSION_SECURE_COOKIE=false
SESSION_HTTP_ONLY=true
SESSION_SAME_SITE=lax
Expand Down Expand Up @@ -126,30 +125,23 @@ AWS_BUCKET=
AWS_USE_PATH_STYLE_ENDPOINT=false

# ------------------------------------------------------------------------------
# 11. LARAVEL 13 FIRST-PARTY AI SDK & AGENT ECOSYSTEM
# 11. ACTIONGUARD POLICY SETTINGS
# ------------------------------------------------------------------------------
AI_DEFAULT_PROVIDER=openai
# OPENAI_API_KEY=
# ANTHROPIC_API_KEY=
# GEMINI_API_KEY=
# OLLAMA_BASE_URL=http://localhost:11434

# ------------------------------------------------------------------------------
# 12. ACTIONGUARD POLICY & ENTERPRISE ENGINE SETTINGS
# ------------------------------------------------------------------------------
# Enable or disable ActionGuard evaluation globally
# Enable or disable ActionGuard evaluation globally. Keep true in production.
ACTIONGUARD_ENABLED=true

# Security posture: Fail-closed (true) blocks actions if a check throws an unhandled exception
ACTIONGUARD_FAIL_CLOSED=true

# Enterprise Business-Core bridge mode:
# - false: Standalone Community mode (evaluates native ActionGuard checks)
# - true: Delegates to allgorithm/business-core operation descriptors when installed
ACTIONGUARD_ENTERPRISE_MODE=false
# Disabled by default. Enable only for a controlled, logged maintenance task.
ACTIONGUARD_ALLOW_BYPASS=false

# Dispatch user-facing Filament danger notifications on state invariant violations
ACTIONGUARD_NOTIFICATIONS_ENABLED=true

# Enable detailed auditing for invariant checks
# Enable data-minimised structured audit events; route the channel to your SIEM.
ACTIONGUARD_AUDIT_TRAIL=true
ACTIONGUARD_AUDIT_CHANNEL=stack

# Relative and HTTPS resolution links are allowed. HTTP is blocked by default.
ACTIONGUARD_ALLOW_INSECURE_RESOLUTION_URLS=false
33 changes: 31 additions & 2 deletions .github/workflows/run-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -59,8 +59,15 @@ jobs:
strategy:
fail-fast: false
matrix:
php: ['8.3', '8.4', '8.5']
stability: ['prefer-stable']
include:
- php: '8.3'
stability: 'prefer-stable'
- php: '8.4'
stability: 'prefer-stable'
- php: '8.5'
stability: 'prefer-stable'
- php: '8.3'
stability: 'prefer-lowest'

steps:
- name: Checkout code
Expand All @@ -83,3 +90,25 @@ jobs:

- name: Execute tests
run: vendor/bin/pest --ci

locked-test:
name: PHP 8.3 - locked dependencies
runs-on: ubuntu-latest
timeout-minutes: 10

steps:
- name: Checkout code
uses: actions/checkout@v7

- name: Setup PHP
uses: shivammathur/setup-php@v2
with:
php-version: '8.3'
extensions: dom, curl, libxml, mbstring, zip, pcntl, pdo, sqlite, pdo_sqlite, bcmath, soap, intl, gd, exif, iconv
coverage: none

- name: Install locked dependencies
run: composer install --prefer-dist --no-interaction --ansi

- name: Execute tests against the release lockfile
run: vendor/bin/pest --ci
2 changes: 1 addition & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,6 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

- **Developer Experience & Tooling**
- Root `artisan` CLI bridge to Orchestra Testbench and Workbench environment.
- Comprehensive test suite with 98 Pest tests and 225 assertions covering architecture, unit checks, traits, enterprise bridge hardening, and demo product scenarios.
- Comprehensive test suite with 103 Pest tests and 234 assertions covering architecture, unit checks, traits, enterprise bridge hardening, and demo product scenarios.

[1.0.0]: https://github.com/allgorithm/filament-actionguard/releases/tag/v1.0.0
56 changes: 19 additions & 37 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
<a href="https://packagist.org/packages/allgorithm/filament-actionguard"><img src="https://img.shields.io/packagist/v/allgorithm/filament-actionguard.svg?style=flat-square&color=0ea5e9" alt="Latest Version on Packagist"></a>
<a href="https://php.net"><img src="https://img.shields.io/badge/PHP-8.3%20--%208.5-777BB4.svg?style=flat-square&logo=php&logoColor=white" alt="PHP 8.3 - 8.5"></a>
<a href="https://filamentphp.com"><img src="https://img.shields.io/badge/Filament-v5.x-FDAE4B.svg?style=flat-square&logo=laravel&logoColor=white" alt="Filament v5"></a>
<a href="https://pestphp.com"><img src="https://img.shields.io/badge/Pest-98%20Tests%20Passing-10b981.svg?style=flat-square&logo=pest" alt="Pest Tests"></a>
<a href="https://pestphp.com"><img src="https://img.shields.io/badge/Pest-103%20Tests%20Passing-10b981.svg?style=flat-square&logo=pest" alt="Pest Tests"></a>
<a href="https://phpstan.org"><img src="https://img.shields.io/badge/PHPStan-Level%208%20(0%20errors)-6366f1.svg?style=flat-square" alt="PHPStan Level 8"></a>
<a href="LICENSE.md"><img src="https://img.shields.io/badge/License-MIT-gray.svg?style=flat-square" alt="License MIT"></a>
</p>
Expand All @@ -17,7 +17,7 @@

> **🛡️ Stop incomplete records and prevent data degradation across critical Filament actions.**

**Filament ActionGuard** is an enterprise-grade preflight gatekeeper and state invariant defense plugin for **Filament**. It prevents incomplete, invalid, or corrupted records from being published, approved, or transitioned into critical lifecycle states.
**Filament ActionGuard** is a production-grade preflight gatekeeper and state invariant defense plugin for **Filament**. It prevents incomplete, invalid, or corrupted records from being published, approved, or transitioned into critical lifecycle states.

---

Expand Down Expand Up @@ -61,9 +61,8 @@ ActionGuard introduces a robust **Two-Phase Invariant Defense System**:
- `RelationshipCheck`: Verifies loaded relationships (e.g. belongs-to, has-many).
- `MediaCheck`: Checks media collections (Spatie MediaLibrary or file upload paths).
- `CallbackCheck`: Flexible check with full `CheckResult` control.
- ⚡️ **Dual-Mode Enterprise Bridge (Coming Soon):** Works 100% standalone out-of-the-box (Community Edition), with seamless integration for `allgorithm/business-core` Domain Operation Descriptors coming soon.
- 🌍 **Fully Localized (i18n):** Complete English and German translations included out-of-the-box.
- 💎 **Bulletproof Quality:** PHPStan **Level 8** (0 errors), 100% PSR-12 code style, and 98 comprehensive Pest tests.
- 💎 **Bulletproof Quality:** PHPStan **Level 8** (0 errors), 100% PSR-12 code style, and 103 comprehensive Pest tests.

---

Expand Down Expand Up @@ -182,6 +181,10 @@ Product::withoutActionGuards(function () use ($product) {
});
```

Bypasses are disabled by default. Enable `ACTIONGUARD_ALLOW_BYPASS=true` only
for a controlled maintenance operation; the bypass is scoped to that callback
and can emit a data-minimised audit event.

---

### 3. Single Source of Truth (`forState`)
Expand All @@ -197,28 +200,6 @@ ActionGuardAction::make('publish')

---

### 4. Dual-Mode Enterprise Bridge (`allgorithm/business-core`) *(Coming Soon)*

> [!NOTE]
> **Enterprise Bridge (Coming Soon)**: ActionGuard is 100% functional standalone out-of-the-box. The direct bridge to `allgorithm/business-core` (`^1.2`) is currently in final integration testing and will be officially unlocked with the upcoming commercial Enterprise release.

The Community package has no dependency on BusinessCore. Once you install a compatible licensed `allgorithm/business-core` package (`^1.2`), ActionGuard will detect its contracts automatically without requiring application or adapter changes:

```php
use App\Domain\Operations\PublishProductOperation;

ActionGuardAction::make('publish')
->label('Publish Product')
->operation(PublishProductOperation::class)
->action(fn ($record) => $record->update(['status' => 'published']));
```

If `operation()` is invoked without the licensed Core, ActionGuard fails closed with a clear, descriptive `LogicException`. Direct Community integrations through `checks()` and `forState()` remain fully available and recommended.

ActionGuard registers a safe default `OperationContextFactoryContract` for Community installations. A licensed BusinessCore package can replace this container binding from its service provider to supply its authoritative actor, role, permission, tenant, and organization context. This activation is automatic: existing applications and `operation()` calls require no changes. Internal Enterprise exceptions are logged with a correlation reference while UI messages remain free of implementation details.

---

## 🗂️ Built-in Checks Reference

| Check Class | Evaluates | Example |
Expand Down Expand Up @@ -250,31 +231,32 @@ ActionGuardAction::make('publish')
ActionGuard is built with strict quality standards:

```bash
# Run automated test suite (98 tests, 225 assertions)
# Run automated test suite (103 tests, 234 assertions)
composer test

# Run code style fixer and static analysis (PHPStan Level 8)
composer lint
```

---

## 🏛️ Architecture Comparison
## Production safeguards

| Feature | `filament-actionguard` (This Plugin) | `allgorithm/business-core` (Enterprise Platform) |
| :--- | :--- | :--- |
| **Layer** | **Presentation Layer** (Filament UI Adapter) | **Domain & Application Layer** (Omnichannel Core) |
| **License** | **MIT (Open Source)** | Commercial Enterprise License |
| **Execution** | Preflight Action Modal & Model Post-Save Invariant | Omnichannel Guard Pipeline (API, Queue, CLI, UI) |
| **Audit Trail** | UI Feedback & Notifications | Tamper-proof 8-W Audit Log with SHA-256 Hash Chain |
| **Integration** | Native `operation()` & `forState()` bridge | Domain Operation Descriptors & Contracts |
ActionGuard is an invariant check, not an authorization, tenancy, or database
constraint system. Enforce authorization with Laravel policies and ensure that
critical bulk writes do not use `Model::where(...)->update()`, because Eloquent
does not dispatch model events for mass updates. For invariants that must hold
against every write path, add database constraints or enforce writes through an
application service. In production, keep `ACTIONGUARD_FAIL_CLOSED=true`, use a
unique `APP_KEY`, disable debug mode, enable secure cookies for HTTPS, and route
the optional data-minimised audit channel to your central logging system.

---

## 📄 License

The MIT License (MIT). Please see [License File](LICENSE.md) for more information.

The project artwork was generated with AI; see [artwork attribution](art/ATTRIBUTION.md).

---

<p align="center">
Expand Down
10 changes: 8 additions & 2 deletions SECURITY.md
Original file line number Diff line number Diff line change
@@ -1,9 +1,15 @@
# Security Policy

## Supported Versions

Only the latest released `1.x` version receives security fixes. Security support
is best effort; do not rely on this package as an authorization boundary.

## Reporting Security Vulnerabilities

If you discover a security vulnerability within **Filament ActionGuard**, please send an e-mail to **security@allgorithm.io** or report it via [GitHub Security Advisories](https://github.com/allgorithm/filament-actionguard/security/advisories/new).
If you discover a security vulnerability within **Filament ActionGuard**, please send an e-mail to **security-allgorithm@online.de** or report it via [GitHub Security Advisories](https://github.com/allgorithm/filament-actionguard/security/advisories/new).

Please do not disclose security issues publicly in issues or discussions until they have been addressed.

All security vulnerabilities will be promptly addressed, and we will issue a security advisory and patch as soon as possible.
We will acknowledge reports within five business days and publish a security
advisory and patch, or a remediation timeline, once the issue has been triaged.
8 changes: 8 additions & 0 deletions art/ATTRIBUTION.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
# Artwork attribution and AI disclosure

`avatar.png` and `banner.png` were generated with AI for Filament ActionGuard.

They are project artwork, not third-party stock assets, and are distributed with
this repository under the project MIT license. This disclosure is informational
and does not assert that the images are protected by copyright in every
jurisdiction. Do not remove this notice when redistributing the artwork.
5 changes: 4 additions & 1 deletion composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -61,11 +61,14 @@
},
"config": {
"sort-packages": true,
"platform": {
"php": "8.3.0"
},
"allow-plugins": {
"pestphp/pest-plugin": true
}
},
"minimum-stability": "dev",
"minimum-stability": "stable",
"prefer-stable": true,
"suggest": {
"allgorithm/business-core": "Required only for the licensed Enterprise Bridge (^1.2); Community checks work without it."
Expand Down
Loading