SEO Image Source custom Twig outputs escaped & instead of &
Describe the bug
Hi!
I’ve encountered what I think might be a regression/behavior change in SEOmatic where custom Twig entered in the “SEO Image Source” field is now being HTML-escaped, resulting in & appearing in query strings instead of &.
This previously worked as expected (unescaped), but now the output is escaped even when the Twig expression itself produces a correctly formatted URL.
To reproduce
Steps to reproduce the behaviour: 1. In the SEOmatic field “SEO Image Source”, enter custom Twig such as:
{%- set asset = entry.image.collect()[0] -%}
{%- if asset -%}
{% set baseUrl = asset.url %}
{% set params = {
'fit': 'crop',
'crop': 'focalpoint',
'w': 1200,
'h': 630,
'fp-x': asset.focalPoint.x,
'fp-y': asset.focalPoint.y,
'blend-color' : (entry.adviceEntryColors.color|first.color ?? '#D9EAD7')|trim('#'),
'blend-size' : 'inherit',
'blend-mode' : 'multiply'
} %}
{{ url(baseUrl, params) }}
{%- endif -%}
- View the og:image tag on the rendered page. SEOmatic escapes the URL inside the tag:
<meta content="https://fivh.imgix.net/.../sparegris-gt.png?fit=crop&crop=focalpoint&w=1200&h=630&fp-x=0.5&fp-y=0.5&blend-color=D9EAD7&blend-size=inherit&blend-mode=multiply" property="og:image">
Expected behaviour
The final URL with unescaped ampersands (as returned by url()):
https://fivh.imgix.net/.../sparegris-gt.png?fit=crop&crop=focalpoint&w=1200&h=630&fp-x=0.5&fp-y=0.5&blend-color=D9EAD7&blend-size=inherit&blend-mode=multiply
Screenshots
Image where params are not passed to Imgix:
Image where params are passed to Imgix:
⸻
This behavior appears to be new — the same Twig previously produced unescaped output. And/or, of course, I might be missing something that should be obvious....
Thanks!
Versions
- Plugin version: 4.1.19
- Craft version: 4.16.13
hmmmm, I don't think anything has changed in this part of SEOmatic in some time. Maybe you can use the | raw filter in Twig?
{{ url(baseUrl, params) | raw }}
...which will prevent the default encoding Twig does? Potentially you could also use the | escape filter.
Thanks for the quick reply!
I've tried different filters, but it seems the output is escaped independently of what is added to the field:
Simplified input:
{{ 'Test raw &'|raw }} {{ 'Test escape &'|escape }}
Outputs:
<meta content="https://fivh.ddev.site/Test raw & Test escape &" property="og:image">
Could there be some string handling that occurs before the meta tags are echoed ?
Also |url_encode breaks the entire content of the field:
{{ 'Test encoding'|url_encode }} outputs <meta content="https://fivh.ddev.site/" property="og:image">
There is some string handling that happens, but what I'm confused by is you saying it used to work, but no longer does. Because there haven't been changes in that area in some time.
I'll take a look into reproducing this, however.
Ah, yes, I was imprecise in my initial description and that would explain the confusion.
The approach that used to work , and currently is not, was using the |url_encode-filter in the "SEO Image Source" Custom URL input field. E.g.
{{ baseUrl}}?{{params|url_encode}}
As far as I can tell from samples in Way back archives, this worked perfectly until at least august this year. But at some point since the |url_encode-filter has stopped working and outputs just nothing. This it is the specific change in behavior we have seen.
Looking for a fix I opted for the url()-function approach instead, with or without filters, and assumed it was related as I couldn't get this to work either.
Thank you for looking into it!