Summary
Fibers is a new feature in the most recent release of the Ruby language. In a detailed tutorial, Programming Ruby author Dave Thomas explains what fibers are, and how they help achieve a high degree of decoupling in a Ruby application.
Advertisement
One of the most interesting new Ruby language features is fibers, available in recently released Ruby 1.9. Dave Thomas, author of Programming Ruby, aka the "PickAxe Book," explains fibers in a two-part excerpt, Pipelines Using Fibers in Ruby 1.9, that did not fit in the latest edition of his book:
Ruby 1.9 adds support for Fibers. At their most basic, let you create simple generators (much as you could do previously with blocks)...
A fiber is somewhat like a thread, except you have control over when it gets scheduled. Initially, a fiber is suspended. When you resume it, it runs the block until the block finishes, or it hits a Fiber.yield. This is similar to a regular block yield: it suspends the fiber and passes control back to the resume. Any value passed to Fiber.yield becomes the value returned by resume...
By default, a fiber can only yield back to the code that resumed it. However, if you require the "fiber" library, Fibers get extended with a transfer method that allows one fiber to transfer control to another. Fibers then become fully fledged coroutines.
Thomas uses the concept of shell-like pipes to explain how fibers can help achieve a high level of decoupling in a Ruby program:
Users of the command line are familiar with the idea of building pipelines: a chain of simple commands strung together... [where] the output of one becomes the input of the next. Using pipelines and a basic set of primitives, shell users can accomplish some sophisticated tasks. Here's a basic Unix shell pipeline that reports the ten longest .tip files in the current directory, based on the number of lines in each file:
wc -l *.tip | grep \.tip | sort -n | tail -10
Let's see how to add something similar to Ruby. By the end of this set of two articles, we'll be able to write things like:
We write little chunks of code, and then combine them to get work done. Just like a pipeline...
In the article, Thomas shows examples of filters that can transform their input and pass their output into another fiber. The result is small chunks of functionality that together produce a highly modular program:
What we've done here is turned the way a program works on it's head. We've written chunks of isolated code, each of which either filters or transforms an input. We've then independently knitted these chunks together. That's a high degree of decoupling. We can also leave it until runtime to determine what gets put into the pipeline (and the order that it appears in the pipeline), which means we can move more power into the hands of our users.
Could we have done all this without Fibers? Of course. Could we do it without Ruby 1.9? Absolutely. But sometimes factors come together which lead us to experiment with new ways of thinking about our code.
What do you think of Ruby fibers? What are your favorite Ruby 1.9 features?
I'm still trying to find an excuse to use Ruby professionally. Contrary to desirable practice, I haven't learned a new language for the last four or five years, which I've spent writing classes-in-C in an embedded firmware environment. I'm still interested though, and not *entirely* brain dead.
One can only hope that there are better uses for Fibers, because Dave's example is not compelling. Otherwise, Fibers will be relegated to the status of Continuations - an interesting academic concept that's ignored in practice.
> Otherwise, Fibers will be relegated to the status of > Continuations - an interesting academic concept that's > ignored in practice. The industry has already demanded this. That's the reason why they have incorporated this for example also in Lua.