Blade Parser

repository·2.x·Indexed 40 days ago

https://github.com/stillat/blade-parser

A Laravel-specific library for parsing, analyzing, and manipulating Blade templates. It provides tools for deep structural inspection, automated validation via the `blade:validate` Artisan command, and a configurable compiler for converting Blade templates into PHP.

Tokens
8.3K
Snippets
29
Records
44
Agent score
97%

What's inside Blade Parser

  1. Overview of Blade Parser components

    2.x

    Blade Parser is a Laravel library designed for parsing, analyzing, and manipulating Blade templates. It consists of five core components:

    • Parser: Generates a list of nodes from a Blade template for analysis.
    • Documents: An abstraction layer for interacting with a single parsed template.
    • Workspaces: An API for managing and working with multiple parsed templates simultaneously.
    • Compiler: A configurable Blade compiler implementation that supports precompilers, extensions, and third-party packages.
    • Validator: An extensible system for detecting issues in Blade documents (e.g., unpaired conditions or invalid component parameter spacing).
  2. Parse Blade templates using the Documents API

    2.x

    You can quickly parse a Blade template string into a Document object using the Document::fromText() method. Once parsed, the Document instance allows you to query the template structure, such as retrieving or finding specific components.

    <?php
     
    use Stillatlade-parser\Document\Document;
     
    $template = <<<'BLADE'
        Hello, {{ $world }}
    BLADE;
     
    $document = Document::fromText($template);
  3. Manage multiple Blade templates with the Workspace class

    2.x

    The Workspace class is used to manage and interact with multiple parsed Blade templates simultaneously. It allows you to discover files in directories, add individual files, and perform operations across all documents in the workspace (such as compilation or validation).

    use Stillat\BladeParser\Workspaces\Workspace;
    
    $workspace = new Workspace();
    
    // Add an entire directory of templates
    $workspace->addDirectory('/path/to/resources/views');
    
    // Or add specific files
    $workspace->addFile('/path/to/resources/views/welcome.blade.php');
    
    // Access the parsed documents
    $documents = $workspace->getDocuments();
  4. Retrieve components from a Blade Document

    2.x

    After parsing a template into a Document, you can use the following methods to interact with component tags:

    • getComponents(): Returns all component tags found in the template.
    • findComponentsByTagName('name'): Returns only the components that match the specified tag name.
    // Get all components
    $document->getComponents()->each(fn($node) => ...);
    
    // Find specific components by tag name
    $document->findComponentsByTagName('alert')->each(fn($node) => ...);
  5. Validate Blade templates with the blade:validate command

    2.x

    Blade Parser includes an Artisan command blade:validate to check all Blade templates in your project for errors.

    Setup

    Before running the command, you must publish the configuration files:

    php artisan vendor:publish --tag=blade

    Usage

    Run the validation against your project using:

    php artisan blade:validate

    If validation issues are found, they will be output directly to your terminal.

    php artisan vendor:publish --tag=blade
    php artisan blade:validate
  6. Configure echo formatting and encoding

    2.x

    You can control how Blade's {{ }} syntax is compiled into PHP using setEchoFormat(string $format).

    Convenience methods include:

    • withDoubleEncoding(): Sets the format to e(%s, true) to double encode entities.
    • withoutDoubleEncoding(): Sets the format to e(%s, false) to prevent double encoding.
  7. Register custom Blade compiler extensions

    2.x

    You can extend the compiler's functionality by registering a callback via extend(). This callback is invoked during the compilation process for text segments. This is useful for adding custom syntax support or modifying how certain parts of the template are processed.

    The callback receives the string value to compile and the Compiler instance itself.

    $compiler->extend(function (string $value, Compiler $compiler) {
        // Modify the template string before it is fully compiled
        return str_replace('{{ custom_var }}', '{{ $real_var }}', $value);
    });
  8. Register validators with BladeValidator

    2.x

    The BladeValidator class allows you to register two types of validators to inspect Blade documents:

    1. Node Validators (AbstractNodeValidator): Used to validate individual nodes within the document tree.
    2. Document Validators (AbstractDocumentValidator): Used to validate the document as a whole.

    You can add single instances or arrays of validators using the following methods:

    • addValidator(AbstractNodeValidator $validator): Registers a single node validator.
    • addValidators(array $validators): Registers multiple node validators.
    • addDocumentValidator(AbstractDocumentValidator $validator): Registers a single document validator.
    • addDocumentValidators(array $validators): Registers multiple document validators.

    Note: If a validator has its requiresStructures property set to true, the BladeValidator will automatically trigger resolveStructures() on document instances during the validation process.

    $validator = new BladeValidator();
    
    // Adding node validators
    $validator->addValidator(new MyCustomNodeValidator());
    $validator->addValidators([new NodeValidatorA(), new NodeValidatorB()]);
    
    // Adding document validators
    $validator->addDocumentValidator(new MyCustomDocumentValidator());
  9. Retrieve parameters from an HtmlFragment

    2.x

    When working with an HtmlFragment, you can access its attributes (parameters) using the following methods:

    • hasParameter(string $name): Returns true if the fragment contains a parameter with the specified name.
    • getParameter(string $name): Returns the FragmentParameter object associated with the given name, or null if it does not exist.
  10. Convert a Document back to a string

    2.x

    You can get a string representation of the document (effectively re-serializing the nodes) using:

    • toString(): Returns a string representation by traversing all nodes and calling their toString() methods.
    • (string) $document: The magic __toString() method performs the same action as toString().
    $templateString = $document->toString();
    // OR
    $templateString = (string) $document;
  11. Traverse directive pairs using DirectiveNode

    2.x

    When working with structural directives (like @if...@endif), DirectiveNode provides methods to navigate the relationship between opening and closing tags.

    • getRootOpeningDirective(): For a closing directive, returns the furthest opening directive in the chain (e.g., for an @endif in a nested structure, it returns the original @if).
    • getFinalClosingDirective(): For an opening directive, returns the furthest closing directive in the chain (e.g., for an @if, it returns the final @endif).
    • getChainedClosingDirectives(): Returns a Collection of all DirectiveNode objects in the chain of closing directives.