From a21d94220b468b23159b912db6919fcbd301dd6b Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 00:40:23 +0000 Subject: [PATCH 1/2] Add integration feedback documentation and roadmap Based on wp-sinople-theme integration feedback: - PHP-AEGIS-HANDOVER.md: Recommendations for php-aegis team - RDF/Turtle escaping functions needed - SPDX headers, PHP 8.1+ features - Differentiation from WordPress core - ROADMAP.md: sanctify-php improvement plan - Phase 1: Pre-built binaries and Docker - Phase 2: Semantic web (RDF/Turtle) support - Phase 3: PHP 8.x syntax completeness - Phase 4: WordPress integration docs - Phase 5: php-aegis integration - IMPLEMENTATION-TRACKER.md: Cross-team coordination --- docs/IMPLEMENTATION-TRACKER.md | 143 ++++++++++ docs/PHP-AEGIS-HANDOVER.md | 311 +++++++++++++++++++++ docs/ROADMAP.md | 496 +++++++++++++++++++++++++++++++++ 3 files changed, 950 insertions(+) create mode 100644 docs/IMPLEMENTATION-TRACKER.md create mode 100644 docs/PHP-AEGIS-HANDOVER.md create mode 100644 docs/ROADMAP.md diff --git a/docs/IMPLEMENTATION-TRACKER.md b/docs/IMPLEMENTATION-TRACKER.md new file mode 100644 index 0000000..ee27c32 --- /dev/null +++ b/docs/IMPLEMENTATION-TRACKER.md @@ -0,0 +1,143 @@ +# Implementation Tracker + +## Status Overview + +| Area | Status | Next Action | +|------|--------|-------------| +| php-aegis Handover | ✅ Complete | Send to php-aegis team | +| sanctify-php Roadmap | ✅ Complete | Begin Phase 1 | +| Binary Releases | 🔲 Not Started | Create CI workflow | +| Docker Container | 🔲 Not Started | Create Dockerfile | +| Semantic Support | 🔲 Not Started | Design AST extensions | + +--- + +## Immediate Actions + +### For php-aegis Team + +1. **Review handover document**: `docs/PHP-AEGIS-HANDOVER.md` +2. **Priority implementation**: + - `Aegis\Semantic\Turtle::escapeString()` + - `Aegis\Semantic\Turtle::escapeIRI()` + - SPDX headers on all files + +### For sanctify-php Team + +1. **Phase 1 Priority**: Make tool accessible without Haskell + - [ ] GitHub Actions for binary releases + - [ ] Dockerfile for container distribution + - [ ] Update README with installation options + +2. **Phase 2 Priority**: Semantic web support + - [ ] Create `Sanctify.Analysis.Semantic` module + - [ ] Extend taint sinks for Turtle/JSON-LD contexts + - [ ] Add WordPress semantic theme detection + +--- + +## Cross-Team Coordination + +### Shared Namespace Agreement + +Both tools should recognize these function signatures: + +```php +// php-aegis provides these at runtime +Aegis\Semantic\Turtle::escapeString(string $value): string +Aegis\Semantic\Turtle::escapeIRI(string $iri): string +Aegis\Semantic\JsonLd::escapeValue(mixed $value): string +Aegis\IndieWeb\Micropub::sanitizeContent(string $content, array $context = []): string +Aegis\IndieWeb\IndieAuth::verifyToken(string $token, string $endpoint): array|false +``` + +```haskell +-- sanctify-php recognizes these as safe sinks +aegisSemantic :: [Text] +aegisSemantic = + [ "Aegis\\Semantic\\Turtle::escapeString" + , "Aegis\\Semantic\\Turtle::escapeIRI" + , "Aegis\\Semantic\\JsonLd::escapeValue" + , "Aegis\\IndieWeb\\Micropub::sanitizeContent" + ] +``` + +### Integration Testing + +When both tools are updated: + +```bash +# 1. Analyze code that uses php-aegis +sanctify-php analyze ./project --aegis-aware + +# 2. Verify no false positives for Aegis-escaped output +# 3. Verify Turtle context detection works +# 4. Verify auto-fix inserts correct Aegis calls +``` + +--- + +## Issue Templates + +### For php-aegis Repository + +**Title**: Add semantic web escaping support (RDF/Turtle) + +**Body**: +```markdown +## Context +Integration feedback from wp-sinople-theme identified missing RDF/Turtle escaping functions. + +## Requirements +- [ ] `Aegis\Semantic\Turtle::escapeString()` - W3C Turtle string escaping +- [ ] `Aegis\Semantic\Turtle::escapeIRI()` - IRI validation and escaping +- [ ] Follow escape rules from https://www.w3.org/TR/turtle/#sec-escapes + +## Reference Implementation +See sanctify-php `docs/PHP-AEGIS-HANDOVER.md` for reference code. + +## Testing +Should correctly escape: +- Backslashes, quotes, newlines, tabs +- Unicode control characters (U+0000 to U+001F) +- Invalid IRI characters per RFC 3987 +``` + +### For sanctify-php Repository + +**Title**: Add pre-built binary releases + +**Body**: +```markdown +## Problem +Users need Haskell toolchain to build sanctify-php, preventing adoption. + +## Solution +Provide statically-linked binaries via GitHub Releases for: +- linux-x86_64 +- linux-aarch64 +- darwin-x86_64 +- darwin-aarch64 +- windows-x86_64 + +## Implementation +- [ ] GitHub Actions workflow with matrix strategy +- [ ] Static linking flags +- [ ] GPG signing +- [ ] Release automation + +## Reference +See `docs/ROADMAP.md` Phase 1 for details. +``` + +--- + +## Communication Channels + +- **sanctify-php issues**: https://github.com/hyperpolymath/sanctify-php/issues +- **php-aegis issues**: https://github.com/hyperpolymath/php-aegis/issues + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath* diff --git a/docs/PHP-AEGIS-HANDOVER.md b/docs/PHP-AEGIS-HANDOVER.md new file mode 100644 index 0000000..0f20053 --- /dev/null +++ b/docs/PHP-AEGIS-HANDOVER.md @@ -0,0 +1,311 @@ +# PHP-Aegis Handover Document + +## Context + +This document provides integration feedback from the wp-sinople-theme WordPress theme project, which attempted to use both `sanctify-php` (static analysis) and `php-aegis` (runtime security library) together. + +**Integration Report Date**: 2025-12-27 +**Integration Target**: WordPress semantic theme with IndieWeb/Micropub support + +--- + +## Integration Feedback Summary + +### Issues Identified with php-aegis + +| Issue | Severity | Impact | +|-------|----------|--------| +| Feature set too minimal | Medium | WordPress has equivalent functions already | +| No RDF/Turtle escaping | High | Semantic themes require W3C-compliant escaping | +| Missing SPDX license headers | Low | Compliance concern for FOSS projects | +| No PHP 8.1+ features | Medium | Missing enums, union types, readonly properties | + +--- + +## Detailed Recommendations + +### 1. Differentiate from WordPress Core Functions + +**Problem**: WordPress already provides `esc_html()`, `esc_attr()`, `sanitize_text_field()`, etc. + +**Recommendation**: php-aegis should provide value *beyond* WordPress core: + +```php +// INSTEAD OF duplicating WordPress functions: +Aegis\Escape::html($string); // ← WordPress already has esc_html() + +// PROVIDE specialized capabilities: +Aegis\Semantic\Turtle::escapeString($string); // ← WordPress doesn't have this +Aegis\Semantic\Turtle::escapeIRI($iri); +Aegis\Semantic\JsonLd::sanitize($data); +Aegis\IndieWeb\Micropub::sanitizeContent($content, $context); +``` + +**Unique Value Opportunities**: +- Semantic web escaping (RDF, Turtle, JSON-LD, N-Triples) +- IndieWeb protocol security (Micropub, Webmention, IndieAuth) +- ActivityPub content sanitization +- Microformats security validation + +### 2. Add RDF/Turtle Escaping Functions + +**Problem**: Semantic WordPress themes generate RDF Turtle output. Using `addslashes()` is incorrect and allows injection. + +**Required Functions**: + +```php + '\\\\', + '"' => '\\"', + "\n" => '\\n', + "\r" => '\\r', + "\t" => '\\t', + ]; + + $escaped = strtr($value, $replacements); + + // Handle control characters (U+0000 to U+001F except handled above) + return preg_replace_callback( + '/[\x00-\x08\x0B\x0C\x0E-\x1F]/', + fn($m) => sprintf('\\u%04X', ord($m[0])), + $escaped + ) ?? $escaped; + } + + /** + * Validate and escape an IRI for Turtle output. + * + * @throws \InvalidArgumentException If IRI is malformed + */ + public static function escapeIRI(string $iri): string + { + // Validate IRI structure + if (!filter_var($iri, FILTER_VALIDATE_URL) && + !preg_match('/^urn:[a-z0-9][a-z0-9-]{0,31}:/i', $iri)) { + throw new \InvalidArgumentException("Invalid IRI: {$iri}"); + } + + // Escape special characters per RFC 3987 + $escape = ['<' => '%3C', '>' => '%3E', '"' => '%22', + '{' => '%7B', '}' => '%7D', '|' => '%7C', + '\\' => '%5C', '^' => '%5E', '`' => '%60']; + + return strtr($iri, $escape); + } +} +``` + +### 3. Add SPDX License Headers + +**Problem**: All source files should have SPDX identifiers for license clarity. + +**Standard Format**: +```php + htmlspecialchars((string)$value, ENT_QUOTES | ENT_HTML5, 'UTF-8'), + EscapeContext::Turtle => Semantic\Turtle::escapeString((string)$value), + // ... + }; + } +} + +// Use readonly properties for immutable security configs +final readonly class SecurityPolicy +{ + public function __construct( + public bool $strictMode = true, + public EscapeContext $defaultContext = EscapeContext::Html, + public array $allowedSchemes = ['https'], + ) {} +} +``` + +--- + +## Suggested Architecture + +### Complementary Roles + +| Tool | Role | When Used | +|------|------|-----------| +| **sanctify-php** | Static analysis & transformation | Build time, CI/CD | +| **php-aegis** | Runtime security library | Application runtime | + +### Integration Points + +``` +┌─────────────────────────────────────────────────────────┐ +│ Development Flow │ +├─────────────────────────────────────────────────────────┤ +│ │ +│ Source Code │ +│ │ │ +│ ▼ │ +│ sanctify-php analyze ◄── Static analysis │ +│ │ Finds missing escaping │ +│ │ Detects taint flows │ +│ │ Reports vulnerabilities │ +│ ▼ │ +│ sanctify-php fix ◄── Auto-transform │ +│ │ Adds php-aegis calls │ +│ │ Inserts strict_types │ +│ ▼ │ +│ Production Code │ +│ │ │ +│ ▼ │ +│ php-aegis (runtime) ◄── Runtime protection │ +│ Semantic escaping │ +│ Protocol sanitization │ +│ Defense in depth │ +│ │ +└─────────────────────────────────────────────────────────┘ +``` + +### Proposed php-aegis Namespace Structure + +``` +Aegis/ +├── Escape.php # Core escaping (extends WP when needed) +├── Sanitize.php # Core sanitization +├── Validate.php # Input validation +├── Semantic/ # ← NEW: RDF/Linked Data +│ ├── Turtle.php # W3C Turtle escaping +│ ├── JsonLd.php # JSON-LD sanitization +│ ├── NTriples.php # N-Triples escaping +│ └── Rdf.php # Generic RDF utilities +├── IndieWeb/ # ← NEW: IndieWeb protocols +│ ├── Micropub.php # Micropub content sanitization +│ ├── Webmention.php # Webmention validation +│ ├── IndieAuth.php # Token verification helpers +│ └── Microsub.php # Microsub security +├── ActivityPub/ # ← NEW: Fediverse +│ ├── Object.php # AS2 object sanitization +│ ├── Signature.php # HTTP signature verification +│ └── Content.php # HTML content policy +├── WordPress/ # WordPress integration layer +│ ├── Hooks.php # Security hook integration +│ └── OptionsEncryption.php # Encrypted options storage +└── Policy/ # Security policies + ├── ContentSecurityPolicy.php + └── PermissionsPolicy.php +``` + +--- + +## sanctify-php Integration Support + +We will add support in sanctify-php to: + +1. **Recognize php-aegis calls as safe sinks** + ```haskell + -- In Sanctify.Analysis.Taint + aegisSafeSinks :: [Text] + aegisSafeSinks = + [ "Aegis\\Escape::html" + , "Aegis\\Semantic\\Turtle::escapeString" + , "Aegis\\IndieWeb\\Micropub::sanitizeContent" + -- ... + ] + ``` + +2. **Auto-insert php-aegis calls during fix** + ```haskell + -- Transform unescaped output to use php-aegis + -- Before: echo $user_input; + -- After: echo \Aegis\Escape::html($user_input); + ``` + +3. **Detect semantic context for appropriate escaping** + ```haskell + -- Detect Turtle output context + -- Recommend: \Aegis\Semantic\Turtle::escapeString() + -- Instead of: esc_html() (wrong context) + ``` + +--- + +## Action Items for php-aegis Team + +### Priority 1 (High) +- [ ] Add `Aegis\Semantic\Turtle` namespace with W3C-compliant escaping +- [ ] Add `Aegis\IndieWeb\Micropub` for content sanitization +- [ ] Add SPDX headers to all files + +### Priority 2 (Medium) +- [ ] Refactor to use PHP 8.1+ enums for contexts +- [ ] Add union types throughout API +- [ ] Document differentiation from WordPress core functions + +### Priority 3 (Low) +- [ ] Add ActivityPub sanitization support +- [ ] Add JSON-LD validation +- [ ] Create WordPress integration hooks + +--- + +## Contact + +For questions about this handover or sanctify-php integration: +- Repository: hyperpolymath/sanctify-php +- Issues: https://github.com/hyperpolymath/sanctify-php/issues + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath* diff --git a/docs/ROADMAP.md b/docs/ROADMAP.md new file mode 100644 index 0000000..899e46b --- /dev/null +++ b/docs/ROADMAP.md @@ -0,0 +1,496 @@ +# Sanctify-PHP Roadmap + +## Context + +This roadmap addresses integration feedback from real-world deployment in the wp-sinople-theme WordPress project, which uses semantic web (RDF/Turtle) output and IndieWeb protocols. + +**Feedback Date**: 2025-12-27 +**Current Version**: 0.1.0.0 + +--- + +## Issues Identified + +| Issue | Severity | User Impact | +|-------|----------|-------------| +| Requires Haskell toolchain | High | Most PHP devs can't build/run sanctify-php | +| No pre-built binaries | High | Installation friction prevents adoption | +| No Docker container | Medium | Alternative deployment path missing | +| No RDF/Turtle awareness | High | Semantic themes get false negatives | +| Limited PHP 8.x syntax | Medium | May miss some modern PHP patterns | +| Missing WP integration docs | Medium | Users don't know how to integrate | + +--- + +## Phase 1: Distribution & Accessibility + +**Goal**: Make sanctify-php usable without Haskell knowledge + +### 1.1 Pre-built Binaries + +Provide statically-linked binaries for common platforms: + +``` +releases/ +├── sanctify-php-0.2.0-linux-x86_64 +├── sanctify-php-0.2.0-linux-aarch64 +├── sanctify-php-0.2.0-darwin-x86_64 +├── sanctify-php-0.2.0-darwin-aarch64 +└── sanctify-php-0.2.0-windows-x86_64.exe +``` + +**Implementation**: +- [ ] Add GitHub Actions workflow for cross-compilation +- [ ] Use static linking (`-optl-static -optl-pthread`) +- [ ] Sign binaries (GPG + sigstore) +- [ ] Create release automation script + +**CI Workflow** (`.github/workflows/release.yml`): +```yaml +name: Release Binaries +on: + push: + tags: ['v*'] + +jobs: + build: + strategy: + matrix: + include: + - os: ubuntu-latest + target: x86_64-linux + - os: macos-latest + target: x86_64-darwin + - os: macos-latest + target: aarch64-darwin + runs-on: ${{ matrix.os }} + steps: + - uses: actions/checkout@v4 + - uses: haskell-actions/setup@v2 + with: + ghc-version: '9.6' + - run: cabal build --enable-executable-static + - uses: actions/upload-artifact@v4 +``` + +### 1.2 Docker Container + +Provide OCI container for easy deployment: + +```dockerfile +# Dockerfile +FROM haskell:9.6-slim AS builder +WORKDIR /build +COPY . . +RUN cabal build --enable-executable-static +RUN cp $(cabal list-bin sanctify-php) /sanctify-php + +FROM gcr.io/distroless/static-debian12 +COPY --from=builder /sanctify-php /usr/local/bin/sanctify-php +ENTRYPOINT ["sanctify-php"] +``` + +**Usage**: +```bash +# Analyze a project +docker run --rm -v $(pwd):/src ghcr.io/hyperpolymath/sanctify-php analyze /src + +# Generate report +docker run --rm -v $(pwd):/src ghcr.io/hyperpolymath/sanctify-php report /src --format=sarif +``` + +### 1.3 Guix Package + +Proper Guix package definition for reproducible builds: + +```scheme +;; guix.scm - enhanced for distribution +(define-public sanctify-php + (package + (name "sanctify-php") + (version "0.2.0") + (source (origin + (method git-fetch) + (uri (git-reference + (url "https://github.com/hyperpolymath/sanctify-php") + (commit (string-append "v" version)))) + (sha256 (base32 "...")))) + (build-system haskell-build-system) + (inputs (list ghc-megaparsec ghc-aeson ghc-prettyprinter)) + (synopsis "PHP security hardening and analysis tool") + (description "Static analyzer that detects vulnerabilities and +transforms PHP code for security compliance.") + (license (list license:expat license:agpl3+)) + (home-page "https://github.com/hyperpolymath/sanctify-php"))) +``` + +--- + +## Phase 2: Semantic Web Support + +**Goal**: First-class support for RDF/Turtle/JSON-LD output contexts + +### 2.1 Semantic Output Detection + +Add detection for semantic web output patterns: + +```haskell +-- src/Sanctify/Analysis/Semantic.hs +-- SPDX-License-Identifier: AGPL-3.0-or-later + +module Sanctify.Analysis.Semantic + ( SemanticContext(..) + , detectSemanticContext + , semanticEscapingRules + ) where + +data SemanticContext + = TurtleContext -- RDF Turtle output + | JsonLdContext -- JSON-LD output + | NTriplesContext -- N-Triples output + | RdfXmlContext -- RDF/XML output + | MicroformatsContext -- Microformats2 in HTML + | NoSemanticContext -- Standard HTML/text + deriving (Eq, Show, Generic) + +-- Detect context from surrounding code +detectSemanticContext :: Statement -> Maybe SemanticContext +detectSemanticContext stmt = case stmt of + -- Detect Content-Type headers + FunctionCall "header" [StringLit ct] + | "text/turtle" `isInfixOf` ct -> Just TurtleContext + | "application/ld+json" `isInfixOf` ct -> Just JsonLdContext + | "application/n-triples" `isInfixOf` ct -> Just NTriplesContext + + -- Detect file extensions in output + FunctionCall "file_put_contents" [StringLit path, _] + | ".ttl" `isSuffixOf` path -> Just TurtleContext + | ".jsonld" `isSuffixOf` path -> Just JsonLdContext + + -- Detect semantic template patterns + Echo (StringLit template) + | "@prefix" `isInfixOf` template -> Just TurtleContext + | "\"@context\"" `isInfixOf` template -> Just JsonLdContext + + _ -> Nothing +``` + +### 2.2 Semantic-Aware Taint Sinks + +Extend taint analysis with semantic sinks: + +```haskell +-- In Sanctify.Analysis.Taint + +data SemanticSink + = TurtleLiteral -- String literal in Turtle + | TurtleIRI -- IRI in Turtle + | JsonLdValue -- Value in JSON-LD + | JsonLdId -- @id field in JSON-LD + deriving (Eq, Show) + +semanticSinkEscaping :: SemanticSink -> [Text] +semanticSinkEscaping = \case + TurtleLiteral -> + [ "Aegis\\Semantic\\Turtle::escapeString" + , "sanctify_escape_turtle_string" -- WP helper + ] + TurtleIRI -> + [ "Aegis\\Semantic\\Turtle::escapeIRI" + , "sanctify_escape_turtle_iri" + ] + JsonLdValue -> + [ "json_encode" -- with JSON_HEX_* flags + , "Aegis\\Semantic\\JsonLd::escapeValue" + ] + JsonLdId -> + [ "Aegis\\Semantic\\JsonLd::validateIRI" + , "filter_var" -- with FILTER_VALIDATE_URL + ] +``` + +### 2.3 WordPress Semantic Theme Detection + +Detect semantic WordPress themes: + +```haskell +-- In Sanctify.WordPress.Constraints + +data ThemeType + = StandardTheme + | SemanticTheme -- Uses RDF/Turtle output + | IndieWebTheme -- Uses IndieWeb protocols + | SemanticIndieWeb -- Both semantic + IndieWeb + deriving (Eq, Show) + +detectThemeType :: [FilePath] -> IO ThemeType +detectThemeType files = do + hasSemanticPhp <- any ("semantic.php" `isSuffixOf`) files + hasIndiewebPhp <- any ("indieweb.php" `isSuffixOf`) files + hasTurtleOutput <- anyM containsTurtlePatterns files + hasMicropub <- anyM containsMicropubPatterns files + + pure $ case (hasSemanticPhp || hasTurtleOutput, hasIndiewebPhp || hasMicropub) of + (True, True) -> SemanticIndieWeb + (True, False) -> SemanticTheme + (False, True) -> IndieWebTheme + _ -> StandardTheme +``` + +--- + +## Phase 3: PHP 8.x Syntax Completeness + +**Goal**: Full support for PHP 8.0-8.4 syntax + +### 3.1 Parser Enhancements + +| Feature | PHP Version | Status | Priority | +|---------|-------------|--------|----------| +| Named arguments | 8.0 | ✅ Parsed | - | +| Match expressions | 8.0 | ✅ AST ready | Medium | +| Union types | 8.0 | ✅ Supported | - | +| Nullsafe operator `?->` | 8.0 | ⚠️ Partial | High | +| Constructor promotion | 8.0 | ✅ Supported | - | +| Intersection types | 8.1 | ✅ Supported | - | +| Readonly properties | 8.1 | ✅ Supported | - | +| Enums | 8.1 | ⚠️ Partial | High | +| First-class callables | 8.1 | ❌ Missing | Medium | +| Readonly classes | 8.2 | ❌ Missing | Medium | +| DNF types | 8.2 | ❌ Missing | Low | +| `#[\Override]` attribute | 8.3 | ❌ Missing | Low | +| Typed class constants | 8.3 | ❌ Missing | Medium | + +### 3.2 Enum Support + +```haskell +-- Extend AST for PHP 8.1 enums +data EnumDeclaration = EnumDeclaration + { enumName :: Text + , enumBackingType :: Maybe PHPType -- int | string + , enumCases :: [EnumCase] + , enumMethods :: [MethodDeclaration] + , enumImplements :: [Text] + } + deriving (Eq, Show, Generic) + +data EnumCase = EnumCase + { caseName :: Text + , caseValue :: Maybe Expression -- For backed enums + } + deriving (Eq, Show, Generic) +``` + +### 3.3 Nullsafe Operator + +```haskell +-- Add nullsafe property access +data Expression + = ... + | PropertyAccess Expression Text -- $obj->prop + | NullsafePropertyAccess Expression Text -- $obj?->prop + | MethodCall Expression Text [Argument] + | NullsafeMethodCall Expression Text [Argument] -- $obj?->method() + ... +``` + +--- + +## Phase 4: WordPress Integration + +**Goal**: Comprehensive WordPress integration documentation and tooling + +### 4.1 WordPress Integration Guide + +Create `docs/WORDPRESS.md`: + +```markdown +# WordPress Integration Guide + +## Quick Start + +### Using Pre-built Binary + +\`\`\`bash +# Download for your platform +curl -LO https://github.com/hyperpolymath/sanctify-php/releases/latest/download/sanctify-php-linux-x86_64 +chmod +x sanctify-php-linux-x86_64 +sudo mv sanctify-php-linux-x86_64 /usr/local/bin/sanctify-php + +# Analyze your theme +sanctify-php analyze ./wp-content/themes/my-theme/ +\`\`\` + +### Using Docker + +\`\`\`bash +docker run --rm -v $(pwd)/wp-content:/src \ + ghcr.io/hyperpolymath/sanctify-php analyze /src/themes/my-theme +\`\`\` + +## CI/CD Integration + +### GitHub Actions + +\`\`\`yaml +name: Security Analysis +on: [push, pull_request] + +jobs: + sanctify: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: hyperpolymath/sanctify-php-action@v1 + with: + path: ./wp-content/themes/my-theme + format: sarif + - uses: github/codeql-action/upload-sarif@v3 + with: + sarif_file: sanctify-results.sarif +\`\`\` + +## Configuration + +Create `sanctify.json` in theme root: + +\`\`\`json +{ + "wordpress": true, + "theme_type": "semantic", + "strict_types": "enforce", + "escaping": { + "semantic_context": true, + "indieweb": true + } +} +\`\`\` +``` + +### 4.2 GitHub Action + +Create reusable GitHub Action: + +```yaml +# action.yml +name: 'Sanctify PHP' +description: 'PHP security analysis and hardening' +inputs: + path: + description: 'Path to analyze' + required: true + format: + description: 'Output format (text, json, sarif, html)' + default: 'text' + fix: + description: 'Apply automatic fixes' + default: 'false' +runs: + using: 'docker' + image: 'Dockerfile' + args: + - analyze + - ${{ inputs.path }} + - --format=${{ inputs.format }} +``` + +### 4.3 Composer Integration + +For projects using Composer: + +```json +{ + "scripts": { + "security:analyze": "sanctify-php analyze ./src", + "security:fix": "sanctify-php fix ./src --policy=conservative", + "security:report": "sanctify-php report ./src --format=html -o security-report.html" + } +} +``` + +--- + +## Phase 5: php-aegis Integration + +**Goal**: Seamless integration with php-aegis runtime library + +### 5.1 Recognize php-aegis as Safe + +```haskell +-- Add php-aegis functions to safe function registry +aegisSafeFunctions :: Map Text SafetyLevel +aegisSafeFunctions = Map.fromList + [ ("Aegis\\Escape::html", SafeForHtml) + , ("Aegis\\Escape::attr", SafeForAttribute) + , ("Aegis\\Escape::url", SafeForUrl) + , ("Aegis\\Escape::js", SafeForJs) + , ("Aegis\\Semantic\\Turtle::escapeString", SafeForTurtleLiteral) + , ("Aegis\\Semantic\\Turtle::escapeIRI", SafeForTurtleIRI) + , ("Aegis\\IndieWeb\\Micropub::sanitizeContent", SafeForHtml) + ] +``` + +### 5.2 Auto-Insert php-aegis Calls + +Transform detected vulnerabilities to use php-aegis: + +```haskell +-- In Sanctify.Transform.Sanitize + +insertAegisEscaping :: TaintedSink -> Expression -> Expression +insertAegisEscaping sink expr = case sink of + HtmlOutput -> + FunctionCall "\\Aegis\\Escape::html" [expr] + + TurtleLiteralOutput -> + FunctionCall "\\Aegis\\Semantic\\Turtle::escapeString" [expr] + + TurtleIRIOutput -> + FunctionCall "\\Aegis\\Semantic\\Turtle::escapeIRI" [expr] + + MicropubContent -> + FunctionCall "\\Aegis\\IndieWeb\\Micropub::sanitizeContent" [expr] + + _ -> expr -- Fallback to WordPress functions +``` + +### 5.3 Configuration Option + +```json +{ + "transforms": { + "escaping_library": "php-aegis", // or "wordpress" or "custom" + "fallback_to_wordpress": true + } +} +``` + +--- + +## Timeline & Milestones + +| Phase | Focus | Target Version | +|-------|-------|----------------| +| Phase 1 | Distribution | v0.2.0 | +| Phase 2 | Semantic Web | v0.3.0 | +| Phase 3 | PHP 8.x Complete | v0.4.0 | +| Phase 4 | WordPress Integration | v0.5.0 | +| Phase 5 | php-aegis Integration | v1.0.0 | + +--- + +## Contributing + +We welcome contributions! Priority areas: + +1. **Distribution**: CI/CD for binary releases +2. **Parser**: PHP 8.1+ enum support +3. **Semantic**: RDF/Turtle detection and escaping rules +4. **Documentation**: WordPress integration examples + +See [CONTRIBUTING.md](./CONTRIBUTING.md) for guidelines. + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath* From ae905704a63448eaa66a1108948c2963c8f90a87 Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 00:48:15 +0000 Subject: [PATCH 2/2] Add critical adoption feedback: Composer wrapper, PHP 7.4 compat Based on integration learning report insights: php-aegis updates: - CRITICAL: PHP 8.1+ blocks WordPress adoption (hosts on 7.4/8.0) - Added php-aegis-compat package design for PHP 7.4+ - Added WordPress adapter (snake_case functions) - Extended validators: int(), ip(), domain(), uuid(), slug() sanctify-php updates: - CRITICAL: Composer plugin wrapper for composer require install - GitHub Action for CI/CD integration - Incremental analysis with file hash cache - Key insight: Haskell dependency is #1 adoption blocker New: STANDALONE.md - Defines minimum viable standalone capabilities - Documents enhanced capabilities when combined - Adoption paths for each tool --- docs/IMPLEMENTATION-TRACKER.md | 55 ++++++- docs/PHP-AEGIS-HANDOVER.md | 248 +++++++++++++++++++++++++++- docs/ROADMAP.md | 253 +++++++++++++++++++++++++++- docs/STANDALONE.md | 292 +++++++++++++++++++++++++++++++++ 4 files changed, 830 insertions(+), 18 deletions(-) create mode 100644 docs/STANDALONE.md diff --git a/docs/IMPLEMENTATION-TRACKER.md b/docs/IMPLEMENTATION-TRACKER.md index ee27c32..f0b4b62 100644 --- a/docs/IMPLEMENTATION-TRACKER.md +++ b/docs/IMPLEMENTATION-TRACKER.md @@ -6,30 +6,67 @@ |------|--------|-------------| | php-aegis Handover | ✅ Complete | Send to php-aegis team | | sanctify-php Roadmap | ✅ Complete | Begin Phase 1 | -| Binary Releases | 🔲 Not Started | Create CI workflow | +| Standalone Requirements | ✅ Complete | See STANDALONE.md | +| Binary Releases | 🔲 Not Started | **CRITICAL** - Create CI workflow | +| Composer Plugin | 🔲 Not Started | **CRITICAL** - Enable `composer require` | +| GitHub Action | 🔲 Not Started | High priority | | Docker Container | 🔲 Not Started | Create Dockerfile | +| Incremental Analysis | 🔲 Not Started | Cache for performance | | Semantic Support | 🔲 Not Started | Design AST extensions | --- +## Critical Path: Adoption Blockers + +> **Key Insight**: The biggest barrier to adoption is the Haskell dependency. +> PHP developers expect `composer require` installation with no external runtime. + +### sanctify-php Critical Items + +| Item | Priority | Blocks | +|------|----------|--------| +| Pre-built binaries | **CRITICAL** | Everything else | +| Composer plugin wrapper | **CRITICAL** | PHP dev adoption | +| GitHub Action | High | CI/CD adoption | +| Incremental analysis | Medium | Performance at scale | + +### php-aegis Critical Items + +| Item | Priority | Blocks | +|------|----------|--------| +| php-aegis-compat (PHP 7.4+) | **CRITICAL** | WordPress adoption | +| WordPress adapter (snake_case) | High | WP dev experience | +| Extended validators | Medium | Common use cases | + +--- + ## Immediate Actions ### For php-aegis Team 1. **Review handover document**: `docs/PHP-AEGIS-HANDOVER.md` -2. **Priority implementation**: - - `Aegis\Semantic\Turtle::escapeString()` - - `Aegis\Semantic\Turtle::escapeIRI()` - - SPDX headers on all files +2. **Critical implementation** (adoption blockers): + - [ ] Create `php-aegis-compat` package for PHP 7.4+ + - [ ] Add WordPress adapter with snake_case functions + - [ ] Extend `Validate` class: `int()`, `ip()`, `domain()` +3. **Priority implementation** (unique value): + - [ ] `Aegis\Semantic\Turtle::escapeString()` + - [ ] `Aegis\Semantic\Turtle::escapeIRI()` + - [ ] SPDX headers on all files ### For sanctify-php Team -1. **Phase 1 Priority**: Make tool accessible without Haskell - - [ ] GitHub Actions for binary releases +1. **Phase 1 CRITICAL**: Enable `composer require` installation + - [ ] GitHub Actions for binary releases (linux, darwin x86_64/arm64) + - [ ] Composer plugin that auto-downloads binary on install + - [ ] GitHub Action for CI/CD integration - [ ] Dockerfile for container distribution - - [ ] Update README with installation options -2. **Phase 2 Priority**: Semantic web support +2. **Phase 1 HIGH**: Performance + - [ ] Incremental analysis with file hash cache + - [ ] Only rescan changed files + +3. **Phase 2 Priority**: Semantic web support - [ ] Create `Sanctify.Analysis.Semantic` module - [ ] Extend taint sinks for Turtle/JSON-LD contexts - [ ] Add WordPress semantic theme detection diff --git a/docs/PHP-AEGIS-HANDOVER.md b/docs/PHP-AEGIS-HANDOVER.md index 0f20053..edf6c9b 100644 --- a/docs/PHP-AEGIS-HANDOVER.md +++ b/docs/PHP-AEGIS-HANDOVER.md @@ -15,16 +15,244 @@ This document provides integration feedback from the wp-sinople-theme WordPress | Issue | Severity | Impact | |-------|----------|--------| +| PHP 8.1+ blocks WordPress adoption | **Critical** | WordPress 6.4 supports PHP 7.4+, most hosts still on 7.4/8.0 | +| No WordPress adapter | High | camelCase API vs snake_case WordPress conventions | | Feature set too minimal | Medium | WordPress has equivalent functions already | | No RDF/Turtle escaping | High | Semantic themes require W3C-compliant escaping | +| Limited validators | Medium | Only email/url - missing int(), ip(), domain() | | Missing SPDX license headers | Low | Compliance concern for FOSS projects | -| No PHP 8.1+ features | Medium | Missing enums, union types, readonly properties | --- ## Detailed Recommendations -### 1. Differentiate from WordPress Core Functions +### 0. CRITICAL: PHP 7.4+ Compatibility Layer + +**Problem**: php-aegis requires PHP 8.1+, but WordPress ecosystem reality: +- WordPress 6.4+ officially supports PHP 7.4+ +- Many shared hosts still run PHP 7.4 or 8.0 +- Plugin/theme developers must support the WordPress minimum + +**Solution**: Split into two packages: + +``` +php-aegis (PHP 8.1+) ← Modern API with enums, union types + │ + └── php-aegis-compat (PHP 7.4+) ← Polyfill package for WordPress +``` + +**php-aegis-compat Implementation**: + +```php +=7.4" + }, + "conflict": { + "hyperpolymath/php-aegis": "*" + }, + "autoload": { + "psr-4": { "Aegis\\": "src/" } + } +} +``` + +**Usage in WordPress plugins**: +```php +// In plugin bootstrap +if (PHP_VERSION_ID >= 80100) { + require_once __DIR__ . '/vendor/hyperpolymath/php-aegis/autoload.php'; +} else { + require_once __DIR__ . '/vendor/hyperpolymath/php-aegis-compat/autoload.php'; +} +``` + +### 1. WordPress Adapter (snake_case API) + +**Problem**: WordPress uses `snake_case` functions, php-aegis uses `CamelCase` methods. + +**Solution**: Provide WordPress adapter functions: + +```php + **The biggest barrier to sanctify-php adoption is the Haskell dependency.** +> PHP developers expect `composer require` installation with no external runtime. +> The solution is a Composer plugin that downloads pre-built binaries. + --- ## Phase 1: Distribution & Accessibility @@ -99,7 +108,247 @@ docker run --rm -v $(pwd):/src ghcr.io/hyperpolymath/sanctify-php analyze /src docker run --rm -v $(pwd):/src ghcr.io/hyperpolymath/sanctify-php report /src --format=sarif ``` -### 1.3 Guix Package +### 1.3 Composer Plugin Wrapper (Critical Path) + +PHP developers expect `composer require`. Provide a Composer plugin that: +1. Detects platform (OS/arch) +2. Downloads the appropriate pre-built binary +3. Provides Composer scripts integration + +**Package Structure**: +``` +sanctify-php-composer/ +├── composer.json +├── src/ +│ ├── Plugin.php # Composer plugin hooks +│ ├── BinaryInstaller.php # Platform detection & download +│ └── ScriptHandler.php # Composer scripts integration +└── bin/ + └── sanctify-php # Wrapper script +``` + +**composer.json**: +```json +{ + "name": "hyperpolymath/sanctify-php", + "description": "PHP security analysis and hardening tool", + "type": "composer-plugin", + "require": { + "php": ">=7.4", + "composer-plugin-api": "^2.0" + }, + "require-dev": { + "composer/composer": "^2.0" + }, + "autoload": { + "psr-4": { "Sanctify\\Composer\\": "src/" } + }, + "extra": { + "class": "Sanctify\\Composer\\Plugin", + "sanctify-binaries": { + "linux-x86_64": "https://github.com/hyperpolymath/sanctify-php/releases/download/v{version}/sanctify-php-linux-x86_64", + "darwin-x86_64": "https://github.com/hyperpolymath/sanctify-php/releases/download/v{version}/sanctify-php-darwin-x86_64", + "darwin-arm64": "https://github.com/hyperpolymath/sanctify-php/releases/download/v{version}/sanctify-php-darwin-aarch64" + } + }, + "scripts": { + "sanctify:analyze": "Sanctify\\Composer\\ScriptHandler::analyze", + "sanctify:fix": "Sanctify\\Composer\\ScriptHandler::fix", + "sanctify:report": "Sanctify\\Composer\\ScriptHandler::report" + }, + "bin": ["bin/sanctify-php"] +} +``` + +**BinaryInstaller.php**: +```php +write("Downloading sanctify-php for {$platform}..."); + + $binPath = self::BINARY_DIR . '/sanctify-php-bin'; + self::download($url, $binPath); + chmod($binPath, 0755); + + $io->write("sanctify-php installed successfully."); + } + + private static function detectPlatform(): string + { + $os = PHP_OS_FAMILY === 'Darwin' ? 'darwin' : 'linux'; + $arch = php_uname('m') === 'arm64' ? 'arm64' : 'x86_64'; + return "{$os}-{$arch}"; + } + + private static function download(string $url, string $dest): void + { + $ch = curl_init($url); + curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); + curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); + $binary = curl_exec($ch); + curl_close($ch); + file_put_contents($dest, $binary); + } +} +``` + +**Usage after installation**: +```bash +# Install +composer require --dev hyperpolymath/sanctify-php + +# Use via Composer scripts +composer sanctify:analyze src/ +composer sanctify:fix src/ -- --policy=conservative +composer sanctify:report src/ -- --format=sarif + +# Or directly +vendor/bin/sanctify-php analyze src/ +``` + +### 1.4 GitHub Action + +Official GitHub Action for CI/CD: + +```yaml +# .github/actions/sanctify-php/action.yml +name: 'Sanctify PHP' +description: 'PHP security analysis and hardening' +branding: + icon: 'shield' + color: 'green' + +inputs: + path: + description: 'Path to analyze' + required: true + default: 'src' + format: + description: 'Output format (text, json, sarif, html, markdown)' + required: false + default: 'sarif' + fail-on: + description: 'Fail on severity level (critical, high, medium, low, none)' + required: false + default: 'high' + upload-sarif: + description: 'Upload SARIF to GitHub Security tab' + required: false + default: 'true' + +outputs: + issues-found: + description: 'Number of security issues found' + value: ${{ steps.analyze.outputs.issues }} + +runs: + using: 'composite' + steps: + - name: Download sanctify-php + shell: bash + run: | + curl -LO https://github.com/hyperpolymath/sanctify-php/releases/latest/download/sanctify-php-linux-x86_64 + chmod +x sanctify-php-linux-x86_64 + sudo mv sanctify-php-linux-x86_64 /usr/local/bin/sanctify-php + + - name: Run analysis + id: analyze + shell: bash + run: | + sanctify-php analyze ${{ inputs.path }} \ + --format=${{ inputs.format }} \ + --output=sanctify-results.${{ inputs.format }} \ + --fail-on=${{ inputs.fail-on }} + echo "issues=$(sanctify-php analyze ${{ inputs.path }} --format=json | jq '.issues | length')" >> $GITHUB_OUTPUT + + - name: Upload SARIF + if: inputs.upload-sarif == 'true' && inputs.format == 'sarif' + uses: github/codeql-action/upload-sarif@v3 + with: + sarif_file: sanctify-results.sarif +``` + +**Usage in workflows**: +```yaml +name: Security +on: [push, pull_request] + +jobs: + sanctify: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: hyperpolymath/sanctify-php-action@v1 + with: + path: src/ + fail-on: high +``` + +### 1.5 Incremental Analysis + +Cache analysis results and only rescan changed files: + +```haskell +-- src/Sanctify/Cache.hs +-- SPDX-License-Identifier: AGPL-3.0-or-later + +module Sanctify.Cache + ( AnalysisCache(..) + , loadCache + , saveCache + , getChangedFiles + ) where + +import qualified Data.Map.Strict as Map +import Crypto.Hash (SHA256, hash) + +data AnalysisCache = AnalysisCache + { cacheVersion :: Text + , fileHashes :: Map FilePath Text -- path -> SHA256 + , cachedResults :: Map FilePath [SecurityIssue] + } + deriving (Generic, FromJSON, ToJSON) + +-- Determine which files need re-analysis +getChangedFiles :: AnalysisCache -> [FilePath] -> IO [FilePath] +getChangedFiles cache files = do + filterM (hasChanged cache) files + where + hasChanged c f = do + currentHash <- hashFile f + pure $ Map.lookup f (fileHashes c) /= Just currentHash +``` + +**CLI usage**: +```bash +# First run: full analysis, creates .sanctify-cache.json +sanctify-php analyze src/ + +# Subsequent runs: only analyze changed files +sanctify-php analyze src/ --incremental + +# Force full rescan +sanctify-php analyze src/ --no-cache +``` + +### 1.6 Guix Package Proper Guix package definition for reproducible builds: diff --git a/docs/STANDALONE.md b/docs/STANDALONE.md new file mode 100644 index 0000000..1672438 --- /dev/null +++ b/docs/STANDALONE.md @@ -0,0 +1,292 @@ +# Standalone vs Combined Capabilities + +This document defines what each tool must provide independently and the enhanced capabilities when used together. + +--- + +## Philosophy + +Each tool should be **fully functional standalone**. Integration provides **enhanced capabilities**, not basic functionality. + +``` +┌─────────────────────────────────────────────────────────────────┐ +│ Standalone Operation │ +├─────────────────────────────────────────────────────────────────┤ +│ │ +│ sanctify-php (alone) php-aegis (alone) │ +│ ┌─────────────────┐ ┌─────────────────┐ │ +│ │ Static Analysis │ │ Runtime Library │ │ +│ │ Auto-transform │ │ Escaping/Sanit. │ │ +│ │ Uses WP funcs │ │ Works anywhere │ │ +│ └─────────────────┘ └─────────────────┘ │ +│ │ +├─────────────────────────────────────────────────────────────────┤ +│ Combined Operation │ +├─────────────────────────────────────────────────────────────────┤ +│ │ +│ ┌─────────────────────────────────────────────────┐ │ +│ │ sanctify-php + php-aegis │ │ +│ │ │ │ +│ │ • sanctify detects → inserts php-aegis calls │ │ +│ │ • php-aegis provides runtime protection │ │ +│ │ • Semantic escaping (Turtle, JSON-LD) │ │ +│ │ • IndieWeb protocol security │ │ +│ │ • Deeper taint analysis with Aegis sinks │ │ +│ └─────────────────────────────────────────────────┘ │ +│ │ +└─────────────────────────────────────────────────────────────────┘ +``` + +--- + +## sanctify-php: Minimum Viable Standalone + +### Must Have (MVP) + +| Capability | Status | Notes | +|------------|--------|-------| +| Detect missing `strict_types` | ✅ | Core feature | +| Detect SQL injection | ✅ | Taint tracking | +| Detect XSS vulnerabilities | ✅ | Output escaping | +| Detect CSRF missing nonces | ✅ | WordPress-aware | +| Auto-add `strict_types` | ✅ | Transform | +| Auto-add WordPress escaping | ✅ | Uses `esc_html()` etc. | +| SARIF output for CI | ✅ | GitHub integration | +| **Pre-built binaries** | ❌ → Priority | Adoption blocker | +| **Composer install** | ❌ → Priority | Adoption blocker | + +### Standalone Behavior (Without php-aegis) + +When php-aegis is not installed, sanctify-php must: + +1. **Use WordPress functions for escaping**: + ```php + // sanctify-php auto-fix output (standalone) + echo esc_html($user_input); // NOT Aegis\Escape::html() + ``` + +2. **Use WordPress functions for sanitization**: + ```php + // sanctify-php auto-fix output (standalone) + $clean = sanitize_text_field($_POST['field']); + ``` + +3. **Warn about missing semantic escaping**: + ``` + WARNING: Turtle output detected at semantic.php:45 + No semantic escaping library found. + Consider installing php-aegis for proper Turtle escaping. + Using esc_html() as fallback (may break RDF syntax). + ``` + +### Installation Requirements (Standalone) + +```bash +# MUST work without Haskell +composer require --dev hyperpolymath/sanctify-php + +# Binary auto-downloads on install +# No manual steps required +``` + +--- + +## php-aegis: Minimum Viable Standalone + +### Must Have (MVP) + +| Capability | Status | Notes | +|------------|--------|-------| +| HTML escaping | ✅ | `Escape::html()` | +| Attribute escaping | ✅ | `Escape::attr()` | +| URL validation | ✅ | `Validate::url()` | +| Email validation | ✅ | `Validate::email()` | +| **PHP 7.4+ compatibility** | ❌ → Critical | Adoption blocker | +| **WordPress adapter** | ❌ → Priority | snake_case functions | +| **Int/IP/Domain validators** | ❌ → Priority | Common needs | +| **Turtle escaping** | ❌ → Priority | Unique value | + +### Standalone Behavior (Without sanctify-php) + +When sanctify-php is not used, php-aegis must: + +1. **Work with any PHP framework**: + ```php + // Generic PHP usage + use Aegis\Escape; + echo Escape::html($userInput); + ``` + +2. **Provide WordPress helpers**: + ```php + // WordPress plugin/theme usage + require_once 'vendor/autoload.php'; + // Functions auto-registered if ABSPATH defined + echo aegis_escape_html($userInput); + ``` + +3. **Not require static analysis**: + - Library is purely runtime + - Developer chooses where to use escaping + - No build step needed + +### Installation Requirements (Standalone) + +```bash +# MUST work on PHP 7.4+ +composer require hyperpolymath/php-aegis-compat # PHP 7.4-8.0 +# OR +composer require hyperpolymath/php-aegis # PHP 8.1+ +``` + +--- + +## Combined Capabilities + +When both tools are used together, additional capabilities unlock: + +### 1. Aegis-Aware Auto-Fix + +sanctify-php inserts php-aegis calls instead of WordPress functions: + +```php +// Before +echo $user_input; + +// After (with php-aegis) +echo \Aegis\Escape::html($user_input); + +// After (without php-aegis) +echo esc_html($user_input); +``` + +### 2. Semantic Context Detection + +sanctify-php detects Turtle/JSON-LD output and suggests correct Aegis escaping: + +```php +// sanctify-php detects Turtle context +header('Content-Type: text/turtle'); +echo "<{$subject}> <{$predicate}> \"{$object}\" ."; + +// Recommends: +echo "<" . \Aegis\Semantic\Turtle::escapeIRI($subject) . "> " + . "<" . \Aegis\Semantic\Turtle::escapeIRI($predicate) . "> " + . "\"" . \Aegis\Semantic\Turtle::escapeString($object) . "\" ."; +``` + +### 3. Deep Taint Analysis + +sanctify-php recognizes Aegis sanitizers as safe sinks: + +```php +// sanctify-php knows this is safe +$content = \Aegis\IndieWeb\Micropub::sanitizeContent($_POST['content']); +echo $content; // No warning - recognized as sanitized +``` + +### 4. Configuration Alignment + +Both tools share configuration: + +```json +// sanctify.json +{ + "runtime_library": "php-aegis", + "semantic_contexts": ["turtle", "jsonld"], + "transforms": { + "use_aegis": true, + "fallback": "wordpress" + } +} +``` + +--- + +## Feature Matrix + +| Feature | sanctify-php alone | php-aegis alone | Combined | +|---------|-------------------|-----------------|----------| +| Detect XSS | ✅ | ❌ | ✅ | +| Fix XSS | ✅ (WP funcs) | ❌ | ✅ (Aegis) | +| Runtime escaping | ❌ | ✅ | ✅ | +| Turtle escaping | ⚠️ Warning only | ✅ | ✅ Auto-insert | +| JSON-LD escaping | ⚠️ Warning only | ✅ | ✅ Auto-insert | +| IndieWeb sanitization | ⚠️ Warning only | ✅ | ✅ Auto-insert | +| Taint tracking | ✅ | ❌ | ✅ Enhanced | +| CI/CD integration | ✅ SARIF | ❌ | ✅ SARIF | +| WordPress integration | ✅ | ✅ | ✅ Seamless | +| PHP 7.4 support | ✅ (binary) | ⚠️ (compat pkg) | ✅ | + +--- + +## Adoption Path + +### Path A: Start with sanctify-php (Static Analysis First) + +```bash +# 1. Install and run analysis +composer require --dev hyperpolymath/sanctify-php +vendor/bin/sanctify-php analyze src/ + +# 2. Apply auto-fixes (uses WordPress functions) +vendor/bin/sanctify-php fix src/ + +# 3. Later: Add php-aegis for semantic escaping +composer require hyperpolymath/php-aegis + +# 4. Re-run sanctify to upgrade to Aegis calls +vendor/bin/sanctify-php fix src/ --use-aegis +``` + +### Path B: Start with php-aegis (Runtime Library First) + +```bash +# 1. Install runtime library +composer require hyperpolymath/php-aegis + +# 2. Manually add escaping where needed +# Use Aegis\Escape::html(), Aegis\Semantic\Turtle::escapeString(), etc. + +# 3. Later: Add sanctify-php for automated detection +composer require --dev hyperpolymath/sanctify-php + +# 4. Find missed spots +vendor/bin/sanctify-php analyze src/ +``` + +### Path C: Install Both (Recommended) + +```bash +# Install both together +composer require hyperpolymath/php-aegis +composer require --dev hyperpolymath/sanctify-php + +# Analyze and fix in one step +vendor/bin/sanctify-php fix src/ --use-aegis +``` + +--- + +## Minimum Implementation Checklist + +### sanctify-php v0.2.0 (Standalone-Ready) + +- [ ] Pre-built binaries (linux-x86_64, darwin-x86_64, darwin-arm64) +- [ ] Composer plugin that auto-downloads binary +- [ ] GitHub Action +- [ ] Standalone mode: use WordPress functions when Aegis not found +- [ ] Warning mode: alert when semantic escaping needed but Aegis missing + +### php-aegis v0.2.0 (Standalone-Ready) + +- [ ] php-aegis-compat package (PHP 7.4+) +- [ ] WordPress adapter (snake_case functions) +- [ ] Extended validators: `int()`, `ip()`, `domain()`, `uuid()`, `slug()` +- [ ] Turtle escaping: `Semantic\Turtle::escapeString()`, `escapeIRI()` +- [ ] Works without sanctify-php or any build step + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath*