Settings

Theme

Show HN: Stepped Actions – distributed workflow orchestration for Rails

github.com

85 points by klevo 16 days ago · 15 comments · 1 min read

Reader

Stepped is a Rails engine, extracted out of Envirobly where it powers tasks like application deployment, that involve complex, out-of-the-band tasks like DNS provisioning, retries, waiting for instances to boot, running health checks and all the fun stuff of a highly distributed networked system.

vicentereig 11 days ago

Nice work. Thanks for sharing it! I've been thinking about using something like this for LLM agent workflows - the outbound action pattern would work well for tool calls that need to wait on external APIs.

I'm working on DSPy.rb [1] and this could pair nicely for multi-step reasoning chains.

Curious - any plans for async gem support?

[1] https://oss.vicente.services/dspy.rb/

  • klevoOP 9 days ago

    Not sure how async gem would fit into this. The backbone of Stepped Actions is ActiveJob which handles execution. Where do you think this would fit in?

    • vicentereig 8 days ago

      You’re right they’re different models. The path would be Falcon + async-job-adapter-active_job. I am exploring eliminating worker processes, so jobs run as fibers in the same process, yielding during I/O.

  • reedlaw 10 days ago

    How does DSPy.rb differ from BAML?

    • vicentereig 10 days ago

      Both model prompts as functions. BAML is a DSL - write .baml files, generate code, get validated structured outputs.

      DSPy is a programming paradigm. I like to look at it like the MVC for the Web. You define Signatures[0]: typed contracts governing the relationship between your models and your app. Signatures model prompts as functions too, without leaving Ruby. Then compose them into modules (Predict, ChainOfThought, ReAct, your own). The framework can automatically optimize prompts based on your metrics.

      DSPy.rb brings the DSPy paradigm's tooling (optimizers, evaluation loops) to Ruby. Comes with OpenTelemetry OOTB. It also borrows BAML's schema format for 85% token savings vs JSON Schema in complex signatures. [1]

      Everyone is talking about prompt, context, and harness engineering -and I agree they are good ways to frame how to build workflows and agents- this is just programming really.

      [0] https://oss.vicente.services/dspy.rb/core-concepts/signature...

      [1] https://oss.vicente.services/dspy.rb/articles/baml-schema-fo...

deedubaya 11 days ago

Congratulations on shipping this, I’m sure folks will find it useful!

The rails native way to do this is to track state in a db row and queuing “next step” jobs as the data changes. This can get verbose especially for smaller pass/fail workflows. However, I find this works better (not worse imo) in more complex workflows as the state is tracked, queryable, can be surfaced in UIs, and resumed “manually” in the event of an outage.

sroussey 11 days ago

Nice. I have a simple system for typescript [1] where you can string tasks together like:

import { Workflow } from "@workglow/task-graph"; const workflow = new Workflow(); workflow .DownloadModel({ model: ["onnx:Xenova/LaMini-Flan-T5-783M:q8", "Universal Sentence Encoder"], }) .TextEmbedding({ text: "The quick brown fox jumps over the lazy dog.", }); await workflow.run();

It automatically caches results of steps if you say `new Workflow({outputCache});`

PS: the example above uses a local onnx model (it switches on model name) which is a good candidate for caching, but can be anything.

You can play around writing this way if you open the console at the web example [2] which has fun console formatters not enough people know about or use in DevTools. You can write code in the console and the example rewrites it as a json format in the web page (and visa-versa).

Or just use the free web app with local user account and local models to play around with. [3]

[1] https://github.com/workglow-dev/workglow

[2] https://workglow-web.netlify.app/

[3] https://workglow.dev

chao- 11 days ago

I have implemented (or managed a team that implemented) this concept four separate times as an internal library somewhere. Each one included slightly different affordances and addressed a few different concerns that stem from the domain that it was built for.

Props for extracting it and offering it up as a library. I'll be interested to compare it to the implementations I've seen, and see what you've added that I've not seen before.

silasb 11 days ago

Seems pretty similar to https://github.com/radioactive-labs/chrono_forge which is what I found when I typed in "rails durable execution patterns" into Google. Have you seen this and if so, how do you think it compares?

  • klevoOP 9 days ago

    That looks cool. It's a different approach with different features.

moh_quz 16 days ago

This looks useful. I've been exploring similar durable execution patterns in Go recently to avoid the complexity of Temporal for smaller workflows.

How does stepped_actions handle the state between steps? Does it persist to the DB after every single action to handle crash recovery, or is it more optimistic?

Good luck with the launch

dzonga 11 days ago

the write up was well done - on why the pivot. & who his actual target market is

Keyboard Shortcuts

j
Next item
k
Previous item
o / Enter
Open selected item
?
Show this help
Esc
Close modal / clear selection