Skip to content

Binary snapshots (in-memory)#610

Merged
max-sixty merged 55 commits intomitsuhiko:masterfrom
lasernoises:in-memory-binary-snapshots
Oct 4, 2024
Merged

Binary snapshots (in-memory)#610
max-sixty merged 55 commits intomitsuhiko:masterfrom
lasernoises:in-memory-binary-snapshots

Conversation

@lasernoises
Copy link
Copy Markdown
Contributor

The biggest difference to the previous attempt in #489 is that the snapshot contents are now kept in-memory instead of being written into a temporary file directly.

For SnapshotContents I decided to make it an enum with two variants like in the previous attempt. I first attempted to change it to three variants so it would also replace the SnapshotKind enum but I realized that a lot of logic is still shared between inline and file text snapshots. That approach would definitely also work though and it's perhaps also a question of how much the logic between the two is expected to diverge in the future.

In runtime::assert_snapshot I replaced the combination of the refval and new_snapshot_value with an enum. In that case it is a three variant enum and some From impls for two value tuples for the macros. Maybe it would be better to make it a two variant enum there too for consistency and keep the ReferenceValue enum for the text case. That might be a bit weird because both binary and non-inline text snapshot have a name and that would then be in two different enums.

I should probably also add some tests in cargo-insta. I'll do that as soon as possible, but I need to figure out how the testing there works.

This is the somewhat simplified version of mitsuhiko#489 where we keep the full files
in-memory during the assert and when reviewing.
…snapshots

This merge is far from compiling. I just picked the side of each conflict that
makes more sense to build upon.
…snapshots

Still WIP like the previous merge.
Comment thread insta/src/runtime.rs
Comment thread insta/src/snapshot.rs Outdated
Comment thread insta/src/snapshot.rs Outdated
Comment thread insta/src/runtime.rs Outdated
Comment thread insta/src/runtime.rs Outdated
Copy link
Copy Markdown
Collaborator

@max-sixty max-sixty left a comment

Choose a reason for hiding this comment

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

It's in impressive effort! And thank you for redoing on top of the new master.

It does add lots more data structures & some complications to the code. I'm going to think about how much we could simplify (I've already simplified the existing code somewhat..). If you have ideas, that would be great too.

Comment thread insta/src/output.rs
Comment thread cargo-insta/tests/main.rs
Comment thread insta/src/snapshot.rs Outdated
Comment thread insta/src/runtime.rs
@max-sixty
Copy link
Copy Markdown
Collaborator

For SnapshotContents I decided to make it an enum with two variants like in the previous attempt. I first attempted to change it to three variants so it would also replace the SnapshotKind enum but I realized that a lot of logic is still shared between inline and file text snapshots. That approach would definitely also work though and it's perhaps also a question of how much the logic between the two is expected to diverge in the future.

FWIW I think the ontology is quite an interesting case — FileText & FileBinary share some properties, but FileText & InlineText also share some completely different properties. So there's no perfect hierarchy.

The proposed structure seems reasonable (as above I'd like to see if we can reduce the number of data structures a bit, but I don't think there are any easy large clean-ups)

@max-sixty
Copy link
Copy Markdown
Collaborator

To sketch out what I think we need to do to merge:

  • Tests — we already have a couple good integration tests. Would be great to extend those to any corner cases — for example, what if someone uses the same extension for a text snapshot? What does it look like if someone has an older version of cargo-insta? (maybe those are too specific, but anything in that direction)
  • @mitsuhiko needs to review, I think focused on the external API
    • Obv great if we can make the internal code nice, but also we can do that later, and would be a loss if this withered based on refinements.
  • We should decide whether we mark as experimental. If we don't mark it as experimental, we're stuck with the API, and in some ways insta has more stringent backward-compatibility constraints than other libraries, since it needs to work with older versions of itself in the form of cargo-insta)
  • Docs — we should add a short section on this in https://github.com/mitsuhiko/insta-website

Comment thread cargo-insta/tests/main.rs Outdated
Comment thread insta/src/runtime.rs Outdated
@max-sixty
Copy link
Copy Markdown
Collaborator

max-sixty commented Oct 4, 2024

Let's add a couple of examples to the docs and then hit the big button. Thank you very much for all your persistence here, I know it was a long road. It's a great feature for insta!

@lasernoises
Copy link
Copy Markdown
Contributor Author

The deleting of unreferenced snapshots does not work for binary snapshots yet. I'm working on fixing that now.

Previously it only deleted the .snap file, but not the binary
file next to it.
@lasernoises
Copy link
Copy Markdown
Contributor Author

Now it works, but I'm not quite sure what the best error handling strategy there is. It needs to load the snapshot now to know whether it's binary and to get the extension. It still ignores errors when deleting the files like before. So I think it should probably also ignore errors when loading the snapshot and just skip it and maybe print a log message.

The message "snapshots are matching" was previously printed when replacing
a binary snapshot with an empty string text snapshot.
Comment thread cargo-insta/src/cli.rs Outdated
Comment thread insta/src/snapshot.rs
@lasernoises
Copy link
Copy Markdown
Contributor Author

What I'm a bit more worried about is the internals module. I am changing some things that are exposed in there. The docstring does imply that it's primarily for documentation. So that might imply that it's not part of the stable API?

Yes, this is hidden and so not part of the public API (somewhat by convention). We only have it public so cargo-insta can access it.

I meant to reply to this earlier but forgot:
I think you meant the _cargo_insta_support module. Because the internals module is actually not hidden. I think given that it's called internals we can probably justify changing things exposed in it. Maybe it would make sense to add a comment there that explicitly states that this is not guaranteed to be stable.

@lasernoises
Copy link
Copy Markdown
Contributor Author

I've started adding a section for the website: https://github.com/mitsuhiko/insta-website/compare/main...lasernoises:insta-website:binary-snapshots?expand=1. I think I'll wait with opening a PR until this is merged.

@max-sixty
Copy link
Copy Markdown
Collaborator

I think you meant the _cargo_insta_support module. Because the internals module is actually not hidden. I think given that it's called internals we can probably justify changing things exposed in it. Maybe it would make sense to add a comment there that explicitly states that this is not guaranteed to be stable.

Yes v good point. Would be great to add the comment (but no need to slow down this PR ofc)

@max-sixty
Copy link
Copy Markdown
Collaborator

@lasernoises anything else? Or we merge? :)

@lasernoises
Copy link
Copy Markdown
Contributor Author

I think from my point of view we can merge.

@max-sixty max-sixty merged commit 0b81773 into mitsuhiko:master Oct 4, 2024
@lasernoises
Copy link
Copy Markdown
Contributor Author

🎉🎉🎉

Thank you so much for your patience and the many reviews/comments!

@max-sixty
Copy link
Copy Markdown
Collaborator

Thank you!!

max-sixty pushed a commit that referenced this pull request Oct 7, 2024
As discussed in #610 it probably makes sense to be explicit about the
`internals` module not being guaranteed to be stable.

I also noticed that `TextSnapshotKind` gets exposed globally. This was
added in #581 when it was still called `SnapshotKind`. I wonder if this
is necessary to expose toplevel.
CommanderStorm added a commit to maplibre/martin that referenced this pull request Jun 30, 2025
This PR migrates us to insta's binary snapshots.
These snapshots were added via
- #1563
- mitsuhiko/insta#610

<details><summary>previous blockers</summary>
<p>

<del>Currently, this PR is not mergable as the binary snapshots don't
actually work. I encountered these two bugs:</del>
- [x] <del>the binary snapshots get created as `FILENAME.snap.new.png`.
This naming is inconsistent with how other snapshots are created.</del>
- [x] <del>Re-running the tests creates different metadata files which
contain different data:</del>
  
  ```diff
  ---
  source: martin/src/sprites/mod.rs
  - assertion_line: 273
  expression: png
  - extension: png
  - snapshot_kind: binary
  ---
  +
  
  ```
  
  <del>
Yes, I looked if I am using the same versions of insta, I am. `cargo
test` and `cargo insta` still provide really weird results
  </del>
<del>
=> to be mergable, this PR would need work upstream.
I am going to try to write this up during the christmas holidays and
provide a fix upstream.</del>

</p>
</details>

---------

Co-authored-by: pre-commit-ci[bot] <66853113+pre-commit-ci[bot]@users.noreply.github.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants