From a21d94220b468b23159b912db6919fcbd301dd6b Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 00:40:23 +0000 Subject: [PATCH 1/7] 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/7] 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* From 1a21fb0104f5b16b3959457879d58cb744a17e69 Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 00:59:50 +0000 Subject: [PATCH 3/7] Add Zotpress integration findings: GHC blocker, WP overlap Key findings from Zotpress integration: sanctify-php: - BLOCKER: Tool could not run at all - GHC not available - Confirms pre-built binaries are mandatory, not optional - Added integration evidence table to ROADMAP.md php-aegis: - CRITICAL: Duplicates WordPress core functionality - WP already has esc_html/attr/url/js, is_email, sanitize_* - Strategic decision required: target non-WP apps OR provide unique value WP lacks (Turtle, IndieWeb, ActivityPub) - Recommendation: Focus on semantic web as unique value New: TARGET-AUDIENCE.md - Decision matrix for when to use each tool - Documents when NOT to use each tool - Clarifies unique value propositions - Combined use scenarios Updated: IMPLEMENTATION-TRACKER.md - Binary releases now marked as BLOCKER - Added integration evidence from both projects --- docs/IMPLEMENTATION-TRACKER.md | 25 +++- docs/PHP-AEGIS-HANDOVER.md | 70 +++++++++- docs/ROADMAP.md | 35 ++++- docs/TARGET-AUDIENCE.md | 231 +++++++++++++++++++++++++++++++++ 4 files changed, 346 insertions(+), 15 deletions(-) create mode 100644 docs/TARGET-AUDIENCE.md diff --git a/docs/IMPLEMENTATION-TRACKER.md b/docs/IMPLEMENTATION-TRACKER.md index f0b4b62..463dfe4 100644 --- a/docs/IMPLEMENTATION-TRACKER.md +++ b/docs/IMPLEMENTATION-TRACKER.md @@ -7,19 +7,36 @@ | php-aegis Handover | ✅ Complete | Send to php-aegis team | | sanctify-php Roadmap | ✅ Complete | Begin Phase 1 | | Standalone Requirements | ✅ Complete | See STANDALONE.md | -| Binary Releases | 🔲 Not Started | **CRITICAL** - Create CI workflow | +| Target Audience | ✅ Complete | See TARGET-AUDIENCE.md | +| Binary Releases | 🔲 Not Started | **BLOCKER** - Tool cannot run without this | | Composer Plugin | 🔲 Not Started | **CRITICAL** - Enable `composer require` | +| Docker Container | 🔲 Not Started | **HIGH** - Fallback for binary issues | | 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 Finding: GHC Requirement is a BLOCKER + +### Integration Evidence + +| Project | Could run sanctify-php? | Result | +|---------|------------------------|--------| +| wp-sinople-theme | ⚠️ With difficulty | Needed Haskell setup | +| Zotpress | ❌ **NO** | GHC not available, couldn't run at all | + +> **Zotpress integration failed completely** — sanctify-php could not be executed. +> Manual analysis was performed instead using documented patterns. +> This is not an inconvenience — it's a **total adoption blocker**. + +--- + ## 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. +> **Key Insight**: The Haskell dependency is a BLOCKER, not just an inconvenience. +> In real-world integrations, the tool literally could not be used. +> PHP developers cannot and will not install GHC. ### sanctify-php Critical Items diff --git a/docs/PHP-AEGIS-HANDOVER.md b/docs/PHP-AEGIS-HANDOVER.md index edf6c9b..a3bf208 100644 --- a/docs/PHP-AEGIS-HANDOVER.md +++ b/docs/PHP-AEGIS-HANDOVER.md @@ -2,10 +2,43 @@ ## 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. +This document provides integration feedback from multiple WordPress projects: +1. **wp-sinople-theme** - Semantic theme with IndieWeb/Micropub support +2. **Zotpress** - Mature WordPress plugin (already well-secured) **Integration Report Date**: 2025-12-27 -**Integration Target**: WordPress semantic theme with IndieWeb/Micropub support + +--- + +## Executive Summary + +### The Core Problem + +**php-aegis duplicates WordPress core functionality** without providing additional value for WordPress projects. + +| php-aegis | WordPress Equivalent | Winner | +|-----------|---------------------|--------| +| `Validator::email()` | `is_email()` | WordPress (more edge cases) | +| `Validator::url()` | `wp_http_validate_url()` | WordPress (protocol-aware) | +| `Sanitizer::html()` | `esc_html()` | WordPress (context-aware) | +| `Sanitizer::stripTags()` | `wp_strip_all_tags()` | WordPress (more thorough) | +| Generic escaping | `esc_html()`, `esc_attr()`, `esc_url()`, `esc_js()` | **WordPress (context-specific)** | + +### Strategic Decision Required + +php-aegis must choose a positioning: + +**Option A: Non-WordPress PHP Library** +- Document that php-aegis is for Laravel, Symfony, vanilla PHP +- Don't compete with WordPress's mature security APIs +- Focus on frameworks that lack built-in security + +**Option B: WordPress Superset Library** +- Provide capabilities WordPress lacks (semantic web, IndieWeb, ActivityPub) +- Integrate with (not replace) WordPress functions +- Be additive, not duplicative + +**Recommendation: Option B** — Provide unique value WordPress lacks. --- @@ -15,18 +48,47 @@ This document provides integration feedback from the wp-sinople-theme WordPress | Issue | Severity | Impact | |-------|----------|--------| +| Duplicates WordPress core | **Critical** | No value add for WP projects | +| Lacks context-aware escaping | **Critical** | WP has html/attr/url/js contexts, Aegis has generic | | 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() | +| Limited validators | Medium | Only email/url - missing int(), ip(), domain(), uuid(), credit_card() | | Missing SPDX license headers | Low | Compliance concern for FOSS projects | +### What Mature WordPress Projects Already Have + +The Zotpress integration revealed that well-maintained WordPress plugins already: +- ✅ Have ABSPATH protection on all files +- ✅ Use prepared statements for all database queries +- ✅ Verify nonces on AJAX handlers +- ✅ Sanitize input and escape output throughout +- ✅ Follow WordPress coding standards + +**Conclusion**: php-aegis provides no value for these projects unless it offers something WordPress doesn't. + --- ## Detailed Recommendations -### 0. CRITICAL: PHP 7.4+ Compatibility Layer +### 0. CRITICAL: Define Target Audience + +Before any implementation, php-aegis must answer: + +> **Who is this library for?** + +| Audience | Should php-aegis target? | Why | +|----------|-------------------------|-----| +| WordPress plugins/themes | Only if offering unique value | WP core already handles standard security | +| Laravel applications | Yes | Laravel has security but less comprehensive | +| Symfony applications | Yes | Similar to Laravel | +| Vanilla PHP | Yes | No built-in security | +| Semantic web apps | **Yes - unique opportunity** | No existing library handles RDF/Turtle | +| IndieWeb apps | **Yes - unique opportunity** | Micropub/Webmention security not solved | +| ActivityPub/Fediverse | **Yes - unique opportunity** | Complex content policies needed | + +### 1. 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+ diff --git a/docs/ROADMAP.md b/docs/ROADMAP.md index 3f580a5..10f1a22 100644 --- a/docs/ROADMAP.md +++ b/docs/ROADMAP.md @@ -2,22 +2,42 @@ ## 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. +This roadmap addresses integration feedback from real-world deployment: +1. **wp-sinople-theme** - Semantic theme with IndieWeb/Micropub support +2. **Zotpress** - Mature WordPress plugin (couldn't run sanctify-php at all) **Feedback Date**: 2025-12-27 **Current Version**: 0.1.0.0 --- +## Critical Finding: Tool Unusable Without Binaries + +### Zotpress Integration Failure + +> **sanctify-php could not be run at all** because GHC (Haskell compiler) was not available. +> Manual analysis was performed instead using documented patterns. + +This confirms the #1 adoption blocker: **the Haskell build requirement prevents any usage**. + +### Evidence from Integration Attempts + +| Project | Could run sanctify-php? | Outcome | +|---------|------------------------|---------| +| wp-sinople-theme | ⚠️ With difficulty | Required Haskell setup | +| Zotpress | ❌ **No** | GHC not available, manual analysis only | + +--- + ## Issues Identified | Issue | Severity | User Impact | |-------|----------|-------------| -| Requires Haskell toolchain | **Critical** | Most PHP devs can't build/run sanctify-php | +| Requires Haskell toolchain | **BLOCKER** | Tool literally cannot run | | No `composer require` install | **Critical** | PHP devs expect Composer installation | +| No pre-built binaries | **Critical** | No workaround for GHC requirement | +| No Docker container | High | Alternative deployment path missing | | No GitHub Action | High | No easy CI/CD integration | -| No pre-built binaries | High | Installation friction prevents adoption | -| No Docker container | Medium | Alternative deployment path missing | | No incremental analysis | Medium | Full rescan on every change is slow | | No RDF/Turtle awareness | High | Semantic themes get false negatives | | Limited PHP 8.x syntax | Medium | May miss some modern PHP patterns | @@ -25,9 +45,10 @@ This roadmap addresses integration feedback from real-world deployment in the wp ### Key Insight -> **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. +> **The Haskell dependency is a BLOCKER, not just an inconvenience.** +> In the Zotpress integration, the tool could not be used at all. +> PHP developers cannot and will not install GHC. +> **Pre-built binaries are not optional — they are required for any adoption.** --- diff --git a/docs/TARGET-AUDIENCE.md b/docs/TARGET-AUDIENCE.md new file mode 100644 index 0000000..dc1e7ff --- /dev/null +++ b/docs/TARGET-AUDIENCE.md @@ -0,0 +1,231 @@ +# Target Audience & Use Cases + +This document clarifies when to use sanctify-php and php-aegis based on real-world integration feedback. + +--- + +## Quick Decision Matrix + +### Should I use sanctify-php? + +| Your Situation | Use sanctify-php? | Why | +|----------------|------------------|-----| +| New PHP project | ✅ Yes | Catch issues early | +| Legacy codebase audit | ✅ Yes | Find security debt | +| WordPress plugin/theme | ⚠️ Maybe | WP already has security APIs | +| CI/CD security gate | ✅ Yes (when binaries exist) | Automated scanning | +| **GHC not installed** | ❌ **No** | Tool cannot run | + +### Should I use php-aegis? + +| Your Situation | Use php-aegis? | Why | +|----------------|---------------|-----| +| WordPress plugin/theme | ⚠️ **Only for unique features** | WP core has equivalent security | +| Laravel/Symfony app | ✅ Yes | Complements framework security | +| Vanilla PHP app | ✅ Yes | Provides missing security layer | +| Semantic web (RDF/Turtle) | ✅ **Yes - unique value** | No other library handles this | +| IndieWeb (Micropub, etc.) | ✅ **Yes - unique value** | Protocol-specific security | +| ActivityPub/Fediverse | ✅ **Yes - unique value** | Content policy enforcement | + +--- + +## sanctify-php: When to Use + +### Ideal Use Cases + +1. **Security Audits** + - Scanning legacy codebases for vulnerabilities + - Pre-deployment security checks + - Compliance requirements (PCI, SOC2) + +2. **CI/CD Integration** + - Block PRs with security issues + - Generate SARIF reports for GitHub Security + - Track security debt over time + +3. **Code Transformation** + - Auto-add `declare(strict_types=1)` + - Insert missing escaping functions + - Enforce WordPress coding standards + +### When NOT to Use + +1. **GHC Not Available** (BLOCKER) + - sanctify-php requires Haskell compiler + - Until pre-built binaries exist, many environments can't use it + - Workaround: Docker container (when available) + +2. **Already Well-Secured WordPress Plugins** + - Mature plugins like Zotpress already follow WP security best practices + - sanctify-php adds limited value if codebase is already clean + - May still be useful for regression detection + +3. **Quick One-Off Scripts** + - Overhead not worth it for disposable code + - Use php-aegis runtime protection instead + +--- + +## php-aegis: When to Use + +### Ideal Use Cases + +1. **Non-WordPress PHP Applications** + ```php + // Laravel, Symfony, vanilla PHP + use Aegis\Escape; + echo Escape::html($userInput); + ``` + +2. **Semantic Web Applications** (UNIQUE VALUE) + ```php + // RDF/Turtle output - WordPress can't do this + use Aegis\Semantic\Turtle; + echo '"' . Turtle::escapeString($label) . '"'; + ``` + +3. **IndieWeb Applications** (UNIQUE VALUE) + ```php + // Micropub content sanitization + use Aegis\IndieWeb\Micropub; + $safe = Micropub::sanitizeContent($content, ['allow_html' => true]); + ``` + +4. **ActivityPub/Fediverse** (UNIQUE VALUE) + ```php + // Federated content policies + use Aegis\ActivityPub\Content; + $safe = Content::sanitize($post, ContentPolicy::STRICT); + ``` + +### When NOT to Use + +1. **WordPress Plugins/Themes (for standard security)** + + WordPress already provides: + | Need | WordPress Function | php-aegis Adds Nothing | + |------|-------------------|----------------------| + | HTML escape | `esc_html()` | ❌ | + | Attribute escape | `esc_attr()` | ❌ | + | URL escape | `esc_url()` | ❌ | + | JS escape | `esc_js()` | ❌ | + | Email validation | `is_email()` | ❌ | + | Sanitize text | `sanitize_text_field()` | ❌ | + + **Exception**: Use php-aegis for Turtle/RDF/IndieWeb in WordPress themes. + +2. **PHP 7.4 Environments (until compat package exists)** + - php-aegis requires PHP 8.1+ + - WordPress supports PHP 7.4+ + - Need `php-aegis-compat` package first + +--- + +## Combined Use: When Both Tools Add Value + +The tools complement each other best when: + +### Scenario: Semantic WordPress Theme + +``` +┌─────────────────────────────────────────────────────────────┐ +│ WordPress theme with RDF/Turtle output (IndieWeb/Semantic) │ +├─────────────────────────────────────────────────────────────┤ +│ │ +│ sanctify-php: │ +│ • Detects Turtle output context │ +│ • Warns: "esc_html() wrong for Turtle, use Aegis" │ +│ • Auto-inserts: Aegis\Semantic\Turtle::escapeString() │ +│ │ +│ php-aegis: │ +│ • Provides runtime Turtle escaping │ +│ • W3C-compliant string/IRI handling │ +│ • WordPress doesn't have this capability │ +│ │ +└─────────────────────────────────────────────────────────────┘ +``` + +### Scenario: Laravel API with Security Requirements + +``` +┌─────────────────────────────────────────────────────────────┐ +│ Laravel API with strict security requirements │ +├─────────────────────────────────────────────────────────────┤ +│ │ +│ sanctify-php (CI/CD): │ +│ • SARIF reports in GitHub Security │ +│ • Block PRs with SQL injection │ +│ • Enforce type hints on all functions │ +│ │ +│ php-aegis (runtime): │ +│ • Defense in depth for validation │ +│ • Consistent escaping API │ +│ • Additional validators (IP, UUID, credit card) │ +│ │ +└─────────────────────────────────────────────────────────────┘ +``` + +### Scenario: Standard WordPress Plugin + +``` +┌─────────────────────────────────────────────────────────────┐ +│ Standard WordPress plugin (no semantic web) │ +├─────────────────────────────────────────────────────────────┤ +│ │ +│ sanctify-php: ⚠️ Limited value │ +│ • May catch issues WP doesn't │ +│ • Useful for security audit │ +│ • But WP security is already comprehensive │ +│ │ +│ php-aegis: ❌ No value │ +│ • WordPress already has esc_html(), etc. │ +│ • Adding Aegis duplicates existing functions │ +│ • Exception: Use for unique validators WP lacks │ +│ │ +└─────────────────────────────────────────────────────────────┘ +``` + +--- + +## Summary: Unique Value Propositions + +### sanctify-php Unique Value + +| Capability | Competition | sanctify-php Advantage | +|------------|-------------|----------------------| +| PHP static analysis | PHPStan, Psalm | Security-focused, not just types | +| WordPress awareness | PHPCS-WPCS | Deeper taint tracking | +| Auto-fix transforms | None | Automatic code hardening | +| SARIF output | Few tools | GitHub Security integration | +| Semantic context | None | Detects Turtle/JSON-LD contexts | + +### php-aegis Unique Value + +| Capability | Competition | php-aegis Advantage | +|------------|-------------|---------------------| +| Turtle/RDF escaping | **None** | Only library for semantic web | +| Micropub sanitization | **None** | IndieWeb protocol security | +| ActivityPub content | **None** | Fediverse content policies | +| Context-aware escaping | Laravel, WP | Unified API across frameworks | +| UUID/IP/credit card | Various | Consolidated validation library | + +--- + +## Recommendations + +### For php-aegis Team + +1. **Don't compete with WordPress core** — document that php-aegis is for non-WP apps or unique WP needs +2. **Focus on unique value** — Turtle, IndieWeb, ActivityPub are unserved markets +3. **Create framework adapters** — Laravel, Symfony, WordPress (for unique features only) + +### For sanctify-php Team + +1. **Pre-built binaries are MANDATORY** — tool literally cannot be used without them +2. **Docker image as fallback** — for environments that can't install binaries +3. **Document when NOT to use** — mature WP plugins may not benefit + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath* From 4d492bd88d35b622a839c5ad444ac2430a93db08 Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 01:06:29 +0000 Subject: [PATCH 4/7] Add consolidated integration summary from all 3 projects Summarizes findings from: - wp-sinople-theme (semantic theme) - Zotpress (mature WP plugin) - Metrics capture Key conclusions: - sanctify-php: GHC is BLOCKER, pre-built binaries mandatory - php-aegis: Duplicates WP core, should focus on unique value (Turtle, IndieWeb, ActivityPub) Includes priority matrix and next steps for both teams. --- docs/INTEGRATION-SUMMARY.md | 162 ++++++++++++++++++++++++++++++++++++ 1 file changed, 162 insertions(+) create mode 100644 docs/INTEGRATION-SUMMARY.md diff --git a/docs/INTEGRATION-SUMMARY.md b/docs/INTEGRATION-SUMMARY.md new file mode 100644 index 0000000..2a1eacf --- /dev/null +++ b/docs/INTEGRATION-SUMMARY.md @@ -0,0 +1,162 @@ +# Integration Feedback Summary + +Consolidated findings from three real-world integration attempts. + +--- + +## Integration Projects + +| # | Project | Type | sanctify-php Result | php-aegis Result | +|---|---------|------|---------------------|------------------| +| 1 | wp-sinople-theme | Semantic WP theme | ⚠️ Ran with difficulty | ⚠️ Limited value | +| 2 | Zotpress | Mature WP plugin | ❌ **Could not run** | ❌ No value added | +| 3 | (Metrics capture) | - | Improvements measured | Issues documented | + +--- + +## Critical Findings + +### sanctify-php: GHC is a BLOCKER + +``` +┌─────────────────────────────────────────────────────────────┐ +│ The Haskell toolchain requirement is a TOTAL BLOCKER │ +│ │ +│ • Zotpress integration: Could not run sanctify-php at all │ +│ • Manual analysis was performed instead │ +│ • PHP developers will NOT install GHC │ +│ • Pre-built binaries are MANDATORY for any adoption │ +└─────────────────────────────────────────────────────────────┘ +``` + +### php-aegis: Duplicates WordPress Core + +``` +┌─────────────────────────────────────────────────────────────┐ +│ php-aegis provides no value for WordPress projects │ +│ │ +│ WordPress already has: │ +│ • esc_html(), esc_attr(), esc_url(), esc_js() │ +│ • sanitize_text_field(), wp_strip_all_tags() │ +│ • is_email(), wp_http_validate_url() │ +│ │ +│ php-aegis should focus on what WordPress LACKS: │ +│ • RDF/Turtle escaping │ +│ • IndieWeb protocol security │ +│ • ActivityPub content policies │ +└─────────────────────────────────────────────────────────────┘ +``` + +--- + +## Metrics Achieved + +| Metric | Before | After | Change | +|--------|--------|-------|--------| +| Files with `strict_types` | 0 | 24 | +100% | +| PHP version support | 7.4+ | 8.2+ | Upgraded | +| WordPress version | 5.8+ | 6.4+ | Upgraded | +| CI security checks | 0 | 4 | +4 new | + +--- + +## Priority Matrix + +### sanctify-php Priorities + +| Priority | Item | Status | Rationale | +|----------|------|--------|-----------| +| **BLOCKER** | Pre-built binaries | 🔲 Not Started | Tool cannot run without this | +| **Critical** | Composer plugin | 🔲 Not Started | PHP devs expect `composer require` | +| **High** | Docker container | 🔲 Not Started | Fallback for binary issues | +| **High** | GitHub Action | 🔲 Not Started | CI/CD adoption | +| Medium | Incremental analysis | 🔲 Not Started | Performance | +| Medium | Semantic support | 🔲 Not Started | Turtle/JSON-LD contexts | + +### php-aegis Priorities + +| Priority | Item | Status | Rationale | +|----------|------|--------|-----------| +| **Critical** | Define target audience | 🔲 Not Started | Don't compete with WP core | +| **Critical** | php-aegis-compat (7.4+) | 🔲 Not Started | WordPress adoption | +| **High** | Turtle escaping | 🔲 Not Started | **Unique value** | +| **High** | WordPress adapter | 🔲 Not Started | snake_case functions | +| Medium | Extended validators | 🔲 Not Started | int(), ip(), domain() | +| Medium | IndieWeb support | 🔲 Not Started | **Unique value** | + +--- + +## Strategic Decisions Required + +### For php-aegis + +> **Question**: Who is this library for? + +| Option | Description | Recommendation | +|--------|-------------|----------------| +| **A** | Non-WordPress PHP library | Don't compete with WP | +| **B** | WordPress superset library | Provide unique value WP lacks | + +**Recommendation: Option B** — Focus on semantic web, IndieWeb, ActivityPub. + +### For sanctify-php + +> **Question**: How do we achieve adoption? + +| Priority | Action | +|----------|--------| +| 1 | Release pre-built binaries (BLOCKER resolution) | +| 2 | Create Composer plugin wrapper | +| 3 | Create GitHub Action | +| 4 | Add Docker container as fallback | + +--- + +## What Works Well + +### sanctify-php Strengths +- ✅ WordPress-aware security constraints +- ✅ OWASP vulnerability coverage +- ✅ Taint tracking analysis +- ✅ SARIF output for GitHub Security +- ✅ Auto-fix transformations + +### php-aegis Strengths +- ✅ Simple, focused API +- ✅ Zero dependencies +- ✅ PSR-12 compliance +- ✅ Type safety + +--- + +## Documentation Produced + +| Document | Purpose | +|----------|---------| +| `PHP-AEGIS-HANDOVER.md` | Recommendations for php-aegis team | +| `ROADMAP.md` | sanctify-php improvement plan | +| `STANDALONE.md` | Minimum viable standalone requirements | +| `TARGET-AUDIENCE.md` | When to use each tool | +| `IMPLEMENTATION-TRACKER.md` | Cross-team coordination | +| `INTEGRATION-SUMMARY.md` | This consolidated summary | + +--- + +## Next Steps + +### Immediate (Week 1) +1. **sanctify-php**: Set up GitHub Actions for binary releases +2. **php-aegis**: Create php-aegis-compat package scaffold + +### Short-term (Week 2-3) +1. **sanctify-php**: Publish Composer plugin wrapper +2. **php-aegis**: Implement Turtle escaping functions + +### Medium-term (Week 4+) +1. **sanctify-php**: Create GitHub Action for CI/CD +2. **php-aegis**: Add IndieWeb protocol support + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath* From 881f63d262c106b7340f851de1b52602731818e9 Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 01:30:04 +0000 Subject: [PATCH 5/7] Add sinople-theme integration: success story + upstream issues Fourth integration report - sinople-theme SUCCESS: - php-aegis provided unique value via TurtleEscaper - sanctify-php integrated into GitHub Actions CI - Graceful fallback pattern when php-aegis unavailable New: UPSTREAM-ISSUES.md Documents bugs/issues to report: - php-aegis: missing compat package, not on Packagist, mu-plugin not implemented, missing Permissions-Policy - sanctify-php: UnsafeRedirect false positive, MissingTextDomain false positive, PHP 8.1+ syntax needs verification Key insight: When focused on UNIQUE value (Turtle escaping), both tools provide real value to WordPress projects. --- docs/IMPLEMENTATION-TRACKER.md | 10 +- docs/INTEGRATION-SUMMARY.md | 25 +++- docs/UPSTREAM-ISSUES.md | 248 +++++++++++++++++++++++++++++++++ 3 files changed, 278 insertions(+), 5 deletions(-) create mode 100644 docs/UPSTREAM-ISSUES.md diff --git a/docs/IMPLEMENTATION-TRACKER.md b/docs/IMPLEMENTATION-TRACKER.md index 463dfe4..96bef29 100644 --- a/docs/IMPLEMENTATION-TRACKER.md +++ b/docs/IMPLEMENTATION-TRACKER.md @@ -8,6 +8,7 @@ | sanctify-php Roadmap | ✅ Complete | Begin Phase 1 | | Standalone Requirements | ✅ Complete | See STANDALONE.md | | Target Audience | ✅ Complete | See TARGET-AUDIENCE.md | +| Upstream Issues | ✅ Complete | See UPSTREAM-ISSUES.md | | Binary Releases | 🔲 Not Started | **BLOCKER** - Tool cannot run without this | | Composer Plugin | 🔲 Not Started | **CRITICAL** - Enable `composer require` | | Docker Container | 🔲 Not Started | **HIGH** - Fallback for binary issues | @@ -21,10 +22,11 @@ ### Integration Evidence -| Project | Could run sanctify-php? | Result | -|---------|------------------------|--------| -| wp-sinople-theme | ⚠️ With difficulty | Needed Haskell setup | -| Zotpress | ❌ **NO** | GHC not available, couldn't run at all | +| Project | Could run sanctify-php? | php-aegis Value? | Result | +|---------|------------------------|------------------|--------| +| wp-sinople-theme | ⚠️ With difficulty | ⚠️ Limited | Needed Haskell setup | +| Zotpress | ❌ **NO** | ❌ None | GHC not available | +| sinople-theme | ✅ **CI Integration** | ✅ **Turtle!** | Success with unique value focus | > **Zotpress integration failed completely** — sanctify-php could not be executed. > Manual analysis was performed instead using documented patterns. diff --git a/docs/INTEGRATION-SUMMARY.md b/docs/INTEGRATION-SUMMARY.md index 2a1eacf..b7d7b08 100644 --- a/docs/INTEGRATION-SUMMARY.md +++ b/docs/INTEGRATION-SUMMARY.md @@ -1,6 +1,6 @@ # Integration Feedback Summary -Consolidated findings from three real-world integration attempts. +Consolidated findings from four real-world integration attempts. --- @@ -11,6 +11,29 @@ Consolidated findings from three real-world integration attempts. | 1 | wp-sinople-theme | Semantic WP theme | ⚠️ Ran with difficulty | ⚠️ Limited value | | 2 | Zotpress | Mature WP plugin | ❌ **Could not run** | ❌ No value added | | 3 | (Metrics capture) | - | Improvements measured | Issues documented | +| 4 | sinople-theme | Semantic WP theme | ✅ **CI integration** | ✅ **Unique value (Turtle!)** | + +### Success Story: sinople-theme + +The sinople-theme integration demonstrates the **correct approach**: + +``` +┌─────────────────────────────────────────────────────────────┐ +│ sinople-theme Integration: BOTH TOOLS PROVIDED VALUE │ +│ │ +│ php-aegis: │ +│ ✅ TurtleEscaper for RDF output (/feed/turtle/) │ +│ ✅ WordPress-style function wrappers │ +│ ✅ Graceful fallback if php-aegis unavailable │ +│ │ +│ sanctify-php: │ +│ ✅ Added to GitHub Actions CI workflow │ +│ ✅ AST-based security analysis │ +│ ✅ WordPress-specific issue detection │ +└─────────────────────────────────────────────────────────────┘ +``` + +**Key success factor**: Focus on **unique value** (Turtle escaping) not WordPress duplicates. --- diff --git a/docs/UPSTREAM-ISSUES.md b/docs/UPSTREAM-ISSUES.md new file mode 100644 index 0000000..e384404 --- /dev/null +++ b/docs/UPSTREAM-ISSUES.md @@ -0,0 +1,248 @@ +# Upstream Issues + +Issues discovered during integration testing that need to be reported to respective repositories. + +--- + +## php-aegis Issues + +### Issue 1: Missing php-aegis-compat Package + +**Severity**: High +**Found in**: sinople-theme integration + +**Description**: +The `COMPATIBILITY.md` documentation references a `php-aegis-compat` package for PHP 7.4+ compatibility, but this package does not exist. + +**Impact**: +WordPress projects targeting PHP 7.4 (the WordPress minimum) cannot use php-aegis. + +**Recommended Fix**: +```bash +# Create the package +mkdir php-aegis-compat +# Implement PHP 7.4 compatible API without enums/union types +``` + +--- + +### Issue 2: Not Published on Packagist + +**Severity**: Medium +**Found in**: sinople-theme integration + +**Description**: +php-aegis is not available on Packagist, requiring VCS repository configuration in composer.json. + +**Current workaround**: +```json +{ + "repositories": [ + { + "type": "vcs", + "url": "https://github.com/hyperpolymath/php-aegis" + } + ] +} +``` + +**Recommended Fix**: +Publish to Packagist for standard `composer require` experience. + +--- + +### Issue 3: WordPress mu-plugin Adapter Not Implemented + +**Severity**: Medium +**Found in**: sinople-theme integration + +**Description**: +Documentation describes a WordPress mu-plugin adapter for automatic loading, but the adapter code does not exist. + +**Expected location**: `src/WordPress/MuPlugin.php` + +**Recommended Fix**: +Implement the mu-plugin adapter or remove from documentation. + +--- + +### Issue 4: Headers::secure() Missing permissionsPolicy() + +**Severity**: Low +**Found in**: sinople-theme integration + +**Description**: +The `Headers::secure()` method sets security headers but is missing `Permissions-Policy` header. + +**Current output**: +``` +X-Content-Type-Options: nosniff +X-Frame-Options: DENY +X-XSS-Protection: 1; mode=block +Content-Security-Policy: ... +``` + +**Missing**: +``` +Permissions-Policy: camera=(), microphone=(), geolocation=() +``` + +--- + +## sanctify-php Issues + +### Issue 1: UnsafeRedirect False Positive + +**Severity**: Medium +**Found in**: sinople-theme integration + +**Description**: +The `UnsafeRedirect` check flags code as unsafe even when `exit` is on the next line. + +**False positive**: +```php +wp_redirect($url); +exit; // This IS safe, but sanctify reports it as unsafe +``` + +**Expected behavior**: +Should recognize `exit`/`die` on the immediately following line as safe. + +**Recommended Fix**: +```haskell +-- In UnsafeRedirect check, look for exit/die within next 2 statements +isFollowedByExit :: Statement -> [Statement] -> Bool +isFollowedByExit redirect following = + case take 2 following of + (ExitStatement:_) -> True + (DieStatement:_) -> True + _ -> False +``` + +--- + +### Issue 2: MissingTextDomain False Positive on WP Core + +**Severity**: Low +**Found in**: sinople-theme integration + +**Description**: +The `MissingTextDomain` check flags WordPress core functions that don't need a text domain. + +**False positive**: +```php +// These are WordPress core, not theme strings +__('Dashboard'); // Flagged, but this is WP core +``` + +**Recommended Fix**: +Maintain allowlist of WordPress core strings, or only check strings in theme/plugin files. + +--- + +### Issue 3: PHP 8.1+ Syntax Verification Needed + +**Severity**: Medium +**Found in**: sinople-theme integration + +**Description**: +Need to verify parser handles modern PHP syntax: +- Nullsafe operator (`?->`) +- Match expressions +- Named arguments +- Enums +- Constructor property promotion + +**Recommended Fix**: +Add test suite with PHP 8.1+ syntax examples. + +--- + +### Issue 4: Incomplete Guix Export Documentation + +**Severity**: Low +**Found in**: sinople-theme integration + +**Description**: +The `sanctify export --guix` command is documented but the output format and usage instructions are incomplete. + +**Missing**: +- Example output +- How to integrate with existing guix.scm +- Container vs package mode + +--- + +## Issue Template for GitHub + +### php-aegis Issue Template + +```markdown +## Issue: [Title] + +**Found during**: sinople-theme integration +**Severity**: [High/Medium/Low] + +### Description +[Description of the issue] + +### Steps to Reproduce +1. [Step 1] +2. [Step 2] + +### Expected Behavior +[What should happen] + +### Actual Behavior +[What actually happens] + +### Suggested Fix +[Code or approach to fix] +``` + +### sanctify-php Issue Template + +```markdown +## Issue: [Title] + +**Found during**: sinople-theme integration +**Severity**: [High/Medium/Low] +**Component**: [Parser/Analysis/Transform/CLI] + +### Description +[Description of the issue] + +### Example Code Triggering Issue +```php +// PHP code that triggers the issue +``` + +### Expected Behavior +[What sanctify-php should report/do] + +### Actual Behavior +[What sanctify-php actually reports/does] + +### Suggested Fix +[Haskell code or approach to fix] +``` + +--- + +## Tracking + +| Issue | Repository | Reported | Status | +|-------|------------|----------|--------| +| php-aegis-compat missing | php-aegis | 🔲 Pending | - | +| Not on Packagist | php-aegis | 🔲 Pending | - | +| mu-plugin not implemented | php-aegis | 🔲 Pending | - | +| Missing Permissions-Policy | php-aegis | 🔲 Pending | - | +| UnsafeRedirect false positive | sanctify-php | 🔲 Pending | - | +| MissingTextDomain false positive | sanctify-php | 🔲 Pending | - | +| PHP 8.1+ syntax verification | sanctify-php | 🔲 Pending | - | +| Guix export docs incomplete | sanctify-php | 🔲 Pending | - | + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath* From a89684e5d7f5ca41ba6f0b03041fb654bfd4b398 Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 01:33:31 +0000 Subject: [PATCH 6/7] Add Sinople full integration: real vulnerability found Fifth integration report - Sinople complete integration SUCCESS: CRITICAL FINDING: addslashes() was used for Turtle escaping - addslashes() is SQL escaping, NOT Turtle escaping - Real RDF injection vulnerability existed - Fixed with TurtleEscaper::literal() and TurtleEscaper::iri() Security fixes applied: - CRITICAL: Turtle escaping (2 issues) - HIGH: URL validation, Micropub sanitization - MEDIUM: Security headers (CSP, HSTS), rate limiting - LOW: strict_types on all files New upstream issues identified: - php-aegis: WordPress validators, TurtleEscaper lang tags, Headers WP integration - sanctify-php: Hook detection, Turtle context, REST API patterns This proves: When focused on unique value (Turtle escaping), php-aegis finds and fixes REAL vulnerabilities WordPress cannot address. --- docs/IMPLEMENTATION-TRACKER.md | 1 + docs/INTEGRATION-SUMMARY.md | 32 +++++++++++++ docs/UPSTREAM-ISSUES.md | 86 ++++++++++++++++++++++++++++++++++ 3 files changed, 119 insertions(+) diff --git a/docs/IMPLEMENTATION-TRACKER.md b/docs/IMPLEMENTATION-TRACKER.md index 96bef29..e6e747a 100644 --- a/docs/IMPLEMENTATION-TRACKER.md +++ b/docs/IMPLEMENTATION-TRACKER.md @@ -27,6 +27,7 @@ | wp-sinople-theme | ⚠️ With difficulty | ⚠️ Limited | Needed Haskell setup | | Zotpress | ❌ **NO** | ❌ None | GHC not available | | sinople-theme | ✅ **CI Integration** | ✅ **Turtle!** | Success with unique value focus | +| Sinople (full) | ✅ **Real vuln found** | ✅ **Critical fix** | TurtleEscaper fixed RDF injection | > **Zotpress integration failed completely** — sanctify-php could not be executed. > Manual analysis was performed instead using documented patterns. diff --git a/docs/INTEGRATION-SUMMARY.md b/docs/INTEGRATION-SUMMARY.md index b7d7b08..863b1b8 100644 --- a/docs/INTEGRATION-SUMMARY.md +++ b/docs/INTEGRATION-SUMMARY.md @@ -12,6 +12,7 @@ Consolidated findings from four real-world integration attempts. | 2 | Zotpress | Mature WP plugin | ❌ **Could not run** | ❌ No value added | | 3 | (Metrics capture) | - | Improvements measured | Issues documented | | 4 | sinople-theme | Semantic WP theme | ✅ **CI integration** | ✅ **Unique value (Turtle!)** | +| 5 | Sinople (full) | Semantic WP theme | ✅ **Real vuln found** | ✅ **TurtleEscaper fix** | ### Success Story: sinople-theme @@ -35,6 +36,37 @@ The sinople-theme integration demonstrates the **correct approach**: **Key success factor**: Focus on **unique value** (Turtle escaping) not WordPress duplicates. +### Major Win: Sinople Full Integration (Real Vulnerability Found) + +The complete Sinople integration found a **real security vulnerability**: + +``` +┌─────────────────────────────────────────────────────────────┐ +│ CRITICAL: addslashes() used for Turtle escaping │ +│ │ +│ Original code: addslashes($value) for RDF Turtle output │ +│ Problem: addslashes() is SQL escaping, NOT Turtle escaping │ +│ Risk: RDF injection attacks possible │ +│ │ +│ Fix: TurtleEscaper::literal() + TurtleEscaper::iri() │ +│ Result: W3C-compliant Turtle escaping │ +└─────────────────────────────────────────────────────────────┘ +``` + +**Security Fixes Applied**: + +| Severity | Issue | Fix | +|----------|-------|-----| +| CRITICAL | addslashes() for Turtle | TurtleEscaper::literal() | +| CRITICAL | IRI without validation | Validator::url() + error handling | +| HIGH | URL validation via strpos() | parse_url() host comparison | +| HIGH | Unsanitized Micropub input | sanitize_text_field() + wp_kses_post() | +| MEDIUM | No security headers | CSP, HSTS, X-Frame-Options | +| MEDIUM | No rate limiting | 1-min rate limit for Webmentions | +| LOW | Missing strict_types | Added to all PHP files | + +**This proves**: When focused on unique value (Turtle escaping), php-aegis finds and fixes real vulnerabilities that WordPress cannot address. + --- ## Critical Findings diff --git a/docs/UPSTREAM-ISSUES.md b/docs/UPSTREAM-ISSUES.md index e384404..75ca939 100644 --- a/docs/UPSTREAM-ISSUES.md +++ b/docs/UPSTREAM-ISSUES.md @@ -229,6 +229,86 @@ The `sanctify export --guix` command is documented but the output format and usa --- +## Issues from Sinople Full Integration + +### php-aegis Issues (from Sinople) + +#### Issue 5: WordPress-Specific Validators Needed + +**Severity**: Medium +**Found in**: Sinople full integration + +**Description**: +WordPress has security patterns (nonces, capabilities) that php-aegis doesn't address. + +**Needed validators**: +```php +Aegis\WordPress\Nonce::verify($action, $nonce); +Aegis\WordPress\Capability::check($cap, $user_id); +``` + +--- + +#### Issue 6: TurtleEscaper Language Tag Case Sensitivity + +**Severity**: Low +**Found in**: Sinople full integration + +**Description**: +Language tags in Turtle should be case-insensitive per BCP 47, but TurtleEscaper may not handle this correctly. + +--- + +#### Issue 7: Headers Class WordPress Integration + +**Severity**: Low +**Found in**: Sinople full integration + +**Description**: +`Headers::secure()` doesn't integrate with WordPress's `send_headers` action. + +**Recommended**: +```php +add_action('send_headers', [Headers::class, 'secure']); +``` + +--- + +### sanctify-php Issues (from Sinople) + +#### Issue 5: WordPress Hook Detection + +**Severity**: Medium +**Found in**: Sinople full integration + +**Description**: +sanctify-php should detect WordPress hooks (`add_action`, `add_filter`) and reduce false positives when code is wrapped in hook callbacks. + +--- + +#### Issue 6: RDF Turtle as Distinct Output Context + +**Severity**: High +**Found in**: Sinople full integration + +**Description**: +Turtle output is a distinct context from HTML. sanctify-php should: +- Detect `Content-Type: text/turtle` +- Warn when `esc_html()` is used in Turtle context +- Suggest `TurtleEscaper` instead + +--- + +#### Issue 7: WordPress REST API Pattern Recognition + +**Severity**: Medium +**Found in**: Sinople full integration + +**Description**: +WordPress REST API endpoints have specific sanitization patterns that sanctify-php should recognize. + +--- + ## Tracking | Issue | Repository | Reported | Status | @@ -237,10 +317,16 @@ The `sanctify export --guix` command is documented but the output format and usa | Not on Packagist | php-aegis | 🔲 Pending | - | | mu-plugin not implemented | php-aegis | 🔲 Pending | - | | Missing Permissions-Policy | php-aegis | 🔲 Pending | - | +| WordPress validators needed | php-aegis | 🔲 Pending | - | +| TurtleEscaper lang tag case | php-aegis | 🔲 Pending | - | +| Headers WP integration | php-aegis | 🔲 Pending | - | | UnsafeRedirect false positive | sanctify-php | 🔲 Pending | - | | MissingTextDomain false positive | sanctify-php | 🔲 Pending | - | | PHP 8.1+ syntax verification | sanctify-php | 🔲 Pending | - | | Guix export docs incomplete | sanctify-php | 🔲 Pending | - | +| WordPress hook detection | sanctify-php | 🔲 Pending | - | +| Turtle as output context | sanctify-php | 🔲 Pending | - | +| REST API pattern recognition | sanctify-php | 🔲 Pending | - | --- From 5ea7ae4c5c46623683385785179384252d1df960 Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 27 Dec 2025 02:05:39 +0000 Subject: [PATCH 7/7] Add IndieWeb collaboration: indieweb2-bastion integration New: INDIEWEB-COLLABORATION.md - Three-layer security model (bastion/aegis/sanctify) - Proposed indieweb2-bastion enhancements: - Nickel contracts for Micropub/Webmention/IndieAuth - Webmention source validation at ingress - Micropub request validation - IndieAuth token introspection cache - SurrealDB provenance schema for IndieWeb events - Integration patterns with php-aegis (header passthrough) - sanctify-php IndieWeb-aware analysis - Issue template for indieweb2-bastion repository - Lessons exchanged between projects Key insight: indieweb2-bastion handles infrastructure-level protection, php-aegis handles application-level security. Combined = defense in depth for IndieWeb protocols. --- docs/IMPLEMENTATION-TRACKER.md | 1 + docs/INDIEWEB-COLLABORATION.md | 473 +++++++++++++++++++++++++++++++++ 2 files changed, 474 insertions(+) create mode 100644 docs/INDIEWEB-COLLABORATION.md diff --git a/docs/IMPLEMENTATION-TRACKER.md b/docs/IMPLEMENTATION-TRACKER.md index e6e747a..f6d495a 100644 --- a/docs/IMPLEMENTATION-TRACKER.md +++ b/docs/IMPLEMENTATION-TRACKER.md @@ -9,6 +9,7 @@ | Standalone Requirements | ✅ Complete | See STANDALONE.md | | Target Audience | ✅ Complete | See TARGET-AUDIENCE.md | | Upstream Issues | ✅ Complete | See UPSTREAM-ISSUES.md | +| IndieWeb Collaboration | ✅ Complete | See INDIEWEB-COLLABORATION.md | | Binary Releases | 🔲 Not Started | **BLOCKER** - Tool cannot run without this | | Composer Plugin | 🔲 Not Started | **CRITICAL** - Enable `composer require` | | Docker Container | 🔲 Not Started | **HIGH** - Fallback for binary issues | diff --git a/docs/INDIEWEB-COLLABORATION.md b/docs/INDIEWEB-COLLABORATION.md new file mode 100644 index 0000000..5e2b17f --- /dev/null +++ b/docs/INDIEWEB-COLLABORATION.md @@ -0,0 +1,473 @@ +# IndieWeb Security: Cross-Project Collaboration + +This document outlines how `indieweb2-bastion`, `php-aegis`, and `sanctify-php` can work together to provide comprehensive IndieWeb security at both infrastructure and application layers. + +--- + +## The IndieWeb Security Gap + +IndieWeb protocols (Micropub, Webmention, IndieAuth, Microsub) have **no dedicated security libraries**. Current state: + +| Protocol | Security Needs | Current Solutions | Gap | +|----------|---------------|-------------------|-----| +| **Micropub** | Content sanitization, auth verification | WordPress `wp_kses_post()` | No protocol-specific sanitization | +| **Webmention** | Rate limiting, source validation | Manual implementation | No standard library | +| **IndieAuth** | Token verification, scope validation | Various implementations | No unified validation | +| **Microsub** | Feed sanitization, auth | Minimal | Almost nothing | + +### Real Vulnerabilities Found + +From the Sinople integration: + +``` +CRITICAL: addslashes() used for Turtle escaping → RDF injection +HIGH: URL validation via strpos() → Bypass possible +HIGH: Unsanitized Micropub input → XSS in content +MEDIUM: No Webmention rate limiting → DoS vector +``` + +--- + +## Three-Layer Security Model + +``` +┌─────────────────────────────────────────────────────────────────┐ +│ indieweb2-bastion │ +│ (Infrastructure Layer) │ +├─────────────────────────────────────────────────────────────────┤ +│ • Ingress gateway with IndieWeb protocol awareness │ +│ • Rate limiting at network level │ +│ • Content-Type validation │ +│ • Malformed request blocking │ +│ • DNS-level protections (ODNS) │ +│ • Provenance tracking of requests │ +└─────────────────────────────────────────────────────────────────┘ + ↓ +┌─────────────────────────────────────────────────────────────────┐ +│ php-aegis │ +│ (Application Layer) │ +├─────────────────────────────────────────────────────────────────┤ +│ • Micropub content sanitization │ +│ • Webmention source validation │ +│ • IndieAuth token verification │ +│ • Turtle/RDF escaping for semantic output │ +│ • Runtime security functions │ +└─────────────────────────────────────────────────────────────────┘ + ↓ +┌─────────────────────────────────────────────────────────────────┐ +│ sanctify-php │ +│ (Analysis Layer) │ +├─────────────────────────────────────────────────────────────────┤ +│ • Static analysis for IndieWeb security patterns │ +│ • Detect missing Micropub sanitization │ +│ • Warn on incorrect escaping context (HTML vs Turtle) │ +│ • CI/CD integration for security gates │ +└─────────────────────────────────────────────────────────────────┘ +``` + +--- + +## Proposed indieweb2-bastion Enhancements + +### 1. IndieWeb Protocol Detection + +Add protocol-aware ingress rules: + +```nickel +# indieweb-protocols.ncl +let IndieWebProtocol = { + micropub = { + endpoint = "/micropub", + methods = ["POST", "GET"], + content_types = ["application/json", "application/x-www-form-urlencoded", "multipart/form-data"], + required_headers = ["Authorization"], + rate_limit = { requests = 60, window_seconds = 60 }, + }, + + webmention = { + endpoint = "/webmention", + methods = ["POST"], + content_types = ["application/x-www-form-urlencoded"], + required_params = ["source", "target"], + rate_limit = { requests = 10, window_seconds = 60 }, # Stricter for external + }, + + indieauth = { + endpoints = { + authorization = "/auth", + token = "/token", + introspection = "/introspect", + }, + methods = ["GET", "POST"], + rate_limit = { requests = 30, window_seconds = 60 }, + }, + + microsub = { + endpoint = "/microsub", + methods = ["GET", "POST"], + required_headers = ["Authorization"], + rate_limit = { requests = 120, window_seconds = 60 }, + }, + + turtle_feed = { + endpoint = "/feed/turtle", + methods = ["GET"], + response_content_type = "text/turtle", + rate_limit = { requests = 300, window_seconds = 60 }, + }, +} +in IndieWebProtocol +``` + +### 2. Webmention Source Validation at Ingress + +Block obviously malicious Webmentions before they reach the application: + +```nickel +# webmention-validation.ncl +let WebmentionPolicy = { + # Block private/local IPs as source + blocked_source_ranges = [ + "10.0.0.0/8", + "172.16.0.0/12", + "192.168.0.0/16", + "127.0.0.0/8", + "::1/128", + "fc00::/7", + ], + + # Require HTTPS sources + require_https_source = true, + + # Block known spam domains + blocked_domains_file = "/etc/bastion/webmention-blocklist.txt", + + # Require source and target on same TLD? (optional) + same_tld_only = false, + + # Maximum source URL length + max_url_length = 2048, +} +in WebmentionPolicy +``` + +### 3. Micropub Request Validation + +Validate Micropub requests at the gateway: + +```nickel +# micropub-validation.ncl +let MicropubPolicy = { + # Required: Bearer token in Authorization header + require_authorization = true, + + # Allowed actions + allowed_actions = ["create", "update", "delete", "undelete"], + + # Content limits + max_content_length = 65536, # 64KB + max_photo_size = 10485760, # 10MB + max_photos = 10, + + # Blocked HTML elements in content (defense in depth) + blocked_elements = ["script", "iframe", "object", "embed", "form"], + + # Rate limits by action + rate_limits = { + create = { requests = 30, window_seconds = 60 }, + update = { requests = 60, window_seconds = 60 }, + delete = { requests = 10, window_seconds = 60 }, + }, +} +in MicropubPolicy +``` + +### 4. IndieAuth Token Introspection Cache + +Cache token introspection results to reduce auth server load: + +```nickel +# indieauth-cache.ncl +let IndieAuthCache = { + # Cache valid tokens + cache_valid_tokens = true, + valid_token_ttl_seconds = 300, # 5 minutes + + # Don't cache invalid tokens (security) + cache_invalid_tokens = false, + + # Introspection endpoint discovery + discover_introspection_endpoint = true, + + # Fallback if no introspection endpoint + fallback_to_token_endpoint = true, + + # Required scopes by endpoint + required_scopes = { + "/micropub" = ["create", "update", "delete", "media"], + "/microsub" = ["read", "follow", "mute", "block", "channels"], + }, +} +in IndieAuthCache +``` + +### 5. Provenance Tracking for IndieWeb + +Track the origin and flow of IndieWeb requests: + +```surql +-- SurrealDB schema for IndieWeb provenance + +DEFINE TABLE webmention_provenance SCHEMAFULL; +DEFINE FIELD source ON webmention_provenance TYPE string; +DEFINE FIELD target ON webmention_provenance TYPE string; +DEFINE FIELD source_ip ON webmention_provenance TYPE string; +DEFINE FIELD received_at ON webmention_provenance TYPE datetime; +DEFINE FIELD verified_at ON webmention_provenance TYPE option; +DEFINE FIELD verification_status ON webmention_provenance TYPE string; +DEFINE FIELD content_hash ON webmention_provenance TYPE string; + +DEFINE TABLE micropub_provenance SCHEMAFULL; +DEFINE FIELD client_id ON micropub_provenance TYPE string; +DEFINE FIELD action ON micropub_provenance TYPE string; +DEFINE FIELD post_url ON micropub_provenance TYPE option; +DEFINE FIELD created_at ON micropub_provenance TYPE datetime; +DEFINE FIELD token_scope ON micropub_provenance TYPE array; +DEFINE FIELD content_hash ON micropub_provenance TYPE string; + +-- Relationships +DEFINE TABLE caused_by SCHEMAFULL; +DEFINE FIELD in ON caused_by TYPE record; +DEFINE FIELD out ON caused_by TYPE record; +DEFINE FIELD relationship ON caused_by TYPE string; +``` + +--- + +## Integration with php-aegis + +indieweb2-bastion provides infrastructure-level protection; php-aegis handles application-level security: + +### Shared Configuration + +```json +{ + "indieweb_security": { + "bastion": { + "enabled": true, + "trust_bastion_headers": true, + "bastion_verified_header": "X-Bastion-Verified" + }, + "aegis": { + "micropub_sanitization": true, + "webmention_validation": true, + "turtle_escaping": true + } + } +} +``` + +### Header Passthrough + +When bastion validates a request, it adds headers that php-aegis can trust: + +``` +X-Bastion-Verified: true +X-Bastion-Protocol: micropub +X-Bastion-Rate-Limit-Remaining: 45 +X-Bastion-Source-Validated: true +X-Bastion-Request-ID: uuid-for-provenance +``` + +### php-aegis IndieWeb Module + +```php + [IndieWebEndpoint] +detectIndieWebEndpoints stmts = + mapMaybe detectEndpoint stmts + where + detectEndpoint (FunctionCall "add_action" [StringLit hook, _]) + | "micropub" `isInfixOf` hook = Just MicropubEndpoint + | "webmention" `isInfixOf` hook = Just WebmentionEndpoint + detectEndpoint _ = Nothing + +-- Check Micropub endpoint security +checkMicropubSecurity :: MicropubEndpoint -> [SecurityIssue] +checkMicropubSecurity endpoint = concat + [ checkAuthVerification endpoint + , checkContentSanitization endpoint + , checkBastionIntegration endpoint + ] + +-- Warn if not checking bastion headers when available +checkBastionIntegration :: Endpoint -> [SecurityIssue] +checkBastionIntegration endpoint + | usesBastionHeaders endpoint = [] + | otherwise = [Advisory "Consider trusting X-Bastion-Verified for defense in depth"] +``` + +--- + +## Issue Template for indieweb2-bastion + +```markdown +## Feature Request: IndieWeb Protocol Support + +### Summary +Add native support for IndieWeb protocols (Micropub, Webmention, IndieAuth, Microsub) +at the bastion ingress layer. + +### Motivation +IndieWeb protocols have unique security requirements: +- Webmention: Source validation, rate limiting for external requests +- Micropub: Content limits, authorization verification +- IndieAuth: Token caching, scope validation + +Currently, all security is handled at the application layer. Adding bastion-level +protection provides defense in depth and reduces load on applications. + +### Proposed Implementation + +1. **Protocol detection** (Nickel contracts) + - Detect IndieWeb endpoints by path/headers + - Apply protocol-specific policies + +2. **Webmention validation** + - Block private IP sources + - Require HTTPS + - Rate limit by source domain + +3. **Micropub limits** + - Content size limits + - Photo count/size limits + - Blocked HTML elements + +4. **IndieAuth integration** + - Token introspection caching + - Scope validation at ingress + +5. **Provenance tracking** + - SurrealDB schema for IndieWeb events + - Request correlation with application events + +### Integration Points +- php-aegis: Trust bastion headers for reduced sanitization +- sanctify-php: Detect bastion integration, warn if missing + +### Reference +See: hyperpolymath/sanctify-php/docs/INDIEWEB-COLLABORATION.md +``` + +--- + +## Lessons Exchanged + +### FROM indieweb2-bastion TO php-aegis/sanctify-php + +| Concept | Application | +|---------|-------------| +| **Nickel contracts** | Define security policies declaratively for sanctify-php | +| **Provenance graphs** | Track sanitization chain (who sanitized what, when) | +| **Consent-aware** | IndieWeb is about user control - reflect in API design | +| **Rate limiting patterns** | Apply at application level as fallback | + +### TO indieweb2-bastion FROM php-aegis/sanctify-php + +| Finding | Recommendation | +|---------|---------------| +| **Turtle escaping gap** | Validate Content-Type for /feed/turtle endpoints | +| **Webmention abuse** | Add source validation at ingress | +| **Micropub content** | Block dangerous HTML elements before application | +| **Real vulnerability found** | addslashes() misuse - validate escaping context | + +--- + +## Next Steps + +1. **Open issue on indieweb2-bastion** with the template above +2. **Create shared Nickel contracts** for IndieWeb security policies +3. **Add bastion header support** to php-aegis IndieWeb module +4. **Extend sanctify-php** to detect bastion integration + +--- + +*SPDX-License-Identifier: MIT OR AGPL-3.0-or-later* +*SPDX-FileCopyrightText: 2024-2025 hyperpolymath*