{"_id":"@aetherframework/template-engine","_rev":"5-3bdff35a0fcd0e94159a40d79173f093","name":"@aetherframework/template-engine","dist-tags":{"latest":"1.0.6"},"versions":{"1.0.0":{"name":"@aetherframework/template-engine","version":"1.0.0","keywords":["template","engine","ssr","aether","html"],"author":{"name":"Aether Framework Team"},"license":"MIT","_id":"@aetherframework/template-engine@1.0.0","maintainers":[{"name":"aetherframework","email":"aetherjs@outlook.com"}],"homepage":"https://www.aetherjs.org","bugs":{"url":"https://github.com/aetherjs/aetherframework-template-engine/issues","email":"support@aetherjs.org"},"dist":{"shasum":"20ae9ef464b96cbddb54785314d13f76725e2d0e","tarball":"https://registry.npmjs.org/@aetherframework/template-engine/-/template-engine-1.0.0.tgz","fileCount":21,"integrity":"sha512-PHZKxi9WeBdKotbObVItE9SO8TTaIoCRAIYxT9ApqEw/zofMQ1JZ6eIptKZ+kRMVa7Bm5caurLtdJIwA8ebkOQ==","signatures":[{"sig":"MEUCIQCwwA/rccbISjF8dMa0KBbm2Jre+qtfqG3zL5PvQPmmMgIgFX6NLXGLgU1zydjps2ECiKApaVHtL2J8JrSmfO/85B8=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":160874},"main":"index.js","type":"module","scripts":{"clean":"rm -rf templates/cache","start":"node examples/basic-usage.js","test:ssr":"node examples/ssr-example.js","test:basic":"node examples/basic-usage.js","test:layout":"node examples/layout-example.js"},"_npmUser":{"name":"aetherframework","email":"aetherjs@outlook.com"},"repository":{"url":"git+https://github.com/aetherjs/aetherframework-template-engine.git","type":"git"},"_npmVersion":"10.9.3","description":"A lightweight, high-performance template engine with SSR support and custom syntax","directories":{},"_nodeVersion":"22.18.0","dependencies":{"fs-extra":"^11.2.0"},"_hasShrinkwrap":false,"_npmOperationalInternal":{"tmp":"tmp/template-engine_1.0.0_1780806052610_0.8130111600077143","host":"s3://npm-registry-packages-npm-production"}},"1.0.1":{"name":"@aetherframework/template-engine","version":"1.0.1","keywords":["template","engine","ssr","aether","html"],"author":{"name":"Aether Framework Team"},"license":"MIT","_id":"@aetherframework/template-engine@1.0.1","maintainers":[{"name":"aetherframework","email":"aetherjs@outlook.com"}],"homepage":"https://www.aetherjs.org","bugs":{"url":"https://github.com/aetherjs/aetherframework-template-engine/issues","email":"support@aetherjs.org"},"dist":{"shasum":"536e793d18ff8f7d7ea8f7db335a49760d7edc37","tarball":"https://registry.npmjs.org/@aetherframework/template-engine/-/template-engine-1.0.1.tgz","fileCount":21,"integrity":"sha512-5cPkhsSVfq54aGK2z1G70ZxuVEbn0Yq1CnhKcN08N85WRozySvKfVR+xXbuvHN8KBo+D/3m8oP5P3aARGBi1Bg==","signatures":[{"sig":"MEUCIQC23fWKcv1WBBSYwJ9B8npRqbmJ+7tmRRVlBHhpMMZ3FAIgfHbJRoXwrgTlRfGAU/PZow260RmiPPCjoIT+TKr7IpQ=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":162649},"main":"index.js","type":"module","scripts":{"clean":"rm -rf templates/cache","start":"node examples/basic-usage.js","test:ssr":"node examples/ssr-example.js","test:basic":"node examples/basic-usage.js","test:layout":"node examples/layout-example.js"},"_npmUser":{"name":"aetherframework","email":"aetherjs@outlook.com"},"repository":{"url":"git+https://github.com/aetherjs/aetherframework-template-engine.git","type":"git"},"_npmVersion":"10.9.3","description":"A lightweight, high-performance template engine with SSR support and custom syntax","directories":{},"_nodeVersion":"22.18.0","dependencies":{"fs-extra":"^11.2.0"},"_hasShrinkwrap":false,"_npmOperationalInternal":{"tmp":"tmp/template-engine_1.0.1_1780823834246_0.029264087763005042","host":"s3://npm-registry-packages-npm-production"}},"1.0.2":{"name":"@aetherframework/template-engine","version":"1.0.2","keywords":["template","engine","ssr","aether","html"],"author":{"name":"Aether Framework Team"},"license":"MIT","_id":"@aetherframework/template-engine@1.0.2","maintainers":[{"name":"aetherframework","email":"aetherjs@outlook.com"}],"homepage":"https://www.aetherjs.org","bugs":{"url":"https://github.com/aetherjs/aetherframework-template-engine/issues","email":"support@aetherjs.org"},"dist":{"shasum":"77059049aa4b94cb6d23d22d2f86d21bfe046c49","tarball":"https://registry.npmjs.org/@aetherframework/template-engine/-/template-engine-1.0.2.tgz","fileCount":18,"integrity":"sha512-3u0RZclbrRpAG3Rpr0LP/xhLLYIRlcbvD4zZB0ImZxF/3j/xDdSJHDG5mghoaL3JJNRQgVzKygMfbpDMbgVUug==","signatures":[{"sig":"MEQCIB4E/MCZmLsR+/mryMuE/41loBJZJWH8pkQvVkAdfsBwAiAHVcqVQLyrzONbugcZG5I6KoNhFLjWfqslI8OFQacmUw==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":191072},"main":"index.js","type":"module","scripts":{"clean":"rm -rf templates/cache","start":"node examples/basic-usage.js","test:ssr":"node examples/ssr-example.js","test:basic":"node examples/basic-usage.js","test:layout":"node examples/layout-example.js"},"_npmUser":{"name":"aetherframework","email":"aetherjs@outlook.com"},"repository":{"url":"git+https://github.com/aetherjs/aetherframework-template-engine.git","type":"git"},"_npmVersion":"10.9.3","description":"A lightweight, high-performance template engine with SSR support and custom syntax","directories":{},"_nodeVersion":"22.18.0","dependencies":{"fs-extra":"^11.2.0"},"_hasShrinkwrap":false,"_npmOperationalInternal":{"tmp":"tmp/template-engine_1.0.2_1780891530705_0.9919438159941125","host":"s3://npm-registry-packages-npm-production"}},"1.0.5":{"name":"@aetherframework/template-engine","version":"1.0.5","keywords":["template","engine","ssr","aether","html"],"author":{"name":"Aether Framework Team"},"license":"MIT","_id":"@aetherframework/template-engine@1.0.5","maintainers":[{"name":"aetherframework","email":"aetherjs@outlook.com"}],"homepage":"https://www.aetherjs.org","bugs":{"url":"https://github.com/aetherjs/aetherframework-template-engine/issues","email":"support@aetherjs.org"},"dist":{"shasum":"d794dd9eaef59f23961781b26fb543e6b7a64f43","tarball":"https://registry.npmjs.org/@aetherframework/template-engine/-/template-engine-1.0.5.tgz","fileCount":21,"integrity":"sha512-7VJdMEhCRfZbPiVswGYB+2H1WLmLH2DoBgQ9pqNsJckNBLC5FT4KC5LCzJRYgCIur7KrbbHFLevgFNjr5b/P6w==","signatures":[{"sig":"MEUCIQCFi/P7XLr0VB0s1l25VNfRRcw9MPsb1IvFfP+SVgkKXQIgVU2h361tV96Q9WHQvUw9NXrYV2pKlXTrJQaPGcnMMIA=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":220002},"main":"index.js","type":"module","scripts":{"clean":"rm -rf templates/cache","start":"node examples/basic-usage.js","test:ssr":"node examples/ssr-example.js","test:basic":"node examples/basic-usage.js","test:layout":"node examples/layout-example.js"},"_npmUser":{"name":"aetherframework","email":"aetherjs@outlook.com"},"repository":{"url":"git+https://github.com/aetherjs/aetherframework-template-engine.git","type":"git"},"_npmVersion":"10.9.3","description":"A lightweight, high-performance template engine with SSR support and custom syntax","directories":{},"_nodeVersion":"22.18.0","dependencies":{"fs-extra":"^11.2.0"},"_hasShrinkwrap":false,"_npmOperationalInternal":{"tmp":"tmp/template-engine_1.0.5_1780931996458_0.0829656325496464","host":"s3://npm-registry-packages-npm-production"}},"1.0.6":{"name":"@aetherframework/template-engine","version":"1.0.6","description":"A lightweight, high-performance template engine with SSR support and custom syntax","main":"index.js","type":"module","scripts":{"start":"node examples/basic-usage.js","test:basic":"node examples/basic-usage.js","test:layout":"node examples/layout-example.js","test:ssr":"node examples/ssr-example.js","clean":"rm -rf templates/cache"},"author":{"name":"Aether Framework Team"},"license":"MIT","repository":{"type":"git","url":"git+https://github.com/aetherjs/aetherframework-template-engine.git"},"bugs":{"url":"https://github.com/aetherjs/aetherframework-template-engine/issues","email":"support@aetherjs.org"},"homepage":"https://www.aetherjs.org","keywords":["template","engine","ssr","aether","html"],"dependencies":{"fs-extra":"^11.2.0"},"_id":"@aetherframework/template-engine@1.0.6","_nodeVersion":"22.18.0","_npmVersion":"10.9.3","dist":{"integrity":"sha512-tbaEvF1fUDjzGrwKIT4vrXt41aAxmCpAE7EBEsC+zkiEz8EPuF0mRpu/xep7iwMgrl5UeJ5nnXO8sJmfYipFGg==","shasum":"897ed07356b4602e6b37c7bc28db5e393cde4e20","tarball":"https://registry.npmjs.org/@aetherframework/template-engine/-/template-engine-1.0.6.tgz","fileCount":21,"unpackedSize":220002,"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEYCIQDJrF9Lc8ux2CvmVCcBrSQ38t/5eihyGinEhHDY5OZFMwIhAPD4pmF1LW7K6mUwtv/AZIzHTBKkJrD+8ZSGjL0sLk6n"}]},"_npmUser":{"name":"aetherframework","email":"aetherjs@outlook.com"},"directories":{},"maintainers":[{"name":"aetherframework","email":"aetherjs@outlook.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/template-engine_1.0.6_1780933849631_0.48410625569036947"},"_hasShrinkwrap":false}},"time":{"created":"2026-06-07T04:20:52.417Z","modified":"2026-06-08T15:50:50.178Z","1.0.0":"2026-06-07T04:20:52.741Z","1.0.1":"2026-06-07T09:17:14.487Z","1.0.2":"2026-06-08T04:05:30.852Z","1.0.5":"2026-06-08T15:19:56.671Z","1.0.6":"2026-06-08T15:50:49.757Z"},"bugs":{"url":"https://github.com/aetherjs/aetherframework-template-engine/issues","email":"support@aetherjs.org"},"author":{"name":"Aether Framework Team"},"license":"MIT","homepage":"https://www.aetherjs.org","keywords":["template","engine","ssr","aether","html"],"repository":{"type":"git","url":"git+https://github.com/aetherjs/aetherframework-template-engine.git"},"description":"A lightweight, high-performance template engine with SSR support and custom syntax","maintainers":[{"name":"aetherframework","email":"aetherjs@outlook.com"}],"readme":"Aether Framework Template Engine\r\n\r\nA modern, lightweight template engine for Node.js with Blade-like syntax, supporting SSR (Server-Side Rendering) and template modes. Features include template inheritance, includes, conditionals, loops, filters, and custom functions.\r\n\r\nFeatures\r\n\r\n- Blade-like Syntax: Familiar syntax similar to Laravel Blade\r\n- Template Inheritance: Support for `@extends`, `@section`, `@yield`, `@include`\r\n- Conditionals & Loops: `@if`, `@else`, `@endif`, `@foreach`, `@endforeach`\r\n- Custom Functions: `{{ route('home') }}`, `{{ asset('images/logo.png') }}`\r\n- Chained Properties: `{{ auth().user.name }}`\r\n- Filters: `{{ variable|upper }}`, `{{ variable|date:'YYYY-MM-DD' }}`\r\n- SSR Support: Server-side rendering mode\r\n- Caching: Built-in template compilation caching\r\n- ES Module: Native ES Module support\r\n\r\nInstallation\r\n\r\n```bash\r\nnpm install @aetherframework/template-engine\r\n```\r\n\r\nQuick Start\r\n\r\nBasic Usage\r\n\r\n```javascript\r\nimport AetherEngine from '@aetherframework/template-engine';\r\n\r\n// Initialize the engine\r\nconst engine = new AetherEngine({\r\n  templateDir: './templates',  // Template directory\r\n  cacheEnabled: true,           // Enable caching\r\n  debug: true                   // Debug mode\r\n});\r\n\r\nawait engine.initialize();\r\n\r\n// Define your template\r\nconst template = `\r\n<header class=\"header\">\r\n    <nav class=\"navbar\">\r\n        <div class=\"container\">\r\n            <a class=\"navbar-brand\" href=\"{{ route('home') }}\">\r\n                <img src=\"{{ asset('images/logo.png') }}\" alt=\"Logo\" height=\"40\">\r\n            </a>\r\n            \r\n            <ul class=\"navbar-nav\">\r\n                <li class=\"nav-item\">\r\n                    <a class=\"nav-link\" href=\"{{ route('home') }}\">Home</a>\r\n                </li>\r\n                <li class=\"nav-item\">\r\n                    <a class=\"nav-link\" href=\"{{ route('about') }}\">About</a>\r\n                </li>\r\n                \r\n                @if(auth().check())\r\n                    <li class=\"nav-item dropdown\">\r\n                        <a class=\"nav-link dropdown-toggle\" href=\"\" role=\"button\">\r\n                            {{ auth().user.name }}\r\n                        </a>\r\n                        <div class=\"dropdown-menu\">\r\n                            <a class=\"dropdown-item\" href=\"{{ route('profile') }}\">Profile</a>\r\n                            <a class=\"dropdown-item\" href=\"{{ route('logout') }}\">Logout</a>\r\n                        </div>\r\n                    </li>\r\n                @else\r\n                    <li class=\"nav-item\">\r\n                        <a class=\"nav-link\" href=\"{{ route('login') }}\">Login</a>\r\n                    </li>\r\n                    <li class=\"nav-item\">\r\n                        <a class=\"nav-link\" href=\"{{ route('register') }}\">Register</a>\r\n                    </li>\r\n                @endif\r\n            </ul>\r\n        </div>\r\n    </nav>\r\n</header>`;\r\n\r\n// Prepare data\r\nconst data = {\r\n  auth: () => ({\r\n    check: () => true,\r\n    user: { name: 'John Doe' }\r\n  }),\r\n  route: (name) => {\r\n    const routes = {\r\n      'home': '/',\r\n      'about': '/about',\r\n      'login': '/login',\r\n      'register': '/register',\r\n      'profile': '/profile',\r\n      'logout': '/logout'\r\n    };\r\n    return routes[name] || '';\r\n  },\r\n  asset: (path) => `/assets/${path}`\r\n};\r\n\r\n// Render the template\r\nconst html = await engine.render(template, data);\r\nconsole.log(html);\r\n```\r\n\r\nUsing Factory Pattern\r\n\r\n```javascript\r\nimport { createEngine } from '@aetherframework/template-engine';\r\n\r\n// Create engine factory\r\nconst factory = await createEngine({\r\n  mode: 'template',     // 'template' or 'ssr'\r\n  templateDir: './views',\r\n  cacheEnabled: true,\r\n  debug: process.env.NODE_ENV === 'development'\r\n});\r\n\r\n// Create renderer\r\nconst renderer = factory.createRenderer('aether');\r\n\r\n// Render template\r\nconst html = await renderer.render(template, data);\r\n```\r\n\r\nTemplate Syntax\r\n\r\nVariables\r\n\r\n```html\r\n<!-- Simple variable -->\r\n<p>Hello, {{ name }}!</p>\r\n\r\n<!-- Object property -->\r\n<p>Email: {{ user.email }}</p>\r\n\r\n<!-- Array access -->\r\n<p>First item: {{ items[0] }}</p>\r\n```\r\n\r\nFunctions\r\n\r\n```html\r\n<!-- Function call -->\r\n<a href=\"{{ route('home') }}\">Home</a>\r\n<img src=\"{{ asset('images/logo.png') }}\">\r\n\r\n<!-- Chained method calls -->\r\n@if(auth().check())\r\n  <p>Welcome, {{ auth().user.name }}!</p>\r\n@endif\r\n```\r\n\r\nConditionals\r\n\r\n```html\r\n@if(user.isAdmin)\r\n  <p>Administrator Access</p>\r\n@elseif(user.isModerator)\r\n  <p>Moderator Access</p>\r\n@else\r\n  <p>User Access</p>\r\n@endif\r\n```\r\n\r\nLoops\r\n\r\n```html\r\n<ul>\r\n@foreach(users as user)\r\n  <li>{{ user.name }} - {{ user.email }}</li>\r\n@endforeach\r\n</ul>\r\n\r\n<!-- Alternative syntax -->\r\n@foreach(items as item)\r\n  <div>{{ item.name }}</div>\r\n@endforeach\r\n```\r\n\r\nFilters\r\n\r\n```html\r\n<!-- Single filter -->\r\n<p>{{ content|upper }}</p>\r\n\r\n<!-- Multiple filters -->\r\n<p>{{ content|escape|lower }}</p>\r\n\r\n<!-- Filter with arguments -->\r\n<p>{{ date|date:'YYYY-MM-DD' }}</p>\r\n<p>{{ price|formatCurrency:'USD' }}</p>\r\n```\r\n\r\nLayouts and Inheritance\r\n\r\nlayouts/base.aether:\r\n```html\r\n<!DOCTYPE html>\r\n<html lang=\"en\">\r\n<head>\r\n    <meta charset=\"UTF-8\">\r\n    <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\">\r\n    <title>@yield('title', 'Default Title')</title>\r\n    @yield('head')\r\n</head>\r\n<body>\r\n    @include('partials/header')\r\n    \r\n    <main>\r\n        @yield('content')\r\n    </main>\r\n    \r\n    @include('partials/footer')\r\n    \r\n    @yield('scripts')\r\n</body>\r\n</html>\r\n```\r\n\r\npages/home.aether:\r\n```html\r\n@extends('layouts/base')\r\n\r\n@section('title', 'Home Page')\r\n\r\n@section('head')\r\n    <link rel=\"stylesheet\" href=\"/css/home.css\">\r\n@endsection\r\n\r\n@section('content')\r\n    <h1>Welcome to {{ site.name }}</h1>\r\n    <p>{{ welcomeMessage }}</p>\r\n    \r\n    @foreach(features as feature)\r\n        <div class=\"feature\">\r\n            <h3>{{ feature.title }}</h3>\r\n            <p>{{ feature.description }}</p>\r\n        </div>\r\n    @endforeach\r\n@endsection\r\n\r\n@section('scripts')\r\n    <script src=\"/js/home.js\"></script>\r\n@endsection\r\n```\r\n\r\nAPI Reference\r\n\r\nAetherEngine Class\r\n\r\nConstructor\r\n\r\n```javascript\r\nconst engine = new AetherEngine(options);\r\n```\r\n\r\nOptions:\r\n- `templateDir` (string): Template directory path (default: './templates')\r\n- `cacheEnabled` (boolean): Enable template caching (default: true)\r\n- `cacheTTL` (number): Cache time-to-live in seconds (default: 3600)\r\n- `debug` (boolean): Enable debug mode (default: false)\r\n\r\nMethods\r\n\r\ninitialize()\r\nInitialize the engine (called automatically on first render).\r\n\r\n```javascript\r\nawait engine.initialize();\r\n```\r\n\r\nrender(template, data, options)\r\nRender a template with data.\r\n\r\n```javascript\r\nconst html = await engine.render(templateString, data);\r\n// or\r\nconst html = await engine.render('template-file.aether', data);\r\n```\r\n\r\nParameters:\r\n- `template` (string): Template content or file path\r\n- `data` (object): Template data\r\n- `options` (object): Render options\r\n\r\nfilter(name, handler)\r\nRegister a custom filter.\r\n\r\n```javascript\r\nengine.filter('uppercase', (value) => value.toUpperCase());\r\nengine.filter('truncate', (value, length = 100) => {\r\n  return value.length > length ? value.substring(0, length) + '...' : value;\r\n});\r\n\r\n// Usage in template: {{ content|uppercase|truncate:50 }}\r\n```\r\n\r\nfunction(name, handler)\r\nRegister a custom function.\r\n\r\n```javascript\r\nengine.function('config', (key, defaultValue = null) => {\r\n  return process.env[key] || defaultValue;\r\n});\r\n\r\nengine.function('csrf_token', () => {\r\n  return generateCSRFToken();\r\n});\r\n\r\n// Usage in template: {{ config('APP_NAME') }}, {{ csrf_token() }}\r\n```\r\n\r\nregisterLayout(name, content)\r\nRegister a layout template.\r\n\r\n```javascript\r\nengine.registerLayout('default', `\r\n<!DOCTYPE html>\r\n<html>\r\n<head>\r\n    <title>@yield('title')</title>\r\n</head>\r\n<body>\r\n    @yield('content')\r\n</body>\r\n</html>\r\n`);\r\n```\r\n\r\nclearCache()\r\nClear the template cache.\r\n\r\n```javascript\r\nengine.clearCache();\r\n```\r\n\r\ngetMetadata()\r\nGet engine metadata.\r\n\r\n```javascript\r\nconst metadata = engine.getMetadata();\r\n// Returns: { name, version, initialized, filters, functions, layouts, cacheEnabled, templateDir }\r\n```\r\n\r\nFactory Functions\r\n\r\ncreateEngine(options)\r\nCreate a template engine factory.\r\n\r\n```javascript\r\nimport { createEngine } from '@aetherframework/template-engine';\r\n\r\nconst factory = await createEngine({\r\n  mode: 'template',  // 'template' or 'ssr'\r\n  templateDir: './views',\r\n  cacheEnabled: true\r\n});\r\n```\r\n\r\ncreateEngineFromEnv()\r\nCreate engine from environment configuration.\r\n\r\n```javascript\r\nconst factory = await createEngineFromEnv();\r\n// Reads from .env file or environment variables\r\n```\r\n\r\nquickStart(options)\r\nQuick start with default configuration.\r\n\r\n```javascript\r\nconst { factory, renderer, config } = await quickStart({\r\n  templateDir: './templates',\r\n  debug: true\r\n});\r\n```\r\n\r\nConfiguration\r\n\r\nEnvironment Variables\r\n\r\n```env\r\nTEMPLATE_ENGINE_MODE=template          'template' or 'ssr'\r\nTEMPLATE_ENGINE=aether                Default engine\r\nTEMPLATE_DIR=./templates              Template directory\r\nCACHE_ENABLED=true                    Enable caching\r\nCACHE_TTL=300000                      Cache TTL in milliseconds (5 minutes)\r\nDEBUG=true                            Debug mode\r\n```\r\n\r\nConfiguration File (.env)\r\n\r\nCreate a `.env` file in your project root:\r\n\r\n```env\r\nTemplate Engine Configuration\r\nTEMPLATE_ENGINE_MODE=template\r\nTEMPLATE_DIR=./resources/views\r\nCACHE_ENABLED=true\r\nCACHE_TTL=300000\r\nDEBUG=false\r\n\r\nCustom Functions Configuration\r\nASSET_URL=/assets\r\nBASE_URL=http://localhost:3000\r\n```\r\n\r\nIntegration Examples\r\n\r\nExpress.js Integration\r\n\r\n```javascript\r\nimport express from 'express';\r\nimport { createEngine } from '@aetherframework/template-engine';\r\n\r\nconst app = express();\r\n\r\n// Initialize template engine\r\nconst factory = await createEngine({\r\n  templateDir: './views',\r\n  cacheEnabled: process.env.NODE_ENV === 'production'\r\n});\r\n\r\nconst renderer = factory.createRenderer('aether');\r\n\r\n// Middleware to add render method\r\napp.use((req, res, next) => {\r\n  res.render = async (template, data = {}) => {\r\n    try {\r\n      const html = await renderer.render(template, {\r\n        ...data,\r\n        req,\r\n        res,\r\n        csrfToken: req.csrfToken ? req.csrfToken() : null\r\n      });\r\n      res.send(html);\r\n    } catch (error) {\r\n      console.error('Render error:', error);\r\n      res.status(500).send('Internal Server Error');\r\n    }\r\n  };\r\n  next();\r\n});\r\n\r\n// Route example\r\napp.get('/', async (req, res) => {\r\n  const data = {\r\n    title: 'Home Page',\r\n    user: req.user || null,\r\n    products: await Product.find(),\r\n    csrfToken: req.csrfToken ? req.csrfToken() : null\r\n  };\r\n  \r\n  await res.render('home', data);\r\n});\r\n\r\napp.listen(3000, () => {\r\n  console.log('Server running on http://localhost:3000');\r\n});\r\n```\r\n\r\nKoa.js Integration\r\n\r\n```javascript\r\nimport Koa from 'koa';\r\nimport { createEngine } from '@aetherframework/template-engine';\r\n\r\nconst app = new Koa();\r\n\r\nconst factory = await createEngine();\r\nconst renderer = factory.createRenderer('aether');\r\n\r\n// Middleware\r\napp.use(async (ctx, next) => {\r\n  ctx.render = async (template, data = {}) => {\r\n    const html = await renderer.render(template, {\r\n      ...data,\r\n      ctx,\r\n      state: ctx.state\r\n    });\r\n    ctx.type = 'html';\r\n    ctx.body = html;\r\n  };\r\n  await next();\r\n});\r\n\r\n// Route\r\napp.use(async (ctx) => {\r\n  if (ctx.path === '/') {\r\n    await ctx.render('home', {\r\n      title: 'Welcome',\r\n      user: ctx.state.user\r\n    });\r\n  }\r\n});\r\n\r\napp.listen(3000);\r\n```\r\n\r\nAdvanced Usage\r\n\r\nCustom Filters\r\n\r\n```javascript\r\n// Register custom filters\r\nengine.filter('formatDate', (date, format = 'YYYY-MM-DD') => {\r\n  return new Intl.DateTimeFormat('en-US', {\r\n    year: 'numeric',\r\n    month: '2-digit',\r\n    day: '2-digit'\r\n  }).format(new Date(date));\r\n});\r\n\r\nengine.filter('pluralize', (count, singular, plural) => {\r\n  return count === 1 ? singular : plural;\r\n});\r\n\r\n// Usage in template\r\n// {{ created_at|formatDate:'MM/DD/YYYY' }}\r\n// {{ count|pluralize:'item':'items' }}\r\n```\r\n\r\nCustom Functions\r\n\r\n```javascript\r\n// Register custom functions\r\nengine.function('url', (path) => {\r\n  const baseUrl = process.env.BASE_URL || 'http://localhost:3000';\r\n  return `${baseUrl}${path.startsWith('/') ? path : '/' + path}`;\r\n});\r\n\r\nengine.function('old', (field, defaultValue = '') => {\r\n  // Simulate Laravel's old() function for form data\r\n  return session?.old?.[field] || defaultValue;\r\n});\r\n\r\nengine.function('can', (permission) => {\r\n  // Check user permissions\r\n  return currentUser?.permissions?.includes(permission) || false;\r\n});\r\n\r\n// Usage in template\r\n// <a href=\"{{ url('/dashboard') }}\">Dashboard</a>\r\n// <input value=\"{{ old('username') }}\">\r\n// @if(can('edit-post')) ... @endif\r\n```\r\n\r\nTemplate Caching\r\n\r\n```javascript\r\n// Enable/disable caching\r\nconst engine = new AetherEngine({\r\n  cacheEnabled: true,\r\n  cacheTTL: 3600000 // 1 hour\r\n});\r\n\r\n// Clear cache manually\r\nengine.clearCache();\r\n\r\n// Or clear cache on specific events\r\napp.post('/clear-cache', (req, res) => {\r\n  engine.clearCache();\r\n  res.json({ message: 'Cache cleared' });\r\n});\r\n```\r\n\r\nError Handling\r\n\r\n```javascript\r\ntry {\r\n  const html = await engine.render(template, data);\r\n  // Success\r\n} catch (error) {\r\n  if (error.message.includes('Template not found')) {\r\n    console.error('Template file not found');\r\n  } else if (error.message.includes('Template compilation failed')) {\r\n    console.error('Template syntax error:', error.message);\r\n  } else if (error.message.includes('Runtime error')) {\r\n    console.error('Template runtime error:', error.message);\r\n  } else {\r\n    console.error('Unknown error:', error);\r\n  }\r\n  \r\n  // Fallback to error template\r\n  const errorHtml = await engine.render('errors/500', { error: error.message });\r\n}\r\n```\r\n\r\nFile Structure\r\n\r\n```\r\nproject/\r\n├── templates/\r\n│   ├── layouts/\r\n│   │   ├── default.aether\r\n│   │   └── admin.aether\r\n│   ├── pages/\r\n│   │   ├── home.aether\r\n│   │   ├── about.aether\r\n│   │   └── contact.aether\r\n│   ├── components/\r\n│   │   ├── header.aether\r\n│   │   ├── footer.aether\r\n│   │   └── sidebar.aether\r\n│   └── partials/\r\n│       ├── nav.aether\r\n│       └── alerts.aether\r\n├── .env\r\n├── package.json\r\n└── app.js\r\n```\r\n\r\n\r\n---\r\n\r\nCompression Features\r\n\r\nThe Aether Template Engine includes a powerful built-in compression system that automatically minifies and optimizes your HTML, CSS, and JavaScript output for production environments. This feature helps reduce bandwidth usage, improve page load times, and enhance overall performance.\r\n\r\nBasic Compression Configuration\r\n\r\n```javascript\r\nimport AetherEngine from '@aetherframework/template-engine';\r\n\r\n// Initialize the engine with compression enabled\r\nconst engine = new AetherEngine({\r\n  templateDir: './templates',\r\n  cacheEnabled: true,\r\n  debug: process.env.NODE_ENV === 'development',\r\n  \r\n  // Compression configuration\r\n  compressionEnabled: true,           // Enable/disable compression globally\r\n  minifyHTML: true,                   // Minify HTML structure (remove whitespace, comments)\r\n  minifyCSS: true,                    // Minify inline CSS styles\r\n  minifyJS: true,                     // Minify inline JavaScript code\r\n  mangleJS: false,                    // Obfuscate JavaScript variable names (production only)\r\n  removeComments: true,               // Remove HTML/CSS/JS comments\r\n  collapseWhitespace: true,           // Collapse multiple whitespace characters\r\n  removeAttributeQuotes: false,       // Remove optional quotes from HTML attributes\r\n  removeEmptyAttributes: false,       // Remove empty HTML attributes\r\n  cacheCompressed: true,              // Cache compressed results for performance\r\n  cacheTTL: 3600000                   // Cache time-to-live in milliseconds (1 hour)\r\n});\r\n\r\nawait engine.initialize();\r\n```\r\n\r\nEnvironment-Based Configuration\r\n\r\n```javascript\r\n// Development environment - disable compression for easier debugging\r\nconst devEngine = new AetherEngine({\r\n  compressionEnabled: false,\r\n  minifyHTML: false,\r\n  minifyCSS: false,\r\n  minifyJS: false,\r\n  mangleJS: false,\r\n  removeComments: false,\r\n  collapseWhitespace: false,\r\n  cacheCompressed: false,\r\n  debug: true\r\n});\r\n\r\n// Production environment - enable all compression for optimal performance\r\nconst prodEngine = new AetherEngine({\r\n  compressionEnabled: true,\r\n  minifyHTML: true,\r\n  minifyCSS: true,\r\n  minifyJS: true,\r\n  mangleJS: true,                    // Obfuscate JS in production for security\r\n  removeComments: true,\r\n  collapseWhitespace: true,\r\n  removeAttributeQuotes: true,\r\n  removeEmptyAttributes: true,\r\n  cacheCompressed: true,\r\n  cacheTTL: 3600000,                 // 1 hour cache\r\n  debug: false\r\n});\r\n```\r\n\r\nPer-Render Compression Options\r\n\r\nYou can override compression settings for individual template renders:\r\n\r\n```javascript\r\n// Render with specific compression options\r\nconst html = await engine.render('template.aether', data, {\r\n  compression: {\r\n    minifyHTML: true,\r\n    minifyCSS: true,\r\n    minifyJS: true,\r\n    mangleJS: process.env.NODE_ENV === 'production',\r\n    removeComments: true,\r\n    collapseWhitespace: true\r\n  }\r\n});\r\n```\r\n\r\nCompression Examples\r\n\r\nBefore Compression (Development):\r\n```html\r\n<!DOCTYPE html>\r\n<html lang=\"en\">\r\n<head>\r\n  <meta charset=\"UTF-8\">\r\n  <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\">\r\n  <title>My Application</title>\r\n  <style>\r\n    /* Main styles */\r\n    body {\r\n      margin: 0;\r\n      padding: 0;\r\n      font-family: Arial, sans-serif;\r\n    }\r\n    \r\n    .container {\r\n      width: 100%;\r\n      max-width: 1200px;\r\n      margin: 0 auto;\r\n      padding: 20px;\r\n    }\r\n  </style>\r\n</head>\r\n<body>\r\n  <div class=\"container\">\r\n    <h1>Welcome to {{ app.name }}</h1>\r\n    <p>This is a sample page with uncompressed output.</p>\r\n  </div>\r\n  \r\n  <script>\r\n    // JavaScript code\r\n    function greetUser(name) {\r\n      console.log(\"Hello, \" + name + \"!\");\r\n    }\r\n    \r\n    greetUser(\"John\");\r\n  </script>\r\n</body>\r\n</html>\r\n```\r\n\r\nAfter Compression (Production):\r\n```html\r\n<!DOCTYPE html><html lang=\"en\"><head><meta charset=\"UTF-8\"><meta name=\"viewport\" content=\"width=device-width,initial-scale=1\"><title>My Application</title><style>body{margin:0;padding:0;font-family:Arial,sans-serif}.container{width:100%;max-width:1200px;margin:0 auto;padding:20px}</style></head><body><div class=\"container\"><h1>Welcome to MyApp</h1><p>This is a sample page with compressed output.</p></div><script>function a(b){console.log(\"Hello, \"+b+\"!\")}a(\"John\")</script></body></html>\r\n```\r\n\r\nCompression Statistics and Cache Management\r\n\r\n```javascript\r\n// Get compression statistics\r\nconst stats = engine.getCompressionStats();\r\nconsole.log(stats);\r\n// Output: { cacheSize: 15, cacheHits: 42, cacheTTL: 3600000, options: {...} }\r\n\r\n// Clear compression cache (useful during development)\r\nengine.clearCompressionCache();\r\n\r\n// Check if compression is enabled\r\nconst isCompressionEnabled = engine.options.compressionEnabled;\r\n```\r\n\r\nSSR Mode with Compression\r\n\r\n```javascript\r\nimport { SSRModeEngine } from '@aetherframework/template-engine';\r\n\r\nconst ssrEngine = new SSRModeEngine({\r\n  templateDir: './templates',\r\n  hydrate: true,\r\n  stream: false,\r\n  \r\n  // SSR-specific compression options\r\n  compressSSR: true,\r\n  minifySSR: true,\r\n  \r\n  // General compression settings\r\n  compressionEnabled: true,\r\n  minifyHTML: true,\r\n  minifyCSS: true,\r\n  minifyJS: true,\r\n  mangleJS: process.env.NODE_ENV === 'production',\r\n  removeComments: true,\r\n  collapseWhitespace: true,\r\n  cacheCompressed: true\r\n});\r\n\r\n// Render with SSR and compression\r\nconst html = await ssrEngine.render('app.aether', data);\r\n```\r\n\r\nTemplate Mode with Compression\r\n\r\n```javascript\r\nimport { TemplateModeEngine } from '@aetherframework/template-engine';\r\n\r\nconst templateEngine = new TemplateModeEngine({\r\n  templateDir: './templates',\r\n  layoutSupport: true,\r\n  includeSupport: true,\r\n  \r\n  // Template-specific compression\r\n  compressTemplates: true,\r\n  minifyTemplates: true,\r\n  \r\n  // General compression settings\r\n  compressionEnabled: true,\r\n  minifyHTML: true,\r\n  minifyCSS: true,\r\n  minifyJS: true,\r\n  mangleJS: false, // Usually keep JS readable in template mode\r\n  removeComments: true,\r\n  collapseWhitespace: true,\r\n  cacheCompressed: true\r\n});\r\n\r\n// Render template with compression\r\nconst html = await templateEngine.render('page.aether', data);\r\n```\r\n\r\nEnvironment Configuration\r\n\r\nCreate a `.env` file with compression settings:\r\n\r\n```env\r\nCompression Configuration\r\nCOMPRESSION_ENABLED=true\r\nMINIFY_HTML=true\r\nMINIFY_CSS=true\r\nMINIFY_JS=true\r\nMANGLE_JS=true\r\nREMOVE_COMMENTS=true\r\nCOLLAPSE_WHITESPACE=true\r\nREMOVE_ATTRIBUTE_QUOTES=true\r\nREMOVE_EMPTY_ATTRIBUTES=true\r\nCACHE_COMPRESSED=true\r\nCACHE_TTL=3600000\r\n\r\nTemplate Engine Configuration\r\nTEMPLATE_ENGINE_MODE=template\r\nTEMPLATE_DIR=./templates\r\nCACHE_ENABLED=true\r\nCACHE_TTL=300000\r\nDEBUG=false\r\n```\r\n\r\nExpress.js Integration with Compression\r\n\r\n```javascript\r\nimport express from 'express';\r\nimport { createEngine } from '@aetherframework/template-engine';\r\n\r\nconst app = express();\r\n\r\n// Initialize template engine with compression\r\nconst factory = await createEngine({\r\n  templateDir: './views',\r\n  cacheEnabled: process.env.NODE_ENV === 'production',\r\n  \r\n  // Compression based on environment\r\n  compressionEnabled: process.env.NODE_ENV === 'production',\r\n  minifyHTML: process.env.NODE_ENV === 'production',\r\n  minifyCSS: process.env.NODE_ENV === 'production',\r\n  minifyJS: process.env.NODE_ENV === 'production',\r\n  mangleJS: process.env.NODE_ENV === 'production',\r\n  removeComments: process.env.NODE_ENV === 'production',\r\n  collapseWhitespace: true,\r\n  cacheCompressed: true\r\n});\r\n\r\nconst renderer = factory.createRenderer('aether');\r\n\r\n// Middleware to add render method with compression\r\napp.use((req, res, next) => {\r\n  res.render = async (template, data = {}, options = {}) => {\r\n    try {\r\n      const html = await renderer.render(template, {\r\n        ...data,\r\n        req,\r\n        res,\r\n        csrfToken: req.csrfToken ? req.csrfToken() : null\r\n      }, {\r\n        // Override compression per route if needed\r\n        compression: {\r\n          minifyHTML: true,\r\n          minifyCSS: true,\r\n          minifyJS: true,\r\n          mangleJS: process.env.NODE_ENV === 'production',\r\n          ...options.compression\r\n        }\r\n      });\r\n      \r\n      // Set compression headers\r\n      res.setHeader('X-Compression-Enabled', 'true');\r\n      res.setHeader('X-Compression-Mode', 'template');\r\n      res.setHeader('Cache-Control', 'public, max-age=3600');\r\n      \r\n      res.send(html);\r\n    } catch (error) {\r\n      console.error('Render error:', error);\r\n      res.status(500).send('Internal Server Error');\r\n    }\r\n  };\r\n  next();\r\n});\r\n\r\n// Route with compressed output\r\napp.get('/', async (req, res) => {\r\n  const data = {\r\n    title: 'Home Page',\r\n    user: req.user || null,\r\n    products: await Product.find(),\r\n    csrfToken: req.csrfToken ? req.csrfToken() : null\r\n  };\r\n  \r\n  await res.render('home', data, {\r\n    // Optional: Custom compression for this route\r\n    compression: {\r\n      minifyHTML: true,\r\n      minifyCSS: true,\r\n      minifyJS: true,\r\n      mangleJS: process.env.NODE_ENV === 'production'\r\n    }\r\n  });\r\n});\r\n\r\napp.listen(3000, () => {\r\n  console.log('Server running on http://localhost:3000');\r\n  console.log(`Compression: ${process.env.NODE_ENV === 'production' ? 'Enabled' : 'Disabled'}`);\r\n});\r\n```\r\n\r\nPerformance Benefits\r\n\r\n1. Reduced Bandwidth Usage: Compressed HTML can be 30-70% smaller than uncompressed versions\r\n2. Faster Page Load Times: Smaller file sizes lead to quicker downloads and parsing\r\n3. Improved SEO: Faster loading pages are favored by search engines\r\n4. Better User Experience: Users see content faster, especially on mobile devices\r\n5. Reduced Server Load: Less data transmission means lower server resource usage\r\n6. Enhanced Security: JavaScript obfuscation (`mangleJS`) makes code harder to reverse-engineer\r\n\r\nCompression Options Reference\r\n\r\n| Option | Type | Default | Description |\r\n|--------|------|---------|-------------|\r\n| `compressionEnabled` | boolean | `false` | Enable/disable compression globally |\r\n| `minifyHTML` | boolean | `true` | Minify HTML structure (remove whitespace, comments) |\r\n| `minifyCSS` | boolean | `true` | Minify inline CSS styles |\r\n| `minifyJS` | boolean | `true` | Minify inline JavaScript code |\r\n| `mangleJS` | boolean | `false` | Obfuscate JavaScript variable names |\r\n| `removeComments` | boolean | `true` | Remove HTML, CSS, and JavaScript comments |\r\n| `collapseWhitespace` | boolean | `true` | Collapse multiple whitespace characters into single spaces |\r\n| `removeAttributeQuotes` | boolean | `false` | Remove optional quotes from HTML attributes |\r\n| `removeEmptyAttributes` | boolean | `false` | Remove empty HTML attributes |\r\n| `cacheCompressed` | boolean | `true` | Cache compressed results to avoid re-compression |\r\n| `cacheTTL` | number | `3600000` | Cache time-to-live in milliseconds (1 hour) |\r\n\r\nTroubleshooting Compression\r\n\r\nCommon Issues:\r\n\r\n1. Compression not working: Ensure `compressionEnabled` is set to `true` in your configuration\r\n2. JavaScript errors after compression: Disable `mangleJS` or check for variable name conflicts in your code\r\n3. CSS broken after compression: Verify CSS syntax is valid and doesn't contain edge cases\r\n4. Cache not updating: Clear compression cache with `engine.clearCompressionCache()` during development\r\n5. Performance issues: Adjust `cacheTTL` based on your application's update frequency\r\n\r\nDebug Mode for Compression:\r\n\r\n```javascript\r\nconst engine = new AetherEngine({\r\n  compressionEnabled: true,\r\n  debug: true  // Enable debug logs\r\n});\r\n\r\n// Check compression logs in console\r\n// [AetherEngine] Compression applied: 10240 → 5120 bytes (50% reduction)\r\n// [AetherEngine] Cache hit for template: home.aether\r\n// [AetherEngine] Compression statistics: { cacheSize: 5, cacheHits: 23 }\r\n```\r\n\r\nBest Practices\r\n\r\n1. Development Environment: Disable compression (`compressionEnabled: false`) for easier debugging and readable output\r\n2. Production Environment: Enable all compression options for optimal performance and security\r\n3. Testing: Test with `mangleJS: false` first, then enable for production after verification\r\n4. Monitoring: Use `getCompressionStats()` to monitor cache performance and hit rates\r\n5. Caching Strategy: Always enable `cacheCompressed: true` in production to avoid re-compressing the same content\r\n6. Incremental Deployment: Deploy compression changes gradually and monitor for issues\r\n7. Backup Originals: Keep uncompressed templates in source control for debugging purposes\r\n\r\nAdvanced Compression Configuration\r\n\r\nFor fine-grained control over compression behavior:\r\n\r\n```javascript\r\nconst engine = new AetherEngine({\r\n  compressionEnabled: true,\r\n  \r\n  // HTML-specific options\r\n  minifyHTML: true,\r\n  collapseWhitespace: true,\r\n  conservativeCollapse: false, // Preserve single whitespace\r\n  preserveLineBreaks: false,   // Remove all line breaks\r\n  removeComments: true,\r\n  removeEmptyAttributes: true,\r\n  removeAttributeQuotes: true,\r\n  removeOptionalTags: false,    // Don't remove optional tags like </li>\r\n  \r\n  // CSS-specific options\r\n  minifyCSS: true,\r\n  cssMinifierOptions: {\r\n    level: 2,                  // Optimization level (1-3)\r\n    compatibility: '*',        // Browser compatibility\r\n    format: 'keep-breaks'      // Output formatting\r\n  },\r\n  \r\n  // JavaScript-specific options\r\n  minifyJS: true,\r\n  mangleJS: true,\r\n  mangleOptions: {\r\n    reserved: ['render', 'data', 'helpers'] // Variables to preserve\r\n  },\r\n  jsMinifierOptions: {\r\n    compress: {\r\n      drop_console: true,      // Remove console statements\r\n      drop_debugger: true      // Remove debugger statements\r\n    },\r\n    mangle: {\r\n      properties: false         // Don't mangle property names\r\n    }\r\n  },\r\n  \r\n  // Cache configuration\r\n  cacheCompressed: true,\r\n  cacheTTL: 3600000,\r\n  cacheMaxSize: 100            // Maximum number of cached items\r\n});\r\n```\r\n\r\nThis compression feature is seamlessly integrated into the Aether Template Engine, providing automatic optimization without requiring changes to your template code. The system intelligently handles different content types and provides configurable options for both development and production environments.\r\n\r\nPerformance Tips\r\n\r\n1. Enable Caching in Production: Always enable caching in production environments\r\n2. Precompile Templates: For frequently used templates, precompile them\r\n3. Use Template Inheritance: Reduces duplication and improves maintainability\r\n4. Minimize Complex Logic in Templates: Move complex logic to controllers or services\r\n5. Use Includes for Reusable Components: Create reusable partials for common UI elements\r\n\r\nTroubleshooting\r\n\r\nCommon Issues\r\n\r\n1. Template not found: Ensure template directory is correctly configured\r\n2. Syntax errors: Check for missing `@endif` or `@endforeach`\r\n3. Function not defined: Register custom functions before rendering\r\n4. Cache issues: Clear cache with `engine.clearCache()`\r\n\r\nDebug Mode\r\n\r\nEnable debug mode for detailed error messages:\r\n\r\n```javascript\r\nconst engine = new AetherEngine({\r\n  debug: process.env.NODE_ENV === 'development'\r\n});\r\n```\r\n\r\nLicense\r\n\r\nMIT License - see LICENSE file for details.\r\n\r\nSupport\r\n\r\nFor issues and feature requests, please visit the [GitHub repository](https://github.com/yourusername/@aetherframework/template-engine).\r\n\r\nContributing\r\n\r\n1. Fork the repository\r\n2. Create a feature branch\r\n3. Make your changes\r\n4. Add tests\r\n5. Submit a pull request\r\n\r\n\r\n📄 License\r\n\r\nThis project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.\r\n\r\n---\r\n\r\nMade with ❤️ by the Aether Team","readmeFilename":"README.md"}