chmln / handlr

A better xdg-utils
MIT License
608 stars 24 forks source link

Should write to mimeapps.list atomically to prevent intermediate states or corruption #43

Open nyanpasu64 opened 3 years ago

nyanpasu64 commented 3 years ago

I think it makes sense to atomically write to mimeapps.list, by writing to a temporary file, then renaming it on top of mimeapps.list.

https://danluu.com/file-consistency/ describes the pitfalls of filesystems and fsync. It describes using log files for atomicity, and advises against rename-based atomic saves. However, rename-based saving is our only option, since apps don't know how to read log files but only mimeapps.list. And GLib uses rename and fsync, so it should be fine...

You can implement atomic saving yourself, or shell out to a crate like atomicwrites or tempfile's persist method (not sure why there are two of them, link, link). Note that tempfile's persist method mentions the risk of the tempfile being deleted or replaced with a different file under the same name. I haven't researched the best approach to take, the crate options out there, or where to create a temp file, or the optimal syscall for renaming. (capnproto's kj filesystem library creates a temporary file in the same directory and uses renameat().)

chmln commented 2 years ago

Hey @nyanpasu64 thanks a lot for your extensive research and contribution ! Do you think you could publish #44 as a library instead and have handlr simply use it ?

nyanpasu64 commented 2 years ago

If you want to take the easy way out, you can just use the upstream atomicwrites library, and if they add support for disabling fsync on directory, you can add that as an optimization later. I think that's a better outcome than me publishing a new crate solely serving as an edited version of atomicwrites that only works on Linux.