Find a different syntax for inline snapshot so that cargo fmt can work
Currently, @r###"..."### the inline snapshot syntax is invalid during cargo fmt analyze and cannot be formatted.
Perhaps a different syntax (e.g. i=r"") can be used for helping in this case.
Check out https://github.com/mitsuhiko/insta/issues/456, both this:
Would be great for inline snapshots to work with
rustfmt, but don't think there's a way — if the inline snapshot is a normal expression without special syntax (such as@), it's not possible to discriminate between(name, value)and(value, snapshot)
...and the broader discussion.
I agree that it would be great to allow rustfmt to work, though lots of other tradeoffs...
Sharing my workaround:
- Before
cargo fmt, runsg scan --rule <path to yaml>(need to install ast-grep)
# Replace `@` with `-` in macros
id: pre-format
language: Rust
rule:
pattern: '@'
precedes:
kind: raw_string_literal
inside:
kind: macro_invocation
stopBy: end
fix: '-'
-
Run
cargo fmt -
Finally, run
sg scan --rule <path to yaml>
# Replace `-` with `@` in macros
id: post-format
language: Rust
rule:
pattern: '-'
precedes:
kind: raw_string_literal
inside:
kind: macro_invocation
stopBy: end
fix: '@'
from https://github.com/mitsuhiko/insta/issues/605#issuecomment-2366916072
rustfmtis requiring a syntactical valid expression, but not semantically valid expression. Thus there is room to find such patterns. For example, my using-r###""###utilize the fact that unary minus to a string is valid in syntax but invalid in type. Symbols like*,!,?(postfix) are also possible.
OK, that's quite interesting.
@andylokandy, on further reflection, I'm not sure there's a syntax which would actually work here?
We need to identify the type of macro in the macro_rules!. Currently we do that with @literal and:
- If we use something syntactically valid like
!"Testing", then the macro has ambiguities - If we use something like
+"Testing", thencargo fmtno longer works
Am I right in thinking this is the full set of options? Or is there some other way around it?
Here's a WIP branch with me trying things (originally tried +, then tried !...): https://github.com/max-sixty/insta/tree/plus
If we use something syntactically valid like !"Testing", then the macro has ambiguities
Could you provide a example of the ambiguities? I may not fully understand it. (and what if *?)
Try my branch — the rust compiler will complain about ambiguities in the macro...
Got it. It's a limitation of the compiler (lack of backtrack when parsing macro), but there is a nasty way to get through: instead of directly defining the pattern arms, consume the tokens one by one. In detail:
- receive input as
$($input:tt)* - match one token a time, until the pattern is determined
- call sub-macro for each pattern
Here is a demo of this technique.
Ah OK cool!
If you want to make a branch / draft PR with this on, I think that would be quite helpful. Assuming the interface for users is still nice and internal stuff is well-documented, I would be +1 on this.
(...though I'm not the sole decider, to set expectations)