January 26, 2026, 2:53pm 1
Forgive me, Andrew, for I am about to sin: I am creating Yet Another IO Thread.
I was eagerly looking to integrate Zig in some of my professional work (this is around 0.14), saw the Writergate storm that was happening and got sidetracked with some other projects. I’m now in a place where I can start looking at Zig again, and boy am I confused. I’ve read a good amount of threads (but not all of them, so feel free to point me to them if they offer explanations), but I haven’t seen a comprehensive explanation on the IO design.
I started reading through the stdlib documentation, which as an aside is a really tough read, and got even more confused. I just don’t get the current IO structure; for instance, what the heck is a CSPRNG state doing randomly tu…
January 26, 2026, 2:53pm 1
Forgive me, Andrew, for I am about to sin: I am creating Yet Another IO Thread.
I was eagerly looking to integrate Zig in some of my professional work (this is around 0.14), saw the Writergate storm that was happening and got sidetracked with some other projects. I’m now in a place where I can start looking at Zig again, and boy am I confused. I’ve read a good amount of threads (but not all of them, so feel free to point me to them if they offer explanations), but I haven’t seen a comprehensive explanation on the IO design.
I started reading through the stdlib documentation, which as an aside is a really tough read, and got even more confused. I just don’t get the current IO structure; for instance, what the heck is a CSPRNG state doing randomly tucked into std.IO.Threaded? It just seems so random. Why is std.IO.randomSecure there? I get that randomness can be a blocking event, and why it would be in the std.IO namespace, but I’d expect it to be tucked into an IO implementation, and not in the top level. Why not put fileRead or fileSetPermissions there too?
I guess my optimal outcome for this thread would be for someone to point at a single, up-to-date document/resource that says “Here is what std.IO is, and here is how you can design your own. Here is how current ones work, and how they’re being improved. Here is why we made the decision to stuff CSPRNG in Threaded. Etc.”
I want to finish my post by saying that I appreciate what Zig is trying to do, I’m generally excited about it, and I get that designing this is not an easy problem. I’m not trying to criticize the patterns, they may just not be right for what I’m trying to do, and that’s okay!
1 Like
The single, up-to-date documentation would be the standard library documentation. This area is in a lot of flux right now, so it’s really only these docs that are updated and useful. Unfortunately that is the best source right now.
I think some of the confusion here is that Io is interface, and Threaded/Evented are the two concrete types being implemented right now. Threaded is more “complete” of the two.
Threaded is the most complete variant right now. There is a lot of exploratory work going on as to what should be in the interface and what should be below the interface. So CSPRNG is below the interface (it’s in Threaded, not Io interface) which is expected. The interface only exposes randomSecure since it requires IO, but the actual imlementation is CSPRNG in Threaded.
1 Like
I was afraid this would be the answer
. Again, wholly appreciate the complexity and pre-release state that Zig is in, but I find myself frustrated by how difficult it is to get some answers when the stdlib documentation is so incomplete. I try my best to read the implementations and tests, but it’s far from being (in my humble opinion) a satisfactory and complete resource.
I’m still not sure why randomSecure is under std.IO, though.
The interface only exposes
randomSecuresince it requires IO, but the actual imlementation is CSPRNG inThreaded.
Isn’t this true for all IO-related activities? Why doesn’t the interface expose fileRead as well, with the implementation being in Threaded? It just seems random to me that it’s at that level. I guess the only difference is namespacing it into a std.Io.Random.randomSecure like std.Io.File.read… is, but it seems random (no pun intended)
lalinsky January 26, 2026, 3:33pm 4
I kind of agree, I’d also prefer if std.fs, std.net, std.time, etc were kept for namespacing purposes and the only change would be that they require io parameter now.
2 Likes
While I find the Io interface concept to be well thought through and a good design, the rest of it is being rapidly developed. Just because randomSecure is in the Io interface right now does not mean it will stay there. A lot of exploration is happening and refactoring will occur. I wouldn’t be surprised if things do get better namespaces as things go on. This is a very volitile time for the standard library which means it is a difficult time to be using the language (if you are riding the 0.16.0-dev` train).
Doesn’t make it any easier to follow right now, but it the current state. I’m inclined to wait on 0.15 for most of my projects for now.
1 Like
One of the threads you might have seen is about namespace organization generals (like, “should there even be top-level Structs, or should everything be sub-namespaced, like io.Io despite contradiction with a pivotal style cornerstone?”) and specifics (like, “where does X belong?”), and Andrew piped in himself admitting that some things are not at all where they belong. For instance, heap.FixedBufferAllocator (FixedBufferAllocator uses a stack buffer, and so is rather the opposite of heap); I wouldn’t be surprised if the allocators all found themselves together in a namespace whose name was something more like alloc - right now, the allocators are all in heap, but the interface, Allocator, is in mem.
So, it’s not “right”, and things will break whenever things get moved around, and everybody who is daring enough to experiment with zig right now will have to sit on their grumbling when it does happen… this is still pre 1.0, as all keep saying, even though it’s being used in some pretty big projects.
1 Like
alanza January 27, 2026, 4:07am 7
just in case it’s useful to say: the age of the code whose lack of documentation we are complaining about is still best measured in weeks or days. if you need better documentation, wait for 0.16.0 and then complain about how it’s undoubtedly still not at a reasonable level 
kristoff January 27, 2026, 7:39am 8
The best place for documentation currently are probably PR descriptions combined with discussions in the ZSF Zulip.
The thing is, the first draft of new I/O is still being worked on and has yet to be part of a tagged release of Zig, so if you want to know what’s up you have to follow the development process.
Or wait for the next tagged release and expect to find a rationale for its design in the release notes.