fossar/htmlawed
Fork of kesar/HTMLawed maintained by selfoss and wallabag. A single-file (~45KB) PHP HTML filter/sanitizer that secures and tidies user input, making it standards-compliant for HTML/XHTML/XML, with extensive customization options.
Installation
composer require fossar/htmlawed:^1.3.4
Note: Updated to version 1.3.4 to leverage new features and fixes.
First Use Case Sanitize user-generated HTML with improved tag handling:
use Fossar\HtmlAwed\HtmlAwed;
$html = '<details><summary>Note</summary><p>Content</p></details>';
$sanitizer = new HtmlAwed();
$cleanHtml = $sanitizer->sanitize($html);
// Output: <details><summary>Note</summary><p>Content</p></details>
Now supports <details> with flow content (e.g., <p>) by default.
Where to Look First
src/HtmlAwed.php (lines ~120–150).details support).Basic Sanitization (Updated)
$sanitizer = new HtmlAwed();
$clean = $sanitizer->sanitize($dirtyHtml);
<img/> → <img>).<details> with nested flow content by default.Custom Rules (Enhanced) Extend or override allowed tags/attributes with new defaults:
$sanitizer = new HtmlAwed();
$sanitizer->allowTags(['details', 'summary']); // Explicitly allowed by default now
$sanitizer->allowAttributes('details', ['open']); // Example: Allow `open` attribute
Laravel Integration (Optimized) Create a macro with versioned dependency:
// app/Providers/AppServiceProvider.php
use Illuminate\Support\Str;
public function boot()
{
Str::macro('sanitizeHtml', function ($html) {
return app(HtmlAwed::class)->sanitize($html);
});
}
Ensure fossar/htmlawed:^1.3.4 is specified in composer.json.
Form Request Validation (Updated) Combine with Laravel’s validation to handle new tag rules:
public function rules()
{
return [
'content' => [
'required',
function ($attribute, $value, $fail) {
$sanitizer = new HtmlAwed();
if ($sanitizer->sanitize($value) !== $value) {
$fail('HTML contains invalid tags or self-closing syntax.');
}
},
],
];
}
Middleware for API Responses (New Use Case)
Sanitize HTML in API responses with <details> support:
// app/Http/Middleware/SanitizeHtml.php
public function handle($request, Closure $next)
{
$response = $next($request);
if ($response->isJson() && $request->has('html_content')) {
$response->setData([
'content' => app(HtmlAwed::class)->sanitize($request->html_content),
]);
}
return $response;
}
Now safely processes <details> elements in responses.
Self-Closing Tag Issues (Fixed)
<img src="x" /> might break sanitization.<img src="x"> (neutralized).<details> Tag Quirks
<p>, <div>) inside <details> by default.<details>, nested tags like <p> will also be stripped.$sanitizer->allowTags(['details', 'summary', 'p']);
Attribute Whitelisting (Still Critical)
open for <details>) breaks functionality.allowTags() with allowAttributes():
$sanitizer->allowAttributes('details', ['open']);
CSS/JS Injections (Unchanged)
style or event handlers.denyAttributes():
$sanitizer->denyAttributes('*', ['style', 'onclick']);
Laravel Blade Conflicts (Updated)
<details> and <summary> are now safe in Blade with sanitizeHtml():
{!! Str::sanitizeHtml($userHtml) !!}
{{ }} (auto-escapes) with raw HTML. Use {!! !!} for sanitized output.Inspect Updated Rules Dump allowed tags/attributes to verify new defaults:
$sanitizer = new HtmlAwed();
dump($sanitizer->getAllowedTags()); // Includes 'details', 'summary'
dump($sanitizer->getAllowedAttributes());
Test Edge Cases (Updated)
<img/> → <img> (auto-fixed).<details> nesting: <details><p>Text</p></details> (now allowed).<details>: <details><summary>Missing closing</summary> (handled).Fallback for Strict Mode (Adjusted) If strict sanitization breaks layouts, relax rules for new tags:
$sanitizer->allowTags(['div', 'span', 'p', 'details', 'summary']);
$sanitizer->allowAttributes('details', ['open']);
Custom Sanitizer Class (Updated)
Extend HtmlAwed to override new defaults:
class AppHtmlAwed extends HtmlAwed
{
public function __construct()
{
parent::__construct();
$this->denyTags(['embed']); // Example: Block new tags explicitly
$this->allowAttributes('details', ['open', 'class']); // Extend defaults
}
}
Hook into Laravel Events (New Tag Support)
Sanitize HTML with <details> in Eloquent models:
// app/Models/Comment.php
protected static function boot()
{
static::creating(function ($model) {
$model->content = app(AppHtmlAwed::class)->sanitize($model->content);
});
}
Cache Sanitizer Instances (Optimized) Register the updated version as a singleton:
// app/Providers/AppServiceProvider.php
public function register()
{
$this->app->singleton(HtmlAwed::class, function () {
$sanitizer = new HtmlAwed();
$sanitizer->allowTags(['p', 'a', 'img', 'details', 'summary']);
return $sanitizer;
});
}
Ensures all requests use the latest 1.3.4 rules.
New: Handle Self-Closing Tags in Legacy Code If legacy code relies on self-closing syntax, preprocess HTML:
$html = preg_replace('/<(\w+)\s*\/?>/', '<$1>', $dirtyHtml);
$clean = app(HtmlAwed::class)->sanitize($html);
How can I help you explore Laravel packages today?