laravel-css-inliner / css-inliner
将 Laravel 邮件中的 CSS 类转换为内联样式
Requires
- php: ^8.1
- illuminate/contracts: ^10.0
- illuminate/support: ^10.0
- symfony/mime: ^6.1
- tijsverkoyen/css-to-inline-styles: ^2.2
Requires (Dev)
- laravel/pint: ^1.10
- orchestra/testbench: ^8.0
- pestphp/pest: ^2.0
- phpstan/phpstan: ^1.9
- symfony/var-dumper: ^5.4.9 || ^6.0.9
README
概览
此包利用 tijsverkoyen/css-to-inline-styles
将可邮寄视图中的 CSS 类转换为内联样式,以改善电子邮件客户端兼容性。
您可以选择利用此包的自动化功能,或者选择挂钩到此包的事件(甚至 Laravel 的核心事件),并手动选择要转换的内容以及要使用的样式表。请参阅使用部分以获取更多详细信息。
安装
通过 Composer
composer require bradietilley/laravel-css-inliner
使用方法
为了演示目的,我们将使用外观 BradieTilley\LaravelCssInliner\Facades\CssInline
,但是如果您喜欢直接使用实例(像我一样),您可以将 BradieTilley\LaravelCssInliner\Facades\CssInline::
替换为以下任何一个
BradieTilley\LaravelCssInliner\Facades\CssInline:
BradieTilley\LaravelCssInliner\CssInliner::singleton()->
app(BradieTilley\LaravelCssInliner\CssInliner::class)->
app()->make(BradieTilley\LaravelCssInliner\CssInliner::class)->
通过 PHP 添加 CSS
在任何时候(在 HTML 转换之前),您都可以定义您希望添加到每个由 CSS Inliner 转换的 HTML 字符串或电子邮件中的 CSS 文件或原始 CSS。一个很好的例子是一个所有电子邮件都应该继承的基本样式表。
use BradieTilley\LaravelCssInliner\Facades\CssInline; CssInline::addCssPath(resource_path('css/email.css')); CssInline::addCssRaw('body { background: #eee; }'); # Or, you can achieve the same outcome by letting CssInline decide whether it's a path or raw CSS: CssInline::addCss(resource_path('css/email.css')); CssInline::addCss('body { background: #eee; }');
手动转换
您可能希望手动转换 HTML 字符串或电子邮件中的某些 CSS。
use BradieTilley\LaravelCssInliner\Facades\CssInline; use Symfony\Component\Mime\Email; CssInline::addCss('.font-bold { font-weight: bold; }'); # Convert an HTML string $html = CssInline::convert('<html><body><div class="font-bold">Bold</div></body></html>'); echo $html; // <html><body><div class="font-bold" style="font-weight: bold;">Bold</div></body></html> # Convert an email $email = new Email(); $email->html('<html><body><div class="font-bold">Bold</div></body></html>'); CssInline::convertEmail($email); echo $email->getHtmlBody(); // <html><body><div class="font-bold" style="font-weight: bold;">Bold</div></body></html>
选项:自动解析 Laravel 电子邮件(或不自动解析 Laravel 电子邮件)
您可能希望有条件地启用或禁用 CSS Inliner,用于从 Laravel 发送的邮件(通过 Mail::send()
)。为此,我们可以利用 emailListener
选项。默认值为 true
(因此将自动转换从 Laravel 发送的电子邮件中找到的 CSS 类)。
use BradieTilley\LaravelCssInliner\Facades\CssInline; CssInline::emailListenerEnabled(); // Current state: true or false CssInline::enableEmailListener(); // Enables option; returns instance of CssInliner CssInline::disableEmailListener(); // Disables option; returns instance of CssInliner
选项:从给定的任何 HTML 或电子邮件中读取 CSS(样式和链接元素)
您可能希望解析 HTML 或电子邮件中找到的 <style>
或 <link>
样式表,例如,如果您想将特定于电子邮件的 CSS 存储在电子邮件视图中。为此,我们可以利用 cssFromHtmlContent
选项。默认值为 false
。
use BradieTilley\LaravelCssInliner\Facades\CssInline; CssInline::cssFromHtmlContentEnabled(); // Current state: true or false CssInline::enableCssExtractionFromHtmlContent(); // Enables option; returns instance of CssInliner CssInline::disableCssExtractionFromHtmlContent(); // Disables option; returns instance of CssInliner
选项:在读取 CSS(如上所述)之后,从 HTML 或电子邮件中删除原始 CSS(样式和链接元素)
您可能希望在将 CSS 转换为内联样式后从 HTML 或电子邮件中删除大型 <style>
或 <link>
样式表,以减少从您的系统发送的电子邮件的有效负载大小。为此,我们可以利用 cssRemovalFromHtmlContent
选项。默认值为 false
。
use BradieTilley\LaravelCssInliner\Facades\CssInline; CssInline::cssRemovalFromHtmlContentEnabled(); // Current state: true or false CssInline::enableCssRemovalFromHtmlContent(); // Enables option; returns instance of CssInliner CssInline::disableCssRemovalFromHtmlContent(); // Disables option; returns instance of CssInliner
use BradieTilley\LaravelCssInliner\Facades\CssInline; CssInline::doSomething(); CssInliner::addCssPath(resource_path('css/email.css')); CssInliner::addCssRaw('.text-success { color: #00ff00; }'); # Convert your own HTML/CSS $html = '<span class="text-success">Success text</span>'; $html = CssInliner::convert($html); echo $html; // <span class="text-success" style="color: #00ff00;">Success text</span>
事件
CssInliner 会触发四个事件 - 两个用于 HTML 转换,所有四个用于电子邮件转换。事件调用的顺序是
- 1st:
BradieTilley\LaravelCssInliner\Events\PreEmailCssInlineEvent
(仅限电子邮件) - 2nd:
BradieTilley\LaravelCssInliner\Events\PreCssInlineEvent
(电子邮件 + HTML) - 3rd:
BradieTilley\LaravelCssInliner\Events\PostCssInlineEvent
(电子邮件 + HTML) - 4th:
BradieTilley\LaravelCssInliner\Events\PostEmailCssInlineEvent
(仅限电子邮件)
可以通过 Laravel 的常规方式监听事件。例如
Event::listen(\BradieTilley\LaravelCssInliner\Events\PreEmailCssInlineEvent::class, fn () => doSomething());
或者,您可能希望使用回调方法 hook 到 CSS Inliner:beforeConvertingEmail
、afterConvertingEmail
、beforeConvertingHtml
、afterConvertingHtml
。这些方法接受一个回调,实际上是 Event::listen()
的代理,因此您可以将以下示例中使用的回调视为对应 CssInliner 事件的 Event::listen()
的第二个参数。
事件:在电子邮件转换之前(beforeConvertingEmail
)
CssInliner::beforeConvertingEmail(function (PreEmailCssInlineEvent $event) { # You have access to the unconverted-Email and CSS Inliner instance via the event $event->email; // instanceof: \Symfony\Component\Mime\Email $event->cssInliner; // instanceof BradieTilley\LaravelCssInliner\CssInliner echo $event->email->getHtmlBody(); // <html>...</html> # Because this is a 'before' event, you may choose to halt the conversion of this *one* Email return $event->cssInliner->halt(); # Laravel will halt any other event listeners; CSS Inliner will return the Email immediately (and not convert it) });
事件:在 HTML 转换之前(beforeConvertingHtml
)
CssInliner::beforeConvertingHtml(function (PreCssInlineEvent $event) { # You have access to the unconverted-HTML and CSS Inliner instance via the event $event->html; // string $event->cssInliner; // instanceof BradieTilley\LaravelCssInliner\CssInliner echo $event->html; // <html>...</html> # Because this is a 'before' event, you may choose to halt the conversion of this *one* HTML string return $event->cssInliner->halt(); # Laravel will halt any other event listeners; CSS Inliner will return the HTML immediately (and not convert it) });
事件:在 HTML 转换之后(afterConvertingHtml
)
CssInliner::afterConvertingHtml(function (PostCssInlineEvent $event) { # You have access to the converted-HTML and CSS Inliner instance via the event $event->html; // string $event->cssInliner; // instanceof BradieTilley\LaravelCssInliner\CssInliner echo $event->html; // <html>...</html> # Because this is an 'after' event, you cannot halt the conversion of the HTML string (unlike the 'before' event) });
事件:在电子邮件转换之后(afterConvertingEmail
)
CssInliner::afterConvertingEmail(function (PostEmailCssInlineEvent $event) { # You have access to the converted-Email and CSS Inliner instance via the event $event->email; // instanceof: \Symfony\Component\Mime\Email $event->cssInliner; // instanceof BradieTilley\LaravelCssInliner\CssInliner echo $event->email->getHtmlBody(); // <html>...</html> # Because this is an 'after' event, you cannot halt the conversion of the Email (unlike the 'before' event) });
变更日志
有关最近更改的详细信息,请参阅变更日志。
测试
composer test
贡献
有关详细信息,请参阅贡献指南。