New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Consider Go's new io/fs filesystem interfaces for IPFS #7556
Comments
A couple initial thoughts:
|
I should also note that, if the IPFS team has any input for the current design, now is the time to give it :) Reddit is probably the right place right now. Once a proposal is filed, then there will be a GitHub thread. |
This is really exciting. Golang needs a shared standard for filesystem interfaces quite badly; I've been sore about the lack on several occasions, even well outside of IPFS. Thrilled to see talk of it happening. The whole proposal reads really well to me. Functions defining most operations, and extensional interfaces making it happen "fast" whenever possible, is definitely the way to go for something like this. The discussion of ensuring the new 'fs' package would not depend on the 'os' package is... yes, please, thank you, oh my goodness. I'm... not a big fan of Similarly: it looks like The discussion about "middleware" such as a "CachingFS", which is mentioned in the section about "archive/zip", is very pleasing. It's good that "archive/zip" would be fitted to this new FS interface. I'm not sure I'm happy to hear that "archive/tar" might not get similar modification to conform to the new FS interface; I'm familiar with the seekability troubles, and amenable to the concern about setting a performance trap, but at the same time, this is just such a common thing to want from the tar package that it seems people would also trip and stumble in surprise at its absence at a very high rate. I think implementing the FS interface for tar with a simple in-memory index of file start positions, which is lazily populated as Open calls are used, and uses seekable readers for the underlining date if possible... while simply making clear remarks in the documentation about the performance and practicality of this... would be both high value and not all that hard. It's interesting that path resolution seems to be left as extremely opaque. I see a couple remarks about slash-delimited, but not much in the way rules for lawful relationship between using a path on the FS as a whole vs stepping individual directories one by one. I didn't see any discussion of symlinks or mention of "Lstat". I find Lstat pokes a lot of very interesting holes in things, so I hope there's more discussion of that upcoming. (Maybe it will simply be handled in a puff of extensional interface smoke with no further ado; but that's not obvious to me.) Most of the questions I might have for this system are oriented around the writer side of things, which is not yet much treated. I like the outline of the idea that it is all handled by just adding more and more extension interfaces... but I think that needs quite a bit more fleshing out. (Maybe there's more in the example prototype implementation; I haven't moved beyond the doc yet.) In particular, when poking about filesystem APIs before myself, I've found that the distinction between operating with paths vs operating on open handles (aka 'fd's) can be fairly subtle and fairly critical. Defining operations in terms of paths seems to be the easier and more convenient of the two; but defining operations in terms of open handles seems to be the much more powerful of the two, because it can operate with considerably more clarity and fewer potential races in the case of other concurrent actors on a filesystem. I realize this is intentionally left out of the current draft -- and also, my concerns here probably go a bit further than what might be relevant to IPFS, even -- and on top of all that, the concurrency semantics I'm talking about lean towards being something of a detail of OS kernels and filesystem drivers... but despite all that, I still think the topic of handle-based operations may be worth some consideration sooner than later, because this is a distinction that might be Tricky to retrofit into supportability at a later date if it does turn out to be desired. I'd also have some questions about if separate extension interfaces for features like chmod and chown will work well. A number of operations like that have varied behavior depending on the order in which they're called -- e.g. using chmod to add a setuid bit, then using chown, has a very different final result on an (e.g.) linux kernel than doing those operations the other way around. I'm not sure it's the FS interface's job to be aware of that... but I'm also not sure future surprises and headaches will be minimized by ignoring this, either? Dunno. Just something to think about. I'd also love to hear more details about any changes to error handling. My experiences with trying to handle the finer details of errors around filesystems, in an OS-agnostic way, are filled with memories of much bewilderment. The mixture of interface-errors vs check-this-with-a-function-errors vs concrete-type-errors vs exact-value-errors vs value-in-a-struct-errors (some of which are syscall-leaks-through(!)-errors) is... really quite difficult to navigate confidently, at present. (An exercise that may help visualize how wild this can get: If I wanted to use switch statements for error handling, and were to make a separate switch for each kind of switch needed, imagine many of them would be needed!) I know this is hard to sort out (desire to be OS-agnostic whilst not hiding or destroying OS-specific info is certainly tricky!), but a more detailed strategy for making this more parsimonious in the future would be nice to hear more about. I share these thoughts here, but I'm not sure if they're of sufficient novelty to be worth reposting to the reddit discussions. And I don't have a reddit account, so I'll probably wait until getting a pretty sharp kick in the shins if someone thinks I've said something worth adding there. (Repost snippets freely though, if anyone has a lower coefficient of friction to reddit than I do.) |
Chiming in here, mostly just saying "same" and "cool". But also referencing some of the IPFS re: @warpfork:
+1 on all this. Including the lack of being able to propose an alternative. The issue of coming up with a cross-platform compatible, metadata interface and/or format, that works for everyone... seems tough.
Another +1 with another "This seems just as tough to get right" remark for the same reasons.
Big +1 on this. Reminds me of the nice things I hear about 9P and composing file systems from sets of other file systems. With Go itself having similar composition patterns, it's fitting to see it talked about in the file system discussions.
I've had things like this on my mind recently. You can imagine people conforming to a chmod interface with some kind of backing mode-store, or passing through to a host system, etc. But allowing the implementations of general concepts like "permissions" to hopefully just be abstracted enough to be swapped. So you can define basic Likewise, even more abstractions via wrapping those operations. Packages that offer guarantees about operation details such as order, what happens when encountering an error, etc. Those are my random thoughts on it.
Another big +1 In trying to deal with this myself, I've had a bit of a hard time coming up with something elegant. Trying to inspect different error standards from different external packages, and translating them into something uniform, while adding or retaining context. There's a lot of duplication up front in my specific case. Translating IPFS "not found" errors into POSIX "not found" values, wrapped with a generic human-oriented message of "not found", but I found (heh) that once things were defined/established in an 'errors' package, it made it easy to make changes to packages at any layer any time I Here's some relevant links of my WIP branch which maps a lot of the IPFS APIs to other file system APIs like FUSE and 9P. The fact that error handling stuff: Here's some relevant sections of the branch: the current actual file system interface I conform to ; an implementation of it ; a FUSE wrapper interface that uses it Random semi-relevant opinions: The selection of responsibility and pace is also nice to see, as expected from the Go community. I appreciate people not trying to be hasty about this, and trying to break it up into phases, or even remove responsibility from std altogether. |
I'm far from familiar with the lower level details here, but on reading the proposal, it seems to me that the approach of leaving the "old way" intact for compatibility, when the new way can do the whole job, is exactly why languages and libraries get filled with bloaty cruft. I get the goal of backwards compatibility, but this screams "deprecation needed" to me. And it looks like the changes needed are pretty much cut-and-paste, not larger code rewrites on the user side - doesn't seem like a lot to ask to keep the stdlib clean. |
For what it's worth I have read-only implementations of |
This would be fantastic. I've written about and open sourced hackpadfs to share the full set of FS operations as I'd love to integrate an IPFS adapter into hackpad.com's runtime at some point. Maybe it could enable folks to share their playground code with a shortlink, which loads their distributed source files. |
See https://go.googlesource.com/proposal/+/master/design/draft-iofs.md; note that it's just a draft still, and it has a Youtube video presentation as well as a Reddit discussion thread.
It's early days for this idea, but if it does get proposed and accepted, it seems like a great fit for IPFS. Pretty much any package that expects to work with a filesystem could magically be composed on top of IPFS with minimal effort, in theory.
/cc @mikeal @warpfork
The text was updated successfully, but these errors were encountered: