Skip to content

Commit

Permalink
fix: support iOS (#523)
Browse files Browse the repository at this point in the history
Hi there! We're developing an open-source app
(https://github.com/dumpus-app/dumpus-app) and use satori to render some
images client-side.
However, we encountered the following error on both ios web (safari) and
capacitor (that uses safari webview) on a lot of iOS devices:
```bash
Invalid regular expression: invalid group specifier name
```
After investigating, we found out it's caused by [regex
lookbehind](https://stackoverflow.com/questions/51568821/works-in-chrome-but-breaks-in-safari-invalid-regular-expression-invalid-group)
not being [supported until iOS
16.4](https://caniuse.com/js-regexp-lookbehind).

This PR replaces this regex by some quite hacky code because we needed a
hotfix.
If anybody wants to update the regex in order not to use `lookbehind`
feature, feel free to do so!.

If you want to test it, you can use satori on the web using the
following package json version:
```json
"satori": "dumpus-app/satori#fix-safari-compatibility-build"
```

Thanks for your time!

Co-authored-by: Androz2091 <[email protected]>
  • Loading branch information
florian-lefebvre and Androz2091 authored Aug 1, 2023
1 parent 2e8dcb4 commit efbb5ec
Showing 1 changed file with 29 additions and 13 deletions.
42 changes: 29 additions & 13 deletions src/parser/mask.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,11 +14,33 @@ export interface MaskProperty {
clip: string
}

function splitMaskImages(maskImage) {
let maskImages = []
let start = 0
let parenCount = 0

for (let i = 0; i < maskImage.length; i++) {
if (maskImage[i] === '(') {
parenCount++
} else if (maskImage[i] === ')') {
parenCount--
}

if (parenCount === 0 && maskImage[i] === ',') {
maskImages.push(maskImage.slice(start, i).trim())
start = i + 1
}
}

maskImages.push(maskImage.slice(start).trim())

return maskImages
}

/**
* url(https:a.png), linear-gradient(blue, red) => [url(https:a.png), linear-gradient(blue, red)]
* rgba(0,0,0,.7) => [rgba(0,0,0,.7)]
*/
const SPILIT_SOURCE_COMMOA_RE = /(?<=\))(?:\s*,\s*)/

export function parseMask(
style: Record<string, string | number>
Expand All @@ -33,16 +55,10 @@ export function parseMask(
clip: getMaskProperty(style, 'origin') || 'border-box',
}

return (
maskImage
.split(SPILIT_SOURCE_COMMOA_RE)
// https://www.w3.org/TR/css-backgrounds-3/#layering
.reverse()
.map((v) => v.trim())
.filter((v) => v && v !== 'none')
.map((m) => ({
image: m,
...common,
}))
)
let maskImages = splitMaskImages(maskImage).filter((v) => v && v !== 'none')

return maskImages.reverse().map((m) => ({
image: m,
...common,
}))
}

1 comment on commit efbb5ec

@vercel
Copy link

@vercel vercel bot commented on efbb5ec Aug 1, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please sign in to comment.