writeFileAtomically function

Future<void> writeFileAtomically(
  1. String path,
  2. String contents
)

Writes contents to path, through a temporary file and a rename.

The rename is the point. A crash, a power cut or a full disk halfway through a direct write leaves a truncated document where the good one was — so one lost session becomes every future one, because the next read finds something that will not parse. Writing beside it and renaming means the worst case is a leftover .new file next to a document that is still whole.

flush: true because a rename that beats the bytes to the disk is the same failure with an extra step.

Throws what the filesystem throws. A caller that would rather report than fail — FileStorage is one — catches it; a caller that must tell somebody their level did not save — the editor is one — lets it out.

Implementation

Future<void> writeFileAtomically(String path, String contents) async {
  final temporary = File('$path.new');
  await temporary.writeAsString(contents, flush: true);
  await temporary.rename(path);
}