Regex: Lazy Matching In Nested Groups

I have this regex: /{(?:{(?:.*?)?)?$/g.

Notice that I'm trying to lazily match .*? in the innermost group.

But it doesn't behave the way I expect:

const regex = /{(?:{(?:.*?)?)?$/g;

let match = "{{abc{".match(regex)
// expected: [ "{" ]
// actual: [ "{{abc{" ]

match = "{{abc{{".match(regex)
// expected: [ "{{" ]
// actual: [ "{{abc{{" ]

match = "{{abc{{def".match(regex)
// expected: [ "{{def" ]
// actual: [ "{{abc{{def" ]

I'm using this regex to match {, {{ or {{something if it is at the end of a string (without taking into account multi-line strings)

It might be because the string is matched from left to right, but is there an elegant way to get the expected behavior?


Using the regex in the selected solution solves the above problem, but fails if the string after the last {{ contains one or many { not following each other.


const regex = /{(?:{(?:[^{]*?)?)?$/g;

let match = "{{abc{{de{f".match(regex)
// expected: [ "{{de{f" ]
// actual: null

match = "{{abc{{de{f{g".match(regex)
// expected: [ "{{de{f{g" ]
// actual: null


With .* you are matching everything, including {. You have to exclude it from the "innermost string" with a [^{], and you may add here any character you also want to exclude:


Check it here.

For the EDIT, you need to make one of the { optional, in order to be able to parse both {{ and {.


Check it here.