PHP code example of qoliber / tsuku

1. Go to this page and download the library: Download qoliber/tsuku library. Choose the download type require.

2. Extract the ZIP file and open the index.php.

3. Add this code to the index.php.
    
        
<?php
require_once('vendor/autoload.php');

/* Start to develop here. Best regards https://php-download.com/ */

    

qoliber / tsuku example snippets


use Qoliber\Tsuku\Tsuku;

$data = ['product' => 'Widget', 'price' => 29.99];

$template = 'Product: {product}, Price: ${price}';

$tsuku = new Tsuku();
echo $tsuku->process($template, $data);
// Output: Product: Widget, Price: $29.99

$template = 'Products:
@for(products as product)
- {product.name}: ${product.price}
@end';

$data = [
    'products' => [
        ['name' => 'Widget A', 'price' => '29.99'],
        ['name' => 'Widget B', 'price' => '39.99'],
    ],
];

echo $tsuku->process($template, $data);
// Output:
// Products:
// - Widget A: $29.99
// - Widget B: $39.99

$template = '@for(items as item)
{item.name}: @if(item.stock > 0)
✓ Available
@else
✗ Out of Stock
@end
@end';

// Works with both arrays AND objects!
class Product {
    private $price = 99.99;
    public function getPrice() { return $this->price; }
    public function isAvailable() { return true; }
}

$template = 'Price: ${product.price}, Available: {product.available}';
$tsuku->process($template, ['product' => new Product()]);
// Output: Price: $99.99, Available: 1

// Register your own functions
$tsuku->registerFunction('currency', fn($amount, $code = 'USD') =>
    match($code) {
        'USD' => '$' . number_format($amount, 2),
        'EUR' => '€' . number_format($amount, 2),
        default => $code . ' ' . number_format($amount, 2)
    }
);

$template = 'Total: @currency(price, "EUR")';
$tsuku->process($template, ['price' => 99.99]);
// Output: Total: €99.99

$tsuku = new Tsuku();

$template = '<?xml version="1.0"

$template = 'SKU,Name,Price,Stock
@for(products as product)
@csv(product.sku),@csv(product.name),$@number(product.price, 2),{product.stock}
@end';

$data = [
    'products' => [
        ['sku' => 'WID-001', 'name' => 'Widget', 'price' => 29.99, 'stock' => '100'],
        ['sku' => 'GAD-002', 'name' => 'Gadget, Premium', 'price' => 1299.50, 'stock' => '50'],
    ],
];

file_put_contents('export.csv', $tsuku->process($template, $data));
// Output:
// SKU,Name,Price,Stock
// WID-001,Widget,$29.99,100
// GAD-002,"Gadget, Premium",$1,299.50,50

$template = '<?xml version="1.0"

$template = 'services:
@for(services as service)
  {service.name}:
    image: {service.image}
    @if(service.ports)ports:
@for(service.ports as port)
      - "{port}"
@end
    @end
@end';

$template = '<ul class="products">
@for(products as product)
  <li>
    <h3>@html(product.name)</h3>
    <p>$@number(product.price, 2)</p>
    <div class="description">@html(product.description)</div>
    @if(product.stock > 0)
    <span class="in-stock">Available</span>
    @else
    <span class="out-of-stock">Out of Stock</span>
    @end
  </li>
@end
</ul>';

$data = [
    'products' => [
        [
            'name' => 'Premium Widget',
            'price' => 1299.99,
            'description' => 'A <strong>powerful</strong> widget',
            'stock' => 5,
        ],
    ],
];

// Output: HTML entities escaped to prevent XSS
// <h3>Premium Widget</h3>
// <p>$1,299.99</p>
// <div class="description">A &lt;strong&gt;powerful&lt;/strong&gt; widget</div>

// All of these work:
{product.price}     // Array: $product['price'] OR Object: $product->getPrice()
{user.name}         // Array: $user['name'] OR Object: $user->getName()
{product.available} // Array: $product['available'] OR Object: $product->isAvailable()
{item.total}        // Array: $item['total'] OR Object: $item->total() OR $item->getTotal()

$tsuku->registerFunction('badge', function(string $text, string $color = 'blue'): string {
    return "<span class=\"badge badge-{$color}\">{$text}</span>";
});

// Use in template:
// @badge(status, "green")

Input:  "Hello {name}, @if(admin)welcome@end"

Tokens: [
  TEXT("Hello "),
  VARIABLE("name"),
  TEXT(", "),
  DIRECTIVE_IF("admin"),
  TEXT("welcome"),
  DIRECTIVE_END
]

Tokens: [TEXT("Hello "), VARIABLE("name"), DIRECTIVE_IF(...)]

AST:
TemplateNode
├── TextNode("Hello ")
├── VariableNode("name")
└── IfNode(condition: "admin")
    └── TextNode("welcome")

AST Tree → Visitor Pattern → Final Output

TemplateNode.accept(compiler)
  ├── TextNode.accept(compiler) → "Hello "
  ├── VariableNode.accept(compiler) → "John"  (looks up data)
  └── IfNode.accept(compiler)
      └── if (condition) TextNode.accept(compiler) → "welcome"

Output: "Hello John, welcome"

$tsuku = new Tsuku();
$result = $tsuku->process('@if(admin){name}@end', ['admin' => true, 'name' => 'John']);

// Internally:
// 1. Lexer::tokenize() → [DIRECTIVE_IF("admin"), VARIABLE("name"), DIRECTIVE_END]
// 2. Parser::parse() → IfNode(condition: "admin", children: [VariableNode("name")])
// 3. Compiler::compile() → Walks tree:
//    - IfNode: evaluate condition (true) → execute children
//    - VariableNode: lookup "name" in data → "John"
// 4. Output: "John"
bash
php benchmarks/run-all.php