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
65 changes: 48 additions & 17 deletions .github/workflows/tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,43 +2,74 @@ name: Tests

on:
push:
branches: [ main, master ]
branches: [main, master]
pull_request:
branches: [ main, master ]
branches: [main, master]

permissions:
contents: read

jobs:
tests:
test:
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
php: ['8.4']
include:
- { php: '8.3', laravel: '12', testbench: '^10.9' }
- { php: '8.4', laravel: '12', testbench: '^10.9' }
- { php: '8.5', laravel: '12', testbench: '^10.9' }
- { php: '8.3', laravel: '13', testbench: '^11.0' }
- { php: '8.4', laravel: '13', testbench: '^11.0' }
- { php: '8.5', laravel: '13', testbench: '^11.0' }

name: PHP ${{ matrix.php }}
name: PHP ${{ matrix.php }} / Laravel ${{ matrix.laravel }}

steps:
- name: Checkout code
uses: actions/checkout@v4
- uses: actions/checkout@v4
Comment thread
coderabbitai[bot] marked this conversation as resolved.
with:
persist-credentials: false

- name: Set up PHP
uses: shivammathur/setup-php@v2
- uses: shivammathur/setup-php@v2
with:
php-version: ${{ matrix.php }}
tools: composer
coverage: none

- name: Cache Composer dependencies
uses: actions/cache@v4
- uses: actions/cache@v4
with:
path: ~/.composer/cache
key: composer-${{ matrix.php }}-${{ hashFiles('composer.lock') }}
restore-keys: composer-${{ matrix.php }}-
key: composer-${{ matrix.php }}-laravel-${{ matrix.laravel }}-${{ hashFiles('composer.json') }}

- name: Select framework version
run: composer require --dev orchestra/testbench:${{ matrix.testbench }} --no-update --no-interaction

- name: Install dependencies
run: composer install --no-interaction --no-progress
run: composer update --with-all-dependencies --no-interaction --no-progress

- name: Run PHPStan
run: vendor/bin/phpstan analyse --memory-limit=2G
- name: Validate package metadata
run: composer validate --strict

- name: Run tests
run: vendor/bin/phpunit tests/
run: composer test

- name: Run PHPStan
run: composer phpstan

- name: Run Rector dry-run
run: composer rector
Comment thread
coderabbitai[bot] marked this conversation as resolved.

lowest-dependencies:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
persist-credentials: false
- uses: shivammathur/setup-php@v2
with:
php-version: '8.3'
tools: composer
coverage: none
- run: composer require --dev orchestra/testbench:^10.9 --no-update --no-interaction
- run: composer update --prefer-lowest --with-all-dependencies --no-interaction --no-progress
- run: composer test
6 changes: 3 additions & 3 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,13 @@ Warden is a Laravel security audit **package** (library), not a standalone appli
|---|---|
| Install dependencies | `composer install --no-interaction` |
| Static analysis (lint) | `composer phpstan` or `vendor/bin/phpstan analyse --memory-limit=2G` |
| Run tests | `vendor/bin/phpunit tests/` |
| Run tests | `composer test` or `vendor/bin/phpunit tests/` |
| Code quality (dry-run) | `vendor/bin/rector process --dry-run` |
| Run package commands | `vendor/bin/testbench warden:audit` / `vendor/bin/testbench warden:syntax` |

### Gotchas

- **Tests target Laravel 12+**: The package supports Laravel 7–13, but `orchestra/testbench ^10.9` pins the test suite to Laravel 12+; CI runs against the latest supported Laravel.
- **Supported framework matrix**: Warden 2 supports Laravel 12–13 on PHP 8.3–8.5. CI covers every declared PHP/Laravel combination using Testbench 10 and 11.
- **PHPStan with full framework**: When `orchestra/testbench` is installed (which brings in `laravel/framework`), PHPStan may report additional errors due to full type information replacing stubs. The CI workflow installs testbench, so check PHPStan passes with `composer phpstan`.
- **testbench.yaml**: Registers `WardenServiceProvider` so `vendor/bin/testbench` can run the package's artisan commands (e.g., `warden:audit`).
- **testbench.yaml**: Registers `WardenServiceProvider` so `vendor/bin/testbench` can run package commands. Testbench uses its fixture application's base path; service fixtures should set an explicit temporary base path when testing manifests and lockfiles.
- **Test app**: To test the package inside a real Laravel app, create one in `/tmp`: `cd /tmp && composer create-project laravel/laravel warden-test-app` then `cd warden-test-app && composer config repositories.warden path /workspace && composer require dgtlss/warden:* --dev`.
60 changes: 60 additions & 0 deletions UPGRADE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
<h1 align="center">Upgrading to Warden 2.0</h1>

<p align="center">A migration guide for Warden 1.x applications.</p>

<p align="center">
<a href="https://github.com/dgtlss/warden/actions"><img src="https://github.com/dgtlss/warden/actions/workflows/tests.yml/badge.svg" alt="Tests"></a>
<a href="https://packagist.org/packages/dgtlss/warden"><img src="https://img.shields.io/packagist/v/dgtlss/warden?style=flat-square" alt="Latest Version on Packagist"></a>
<a href="https://packagist.org/packages/dgtlss/warden"><img src="https://img.shields.io/packagist/dt/dgtlss/warden?style=flat-square" alt="Total Downloads"></a>
<a href="https://packagist.org/packages/dgtlss/warden"><img src="https://img.shields.io/packagist/php-v/dgtlss/warden?style=flat-square" alt="PHP Version"></a>
<a href="https://github.com/dgtlss/warden/blob/main/LICENSE"><img src="https://img.shields.io/github/license/dgtlss/warden?style=flat-square" alt="License"></a>
</p>

## Introduction

Warden 2.0 is a CI-first major release. Review the following changes before updating pipeline configuration.

## Supported Platforms

- PHP 8.3–8.5
- Laravel 12–13
- Install with `composer require --dev dgtlss/warden`

Run Warden before the production artifact is rebuilt with `composer install --no-dev`.

## Command changes

| Warden 1.x | Warden 2.0 |
|---|---|
| `--severity=high` | `--fail-on=high` |
| `--output=json` | `--format=json` |
| Shell redirection | `--output-file=report.json` |
| `--npm` | Automatic when `package-lock.json` exists |
| `--ignore-abandoned` | Reviewed suppression or a higher `--fail-on` threshold |
| `--force` | Removed; Warden no longer caches audit results |
| `--no-notify` | Notifications are off by default; use `--notify` to enable |
| `warden:schedule` | Removed; schedule the CI pipeline instead |
| `--output=jenkins` | `--format=junit` |

Warden 2.0 also adds `warden:init`, the default `source` and `platform` audits, and parser-backed application security findings.

The exit code contract is now strict: findings return `1`, while an incomplete or invalid audit returns `2` even when `--fail-on=never` is used.

## Configuration changes

- Remove `cache`, `schedule`, `history`, `sensitive_keys`, `webhook_url`, and top-level `email_recipients` entries.
- Replace wildcard `ignore_findings` rules with entries containing `id`, `reason`, and `expires_at`; add `fingerprint` when only one occurrence should be accepted.
- Replace custom audit implementations with the typed `run(AuditContext): AuditResult` contract.
- Configure notifications only under `warden.notifications`; the legacy webhook path is no longer dispatched.
- Add optional `rule_overrides` values using `enforced`, `advisory`, or `off`; malformed overrides fail before any scan starts.
- Review `audits.source`, `audits.supply_chain`, and `audits.platform` when merging published configuration.

Republish the configuration or merge the new defaults manually:

```bash
php artisan vendor:publish --tag=warden-config --force
```

## Removed runtime features

The production scheduler and audit-history migration were removed because a development dependency is not present after a production `--no-dev` install. Use CI scheduling and persist JSON, SARIF, GitLab, or JUnit artifacts in the CI platform instead.
34 changes: 24 additions & 10 deletions composer.json
Original file line number Diff line number Diff line change
@@ -1,36 +1,47 @@
{
"name": "dgtlss/warden",
"description": "A Laravel package that proactively monitors your dependencies for security vulnerabilities by running automated composer audits and sending notifications via webhooks and email",
"description": "A deterministic Laravel security gate for CI and deployment pipelines",
"keywords": [
"laravel",
"composer",
"security",
"vulnerabilities",
"audits",
"ci",
"sast",
"secret-scanning",
"supply-chain",
"notifications",
"CVE"
],
"version": "1.5.3",
"license": "MIT",
"autoload": {
"psr-4": {
"Dgtlss\\Warden\\": "src/"
}
},
"autoload-dev": {
"psr-4": {
"Dgtlss\\Warden\\Tests\\": "tests/"
}
},
"authors": [
{
"name": "Nathan Langer",
"email": "nathanlanger@googlemail.com"
}
],
"minimum-stability": "dev",
"prefer-stable": true,
"require": {
"php": ">=8.3",
"illuminate/support": "^7.0|^8.0|^9.0|^10.0|^11.0|^12.0|^13.0",
"illuminate/cache": "^7.0|^8.0|^9.0|^10.0|^11.0|^12.0|^13.0",
"php": ">=8.3 <8.6",
"illuminate/console": "^12.0|^13.0",
"illuminate/contracts": "^12.0|^13.0",
"illuminate/encryption": "^12.0|^13.0",
"illuminate/http": "^12.0|^13.0",
"illuminate/support": "^12.0|^13.0",
"guzzlehttp/guzzle": "^7.0",
"laravel/prompts": "^0.3"
"nikic/php-parser": "^5.8",
"symfony/finder": "^7.2|^8.0",
"symfony/process": "^7.2|^8.0"
},
"extra": {
"laravel": {
Expand All @@ -43,9 +54,12 @@
"phpstan/phpstan": "^2.1",
"rector/rector": "^2.2",
"larastan/larastan": "^3.0",
"orchestra/testbench": "^10.9|^11.0"
"orchestra/testbench": "^10.9|^11.0",
"phpunit/phpunit": "^11.5|^12.0"
},
"scripts": {
"phpstan": "vendor/bin/phpstan analyse --memory-limit=2G"
"phpstan": "vendor/bin/phpstan analyse --memory-limit=2G",
"test": "vendor/bin/phpunit tests/",
"rector": "vendor/bin/rector process --dry-run --no-progress-bar"
}
}
Loading
Loading