Remix.run Logo
dismalaf 6 days ago

> - Rails handles our API, domain logic, and billing workflows.

> - Go powers services that need high I/O concurrency or long-lived network connections.

> - Rust handles CPU-bound jobs.

It's always amazed me than the discourse around dynamic vs. static languages is that you can't have both.

Like, dynamic languages are literally built on a foundation of static, compiled languages. Ruby's source is C and now some Rust.

So just build in Ruby and when you hit a bottleneck, rewrite that bottleneck in C or Rust...

drzaiusx11 6 days ago | parent | next [-]

Many times with JIT you don't even need to drop to a more performant language. You can actually get some speed gains by moving C library code back to Ruby so you don't have to pay the translation costs

dismalaf 6 days ago | parent [-]

True. Ruby JIT has increased performance for some tasks you'd drop down to C for back in the day...

All the gains Ruby has made in the last few years are pretty incredible. I never picked it because of performance reasons but it's pretty nice that it's getting faster.

Either way though, Ruby FFI is super super easy. Just for fun, because of this thread, I spent a whole 2 minutes (lol) linking an Odin (my new low-level hobby language) library to Ruby. Literally all it took. Credit to Odin for having such easy export and Ruby for having such easy FFI.

Alifatisk 5 days ago | parent [-]

> I spent a whole 2 minutes (lol) linking an Odin (my new low-level hobby language) library to Ruby.

Would you mind creating a gist of your steps?

dismalaf 5 days ago | parent [-]

Odin code:

    package main

    import "core:fmt"

    @export
    sayhi :: proc() {
      fmt.println("Hello World")
    }
Key is the "@export" statement. Then build Linux dynamic library by doing "odin build main.odin -file -build-mode:shared". -file flag is since I'm just building a single Odin file, didn't set up a project structure or anything. -build-mode:shared is pretty obvious, there's separate build mode flags for Windows or Mac platforms (called "dll" and "dynamic" I think).

Ruby code:

    require 'ffi'
    module MyLib
      extend FFI::Library
      ffi_lib "./main.so"
      attach_function :sayhi, [], :void
    end

    MyLib.sayhi
That's literally all there is to it. Odin lib is a single file. Ruby code is a single file. Don't even need a project setup since Odin can compile single files into programs or libraries and Ruby can of course link to a shared lib that's anywhere.
Alifatisk 4 days ago | parent [-]

Thank you so much, that was way easier than what I expected, amazing!

SkyPuncher 6 days ago | parent | prev | next [-]

> So just build in Ruby and when you hit a bottleneck, rewrite that bottleneck in C or Rust...

This is basically what we do at my startup. Though, some things we build elsewher from the start, knowing they need language specific tooling (like Python is best for working with LLMs).

You just can't beat the speed at which you can build business logic in Rails. Most features never hit the point of needing actual, raw performance so on 95% of what you build, you get to work incredibly fast. That still makes up for the 5% of features that you rip out and move elsewhere.

dismalaf 6 days ago | parent [-]

> Python is best for working with LLMs

Just curious how you're integrating LLMs... Self hosting?

I've been using RubyLLM and find it pretty decent for my needs, it's also improving at a very rapid rate. But it does focus on the most common providers and tools...

SkyPuncher 5 days ago | parent [-]

Basically, the entire data and language processing world works in Python.

It's not that tools don't exist in other languages. It's that Python has the most readily available tooling. That makes analysis and iteration a lot easier.

dismalaf 4 days ago | parent [-]

> Basically, the entire data and language processing world works in Python.

Dunno, when I started I learned Stata, but it seemed the big open-source thing was R. Python data stuff was in its infancy. R got huge, then Python got huge. Of course all the underlying libraries are C/C++ or Fortran. Everything does exist in Ruby as well.

But hey, I also just hate Python (find it super complicated to set up, their package managers are terrible, plus find the language inconsistent) so I avoid it at all costs. Would much rather Julia become the de-facto standard.

Alifatisk 5 days ago | parent | prev [-]

> So just build in Ruby and when you hit a bottleneck, rewrite that bottleneck in C or Rust

Nowadays, yjit is so good that there is no real reason to use c extensions

maleldil 5 days ago | parent [-]

That's an exaggeration. This can be true in certain cases, but it is not a general rule. YJIT is still orders of magnitude slower than C.