📗 That is the sequence on creating internet purposes with generative AI integration. Half 1 targeted on explaining the AI stack and why the appliance layer is one of the best place within the stack to be. Verify it out right here.
Desk of Contents
Introduction
It’s not usually that you simply hear the Ruby language talked about when discussing AI.
Python, in fact, is the king on this world, and for good cause. The neighborhood has coalesced across the language. Most mannequin coaching is finished in PyTorch or TensorFlow lately. Scikit-learn and Keras are additionally highly regarded. RAG frameworks comparable to LangChain and LlamaIndex cater primarily to Python.
Nevertheless, on the subject of constructing internet purposes with AI integration, I imagine Ruby is the higher language.
Because the co-founder of an company devoted to constructing MVPs with generative AI integration, I often hear potential shoppers complaining about two issues:
- Functions take too lengthy to construct
- Builders are quoting insane costs to construct customized internet apps
These complaints have a typical supply: complexity. Fashionable internet apps have much more complexity in them than within the good ol’ days. However why is that this? Are the advantages introduced by complexity price the price?
I assumed spas had been speculated to be enjoyable?
One huge piece of the puzzle is the current rise of single-page purposes (SPAs). The preferred stack used at present in constructing fashionable SPAs is MERN (MongoDB, Categorical.js, React.js, Node.js). The stack is common for just a few causes:
- It’s a JavaScript-only stack, throughout each front-end and back-end. Having to solely code in just one language is fairly good!
- SPAs can provide dynamic designs and a “clean” person expertise. Clean right here implies that when some piece of information adjustments, solely part of the positioning is up to date, versus having to reload the entire web page. In fact, for those who don’t have a contemporary smartphone, SPAs received’t really feel so clean, as they are usually fairly heavy. All that JavaScript begins to pull down the efficiency.
- There’s a massive ecosystem of libraries and builders with expertise on this stack. That is fairly round logic: is the stack common due to the ecosystem, or is there an ecosystem due to the recognition? Both method, this level stands.
React was created by Meta. - Numerous cash and energy has been thrown on the library, serving to to shine and promote the product.
Sadly, there are some downsides of working within the MERN stack, essentially the most important being the sheer complexity.
Conventional internet growth was completed utilizing the Mannequin-View-Controller (MVC) paradigm. In MVC, the entire logic managing a person’s session is dealt with within the backend, on the server. One thing like fetching a person’s knowledge was completed by way of perform calls and SQL statements within the backend. The backend then serves absolutely constructed HTML and CSS to the browser, which simply has to show it. Therefore the title “server”.
In a SPA, this logic is dealt with on the person’s browser, within the frontend. SPAs must deal with UI state, utility state, and typically even server state all within the browser. API calls must be made to the backend to fetch person knowledge. There’s nonetheless fairly a little bit of logic on the backend, primarily exposing knowledge and performance by way of APIs.
As an instance the distinction, let me use the analogy of a business kitchen. The client would be the frontend and the kitchen would be the backend.

Conventional MVC apps are like eating at a full-service restaurant. Sure, there’s plenty of complexity (and yelling, if The Bear is to be believed) within the backend. However the frontend expertise is easy and satisfying: all the client has to do is choose up a fork and eat their meals.
SPAs are like consuming at a buffet-style eating restaurant. There’s nonetheless fairly a little bit of complexity within the kitchen. However now the client additionally has to determine what meals to seize, find out how to mix them, find out how to prepare them on the plate, the place to place the plate when completed, and so forth.
Andrej Karpathy had a tweet not too long ago discussing his frustration with making an attempt to construct internet apps in 2025. It may be overwhelming for these new to the house.
To be able to construct MVPs with AI integration quickly, our company has determined to forgo the SPA and as a substitute go along with the normal MVC method. Particularly, now we have discovered Ruby on Rails (usually denoted as Rails) to be the framework finest suited to shortly creating and deploying high quality apps with AI integration. Ruby on Rails was developed by David Heinemeier Hansson in 2004 and has lengthy been referred to as a fantastic internet framework, however I’d argue it has not too long ago made leaps in its potential to include AI into apps, as we’ll see.
Django is the preferred Python internet framework, and in addition has a extra conventional sample of growth. Sadly, in our testing we discovered Django was merely not as full-featured or “batteries included” as Rails is. As a easy instance, Django has no built-in background job system. Practically all of our apps incorporate background jobs, so to not embody this was disappointing. We additionally desire how Rails emphasizes simplicity, with Rails 8 encouraging builders to simply self-host their apps as a substitute of going by way of a supplier like Heroku. Additionally they not too long ago launched a stack of instruments meant to exchange exterior companies like Redis.
“However what concerning the clean person expertise?” you may ask. The reality is that fashionable Rails contains a number of methods of crafting SPA-like experiences with out the entire heavy JavaScript. The first software is Hotwire, which bundles instruments like Turbo and Stimulus. Turbo helps you to dynamically change items of HTML in your webpage with out writing customized JavaScript. For the occasions the place you do want to incorporate customized JavaScript, Stimulus is a minimal JavaScript framework that permits you to do exactly that. Even if you wish to use React, you are able to do so with the react-rails gem. So you possibly can have your cake, and eat it too!
SPAs aren’t the one cause for the rise in complexity, nonetheless. One other has to do with the appearance of the microservices structure.
Microservices are for Macrocompanies
As soon as once more, we discover ourselves evaluating the easy previous with the complexity of at present.
Previously, software program was primarily developed as monoliths. A monolithic utility implies that all of the totally different components of your app — such because the person interface, enterprise logic, and knowledge dealing with — are developed, examined, and deployed as one single unit. The code is all sometimes housed in a single repo.
Working with a monolith is easy and satisfying. Working a growth setup for testing functions is straightforward. You might be working with a single database schema containing your entire tables, making queries and joins simple. Deployment is easy, because you simply have one container to take a look at and modify.
Nevertheless, as soon as your organization scales to the scale of a Google or Amazon, actual issues start to emerge. With lots of or hundreds of builders contributing concurrently to a single codebase, coordinating adjustments and managing merge conflicts turns into more and more troublesome. Deployments additionally turn out to be extra complicated and dangerous, since even minor adjustments can blow up all the utility!
To handle these points, massive corporations started to coalesce across the microservices structure. This can be a type of programming the place you design your codebase as a set of small, autonomous companies. Every service owns its personal codebase, knowledge storage, and deployment pipelines. As a easy instance, as a substitute of stuffing your entire logic relating to an OpenAI shopper into your fundamental app, you possibly can transfer that logic into its personal service. To name that service, you’ll then sometimes make REST calls, versus perform calls. This ups the complexity, however resolves the merge battle and deployment points, since every group within the group will get to work on their very own island of code.
One other profit to utilizing microservices is that they permit for a polyglot tech stack. Which means that every group can code up their service utilizing no matter language they like. If one group prefers JavaScript whereas one other likes Python, that is no situation. After we first started our company, this concept of a polyglot stack pushed us to make use of a microservices structure. Not as a result of we had a big group, however as a result of we every needed to make use of the “finest” language for every performance. This meant:
- Utilizing Ruby on Rails for internet growth. It’s been battle-tested on this space for many years.
- Utilizing Python for the AI integration, maybe deployed with one thing like FastAPI. Critical AI work requires Python, I used to be led to imagine.
Two totally different languages, every targeted on its space of specialty. What may go incorrect?
Sadly, we discovered the method of growth irritating. Simply establishing our dev setting was time-consuming. Having to wrangle Docker compose information and handle inter-service communication made us want we may return to the sweetness and ease of the monolith. Having to make a REST name and arrange the suitable routing in FastAPI as a substitute of creating a easy perform name sucked.
“Absolutely we will’t develop AI apps in pure Ruby,” I assumed. After which I gave it a strive.
And I’m glad I did.
I discovered the method of creating an MVP with AI integration in Ruby very satisfying. We had been capable of dash the place earlier than we had been jogging. I cherished the emphasis on magnificence, simplicity, and developer happiness within the Ruby neighborhood. And I discovered the state of the AI ecosystem in Ruby to be surprisingly mature and getting higher day by day.
If you’re a Python programmer and are scared off by studying a brand new language like I used to be, let me consolation you by discussing the similarities between the Ruby and Python languages.
Ruby and Python: Two Sides of the Identical Coin
I think about Python and Ruby to be like cousins. Each languages incorporate:
- Excessive-level Interpretation:Â This implies they summary away plenty of the complexity of low-level programming particulars, comparable to reminiscence administration.
- Dynamic Typing:Â Neither language requires you to specify if a variable is anÂ
int
,Âfloat
,Âstring
, and so forth. The kinds are checked at runtime. - Object-Oriented Programming: Each languages are object-oriented. Each help lessons, inheritance, polymorphism, and so forth. Ruby is extra “pure”, within the sense that actually all the pieces is an object, whereas in Python just a few issues (comparable toÂ
if
 andÂfor
 statements) aren’t objects. - Readable and Concise Syntax: Each are thought-about simple to study. Both is nice for a first-time learner.
- Huge Ecosystem of Packages:Â Packages to do all types of cool issues can be found in each languages. In Python they’re referred to as libraries, and in Ruby they’re referred to as gems.
The first distinction between the 2 languages lies of their philosophy and design ideas. Python’s core philosophy could be described as:
There must be one — and ideally just one — apparent option to do one thing.
In principle, this could emphasize simplicity, readability, and readability. Ruby’s philosophy could be described as:
There’s all the time multiple option to do one thing. Maximize developer happiness.
This was a shock to me once I converted from Python. Take a look at this easy instance emphasizing this philosophical distinction:
# A battle over philosophy: iterating over an array
# Pythonic method
for i in vary(1, 6):
print(i)
# Ruby method, choice 1
(1..5).every do |i|
places i
finish
# Ruby method, choice 2
for i in 1..5
places i
finish
# Ruby method, choice 3
5.occasions do |i|
places i + 1
finish
# Ruby method, choice 4
(1..5).every places i
One other distinction between the 2 is syntax type. Python primarily makes use of indentation to indicate code blocks, whereas Ruby makes use of do…finish
 or {…}
 blocks. Most embody indentation inside Ruby blocks, however that is fully elective. Examples of those syntactic variations could be seen within the code proven above.
There are plenty of different little variations to study. For instance, in Python string interpolation is finished utilizing f-strings:Â f"Good day, {title}!"
, whereas in Ruby they’re completed utilizing hashtags:Â "Good day, #{title}!"
. Inside just a few months, I believe any competent Python programmer can switch their proficiency over to Ruby.
Latest AI-based Gems
Regardless of not being within the dialog when discussing AI, Ruby has had some current developments on this planet of gems. I’ll spotlight a few of the most spectacular current releases that now we have been utilizing in our company to construct AI apps:
RubyLLM (hyperlink) — Any GitHub repo that will get greater than 2k stars inside just a few weeks of launch deserves a point out, and RubyLLM is unquestionably worthy. I’ve used many clunky implementations of LLM suppliers from libraries like LangChain and LlamaIndex, so utilizing RubyLLM was like a breath of recent air. As a easy instance, let’s check out a tutorial demonstrating multi-turn conversations:
require 'ruby_llm'
# Create a mannequin and provides it directions
chat = RubyLLM.chat
chat.with_instructions "You're a pleasant Ruby professional who loves to assist freshmen."
# Multi-turn dialog
chat.ask "Hello! What does attr_reader do in Ruby?"
# => "Ruby creates a getter technique for every image...
# Stream responses in actual time
chat.ask "May you give me a brief instance?" do |chunk|
print chunk.content material
finish
# => "Positive!
# ```ruby
# class Particular person
# attr...
Merely wonderful. Multi-turn conversations are dealt with robotically for you. Streaming is a breeze. Examine this to an analogous implementation in LangChain:
from langchain_openai import ChatOpenAI
from langchain_core.schema import SystemMessage, HumanMessage, AIMessage
from langchain_core.callbacks.streaming_stdout import StreamingStdOutCallbackHandler
SYSTEM_PROMPT = "You're a pleasant Ruby professional who loves to assist freshmen."
chat = ChatOpenAI(streaming=True, callbacks=[StreamingStdOutCallbackHandler()])
historical past = [SystemMessage(content=SYSTEM_PROMPT)]
def ask(user_text: str) -> None:
"""Stream the reply token-by-token and hold the context in reminiscence."""
historical past.append(HumanMessage(content material=user_text))
# .stream yields message chunks as they arrive
for chunk in chat.stream(historical past):
print(chunk.content material, finish="", flush=True)
print() # newline after the reply
# the ultimate chunk has the total message content material
historical past.append(AIMessage(content material=chunk.content material))
ask("Hello! What does attr_reader do in Ruby?")
ask("Nice - may you present a brief instance with attr_accessor?")
Yikes. And it’s vital to notice that it is a grug implementation. Need to know the way LangChain actually expects you to handle reminiscence? Verify out these hyperlinks, however seize a bucket first; chances are you’ll get sick.
Neighbors (hyperlink) — This is a superb library to make use of for nearest-neighbors search in a Rails utility. Very helpful in a RAG setup. It integrates with Postgres, SQLite, MySQL, MariaDB, and extra. It was written by Andrew Kane, the identical man who wrote the pgvector extension that permits Postgres to behave as a vector database.
Async (hyperlink) — This gem had its first official launch again in December 2024, and it has been making waves within the Ruby neighborhood. Async is a fiber-based framework for Ruby that runs non-blocking I/O duties concurrently whereas letting you write easy, sequential code. Fibers are like mini-threads that every have their very own mini name stack. Whereas not strictly a gem for AI, it has helped us create options like internet scrapers that run blazingly quick throughout hundreds of pages. We now have additionally used it to deal with streaming of chunks from LLMs.
Torch.rb (hyperlink) — If you’re involved in coaching deep studying fashions, then certainly you’ve heard of PyTorch. Properly, PyTorch is constructed on LibTorch, which primarily has plenty of C/C++ code below the hood to carry out ML operations shortly. Andrew Kane took LibTorch and made a Ruby adapter over it to create Torch.rb, primarily a Ruby model of PyTorch. Andrew Kane has been a hero within the Ruby AI world, authoring dozens of ML gems for Ruby.
Abstract
Briefly: constructing an online utility with AI integration shortly and cheaply requires a monolithic structure. A monolith calls for a monolingual utility, which is critical in case your finish purpose is high quality apps delivered with velocity. Your fundamental choices are both Python or Ruby. Should you go along with Python, you’ll most likely use Django on your internet framework. Should you go along with Ruby, you can be utilizing Ruby on Rails. At our company, we discovered Django’s lack of options disappointing. Rails has impressed us with its function set and emphasis on simplicity. We had been thrilled to search out nearly no points on the AI facet.
In fact, there are occasions the place you’ll not wish to use Ruby. If you’re conducting analysis in AI or coaching machine studying fashions from scratch, then you’ll possible wish to stick to Python. Analysis nearly by no means entails constructing Internet Functions. At most you’ll construct a easy interface or dashboard in a pocket book, however nothing production-ready. You’ll possible need the newest PyTorch updates to make sure your coaching runs shortly. It’s possible you’ll even dive into low-level C/C++ programming to squeeze as a lot efficiency as you possibly can out of your {hardware}. Possibly you’ll even strive your hand at Mojo.
But when your purpose is to combine the newest LLMs — both open or closed supply — into internet purposes, then we imagine Ruby to be the far superior choice. Give it a shot yourselves!
Partly three of this sequence, I’ll dive right into a enjoyable experiment: simply how easy can we make an online utility with AI integration? Keep tuned.
🔥 Should you’d like a customized internet utility with generative AI integration, go to losangelesaiapps.com