PHPackages                             xoops/smartyextensions - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Templating &amp; Views](/categories/templating)
4. /
5. xoops/smartyextensions

ActiveLibrary[Templating &amp; Views](/categories/templating)

xoops/smartyextensions
======================

XOOPS Smarty template extensions — domain-grouped plugins for Smarty 4/5

v1.0.0-Beta1(yesterday)01↑2900%1GPL-2.0-or-laterPHPPHP ^8.2CI failing

Since Jun 8Pushed yesterdayCompare

[ Source](https://github.com/XOOPS/smartyextensions)[ Packagist](https://packagist.org/packages/xoops/smartyextensions)[ Docs](https://xoops.org)[ RSS](/packages/xoops-smartyextensions/feed)WikiDiscussions master Synced yesterday

READMEChangelog (1)Dependencies (4)Versions (2)Used By (0)

xoops/smartyextensions
======================

[](#xoopssmartyextensions)

Domain-grouped Smarty 4/5 plugins for the XOOPS CMS.

[![PHP](https://camo.githubusercontent.com/187240af044d09d5b14a1d9d9ebdf3f7a993e4c7bc09bdb46b4ba661a891bf5b/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f5048502d382e322532422d626c7565)](https://www.php.net/)[![License: GPL v2](https://camo.githubusercontent.com/77e900ae34f8da9ccccc42662fce61a94ab07ddbfe3f7d066178e824f3673dbd/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f4c6963656e73652d47504c25323076322d626c75652e737667)](https://www.gnu.org/licenses/gpl-2.0)[![Smarty](https://camo.githubusercontent.com/0d587522968ea509c9d04bf3fcff8837b795cc0f8f2734a42b78142fe93eb0f9/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f536d617274792d342e78253230253743253230352e782d6f72616e6765)](https://smarty.net/)

---

Overview
--------

[](#overview)

`xoops/smartyextensions` replaces the traditional flat pile of Smarty plugin files with a structured, testable, PSR-4 library. Extensions are grouped by domain, registered through a unified `ExtensionRegistry`, and fully compatible with both Smarty 4 (`registerPlugin`) and Smarty 5 (`addExtension`).

XOOPS uses `` as Smarty delimiters. All examples below use these delimiters.

---

Requirements
------------

[](#requirements)

RequirementVersionPHP^8.2Smarty^4.5 or ^5.0---

Installation
------------

[](#installation)

```
composer require xoops/smartyextensions
```

---

Quick Start
-----------

[](#quick-start)

```
use Xoops\SmartyExtensions\ExtensionRegistry;
use Xoops\SmartyExtensions\Extension\TextExtension;
use Xoops\SmartyExtensions\Extension\SecurityExtension;

$registry = new ExtensionRegistry();
$registry->add(new TextExtension());
$registry->add(new SecurityExtension($xoopsSecurity, $xoopsGroupPermHandler));
$registry->registerAll($smarty); // works with both Smarty 4 and Smarty 5
```

Or register a single extension directly:

```
(new TextExtension())->register($smarty);
```

---

Extension Catalogue
-------------------

[](#extension-catalogue)

### TextExtension

[](#textextension)

Modifiers for string processing and readability.

NameSignatureDescription`excerpt``$text|excerpt:150:' ...'`Truncate at word boundary with multibyte safety`truncate_words``$text|truncate_words:20`Truncate at exact word count`nl2p``$text|nl2p`Convert newlines to `` and ```highlight_text``$text|highlight_text:'XOOPS'`Wrap search term in ```reading_time``$text|reading_time`Estimated reading time, e.g. "3 min read"`pluralize``$count|pluralize:'comment'`Singular/plural based on count`extract_hashtags``$text|extract_hashtags`Returns array of hashtag strings---

### FormatExtension

[](#formatextension)

Date, time, number, and display formatting.

NameSignatureDescription`format_date``$date|format_date:'Y-m-d'`Format any date string or timestamp`relative_time``$ts|relative_time`"3 days ago" / "2 hours from now"`format_currency``$amount|format_currency:'USD'`Currency formatting with ICU/intl fallback`number_format``$n|number_format:2:',':'.'`Locale-aware number formatting`bytes_format``$bytes|bytes_format:1`Human-readable file size (e.g. "1.5 MB")`format_phone_number``$phone|format_phone_number`Formats 10- or 11-digit US phone numbers`gravatar``$email|gravatar:64:'mp'`Gravatar URL for an email address`datetime_diff```Human-readable span between two dates`get_current_year```Current 4-digit year---

### NavigationExtension

[](#navigationextension)

URL generation, breadcrumbs, pagination, and social sharing.

NameTypeDescription`generate_url`functionBuild a URL with query params; direct output is HTML-escaped, `assign` stores raw URL`generate_canonical_url`functionBuild canonical URL from `XOOPS_URL`; no-op without it`url_segment`functionExtract a path segment from the current URL`social_share`functionSocial share links/bar (Twitter, Facebook, LinkedIn)`render_breadcrumbs`functionBootstrap 5 breadcrumb nav`render_pagination`functionBootstrap 5 pagination with prev/next`render_qr_code`function`` tag via Google Charts QR API`render_alert`functionBootstrap 5 dismissible alert`parse_url`modifierReturns parsed URL components as array`strip_protocol`modifierRemoves `http://` or `https://` scheme`slugify`modifierConverts text to URL-safe slug`youtube_id`modifierExtracts YouTube video ID from any URL format`linkify`modifierConverts plain-text URLs to `` anchors**Assign contract**: when `assign` is given, the **raw** value is stored. Only direct output applies `htmlspecialchars`.

```
 42] assign="articleUrl"}>
Read more
```

---

### SecurityExtension

[](#securityextension)

CSRF, permission checks, email masking, and sanitization.

**Constructor**: `new SecurityExtension(?XoopsSecurity $security, ?XoopsGroupPermHandler $permHandler)`

NameTypeDescription`sanitize_string`modifier`htmlspecialchars` with `ENT_QUOTES``sanitize_url`modifierBlocks `javascript:`, `data:`, entity-encoded variants`sanitize_filename`modifier`basename()` + allowlist + strip leading dots`sanitize_string_for_xml`modifierXML-safe entity encoding`mask_email`modifier`us***@example.com` format`obfuscate_text`modifierConverts all chars to HTML entities`hash_string`modifierHash with any algorithm; defaults to SHA-256`generate_csrf_token`functionRenders XOOPS CSRF hidden input`validate_csrf_token`functionValidates XOOPS CSRF token`has_user_permission`functionChecks group permission via `XoopsGroupPermHandler``is_user_logged_in`functionBoolean check on `$xoopsUser` global`user_has_role`functionChecks if user belongs to a group ID`xo_permission`blockConditionally renders content based on login/permission/group```

  Admin panel

```

---

### FormExtension

[](#formextension)

Form rendering with automatic CSRF injection and validation.

**Constructor**: `new FormExtension(?XoopsSecurity $security)`

NameDescription`form_open`Opens `` with CSRF token auto-injected for POST`form_close`Closes ```form_input`Renders `` with XSS-safe escaping`create_button`Renders `` with optional Bootstrap icon`render_form_errors`Renders Bootstrap 5 error alert list`validate_form`Validates data against rules; returns errors array`validate_email`Validates a single email address`display_error`Renders a single Bootstrap 5 danger alert`validate_form` rules example:

```
 ['required' => true, 'email' => true], 'bio' => ['max_length' => 500]] assign="errors"}>

```

Validation uses `mb_strlen` for `min_length`/`max_length`, ensuring multibyte UTF-8 characters (CJK, Arabic, etc.) count correctly.

---

### DataExtension

[](#dataextension)

Data manipulation, CSV export, file info, and XML sitemaps.

**Modifiers**: `array_filter`, `array_sort`, `pretty_print_json`, `get_file_size`, `get_mime_type`, `is_image`, `strip_html_comments`

**Functions**: `array_to_csv`, `base64_encode_file`, `embed_pdf`, `generate_xml_sitemap`, `generate_meta_tags`, `get_referrer`, `get_session_data`

The `get_referrer` assign path stores the **raw** referrer URL; direct output applies `htmlspecialchars`.

---

### AssetExtension

[](#assetextension)

Deferred CSS/JS asset queuing with deduplication and XSS-safe scheme validation.

FunctionDescription`require_css`Queue a stylesheet (deduplicates by file path)`require_js`Queue a script (deduplicates by file path)`flush_css`Output all queued `` tags and clear queue`flush_js`Output all queued `` tags and clear queueBlocked schemes: `javascript:`, `data:`, and their HTML entity-encoded variants. Last-write wins for conflicting attributes (e.g., `defer` vs no defer for the same file).

```

```

---

### XoopsCoreExtension

[](#xoopscoreextension)

Wrappers around XOOPS globals and handlers.

NameTypeDescription`xo_get_config`functionRead from `$xoopsConfig``xo_get_current_user`functionCurrent user as array (uid, uname, name, email, groups, is\_admin)`xo_get_module_info`functionModule info by dirname`xo_get_notifications`functionCurrent user's notification list`xo_module_url`functionModule URL; assign stores raw, output is HTML-escaped`xo_render_block`functionRender a XOOPS block object`xo_render_menu`functionModule admin menu as Bootstrap nav`xo_avatar`functionUser avatar (XOOPS upload or Gravatar fallback)`xo_debug`functionDump variable (only outputs when `debug_mode` is active)`translate`modifierResolve XOOPS language constant with string fallback```

```

---

### RayDebugExtension

[](#raydebugextension)

Zero-cost debug output via [spatie/ray](https://spatie.be/products/ray). All functions and the modifier silently no-op when Ray is not installed — no runtime dependency.

NameType`ray`function + modifier`ray_context`function`ray_dump`function`ray_table`function---

Architecture
------------

[](#architecture)

```
src/
├── AbstractExtension.php       Base class — register(), getModifiers(), getFunctions(), getBlockHandlers()
├── ExtensionRegistry.php       Collects extensions, auto-detects Smarty 4/5, registers all
├── Adapter/
│   └── Smarty5Adapter.php      Wraps AbstractExtension for Smarty 5 addExtension() API
└── Extension/
    ├── TextExtension.php
    ├── FormatExtension.php
    ├── NavigationExtension.php
    ├── SecurityExtension.php
    ├── FormExtension.php
    ├── DataExtension.php
    ├── AssetExtension.php
    ├── XoopsCoreExtension.php
    └── RayDebugExtension.php

```

`AbstractExtension::register($smarty)` iterates the three registries (modifiers, functions, block handlers) and calls `$smarty->registerPlugin()` for each — the Smarty 4 API.

`ExtensionRegistry::registerAll($smarty)` auto-detects the Smarty version: if `\Smarty\Extension\Base` exists (Smarty 5), each extension is wrapped in `Smarty5Adapter` and passed to `$smarty->addExtension()`.

---

Security Conventions
--------------------

[](#security-conventions)

All extensions follow a consistent **assign contract**:

- **Direct output** (no `assign` param): HTML-escaped with `htmlspecialchars($value, ENT_QUOTES, 'UTF-8')`.
- **Assign path** (`assign` param present): raw value is stored in the template variable. The caller is responsible for escaping when interpolating into HTML (e.g. `href=""`).

This prevents double-escaping while maintaining XSS safety at every output point.

---

Running Tests
-------------

[](#running-tests)

```
composer install
composer test
```

PHPUnit scans `tests/Unit/` and uses `tests/bootstrap.php`, which loads XOOPS class stubs so the suite runs standalone (no XOOPS installation required).

```
composer analyse   # PHPStan level 9
composer lint      # PHPCS
composer fix       # PHPCBF
```

---

Contributing
------------

[](#contributing)

1. Fork the repository.
2. Create a feature branch.
3. Write or update tests in `tests/Unit/`.
4. Ensure `composer test` passes with no failures.
5. Submit a pull request.

---

License
-------

[](#license)

GNU General Public License v2.0 or later. See [LICENSE](LICENSE) for details.

© 2000–2026 [XOOPS Project](https://xoops.org)

###  Health Score

37

—

LowBetter than 81% of packages

Maintenance100

Actively maintained with recent releases

Popularity3

Limited adoption so far

Community9

Small or concentrated contributor base

Maturity31

Early-stage or recently created project

 Bus Factor1

Top contributor holds 65.4% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Unknown

Total

1

Last Release

1d ago

### Community

Maintainers

![](https://www.gravatar.com/avatar/122f20c0edc2c6b86e8354286b09f6e982ecc6dcfbfaffcd91c3638406ffc39f?d=identicon)[xoops](/maintainers/xoops)

---

Top Contributors

[![mambax7](https://avatars.githubusercontent.com/u/613686?v=4)](https://github.com/mambax7 "mambax7 (17 commits)")[![dependabot[bot]](https://avatars.githubusercontent.com/in/29110?v=4)](https://github.com/dependabot[bot] "dependabot[bot] (9 commits)")

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Code StylePHP\_CodeSniffer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/xoops-smartyextensions/health.svg)

```
[![Health](https://phpackages.com/badges/xoops-smartyextensions/health.svg)](https://phpackages.com/packages/xoops-smartyextensions)
```

###  Alternatives

[modx/revolution

MODX Revolution is a Content Management System

1.4k9.4k12](/packages/modx-revolution)[ytake/laravel-smarty

Smarty template engine for Laravel and Lumen

85406.6k](/packages/ytake-laravel-smarty)[noiselabs/smarty-bundle

This Symfony bundle provides integration for the Smarty3 template engine.

54195.6k1](/packages/noiselabs-smarty-bundle)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
