Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions fsspec/implementations/memory.py
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,15 @@ def _open(
# position at the beginning of file
f.seek(0)
return f
elif "a" in mode:
# append modes create the file if it does not exist, matching
# builtin open() and LocalFileSystem
m = MemoryFile(self, path, kwargs.get("data"))
if not self._intrans:
m.commit()
Comment on lines +203 to +205

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Should make sure to seek to the end of the file. In the test, it is already at the end, but this is not guaranteed.

# position at the end of file, like the existing-file path above
m.seek(0, 2)
return m
else:
raise FileNotFoundError(path)
elif mode in {"wb", "w+b", "xb", "x+b"}:
Expand Down
13 changes: 13 additions & 0 deletions fsspec/implementations/tests/test_memory.py
Original file line number Diff line number Diff line change
Expand Up @@ -177,6 +177,19 @@ def test_no_rewind_append_mode(m):
assert f.tell() == 7


@pytest.mark.parametrize("mode", ["a", "ab", "a+b"])
def test_append_creates_missing_file(m, mode):
# append modes create the file if it does not exist, matching builtin
# open() and LocalFileSystem
filename = "newfile.txt"
assert not m.exists(filename)
with m.open(filename, mode) as f:
# append mode must position at the end of the (newly created) file
assert f.tell() == f.seek(0, 2)
f.write(b"data" if "b" in mode else "data")
assert m.cat(filename) == b"data"


def test_moves(m):
m.touch("source.txt")
m.mv("source.txt", "target.txt")
Expand Down