<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>home on luis angel ortega</title><link>https://luisangel.me/</link><description>Recent home on luis angel ortega</description><generator>Hugo</generator><language>en-US</language><managingEditor>hey@luisangel.me (Luis Angel Ortega)</managingEditor><webMaster>hey@luisangel.me (Luis Angel Ortega)</webMaster><copyright>2025 Luis Angel Ortega Holguin All rights reserved</copyright><lastBuildDate>Thu, 14 May 2026 16:53:22 +0000</lastBuildDate><atom:link href="https://luisangel.me/index.xml" rel="self" type="application/rss+xml"/><item><title>Without Warning</title><link>https://luisangel.me/post/2026/05/14/without-warning/</link><pubDate>Thu, 14 May 2026 16:53:22 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/05/14/without-warning/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/42ef8ad6-26cf-405d-ad7a-ce9cb7ffd7d3_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Green and yellow
a light movement
toward the left
to the rhythm of wind
and clouds
 
I have no choice
I become grass
helpless
without warning
 
Our song played
our first dance
as husband and wife
and the weight of the world 
that was
came down on me
hollowness
in my chest
and the feeling
of my soul 
leaving
 
Six.
Control.
Eight.
Breathe.
Six—
 
I clench.
Hard.
It hurts.
I release.
 
A weight.
Goes.
 
The birds fly.
The leaves tremble.
I wish
to become
grass.
&lt;/pre></description></item><item><title>Knowingly</title><link>https://luisangel.me/post/2026/05/04/knowingly/</link><pubDate>Mon, 04 May 2026 16:27:08 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/05/04/knowingly/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/581797ea-4d78-4b21-af95-e9f9e333db5f_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Dried flowers 
						solitude
beer 
				 haze
brown lace 
						 body
a prayer
so as not to drown
in their hazel eyes

a void in me
 anguish
 fear
to be lost
in their hands
only to be left
 behind
&lt;/pre>
&lt;hr>
&lt;p>Statement&lt;/p>
&lt;p>This poem came out of a series of exercises in a surrealist poetry workshop: paintings, collage, automatic writing. Somewhere in that process something more personal surfaced.&lt;/p>
&lt;p>It’s a poem about the rituals we build to protect ourselves, and how sometimes we walk into the fire anyway. The knowing doesn’t make it easier. It just makes it more honest.&lt;/p></description></item><item><title>Times</title><link>https://luisangel.me/post/2026/03/19/times/</link><pubDate>Thu, 19 Mar 2026 17:30:49 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/03/19/times/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/0594eb8b-9fd4-4956-b2a9-655d76ce41bb_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Four cubes
in a glass —
transparent.
Passing.

From the glass
so close
with no way
to reach
the amber horizon
with white crest

Unbidden
a sprig
of chamomile —
the only one
I have received
keeps me company

Dry flowers
stay
with me
drinking
from me

Some day
I will return
to my balance
they will bloom again
and I'll become
my destiny
&lt;/pre>
&lt;hr>
&lt;h2 id="statement">Statement&lt;/h2>
&lt;p>This poem came out of a surrealist poetry workshop. The prompt was simple: write from the perspective of a cup of ice with a beer and a sprig of chamomile nearby.&lt;/p>
&lt;p>I sat with those objects for a while and somewhere in that stillness the ice started feeling familiar. The longing for something just out of reach, a dry chamomile sprig as unexpected company, and the quiet peace of knowing that change is coming, not as loss, but as return.&lt;/p>
&lt;p>The ice knows it’s nothing but a blink of an eye . That’s not the sad part. The sad part is how close the beer is.&lt;/p></description></item><item><title>Lilac (for Rita)</title><link>https://luisangel.me/post/2026/02/10/lilac-for-rita/</link><pubDate>Tue, 10 Feb 2026 17:31:16 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/02/10/lilac-for-rita/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/304248a1-7d54-4167-803a-6f76fcc43d12_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
six-thirty, 
the sky splits—
pale yellow
where the sun falls, 
blue
above my head. 
The greenest park 
in the city,
tall pines 
that never lose their needles, 
a sycamore
that keeps its bark.
And this lilac, 
alone among so much
that stays,
leafless,
full of seed pods—
yellow-brown,
clustered at the crown
where I cannot reach them.

My grandmother's lilac 
was the center of her patio. 
After she died, 
someone said it brought bad luck. 

They cut it down.

I don't remember when I stopped
seeing lilacs. 
Until recently—
I picked a seed from the ground,
carried it in my pocket
like I did as a boy.

Now I stand 
beneath this tree
without leaves, 
in the greenest park,
looking up 
at what I cannot touch.
The seed pod still in my pocket—
small, 
dry, 
impossible to lose.
&lt;/pre></description></item><item><title>January in Poetry</title><link>https://luisangel.me/post/2026/02/08/january-in-poetry/</link><pubDate>Sun, 08 Feb 2026 19:30:34 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/02/08/january-in-poetry/</guid><description>&lt;p>I went out for a walk this morning looking for a tree. Not just any tree, but one that would tell me something, that would give me permission to write the day’s poem. I’ve done this several times in January, at least once a week, sometimes more. Sometimes I find the tree, sometimes the insects find me, the sky, the air moving through the branches. Chihuahua has become strange to me, or perhaps I’ve become strange in it: now I know where the desert trees are, which ones are in bloom, which ones just endure.&lt;/p>
&lt;p>January has been a month of exercise. Not in the poetic, elevated sense of the word, but in the literal sense: something that must be done, a muscle that must be flexed even when I don’t always want to. Some days the poem turns out interesting. Other days it just comes out and that’s it. But it comes out, and that’s what matters in this experiment I imposed on myself without really knowing where it was going.&lt;/p>
&lt;p>What I didn’t expect was how much making it public would change things. I publish each poem knowing someone might read it, and that forces me to be more careful, to refine, to ask myself if I really want this out there. I’ve discovered that I have poems saved up, poems I wrote in January but don’t feel ready to share. Not because they’re bad, I don’t know yet, but because they touch something too recent, too raw. They’re private in a way I can’t fully explain. I’m surprised that other poems, on the other hand, cost me nothing to release into the world. I don’t know what that says about me, but there’s something.&lt;/p>
&lt;p>Nature became my muse without me consciously deciding it. I suppose that’s what happens when you go out looking for poems regularly: you start paying attention to what’s there, to what was always there but you’d never seen. I’ve fallen in love with trees, with insects, with the sound of wind in the afternoon. I know my city in a new way, more intimately. I know where certain trees grow, how many there are, how common they are. Before, I walked through Chihuahua thinking about other things, listening to podcast or music maybe, now I walk to see.&lt;/p>
&lt;p>But beneath the trees and insects there’s something else. There’s a subtext running through many of these poems, a reflection of what’s going on in my mind, personal games that only I fully understand. Some more obvious than others. It’s curious how nature can become metaphor without you intending it, how writing about a tree can be writing about oneself.&lt;/p>
&lt;p>I don’t know if these are good poems. Time will tell, I suppose. What I do know is that January taught me something about sustaining a creative commitment, about going out to look even when I don’t feel like it, about making vulnerability public even when it’s uncomfortable. It taught me that poetry can be an exercise and still be genuine, that I can experiment and refine at the same time, that knowing my city is a way of knowing myself.&lt;/p>
&lt;p>Now it’s February. The muscle is a bit stronger. The trees are still there, waiting.&lt;/p>
&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/45b50165-f99e-4fa0-ba1c-9573b02d6e19_3024x3024.jpeg" alt="">&lt;/p></description></item><item><title>Drywall wall</title><link>https://luisangel.me/post/2026/02/05/drywall-wall/</link><pubDate>Thu, 05 Feb 2026 19:32:12 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/02/05/drywall-wall/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/ea37a4e9-c181-4be8-82b2-3a613552b120_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
A drywall wall
in a new construction,
at that hour:
a perfect shadow appeared.

The last worker
saw it with something like devotion
or sadness
for a few extended seconds.

He placed his sanding disc
in the sight of the sun,
then the putty knife behind the disc,
and turned them slowly
to resemble the shadow.

The man believed he was approaching the form
because his adjustments were minimal.

There is no one nearby,
and I still have distance to travel.
I wish I could stay here
until the sun goes down
&lt;/pre>
&lt;hr>
&lt;p>This is an amazing poem by , another poet from the north of México. Baltazar and I decided to collaborate publishing a poem from each other in our publication so it can reach a new, bigger hopefully, public.&lt;/p>
&lt;p>In this work Baltazar approaches the cotidianity of the worksite with the beauty that it may come from nature, the light, or the human-made tools. He reminds us again that the beauty is in the every day, in the moment of now. In all of us and in everywhere.&lt;/p>
&lt;p>Make sure to check , Baltazar’s publication for more poems, micro-fictions and non fiction articles!&lt;/p></description></item><item><title>January</title><link>https://luisangel.me/post/2026/02/03/january/</link><pubDate>Tue, 03 Feb 2026 17:31:02 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/02/03/january/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/3ddb9baf-17a4-456b-9204-032a576c9a5e_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
A cafe
warm in January
too loud to think

outside
in the shadow of buildings
a breeze

green plastic leaves
brown dead leaves

the murmur inside
music, chatter

my ears hot
my drink cold

I chose cold
wanted warm
&lt;/pre></description></item><item><title>Desire Path</title><link>https://luisangel.me/post/2026/01/29/desire-path/</link><pubDate>Thu, 29 Jan 2026 17:30:51 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/01/29/desire-path/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/ce872f40-382d-4d93-b0af-080f69b4a525_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Beside
the busy road
through dry grass
crossing an empty lot
there is a path
marked by hundreds of shoes
no sidewalks
surrounded by cars
the asphalt steams under the sun
the only way to cross
&lt;/pre></description></item><item><title>Kiosk</title><link>https://luisangel.me/post/2026/01/22/kiosk/</link><pubDate>Thu, 22 Jan 2026 17:30:46 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/01/22/kiosk/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/593409cb-861d-44e8-aba9-c961ea90aea9_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
At the center of the park
like many in the city
there is a kiosk:
sheet metal roof
failed Mediterranean architecture
colorful paint
political images on the metal

Castle for children
shelter for adolescents
shade for adults
refuge for poets

So universal
I forgot to stop
to remember how important they are
&lt;/pre></description></item><item><title>Agave</title><link>https://luisangel.me/post/2026/01/20/agave/</link><pubDate>Tue, 20 Jan 2026 17:41:19 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/01/20/agave/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/f613d29b-7571-4978-8c07-e40f9dbf0d95_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Midday—
a clear day,
almost warm for winter.
Under an oak's shade
an agave is rooted.

Pale green in the sun,
dark green in the shade—
yellow stripes, thorns
along each blade.

Tall as I am,
surrounded by dry grass
and untended trees,
an empty park,
the silence of early afternoon.

I approach carelessly—
the thorns cut me.
This neglected park
where everything seems to wither,
but the agave remains.

Blades marked by years,
roots deeper
than the dry grass around it—
as ancient as the oak
that gives it shade.
&lt;/pre></description></item><item><title>Sycamore</title><link>https://luisangel.me/post/2026/01/13/sycamore/</link><pubDate>Tue, 13 Jan 2026 19:37:53 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/01/13/sycamore/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/6b8fdaba-ba9c-400b-bfdb-69ebdd7cea50_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
The sun falls behind the sycamore
barely enough light—
I sit and watch.

Its leaves,
yellow and brown, lie
while some green still
cling to branches.

Its brown bark peels
to the left, a white
then cream
to the right, yellow—
anyone can tear off a piece.
&lt;/pre></description></item><item><title>Migraine</title><link>https://luisangel.me/post/2026/01/07/migraine/</link><pubDate>Wed, 07 Jan 2026 17:35:46 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/01/07/migraine/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/62f856c4-6a25-4dfb-8116-afdd201e3c0a_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Mulberry leaves
against the rust sky—
each one too bright,
spinning

Static hum
where silence should be
electric, unrelenting

Reclined in the car seat
jaw clenched
holding back
what wants to rise

The taste of metal
spreads

The only word
left:
pain
&lt;/pre></description></item><item><title>London Fog</title><link>https://luisangel.me/post/2026/01/05/london-fog/</link><pubDate>Mon, 05 Jan 2026 17:35:21 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/01/05/london-fog/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/47e28005-1d39-4ada-8ca1-3b2782739917_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
On a corner,
a café
at the street's edge,
under yellow lights,
plywood walls
fake white brick.
In front of the olive-green chair
sits:
glass straw,
cup full of ice
cold to the touch.

The taste of tea
has been lost
in the cream color
of oat milk.

Lavender and vanilla
upfront, unmistakable,
settle on the sides of the tongue
while Earl Grey hides
at the back of the palate.
&lt;/pre></description></item><item><title>Rosemary</title><link>https://luisangel.me/post/2026/01/02/rosemary/</link><pubDate>Fri, 02 Jan 2026 17:35:25 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2026/01/02/rosemary/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/47aec295-db56-475d-8276-1f32b83c27c5_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
I see you across the table—
sprigs of rosemary
decorating everyone's drinks,
adorning some dishes.
Ever festive,
your unique herbal scent.
Evergreen branches
from some shrub
of unknown origin,
perfuming this night's gathering.
&lt;/pre></description></item><item><title>Ocotillo</title><link>https://luisangel.me/post/2025/12/09/ocotillo/</link><pubDate>Tue, 09 Dec 2025 18:53:21 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/12/09/ocotillo/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/c117badd-a2c3-4cfb-a664-7b56621851e3_1280x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Next to the street
gray fingers
rise from the ground
passing the white wall
where some lean

Gray, with green lights
of porous wood, fragile perhaps—
short thorns prevent confirming it,
they run along each branch
&lt;/pre></description></item><item><title>6:45</title><link>https://luisangel.me/post/2025/12/08/645/</link><pubDate>Mon, 08 Dec 2025 23:42:51 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/12/08/645/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/204a9e53-7936-4397-a07d-5ac2e4daa0c8_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
A yellow and orange crown
behind the hills
a layer of mist
halfway up them —
birdsong
cold smells of grass
gray and blue colors
filling my lungs —
children cross the park
on their way to school —
&lt;/pre></description></item><item><title>Roof Shadows</title><link>https://luisangel.me/post/2025/12/07/roof-shadows/</link><pubDate>Sun, 07 Dec 2025 17:07:39 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/12/07/roof-shadows/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/cda3a3cf-f65b-4947-884a-249dcaff5ba7_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Always watching you
up on the roof,
on the lights,
following you through the park.

Coming and going
you sing, announce yourself.

Though only from afar
you let me observe you.

Masters of song,
of that blue-black plumage,
fighting for territory
and their own.

At home with you—
wingspan of 30 centimeters,
black eyes
watching over the neighborhood.
&lt;/pre></description></item><item><title>First Cold</title><link>https://luisangel.me/post/2025/12/06/first-cold/</link><pubDate>Sat, 06 Dec 2025 17:30:51 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/12/06/first-cold/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/290139d3-dd36-413e-b2b7-e5dd97cd5461_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Through my window
crowning the hills
a thin fog—
scent of woodsmoke

A gray mantle
where blue once reigned
silencing everything

No rain.
No snow.

Only cold
and my hands against the glass
&lt;/pre></description></item><item><title>The Wounded Bird</title><link>https://luisangel.me/post/2025/12/04/the-wounded-bird/</link><pubDate>Thu, 04 Dec 2025 21:55:45 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/12/04/the-wounded-bird/</guid><description>&lt;p>&lt;img src="https://substack-post-media.s3.amazonaws.com/public/images/98e18c5e-d959-4476-9911-e471b8e7950f_1600x1600.jpeg" alt="">&lt;/p>
&lt;pre>
Yesterday while walking
I found a bird
it was hurt, fallen and helpless—
I should have helped it.

Cold.
 Fear.
 Death.
I could have spared it that.

I don’t have the courage to return,
I don’t want to see the body,
and know that I could have prevented it—
to change the future

How many things slip by
from having our hands full
our heads crowded
How many could we save?
&lt;/pre></description></item><item><title>The lack of joy in the era of generative artificial intelligence</title><link>https://luisangel.me/post/2025/10/03/lack-of-joy-with-ai/</link><pubDate>Fri, 03 Oct 2025 17:00:00 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/10/03/lack-of-joy-with-ai/</guid><description>&lt;p>Recently I was remembering the famous painter Bob Ross&amp;rsquo;s program: &lt;em>The Joy of Painting&lt;/em>. For 30 to 40 minutes, Bob taught us step by step how to turn a blank canvas into a work of art. Along the way he reminded us that it&amp;rsquo;s okay to make mistakes and that anyone, if they wanted to, could follow his steps and create the same artwork. This American program was broadcast on public television channels in that country, and on Reddit there are testimonials from people who did manage to recreate these paintings, proving that Ross was right when he said &amp;ldquo;imperfection is what makes something beautiful, that&amp;rsquo;s what makes it different and unique from everything else.&amp;rdquo;&lt;/p>
&lt;p>I&amp;rsquo;ve rarely tried to paint, but I related this feeling to programming. It took me three years of college to find my taste for it, but as time went on I began to find topics that passionate me and to appreciate other people&amp;rsquo;s code: seeing the way someone solved something particular after spending a couple of hours reading code in their repository, the difference between libraries that solve the same problem and, of course, seeing something I had created after hours being used by other people.&lt;/p>
&lt;p>At the same time this was happening, I was given the opportunity to be a mentor in a high school robotics club. This consisted, mostly, of teaching the fundamentals of programming with Java and using the libraries the robot needed. That was my first experience in front of a group, I had no idea how to teach a class so the first sessions were just presenting a topic, just like in university. The problem is that due to their age, and the time I had to teach the class, I couldn&amp;rsquo;t maintain their interest and those who paid attention to me didn&amp;rsquo;t quite understand the topic. Looking for a way to communicate with them, to speak the same language, I realized that a love for anime was the common denominator among all of us in that classroom. So I began to change technical terms or generic exercises for examples related to anime: the exercise to practice conditionals went from being a grading system to a &lt;em>simplified dating simulator&lt;/em>. Objects went from being cars or animals to character archetypes in anime. With this I managed to connect with them and they managed to learn what I wanted to teach them. This planted the seed of wanting to teach.&lt;/p>
&lt;p>Several years after graduating with my bachelor&amp;rsquo;s degree, I had the opportunity to teach a subject for the same program I had graduated from, a former professor (now colleague) of mine had recommended me for it. I gladly accepted and began teaching in the same way I had done with the robotics club: as best I could. With this group I found the common language differently, giving them the opportunity to express themselves uncensored in front of me and offering them my advice in the academic and work environment. That semester I was among the ten best-rated professors in the Engineering Coordination, so this year I started my master&amp;rsquo;s degree in education, with a focus on online education. I was sure that, while it wouldn&amp;rsquo;t be my full-time job, I had been wanting to teach for years. Now we&amp;rsquo;re mid-semester with the second group I&amp;rsquo;m teaching this subject to but things couldn&amp;rsquo;t be more different.&lt;/p>
&lt;p>In one year, the artificial intelligence landscape has advanced a lot. A whole lot. Both technically, with more models, larger and more tools to use them, and in people&amp;rsquo;s confidence with them. A year ago, at work, I used to use &lt;em>some&lt;/em> LLM to get me out of some doubt, solve an error or create a small block of code. Now, the same company gives us tools so that, with the right ticket, we just give the instruction to the chatbot and supervise it while it solves the ticket in its entirety. Outside of work, I implemented a &lt;em>script&lt;/em> to update the &amp;ldquo;latest reads&amp;rdquo; section of the blog according to my Raindrop account. I went from idea to execution in an hour, but I didn&amp;rsquo;t feel any sense of accomplishment for having done it.&lt;/p>
&lt;p>My students now use some form of generative artificial intelligence in all the assignments and projects in the class. The exercises (designed to make them reflect, research a topic or learn to use a tool) go: from the school platform to a chatbot and back to the platform. You can rarely see that the students did most of the work, most just read the response that the models generated for them. Some don&amp;rsquo;t read it, they just copy, paste and, if they have to present it, they read the slides.&lt;/p>
&lt;p>At work, used the right way, artificial intelligence is more efficient for me and for the company. It gives me a better work-life balance. In the same way, why wouldn&amp;rsquo;t my students use it in class? They turn in what I ask for, they solve the problems and before the exam they study enough to pass. The only thing left out of the equation is the joy I felt for teaching. This semester, I&amp;rsquo;ve rarely felt it, and, on those occasions, it was with activities precisely designed so that students couldn&amp;rsquo;t use any LLM. But those activities are difficult to conceptualize, especially in this area.&lt;/p>
&lt;p>I don&amp;rsquo;t know if it&amp;rsquo;s my failure as a teacher, for not trying hard enough. I don&amp;rsquo;t know if it&amp;rsquo;s lack of knowledge. In the master&amp;rsquo;s program, I&amp;rsquo;ve understood that it&amp;rsquo;s necessary to learn how to teach. I don&amp;rsquo;t know if my students shouldn&amp;rsquo;t use artificial intelligence in school, since it&amp;rsquo;s something they&amp;rsquo;re going to have to use in the workplace or they&amp;rsquo;ll be at a disadvantage. I don&amp;rsquo;t know if it&amp;rsquo;s the system, which has to be reformed in the face of a paradigm shift. The only thing I know is that I no longer feel the joy for programming or for teaching. There are no longer, as Bob Ross said, mistakes that are just happy accidents.&lt;/p>
&lt;blockquote>
&lt;p>Originally published on &lt;a href="https://eltelar.xyz/blog/falta-alegria-con-la-ia/">El telar&lt;/a> blog&lt;/p>
&lt;/blockquote></description></item><item><title>Who are we digitalizing education for? An urgent call for accessibility</title><link>https://luisangel.me/post/2025/06/26/digitalizing-education/</link><pubDate>Thu, 26 Jun 2025 17:00:00 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/06/26/digitalizing-education/</guid><description>&lt;p>For more than two decades, talking about digital transformation in education has become almost mandatory. Investments are made in platforms, new methodologies are promoted, and technological advances in classrooms are celebrated. But there&amp;rsquo;s a question that is rarely asked clearly: &lt;strong>Who are we digitalizing for?&lt;/strong>&lt;/p>
&lt;p>The enthusiasm for innovation has left out an essential element: accessibility. It&amp;rsquo;s not just about whether a person has internet, but whether they can use, understand, and benefit from the available educational tools from their context. And in Mexico, that context is usually a mid-range cell phone, an intermittent mobile connection, and the absence of a computer at home.&lt;/p>
&lt;p>According to INEGI data (2024), &lt;strong>more than 97% of internet users in the country connect from their cell phone&lt;/strong>, while &lt;strong>less than 44% of households have a computer&lt;/strong>. Additionally, the average mobile connection speed —25 Mbps— is barely sufficient for basic browsing, not for heavy platforms full of animations, embedded videos, and unnecessary visual load.&lt;/p>
&lt;p>Despite this reality, we continue to promote platforms that are not designed for that majority. Tools like Genially, Canva, or even Moodle with heavy themes become an obstacle for many students. Not due to lack of interest, but because they simply &lt;strong>don&amp;rsquo;t load&lt;/strong> or overwhelm the device. The message is clear: if you don&amp;rsquo;t have the right hardware or connection, you&amp;rsquo;re out.&lt;/p>
&lt;p>This isn&amp;rsquo;t about rejecting technology. It&amp;rsquo;s about demanding that it be designed from the perspective of the real user and not from the desktop of the designer or decision-maker. An educational platform that doesn&amp;rsquo;t work offline, that doesn&amp;rsquo;t adapt to small screens, or that requires expensive equipment &lt;strong>is not designed to include, but to exclude&lt;/strong>.&lt;/p>
&lt;p>Teachers, administrators, and developers must understand that digital transformation is not synonymous with sophistication or aesthetics. It&amp;rsquo;s an opportunity to do things better, to close gaps, not to open new ones. Betting on lightweight sites, responsive design, open standards, and free software is not just a technical decision: &lt;strong>it&amp;rsquo;s an ethical and pedagogical stance&lt;/strong>.&lt;/p>
&lt;p>In a country with such social and technological diversity, it&amp;rsquo;s not enough to offer access. We must think about real, daily, situated use. As long as we don&amp;rsquo;t take digital accessibility seriously, any attempt at inclusion will be just an empty promise. And the gap, far from closing, will continue to grow&amp;hellip; loading slowly.&lt;/p>
&lt;hr>
&lt;h3 id="references">References&lt;/h3>
&lt;ul>
&lt;li>
&lt;p>Covarrubias Hernández, L. Y. (2021). &lt;em>Distance education: transformation of learning&lt;/em>. &lt;em>Telos: Journal of Interdisciplinary Studies in Social Sciences&lt;/em>. Retrieved from Gale database: Academic Report &lt;a href="https://doi.org/10.36390/telos231.12">https://doi.org/10.36390/telos231.12&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>Fernández-Enguita, M. (2023). &lt;em>The fifth wave: the digital transformation of learning, education and school&lt;/em>. Ediciones Morata, S. L. Retrieved from eLibro Cátedra database &lt;a href="https://elibro.net/es/lc/bibliotecauveg/titulos/232678">https://elibro.net/es/lc/bibliotecauveg/titulos/232678&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>National Institute of Statistics and Geography. (2025, May 6). &lt;em>National Survey on Availability and Use of Information Technologies in Households (ENDUTIH) 2024: Main results&lt;/em>. &lt;a href="https://www.inegi.org.mx/programas/endutih/2024/">https://www.inegi.org.mx/programas/endutih/2024/&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>Speedtest by Ookla. (2024). &lt;em>Speedtest Global Index – Mexico&lt;/em>. &lt;a href="https://www.speedtest.net/global-index/mexico">https://www.speedtest.net/global-index/mexico&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>The Competitive Intelligence Unit. (2024). &lt;em>Smartphone market in Mexico, Q1-2024&lt;/em>. &lt;a href="https://www.theciu.com/publicaciones-analisis/2024/03/smartphones-en-mexico-1T-2024">https://www.theciu.com/publicaciones-analisis/2024/03/smartphones-en-mexico-1T-2024&lt;/a>&lt;/p>
&lt;/li>
&lt;/ul>
&lt;blockquote>
&lt;p>Originally published on &lt;a href="https://eltelar.xyz/blog/para-quien-estamos-digitalizando-la-educacion/">El telar&lt;/a> blog&lt;/p>
&lt;/blockquote></description></item><item><title>Report: Project Hail Mary by Andy Weir</title><link>https://luisangel.me/post/2025/02/05/project-hail-mary/</link><pubDate>Wed, 05 Feb 2025 17:00:00 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2025/02/05/project-hail-mary/</guid><description>&lt;p>Some time ago, I finished &lt;em>Project Hail Mary&lt;/em> by Andy Weir, and I felt like writing about it.&lt;/p>
&lt;p>The premise is simple: a man wakes up on a spaceship with no memory of who he is or what he’s doing there. He’s alone, his crewmates are dead, and little by little, he realizes that his mission is to save humanity. The story follows a progressive discovery format, where both the character and the reader figure things out together. Amnesia as a narrative device can be a cliché if used poorly, but here it works because it gives the story a really engaging pace.&lt;/p>
&lt;p>One thing I really liked is that the protagonist isn’t your typical sci-fi hero. He’s not the brave, perfect astronaut who already knows everything. He’s just a regular guy facing an extraordinary situation with the only thing he has—his scientific knowledge. It reminded me a lot of The Martian (well, I’ve only seen the movie, but it feels like the same kind of protagonist). This is sci-fi that doesn’t try to be overly philosophical or groundbreaking; it just wants to entertain you and make everything feel like it could be possible.&lt;/p>
&lt;p>When it comes to the science, Andy Weir has an impressive ability to explain complex concepts without making them feel heavy. It’s not hard sci-fi in the traditional sense, but there’s enough technical detail to make everything seem realistic. From the problem threatening humanity to the space travel solutions and the way the protagonist overcomes each obstacle, everything is packed with scientific explanations that make the story feel believable without making you feel like you’re sitting in a physics lecture.&lt;/p>
&lt;p>There’s also an interesting twist in the plot that I don’t want to spoil too much, but it involves the discovery of a new form of intelligent life. What I liked is that it’s not the typical humanoid alien you can communicate with right away. The way that relationship develops is one of the book’s strongest aspects and adds an extra layer of originality.&lt;/p>
&lt;p>If I had to mention something that might not work for everyone, it’s the protagonist. Not everyone is going to like him. He has a lot of energy, a lot of internal monologue, and a sense of humor that might feel repetitive if you don’t click with it. It didn’t bother me, but I can see how it might not be for everyone.&lt;/p>
&lt;p>I don’t think the book has a particularly deep message. It’s not one of those stories that make you question existence or rethink the future of humanity. It does touch on themes like global cooperation, the importance of science, and sacrifice, but never in a very profound way. And I don’t think that’s a problem. Not every book has to change your life—some just need to be fun.&lt;/p>
&lt;p>As for who I’d recommend it to, I think it’s perfect for someone who enjoys sci-fi but doesn’t want to dive into something as dense as Foundation or Dune. It’s a fast-paced, easy-to-read book with solid science and a gripping rhythm. If you like stories that include a lot of scientific explanations but don’t feel like a technical manual, this book is for you. On the other hand, if you find detailed scientific explanations boring, this might not be the best choice, since Andy Weir dedicates a lot of space to breaking down how things work.&lt;/p>
&lt;p>I’d definitely read it again. Not because it has hidden mysteries that require a second read, but simply because I enjoyed it enough to want to relive the experience in a few years when I’ve forgotten some details. It also made me want to read &lt;em>The Martian&lt;/em> and &lt;em>Artemis&lt;/em>, so those are probably next on my list.&lt;/p></description></item><item><title>Goodbye Nextra, hello Hugo</title><link>https://luisangel.me/post/2024/07/31/goodbye-nextra-hello-hugo/</link><pubDate>Wed, 31 Jul 2024 17:00:00 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2024/07/31/goodbye-nextra-hello-hugo/</guid><description>&lt;p>This blog has been abandoned for years at this point. Since I stopped writing on &lt;a href="https://aviyel.com">Aviyel&lt;/a>, I haven’t done anything very technical, and for more personal writings, I&amp;rsquo;ve been advised not to publish them online as freely as I used to, because some submissions consider a story &amp;ldquo;published&amp;rdquo; if it’s available on a website.&lt;/p>
&lt;p>That doesn&amp;rsquo;t mean I&amp;rsquo;ve lost interest in the topic during these years; quite the opposite. Thanks to Hacker News and Mastodon, I’ve discovered a bunch of blogs that I love and that have inspired me for the next stage of my own.&lt;/p>
&lt;h2 id="the-big-static-site-generator-change">The Big Static Site Generator Change&lt;/h2>
&lt;p>Previously, my website used &lt;a href="https://github.com/shuding/nextra">Nextra&lt;/a> and was hosted on &lt;a href="https://vercel.com/">Vercel&lt;/a>. Honestly, this combo made development and deployment very easy, as well as adding my custom domain. But since I adopted Nextra in a very early stage, customization was minimal. Now it seems more focused on project documentation pages, and the style can be changed through &lt;a href="https://tailwindcss.com/">Tailwind&lt;/a> helpers.&lt;/p>
&lt;p>Even so, during my inactive time, I came across Hugo and started playing around with it. I created several test projects with different themes and goals as practice, and while Hugo has many advantages in terms of speed for generating the website thanks to being built in Go, what caught my attention was the number of pre-made themes and how easy they are to customize. From simple things like colors or other styles via a CSS file to being able to modify essential parts of the theme like headers, the navbar, and the RSS feed. I finally settled on the &lt;a href="https://github.com/goodroot/hugo-classic">hugo-classic&lt;/a> theme with modifications to everything mentioned above.&lt;/p>
&lt;p>For hosting, I switched from Vercel to GitHub Pages for the convenience of having everything related to the blog in one place. The domain migration wasn&amp;rsquo;t complex but had its details—nothing that deleting all the records in &lt;a href="https://porkbun.com/">Porkbun&lt;/a> and adding them again couldn’t fix. On the other hand, deployment was more complex. Hugo has a &lt;a href="https://gohugo.io/hosting-and-deployment/hosting-on-github/#prose">guide&lt;/a> in its documentation on how to deploy through an action, but in my opinion, it&amp;rsquo;s incomplete. It misses things like ensuring to include the git submodule if using a theme, among other small tweaks you might need. As of writing this, the site is free of these types of errors, although there are still some style issues on mobile screens.&lt;/p>
&lt;p>Overall, despite the multiple attempts it took to get the site up correctly, I’m very happy with the new setup and recommend it to anyone thinking of following this path.&lt;/p>
&lt;h2 id="the-new-blog-organization-and-philosophy">The New Blog Organization and Philosophy&lt;/h2>
&lt;p>When I first created the website, I didn’t have much experience reading or following other people’s blogs, so I structured it as best I could. Now things have changed; I know what I like and don’t like, what and how to share.&lt;/p>
&lt;p>For now, the layout of the pages will be as follows. Since the main focus of the site is as a blog, the most extensive section will be the writings. Although the RSS feed will group all posts in one place, I didn’t want them to live like that on the site. Blogposts will be for these types of things—simply writings into the void of the internet. Articles are for guides and more technical stuff. Reviews are for writing about movies, books, games, etc. Finally, Works are for my published pieces, though at the moment there’s only one, I hope it will be one of the most extensive.&lt;/p>
&lt;p>Outside of the writings, Projects is a showcase of my work, like a small CV of my online footprint. About Me is, well, a short biography, and finally, The Garden is something strange and complex, but basically, it’s where everything else lives. Honestly, it’s the best section.&lt;/p>
&lt;p>In the index, I also list what I’m “doing”—what I’m playing, reading, listening to, and watching. It’s just a way to share what I’m passionate about at the moment, with the hope that many of those bullet points will turn into reviews. It also has my latest readings, articles that I find interesting to share and/or comment on.&lt;/p>
&lt;p>As for the blog’s philosophy, specifically with the &amp;ldquo;blogposts,&amp;rdquo; I want to write more. I want to capture the spirit of the blogs I follow with how they share things, without necessarily writing essays or technical guides. I’d also like to write more reviews, share my notes, my favorite quotes. Stop consuming without thinking.&lt;/p>
&lt;p>In summary, I want the page to be an excuse to keep writing and sharing.&lt;/p>
&lt;h2 id="the-difference-with-social-media">The Difference with Social Media&lt;/h2>
&lt;p>Finally, I’m doing this because I no longer enjoy social media as much as I used to. What was once Twitter has fragmented, Facebook and Instagram have a horrible feed full of ads. Really, where I spend my time now is YouTube and TikTok.&lt;/p>
&lt;p>Besides the fact that it’s just not the same anymore, knowing that all my contacts see what I publish in their feed has made me hesitant to post. Here, it’s still public; I can keep sharing the things I’m passionate about without the certainty that everyone will see it. Everyone &lt;em>can&lt;/em> see it, but no one is forced to.&lt;/p>
&lt;p>This post was just to share these thoughts, document the change this page has gone through—a rant and monologue into the air. I don’t have a real conclusion, so I’ll leave it at that.&lt;/p></description></item><item><title>latest reads</title><link>https://luisangel.me/garden/latest-reads/</link><pubDate>Fri, 24 May 2024 12:26:36 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/garden/latest-reads/</guid><description>&lt;ul>
&lt;li>
&lt;p>(01/10/25) &lt;a href="https://www.theguardian.com/lifeandstyle/2025/oct/01/artificial-intelligence-em-dashes-ai-stealing-my-livelihood">My petty gripe: not only am I losing my livelihood to AI – now it’s stealing my em dashes too&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(01/10/25) &lt;a href="https://www.wallpaper.com/design-interiors/booker-prize-2025-longlist-writers-desks">This is where The Booker Prize nominees write: from kitchen tables to a cemetery bench&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(30/09/25) &lt;a href="https://www.joanwestenberg.com/p/remember-kurt-vonnegut-was-47">Remember: Kurt Vonnegut was 47&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(30/09/25) &lt;a href="https://literalmagazine.com/cuentos-imprescindibles-del-siglo-xx-de-america-latina/">Cuentos imprescindibles del siglo XX de América Latina - Literal Magazine&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(24/09/25) &lt;a href="https://cjauvin.github.io/posts/learning-persian/">Learning Persian with Anki, ChatGPT and YouTube&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(18/09/25) &lt;a href="https://kokada.dev/blog/kde-is-now-my-favorite-desktop/">KDE is now my favorite desktop — kokada&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(17/09/25) &lt;a href="https://jriddell.org/2025/09/14/adios-chicos-25-years-of-kde/">Adios Chicos, 25 Years of KDE – Jonathan Riddell&amp;rsquo;s Diary&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(17/09/25) &lt;a href="https://herman.bearblog.dev/slow-social-media/">Slow social media&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(17/09/25) &lt;a href="https://www.sfgate.com/tech/article/bay-area-tech-scene-dorky-now-terrifying-21042943.php">The old SF tech scene is dead. What it&amp;rsquo;s morphing into is far more sinister.&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(17/09/25) &lt;a href="https://www.bbc.com/news/articles/c1lelqg0jy3o">What happened when teens tried out tech-free bedrooms?&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(09/09/25) &lt;a href="https://www.xipu.li/posts/the-last-programmers">The Last Programmers ｜｜ Xipu Li&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(18/08/25) &lt;a href="https://ofdollarsanddata.com/its-the-housing-stupid/">It&amp;rsquo;s the Housing, Stupid&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(18/08/25) &lt;a href="https://xeiaso.net/blog/2025/who-assistant-serve/">Who does your assistant serve?&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(18/08/25) &lt;a href="https://buttondown.com/hillelwayne/archive/why-i-prefer-rst-to-markdown/">Why I prefer rST to markdown&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(14/08/25) &lt;a href="https://teejeetech.com/2025/08/14/debian_13_tips/">Optimizing Your Debian 13 Desktop&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(08/08/25) &lt;a href="https://bytemash.net/posts/i-went-down-the-linear-rabbit-hole/">Linear sent me down a local-first rabbit hole ｜ Bytemash&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(22/07/25) &lt;a href="https://sophiebits.com/2025/07/21/todos-arent-for-doing">TODOs aren&amp;rsquo;t for doing – Sophie Alpert&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(22/07/25) &lt;a href="https://kau.sh/blog/how-to-firefox/#fnref:2">🦊 How to Firefox - Kaushik Gopal&amp;rsquo;s Website&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(21/07/25) &lt;a href="https://yberreby.com/posts/i-used-arch-btw-macos-day-1/">I Used Arch, BTW: macOS, Day 1 - @yberreby&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(21/07/25) &lt;a href="https://hamy.xyz/blog/2024-02_htmx-for-side-projects">Why you should choose HTMX for your next web-based side project - and ditch the crufty MPA and complex SPA&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(19/07/25) &lt;a href="https://varunraghu.com/im-rebelling-against-the-algorithm/">I&amp;rsquo;m rebelling against the algorithm&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(09/07/25) &lt;a href="https://websmith.studio/blog/astro-is-a-developers-dream/">Astro is a developers f***ing dream — Websmith Studio&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(27/06/25) &lt;a href="https://kramkow.ski/article/2025/06/27/my_lights_run_on_bash.html">My Lights Run on Bash - Tomasz Kramkowski&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(27/06/25) &lt;a href="https://ralphammer.com/thomas-aquinas-the-world-is-divine/">Thomas Aquinas — The world is divine&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(27/06/25) &lt;a href="https://fireborn.mataroa.blog/blog/you-dont-own-the-word-freedom-a-full-burn-response-to-the-gnulinux-comment-that-tried-to-gatekeep-me-off-my-own-machine/">You Don&amp;rsquo;t Own the Word &amp;ldquo;Freedom&amp;rdquo;: A Full-Burn Response to the GNU/Linux Comment That Tried to Gatekeep Me Off My Own Machine — fireborn&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(24/06/25) &lt;a href="https://jyn.dev/how-i-use-my-terminal/">how i use my terminal&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(17/06/25) &lt;a href="https://gizvault.com/archives/hack-the-planet">Hack the Planet: 90s Hacker Culture vs. Today&amp;rsquo;s AI Devs&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(17/06/25) &lt;a href="https://literalmagazine.com/la-sombria-primavera-de-unica-zurn/">La sombría primavera de Unica Zürn - Literal Magazine&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(16/06/25) &lt;a href="https://bowshock.nl/irc/">Start your own Internet Resiliency Club – Bow Shock Systems Consulting&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(04/06/25) &lt;a href="https://happihacking.com/blog/posts/2025/why_I_wrote_theBEAMBook/">Why I Wrote the BEAM Book&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(02/06/25) &lt;a href="https://notsocommonthoughts.com/blog/ai-and-judgement/">Not So Common Thoughts&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(02/06/25) &lt;a href="https://shkspr.mobi/blog/2025/05/whatever-happened-to-cheap-ereaders/">Whatever happened to cheap eReaders?&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(27/05/25) &lt;a href="https://www.faisalabid.com/p/you-share-a-house-with-einstein-hawking">You share a house with Einstein, Hawking and Tao&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(16/05/25) &lt;a href="https://www.orwellfoundation.com/the-orwell-foundation/orwell/essays-and-other-works/a-nice-cup-of-tea/">A Nice Cup of Tea ｜ The Orwell Foundation&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(16/05/25) &lt;a href="https://thepointmag.com/examined-life/gateway-books/">Gateway Books ｜ The Point Magazine&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(14/05/25) &lt;a href="https://bloggeroo.dev/articles/202504031434">I failed a take-home assignment from Kagi Search - Bloggeroo&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(08/04/25) &lt;a href="https://www.theverge.com/tech/639126/india-frankenstein-laptops">The rise of &amp;lsquo;Frankenstein&amp;rsquo; laptops in New Delhi&amp;rsquo;s repair markets&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(02/04/25) &lt;a href="https://www.theatlantic.com/family/archive/2025/03/e-bike-family-parenthood/682052/?gift=2PSdP8nFdCJv4156wCBBiLgFRUe05yhjKAjml8A4Wrk">An E-Bike Transformed My Family&amp;rsquo;s Life&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(26/03/25) &lt;a href="https://supernuclear.substack.com/p/stoop-coffee-how-a-simple-idea-transformed">Stoop Coffee: How a Simple Idea Transformed My Neighborhood&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(03/03/25) &lt;a href="https://moultano.wordpress.com/2024/05/03/a-few-of-the-birds-i-love/">A Few of the Birds I Love&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(03/03/25) &lt;a href="https://oem.com.mx/elheraldodechihuahua/local/enfrenta-chihuahua-un-deficit-de-6-metros-cuadrados-de-areas-verdes-por-habitante-alerta-el-implan-21810703">Enfrenta Chihuahua un déficit de 6 metros cuadrados de áreas verdes por habitante: alerta el IMPLAN - El Heraldo de Chihuahua ｜ Noticias Locales, Policiacas, de México, Chihuahua y el Mundo&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(01/03/25) &lt;a href="https://www.404media.co/the-digital-packrat-manifesto/">The Digital Packrat Manifesto&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(23/02/25) &lt;a href="https://www.contraption.co/rails-versus-nextjs/">Why Ruby on Rails still matters&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(30/01/25) &lt;a href="https://www.henrikkarlsson.xyz/p/start-a-blog">Advice for a friend who wants to start a blog&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(07/01/25) &lt;a href="https://den.dev/blog/be-a-property-owner-not-a-renter-on-the-internet/">Be A Property Owner And Not A Renter On The Internet&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(07/01/25) &lt;a href="https://medium.com/@metapgmr/software-is-eating-the-world-all-right-faedbab6d623">Software is eating the world, … all right&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(04/01/25) &lt;a href="https://healeycodes.com/building-game-prototypes-with-love">Building Game Prototypes with LÖVE&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(02/01/25) &lt;a href="https://blog.jacobvosmaer.nl/0036-beeper/">My favourite computer ergonomics hack&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(02/01/25) &lt;a href="https://lehnews.wordpress.com/2014/03/25/walter-isaacson-my-so-called-writing-life/">Walter Isaacson: &amp;ldquo;My So-Called Writing Life&amp;rdquo;&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(23/12/24) &lt;a href="https://ntietz.com/blog/feel-dont-think/">Feel, don&amp;rsquo;t think ｜ nicole@web&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(20/12/24) &lt;a href="https://www.404media.co/apparently-this-is-how-you-jailbreak-ai/">APpaREnTLy THiS iS hoW yoU JaIlBreAk AI&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(12/12/24) &lt;a href="https://www.youtube.com/watch?v=T31HKuabyMA">When Your Hero Is A Monster&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(11/12/24) &lt;a href="https://calebhearth.com/dont-get-distracted">Don&amp;rsquo;t Get Distracted&lt;/a>&lt;/p>
&lt;/li>
&lt;li>
&lt;p>(11/12/24) &lt;a href="https://www.ntietz.com/blog/evolving-ergo-setup/">Evolving my ergonomic setup (or, my laptop with extra steps) ｜ nicole@web&lt;/a>&lt;/p>
&lt;/li>
&lt;/ul></description></item><item><title>Titan (Short Story)</title><link>https://luisangel.me/post/2024/04/24/titan/</link><pubDate>Wed, 24 Apr 2024 15:15:49 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2024/04/24/titan/</guid><description>&lt;p>My short story Titán won third place in the 4th Short Story Contest of the Lasallian Library Network in 2024! This story will be part of an upcoming anthology currently in editorial production. I am incredibly honored to have Titán included in this collection, which features outstanding works from talented writers. Stay tuned for the official publication!&lt;/p></description></item><item><title>El Templo sin Tiempo (poem) and L05T P03T45 (short story)</title><link>https://luisangel.me/post/2024/03/07/aventuras-de-papel/</link><pubDate>Thu, 07 Mar 2024 15:15:49 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2024/03/07/aventuras-de-papel/</guid><description>&lt;p>I am thrilled to announce that my works El Templo sin Tiempo (poem) and L05T P03T45 (short story) were featured in the Aventuras de Papel international literary exhibition held in Mar del Plata, Argentina, in 2024. This event brought together diverse voices in literature, and I am proud to have contributed my work to this celebration of creativity.&lt;/p>
&lt;p>Discover them here:&lt;/p>
&lt;ul>
&lt;li>&lt;a href="http://aventuraspapel.blogspot.com/2024/03/el-templo-sin-tiempo.html">El Templo sin Tiempo (poem)&lt;/a>&lt;/li>
&lt;li>&lt;a href="http://aventuraspapel.blogspot.com/2024/02/atencion-cazadores.html">L05T P03T45 (short story)&lt;/a>&lt;/li>
&lt;/ul></description></item><item><title>Dropdowns and Toggles with Pure CSS</title><link>https://luisangel.me/post/2022/11/05/dropdowns-and-toggles-with-css/</link><pubDate>Sat, 05 Nov 2022 11:53:11 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2022/11/05/dropdowns-and-toggles-with-css/</guid><description>&lt;p>We could imagine the technologies of the platform on which I work, &lt;a href="https://www.joinbuildit.com/">Build It&lt;/a>, as a dish; where Ruby on Rails is our main dish but is accompanied by a good portion of JavaScript through &lt;a href="https://stimulus.hotwired.dev/">Stimulus JS&lt;/a>, and while this brings the functionality and that magical feeling of a single page application (SPA), there are things we want to keep simple instead of using a sledgehammer to kill an ant, as a university professor used to say. Therefore, we decided to take a page from &lt;a href="https://apple.com/mx">Apple&lt;/a> when handling dropdown menus or dropdowns and do it through pure CSS and HTML; without requiring a line of JavaScript.&lt;/p>
&lt;h2 id="the-pillars">The Pillars&lt;/h2>
&lt;p>Our two pillars in the view will be &lt;code>&amp;lt;input&amp;gt;&lt;/code> elements of checkbox type and &lt;code>&amp;lt;label&amp;gt;&lt;/code> tags. We will form our basic skeleton as follows:&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-html" data-lang="html">&lt;span style="display:flex;">&lt;span>&amp;lt;&lt;span style="color:#ca9ee6">input&lt;/span> &lt;span style="color:#8caaee">id&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;toggle&amp;#34;&lt;/span> &lt;span style="color:#8caaee">type&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;checkbox&amp;#34;&lt;/span>&amp;gt;&amp;lt;/&lt;span style="color:#ca9ee6">input&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&amp;lt;&lt;span style="color:#ca9ee6">label&lt;/span> &lt;span style="color:#8caaee">for&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;toggle&amp;#34;&lt;/span>&amp;gt;&amp;lt;/&lt;span style="color:#ca9ee6">label&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>We will be using the checked property of checkbox-type inputs to control the content we show and when we show it. For this, we will be relying on the &lt;code>&amp;lt;label&amp;gt;&lt;/code> element since by linking it through its &lt;code>for&lt;/code> property it will also be affected by the class change when the checked property of our checkbox is present.&lt;/p>
&lt;p>All our code will really be inside &lt;code>&amp;lt;label&amp;gt;&lt;/code> in two sections: container and toggle as shown below.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-html" data-lang="html">&lt;span style="display:flex;">&lt;span>&amp;lt;&lt;span style="color:#ca9ee6">input&lt;/span> &lt;span style="color:#8caaee">id&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;toggle&amp;#34;&lt;/span> &lt;span style="color:#8caaee">type&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;checkbox&amp;#34;&lt;/span>&amp;gt;&amp;lt;/&lt;span style="color:#ca9ee6">input&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&amp;lt;&lt;span style="color:#ca9ee6">label&lt;/span> &lt;span style="color:#8caaee">for&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;toggle&amp;#34;&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">div&lt;/span> &lt;span style="color:#8caaee">class&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;toggle&amp;#34;&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#737994;font-style:italic">&amp;lt;!-- The element with which the user will interact --&amp;gt;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;/&lt;span style="color:#ca9ee6">div&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">div&lt;/span> &lt;span style="color:#8caaee">class&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>&lt;span style="color:#a6d189">&amp;#34;container&amp;#34;&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#737994;font-style:italic">&amp;lt;!-- What we want to show--&amp;gt;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;/&lt;span style="color:#ca9ee6">div&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&amp;lt;/&lt;span style="color:#ca9ee6">label&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="the-magic">The Magic&lt;/h2>
&lt;p>Now that we have our HTML skeleton ready, it&amp;rsquo;s time to add the CSS that will give our component the magical touch:&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-css" data-lang="css">&lt;span style="display:flex;">&lt;span>#&lt;span style="color:#ef9f76">toggle&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">display&lt;/span>: &lt;span style="color:#ef9f76">none&lt;/span>;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>}
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>.&lt;span style="color:#e5c890">container&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">display&lt;/span>: &lt;span style="color:#ef9f76">none&lt;/span>;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>}
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>#&lt;span style="color:#ef9f76">toggle&lt;/span>:&lt;span style="color:#8caaee;font-weight:bold">checked&lt;/span> &lt;span style="color:#99d1db;font-weight:bold">+&lt;/span> &lt;span style="color:#ca9ee6">label&lt;/span> .&lt;span style="color:#e5c890">container&lt;/span> { 
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">display&lt;/span>: &lt;span style="color:#ef9f76">inherit&lt;/span>; 
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>}
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Our input with the toggle id will never be shown so that we do not have the checkbox present on our page, what we will show and with which the user interacts is what is inside our div with toggle class. Once they click on our toggle, the input will have the value of checked and with &lt;code>#toggle:checked+label&lt;/code> we affect the style of our &lt;code>&amp;lt;label&amp;gt;&lt;/code> to obtain a result like the following&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/dropdowns-toggle-css-1.gif" alt="Demo 1">&lt;/p>
&lt;p>And with a little more style (courtesy of Thulio Philipe) we can have results like this&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/dropdowns-toggle-css-2.gif" alt="Demo 2">&lt;/p>
&lt;p>Or as the examples we have inside Build It&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/dropdowns-toggle-css-3.gif" alt="Demo 3">&lt;/p>
&lt;p>A small popover that is always present, giving vital information to the user&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/dropdowns-toggle-css-4.gif" alt="Demo 4">&lt;/p>
&lt;p>Or a filter menu that can be shown easily.&lt;/p>
&lt;p>As we can see, modern CSS allows us to make interactive pages without the need for a script for it; giving us a new solution to a problem with endless ways to solve it, so it will be necessary to consider the needs of the project and what is most suitable.&lt;/p>
&lt;p>Finally, I leave you &lt;a href="https://github.com/LinkSake/toggle-dropdown-css">a repository&lt;/a> with a couple of examples seen in this article for future reference and I invite you to visit &lt;a href="https://www.joinbuildit.com/early_access/client">the platform&lt;/a> and especially &lt;a href="https://www.joinbuildit.com/u/luis-ortega-160">my profile&lt;/a>, where we can connect for future projects.&lt;/p></description></item><item><title>Thinking Outside the Box an Online Resume With Docz</title><link>https://luisangel.me/post/2021/10/21/thinking-outside-the-box-an-online-resume-with-docz/</link><pubDate>Thu, 21 Oct 2021 15:32:45 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2021/10/21/thinking-outside-the-box-an-online-resume-with-docz/</guid><description>&lt;p>One of the best traits of humankind is its curiosity. It is so human that in honor of it we named a Mars rover &amp;ldquo;Curiosity&amp;rdquo; in 2003.&lt;/p>
&lt;p>Talking about curiosity in the developer world, open source projects top the list, since by nature they invite us to experiment, modify and share what else we can do with them. This is why I propose to think a little outside the box with &lt;a href="https://www.docz.site/">Docz&lt;/a> - a software documentation tool that is completely open source.&lt;/p>
&lt;h2 id="what-is-docz">What is Docz?&lt;/h2>
&lt;p>Docz is a &lt;a href="https://www.gatsbyjs.com/">Gatsby-based&lt;/a> project that simplifies the process of documenting other projects without worrying about configuration, speed and support.&lt;/p>
&lt;p>It provides a library that allows you to write MDX pages instead of HTML or JSX files, handles the routing and provides plugins for all the other needs that you may have. All of this results on projects anyone can contribute to!&lt;/p>
&lt;p>Is this simplicity and friendliness that makes Docz a great option for more than just docs.&lt;/p>
&lt;h2 id="creating-our-docz-project">Creating our Docz project&lt;/h2>
&lt;p>Before we can jump into Docz, there are some prerequisites that you will need have in order to create the project:&lt;/p>
&lt;ul>
&lt;li>&lt;a href="https://docs.npmjs.com/downloading-and-installing-node-js-and-npm#overview">NodeJS&lt;/a>&lt;/li>
&lt;li>&lt;a href="https://yarnpkg.com/getting-started/install">Yarn&lt;/a> or &lt;a href="https://docs.npmjs.com/downloading-and-installing-node-js-and-npm#overview">npm&lt;/a>&lt;/li>
&lt;/ul>
&lt;p>Now that you have the prerequisites, let’s start by creating a new React app with &lt;code>create-react-app&lt;/code> (CRA)&lt;/p>
&lt;p>Go to your terminal and run:&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>npx create-react-app my-resume
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>If you don’t have CRA installed, npm will ask you if it’s okay to install &lt;code>create-react-app&lt;/code> type &lt;code>y&lt;/code> to continue and let CRA create the new project.&lt;/p>
&lt;blockquote>
&lt;p>We are using the command &lt;code>npx&lt;/code> instead of &lt;code>npm&lt;/code> since we want to execute a package, not install it to a project. You can read more about it &lt;a href="https://stackoverflow.com/questions/50605219/difference-between-npx-and-npm">here&lt;/a>.&lt;/p>
&lt;/blockquote>
&lt;p>Now lets move to the directory of our project and install Docz.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#99d1db">cd&lt;/span> my-resume
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>yarn add docz &lt;span style="color:#737994;font-style:italic"># or npm install docz&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Then let’s remove everything that CRA created for us inside the &lt;code>src&lt;/code> folder, since we don’t need it.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>rm src/*
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Also, it is a good idea to add to the .gitignore the .docz folder since we only needed for development.&lt;/p>
&lt;pre tabindex="0">&lt;code class="language-.gitignore" data-lang=".gitignore"># .gitignore

# Docz generated files
.docz/
&lt;/code>&lt;/pre>&lt;p>Let’s go and create a file named &lt;code>index.mdx&lt;/code> and a &lt;em>hello world&lt;/em> header in the following way.&lt;/p>
&lt;pre tabindex="0">&lt;code class="language-mdx" data-lang="mdx">&amp;lt;!-- src/index.mdx --&amp;gt;

---
name: Hello World
route: /
---

# Hello world from Docz!
&lt;/code>&lt;/pre>&lt;p>And it’s time to run our development server to see what we have just created.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>yarn docz dev &lt;span style="color:#737994;font-style:italic"># or npm run docz dev&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>If you get an error &lt;a href="https://github.com/gatsbyjs/gatsby/issues/19922">ERROR #98123&lt;/a> while trying to run the development server, just delete your &lt;code>yarn.lock&lt;/code> or &lt;code>package-json.lock&lt;/code> and the &lt;code>node_modules&lt;/code> folder and install the dependencies again.&lt;/p>
&lt;/blockquote>
&lt;p>&lt;em>Et voila!&lt;/em> We have successfully created our Docz project.&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-1.png" alt="Hello from Docz">&lt;/p>
&lt;blockquote>
&lt;p>Now is a good time to commit your files!&lt;/p>
&lt;/blockquote>
&lt;h2 id="your-time-to-shine">Your time to shine&lt;/h2>
&lt;p>Before we start adding more pages, let’s create a configuration file named &lt;code>doczrc.js&lt;/code> on the root of our project. This will help us to set some meta tags easily, but it manages &lt;a href="https://www.docz.site/docs/project-configuration">all the configuration&lt;/a> of our project.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-js" data-lang="js">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#737994;font-style:italic">// doczrc.js
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#737994;font-style:italic">&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">export&lt;/span> &lt;span style="color:#ca9ee6">default&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> title&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#34;Luis Angel Ortega&amp;#34;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> description&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#34;Hello, I&amp;#39;m Luis Angel and this is my resume made with Docz!&amp;#34;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> ignore&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> [&lt;span style="color:#a6d189">&amp;#34;README.md&amp;#34;&lt;/span>]
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>}
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>The title key will set the suffix for our &lt;a href="https://www.w3schools.com/tags/tag_title.asp">title tag&lt;/a> and it will change the text on the top left corner of our project, since it’s an online resume I recommend using your name in this field.&lt;/p>
&lt;p>Then, the description key that we added will modify the &lt;a href="https://moz.com/learn/seo/meta-description">meta description tag&lt;/a> on our webpage to display it when it’s looked up or shared online.&lt;/p>
&lt;p>The last key will tell Docz to ignore some files and don’t display them on the webpage, as is in this case with the README file.&lt;/p>
&lt;p>Now let’s add more pages! I’ll add a contact page with my socials and resume one in the following way&lt;/p>
&lt;pre tabindex="0">&lt;code class="language-mdx" data-lang="mdx">&amp;lt;!-- src/contact.mdx --&amp;gt;

---
name: Contact
route: /contact
---

# Contact me! 🗣

---

Let&amp;#39;s talk! You can find me on these platforms:

- ✉️ [Email](mailto:hey@luisangelme)
- 🤝 [LinkedIn](https://www.linkedin.com/in/luisangel-ortega)
- 🐙 [GitHub](https://github.com/LinkSake)
- 🐦 [Twitter](https://twitter.com/LinkSake)
- 🌐 [Website](https://luisangel.me)
&lt;/code>&lt;/pre>&lt;pre tabindex="0">&lt;code class="language-mdx" data-lang="mdx">&amp;lt;!-- src/resume.mdx --&amp;gt;

---
name: Resume
route: /resume
---

# Resume 💼

---

## Work Experience

&amp;lt;details&amp;gt;
 &amp;lt;summary&amp;gt;Software Developer. &amp;lt;a href=&amp;#39;growthconstant.co&amp;#39; target=&amp;#39;_blank&amp;#39;&amp;gt;Growth Constant&amp;lt;/a&amp;gt;, (Mar. 2021 - Currently)&amp;lt;/summary&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt; Full stack developer (Ruby on Rails) and copywriter for the first project of the start-up: &amp;lt;a href=&amp;#39;virtualdash.co&amp;#39; target=&amp;#39;_blank&amp;#39;&amp;gt;Virtual Dash &amp;lt;/a&amp;gt;.&amp;lt;/li&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/details&amp;gt;

&amp;lt;details&amp;gt;
 &amp;lt;summary&amp;gt;Backend Developer Intern. &amp;lt;a href=&amp;#39;facturasamurai.com&amp;#39; target=&amp;#39;_blank&amp;#39;&amp;gt;Factura Samurai&amp;lt;/a&amp;gt;, (Aug. - Dec. 2020)&amp;lt;/summary&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt; Implemented the user authentication on the Elixir API. &amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt; Learn and developed serverless services (Cloudflare Workers) with TypeScript. &amp;lt;/li&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/details&amp;gt;

&amp;lt;details&amp;gt;
 &amp;lt;summary&amp;gt;Full Stack Web Developer. &amp;lt;a href=&amp;#39;biobot.farm&amp;#39; target=&amp;#39;_blank&amp;#39;&amp;gt;biobot.farm&amp;lt;/a&amp;gt;, (Aug. 2019 - Jun. 2020)&amp;lt;/summary&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt; Successfully launched a new service (web application) that was developed form scratch while learning React. &amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt; Documented the web application and taught a colleague to mantener said application. &amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt; Improved speed, functionality and readability of a Python API and micro-services. &amp;lt;/li&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/details&amp;gt;

## Education

&amp;lt;details&amp;gt;
 &amp;lt;summary&amp;gt;Bachelor&amp;#39;s Degree in Information Technologies and Telecomunications. &amp;lt;a href=&amp;#39;ulsachihuahua.edu.mx/site&amp;#39; target=&amp;#39;_blank&amp;#39;&amp;gt;Universidad La Salle Chihuahua&amp;lt;/a&amp;gt;, (Aug. 2016 - Dic. 2020)&amp;lt;/summary&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt; Degree on engineering on information and telecommunication with specialization on mobile development. &amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt; Academic exchange semester at La Salle Ramon Llull University (Barcelona, Spain) from January to June 2019 with the Computer Engineering degree. &amp;lt;/li&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/details&amp;gt;

## Skills

&amp;lt;details&amp;gt;
 &amp;lt;summary&amp;gt; Languages &amp;lt;/summary&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt;Spanish: Native&amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt;English: Advanced (TOFEL ITP: 627)&amp;lt;/li&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/details&amp;gt;
&amp;lt;details&amp;gt;
&amp;lt;summary&amp;gt; Tech &amp;lt;/summary&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt; &amp;lt;b&amp;gt; Professional level &amp;lt;/b&amp;gt; &amp;lt;/li&amp;gt;
 &amp;lt;div div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt;JavaScript (Node, React, Next)&amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt;Ruby (Rails)&amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt;SQL (MySQL, PostgreSQL)&amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt;Version manager (Git)&amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt;HTML &amp;amp; CSS&amp;lt;/li&amp;gt;
 &amp;lt;/div&amp;gt;
 &amp;lt;/div&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt; &amp;lt;b&amp;gt; Novice Level &amp;lt;/b&amp;gt; &amp;lt;/li&amp;gt;
 &amp;lt;div style={{marginLeft: &amp;#39;1em&amp;#39;}}&amp;gt;
 &amp;lt;li&amp;gt;Python (Bottle)&amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt;Docker&amp;lt;/li&amp;gt;
 &amp;lt;li&amp;gt;UNIX&amp;lt;/li&amp;gt;
 &amp;lt;/div&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/details&amp;gt;

## Achivements

- Essential part of the winning team of the following hackathons:
 - Ideacon (2018)
 - Reset (2018)
- Essential part of the 2nd place team of the Blockchain Mobility Hackathon 2019 in Barcelona, Spain.
&lt;/code>&lt;/pre>&lt;p>As you can see, using MDX means that we can use &lt;a href="https://www.markdownguide.org/">Markdown syntax&lt;/a> and &lt;a href="https://es.reactjs.org/docs/introducing-jsx.html">JSX&lt;/a> in the same document, giving a lot of flexibility and customization to our Docz projects.&lt;/p>
&lt;p>At the end they will look something like this:&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-2.png" alt="Contact page">&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-3.png" alt="Resume page">&lt;/p>
&lt;h2 id="spice-it-adding-a-custom-component">Spice it! Adding a custom component&lt;/h2>
&lt;p>Now let’s focus on our &lt;code>index.mdx&lt;/code> file. Let’s change it’s title to &amp;ldquo;About me&amp;rdquo;&lt;/p>
&lt;pre tabindex="0">&lt;code class="language-mdx" data-lang="mdx">&amp;lt;!-- src/index.mdx --&amp;gt;
---
name: About me
route: /
---

# Hello world from Docz!
&lt;/code>&lt;/pre>&lt;p>And then, create a &lt;code>components&lt;/code> folder inside of the &lt;code>src&lt;/code> directory. There create a &lt;code>welcome.jsx&lt;/code> component, this will replace our Markdown heading to make the root page more interesting.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-jsx" data-lang="jsx">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#737994;font-style:italic">// src/components/welcome.jsx
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#737994;font-style:italic">&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">import&lt;/span> React from &lt;span style="color:#a6d189">&amp;#39;react&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">const&lt;/span> Welcome &lt;span style="color:#99d1db;font-weight:bold">=&lt;/span> ( props ) =&amp;gt; {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">const&lt;/span> style &lt;span style="color:#99d1db;font-weight:bold">=&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> container&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> display&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;flex&amp;#39;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> flexDirection&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;column&amp;#39;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> },
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> textContainer&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> textAlign&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;center&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> },
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> imgContainer&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> paddingTop&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;1em&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> },
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> img&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> display&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;flex&amp;#39;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> margin&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;auto&amp;#39;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> maxWidth&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;40%&amp;#39;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> borderRadius&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#39;50%&amp;#39;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> },
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> }
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">return&lt;/span> (
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">div&lt;/span> &lt;span style="color:#8caaee">style&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>{style.container}&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">div&lt;/span> &lt;span style="color:#8caaee">style&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>{style.textContainer}&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">h1&lt;/span>&amp;gt;{props.title}&amp;lt;/&lt;span style="color:#ca9ee6">h1&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">span&lt;/span>&amp;gt;{props.children}&amp;lt;/&lt;span style="color:#ca9ee6">span&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;/&lt;span style="color:#ca9ee6">div&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">div&lt;/span> &lt;span style="color:#8caaee">style&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>{style.imgContainer}&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;&lt;span style="color:#ca9ee6">img&lt;/span> &lt;span style="color:#8caaee">style&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>{style.img} &lt;span style="color:#8caaee">src&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>{props.img} &lt;span style="color:#8caaee">alt&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">=&lt;/span>{props.title}/&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;/&lt;span style="color:#ca9ee6">div&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &amp;lt;/&lt;span style="color:#ca9ee6">div&lt;/span>&amp;gt;
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> )
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>}
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">export&lt;/span> &lt;span style="color:#ca9ee6">default&lt;/span> Welcome
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Here I just made a quick component that takes a title, some text and displays it all centered and the image as a circle, but you can make your creativity go wild on this one!&lt;/p>
&lt;p>Next, let’s change index.mdx to import our component and use it to give a warm welcome to all the visitors on our webpage, here is how it looks:&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-4.png" alt="Welcome page">&lt;/p>
&lt;h2 id="its-alive-time-to-deploy">It&amp;rsquo;s alive! Time to deploy&lt;/h2>
&lt;p>ow that we have our Docz project it’s time to build it and deploy it to GitHub Pages (since we already have the repository there).&lt;/p>
&lt;p>First we need to configure some things, go to your doczrc.js file and add a dest key with the value “/docs” and a base key the name of your repo as it’s value.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-js" data-lang="js">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#737994;font-style:italic">// doczrc.js
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#737994;font-style:italic">&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">export&lt;/span> &lt;span style="color:#ca9ee6">default&lt;/span> {
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> title&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#34;Luis Angel Ortega&amp;#34;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> description&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#34;Hello, I&amp;#39;m Luis Angel and this is my resume made with Docz!&amp;#34;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> ignore&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> [&lt;span style="color:#a6d189">&amp;#34;README.md&amp;#34;&lt;/span>],
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> dest&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#34;/docs&amp;#34;&lt;/span>,
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> base&lt;span style="color:#99d1db;font-weight:bold">:&lt;/span> &lt;span style="color:#a6d189">&amp;#34;docz-resume&amp;#34;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>}
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>The first key is telling Docz to build the project into the docs directory, we’re doing this since GitHub Pages expects the static files to be on the root or docs directories.&lt;/p>
&lt;p>The base key is changing the base folder to match the name of the repo in order to make the public files and links to work in GitHub Pages.&lt;/p>
&lt;p>Once we have everything correctly configured, we need to build the project with the following command:&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>yarn docz build &lt;span style="color:#737994;font-style:italic"># or npm run docz build&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>When it is done, you will see a docs folder on your project. Commit and push everything to your repo. After that, let’s go to the settings tab on your project and in the left menu go to the Pages section.&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-5.png" alt="Repo page">&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-6.png" alt="Settings page">&lt;/p>
&lt;p>Then select your main branch (or the branch on which you are working on) and select the docs folder.&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-7.png" alt="Pages page">&lt;/p>
&lt;p>And that is it! In a few minutes your website should be live on the link that GitHub has given you.&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-8.png" alt="Done!">&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/cv-docz-9.png" alt="Handsome you">&lt;/p>
&lt;h2 id="the-future-awaits">The future awaits&lt;/h2>
&lt;p>In this article we only scratched the surface of what Docz is capable of, so be sure to check their &lt;a href="https://www.docz.site/docs/getting-started">documentation&lt;/a> to learn more.&lt;/p>
&lt;p>I encourage you to read about them to make your resume stand out from the crowd and always remember to support the creators of this amazing project and contribute if you can.&lt;/p>
&lt;p>Find the repo of the project &lt;a href="https://github.com/LinkSake/docz-resume">here&lt;/a>. For end result, check out &lt;a href="https://linksake.github.io/docz-resume/">GitHub&lt;/a>.&lt;/p></description></item><item><title>Docker + Rails: A Solution for Your Headaches</title><link>https://luisangel.me/post/2021/09/02/docker-and-rails/</link><pubDate>Thu, 02 Sep 2021 15:15:49 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2021/09/02/docker-and-rails/</guid><description>&lt;p>Have you ever spent a week just trying to run the project you just joined? Or does your application not run in production as it did locally?
There are a multitude of factors that can contribute to this, which is why &lt;a href="https://www.docker.com/">Docker&lt;/a> offers us a solution with which we can have greater control over these variables across the necessary computers.&lt;/p>
&lt;p>With that said, in this article we will see how to make our lives easier by having our entire Ruby on Rails application running on Docker; including any necessary databases.&lt;/p>
&lt;h2 id="prerequisites">Prerequisites&lt;/h2>
&lt;p>To follow this guide, you will need to have &lt;a href="https://docs.docker.com/get-docker/">Docker installed&lt;/a> as well as a project you want to &lt;em>dockerize&lt;/em>. If you just want to practice, you can use &lt;a href="https://github.com/LinkSake/docker-rails">this example project&lt;/a> which requires a connection to &lt;a href="https://en.wikipedia.org/wiki/PostgreSQL">Postgres&lt;/a> and &lt;a href="https://en.wikipedia.org/wiki/Redis">Redis&lt;/a> to function.&lt;/p>
&lt;p>Are you impatient? You can clone &lt;a href="https://github.com/LinkSake/docker-rails/tree/docker">this branch&lt;/a> of the project where the necessary files to run the project inside Docker are already present!&lt;/p>
&lt;h2 id="first-comes-the-dockerfile">First Comes the Dockerfile&lt;/h2>
&lt;p>The first thing we will do is create a custom &lt;a href="https://docs.docker.com/get-started/overview/#docker-objects">image&lt;/a> for our project, so we will create a file at the root of it called &lt;code>Dockerfile&lt;/code>&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>touch Dockerfile
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>The first line of our file will define the image we will base on, in this case, it will be the &lt;a href="https://hub.docker.com/_/ruby">official Ruby image&lt;/a>, but we will use the Alpine version to have a lighter image as a result.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-Dockerfile" data-lang="Dockerfile">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">FROM&lt;/span>&lt;span style="color:#a6d189"> ruby:3.0.1-alpine&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>⚠️ Make sure the Ruby version (ruby:X.X.X-alpine) is the same as in your project, or you will have errors when trying to build the image. You can find the version used by your project in your Gemfile.&lt;/p>
&lt;/blockquote>
&lt;p>Next comes the most difficult part of this Dockerfile, installing the necessary dependencies for the project to function; those shown here are the ones that work for our &lt;a href="https://github.com/LinkSake/docker-rails">example project&lt;/a>, which include the necessary ones to make a connection with Postgres, but you will have to discover which ones are necessary for your project.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-Dockerfile" data-lang="Dockerfile">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">FROM&lt;/span>&lt;span style="color:#a6d189"> ruby:3.0.1-alpine&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> apk add --update --no-cache --virtual run-dependencies &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>build-base &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-client &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-dev &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>yarn &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>git &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>tzdata &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>libpq &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">&amp;amp;&amp;amp;&lt;/span> rm -rf /var/cache/apk/*&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>You can wait to build the image (&lt;code>docker build .&lt;/code>) to check the error printed by Docker, with that you can find out what dependencies are missing 😉&lt;/p>
&lt;/blockquote>
&lt;p>The last line (&lt;code>rm -rf /var/cache/apk/*&lt;/code>) deletes the packages of the dependencies we just installed, this will save space in the image.&lt;/p>
&lt;p>Next, we need to create a directory inside the container where we can copy the code of our application for its execution, we will do this with the following command inside our Dockerfile.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-Dockerfile" data-lang="Dockerfile">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">FROM&lt;/span>&lt;span style="color:#a6d189"> ruby:3.0.1-alpine&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> apk add --update --no-cache --virtual run-dependencies &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>build-base &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-client &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-dev &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>yarn &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>git &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>tzdata &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>libpq &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">&amp;amp;&amp;amp;&lt;/span> rm -rf /var/cache/apk/*&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">WORKDIR&lt;/span>&lt;span style="color:#a6d189"> /docker-rails&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>Remember to change &lt;code>docker-rails&lt;/code> to your project name!&lt;/p>
&lt;/blockquote>
&lt;p>Just as we gave your project a home inside the container we will create, the gems of the same need a folder too. Therefore, we will inform &lt;a href="https://bundler.io/">bundler&lt;/a> where to place them through an environment variable.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-Dockerfile" data-lang="Dockerfile">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">FROM&lt;/span>&lt;span style="color:#a6d189"> ruby:3.0.1-alpine&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> apk add --update --no-cache --virtual run-dependencies &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>build-base &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-client &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-dev &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>yarn &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>git &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>tzdata &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>libpq &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">&amp;amp;&amp;amp;&lt;/span> rm -rf /var/cache/apk/*&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">WORKDIR&lt;/span>&lt;span style="color:#a6d189"> /docker-rails&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">ENV&lt;/span> BUNDLE_PATH /gems&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>And although we have already installed the necessary dependencies to run Rails within the container, your project will need some gems and some JavaScript packages to function correctly, we will take care of that as follows.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-Dockerfile" data-lang="Dockerfile">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">FROM&lt;/span>&lt;span style="color:#a6d189"> ruby:3.0.1-alpine&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> apk add --update --no-cache --virtual run-dependencies &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>build-base &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-client &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-dev &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>yarn &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>git &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>tzdata &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>libpq &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">&amp;amp;&amp;amp;&lt;/span> rm -rf /var/cache/apk/*&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">WORKDIR&lt;/span>&lt;span style="color:#a6d189"> /docker-rails&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">ENV&lt;/span> BUNDLE_PATH /gems&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> package.json yarn.lock /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> yarn install&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> Gemfile Gemfile.lock /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> bundle install&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Now that we have everything necessary for your project to function, we will copy the code to the container inside the folder we created with the &lt;code>WORKDIR&lt;/code> command.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-Dockerfile" data-lang="Dockerfile">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">FROM&lt;/span>&lt;span style="color:#a6d189"> ruby:3.0.1-alpine&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> apk add --update --no-cache --virtual run-dependencies &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>build-base &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-client &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-dev &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>yarn &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>git &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>tzdata &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>libpq &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">&amp;amp;&amp;amp;&lt;/span> rm -rf /var/cache/apk/*&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">WORKDIR&lt;/span>&lt;span style="color:#a6d189"> /docker-rails&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">ENV&lt;/span> BUNDLE_PATH /gems&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> package.json yarn.lock /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> yarn install&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> Gemfile Gemfile.lock /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> bundle install&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> . /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>Why do we first copy the manifests (package.json, Gemfile, etc.) and then the rest of the project? This avoids having to reinstall the dependencies (since they stay in the cache) after changing the base code and rebuilding the image; this way only when the manifests change will their installation commands be run again.&lt;/p>
&lt;/blockquote>
&lt;p>Finally, we will tell Docker what command to run when we start our container (&lt;code>rails&lt;/code>), as well as the arguments for it (&lt;code>s -b 0.0.0.0&lt;/code>) and which port to expose so that we can access our application.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-Dockerfile" data-lang="Dockerfile">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">FROM&lt;/span>&lt;span style="color:#a6d189"> ruby:3.0.1-alpine&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> apk add --update --no-cache --virtual run-dependencies &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>build-base &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-client &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>postgresql-dev &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>yarn &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>git &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>tzdata &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>libpq &lt;span style="color:#8caaee">\
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#8caaee">&lt;/span>&lt;span style="color:#99d1db;font-weight:bold">&amp;amp;&amp;amp;&lt;/span> rm -rf /var/cache/apk/*&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>WORKROOM /docker-rails&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">ENV&lt;/span> BUNDLE_PATH /gems&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> package.json yarn.lock /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> yarn install&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> Gemfile Gemfile.lock /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">RUN&lt;/span> bundle install&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">COPY&lt;/span> . /docker-rails/&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">ENTRYPOINT&lt;/span> [&lt;span style="color:#a6d189">&amp;#34;bin/rails&amp;#34;&lt;/span>]&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">CMD&lt;/span> [&lt;span style="color:#a6d189">&amp;#34;s&amp;#34;&lt;/span>, &lt;span style="color:#a6d189">&amp;#34;-b&amp;#34;&lt;/span>, &lt;span style="color:#a6d189">&amp;#34;0.0.0.0&amp;#34;&lt;/span>]&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#e78284">&lt;/span>&lt;span style="color:#ca9ee6">EXPOSE&lt;/span>&lt;span style="color:#a6d189"> 3000&lt;/span>&lt;span style="color:#e78284">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>The default port over which Rails runs is 3000, but if you have designated another port within your application make sure to expose it correctly.&lt;/p>
&lt;/blockquote>
&lt;p>And with this we have our Dockerfile ready, although we are far from having our application ready. If we build our image with &lt;code>docker build .&lt;/code> and try to run it with &lt;code>docker start docker-rails&lt;/code> we would encounter an error, since Rails does not find the databases it needs to start correctly; but we will soon take care of that.&lt;/p>
&lt;h2 id="then-the-docker-composeyml">Then the docker-compose.yml&lt;/h2>
&lt;p>To coordinate all the services we need for the correct functioning of our application (in this case 2 databases: Postgres and Redis) we will use &lt;a href="https://docs.docker.com/compose/">docker-compose&lt;/a>, this Docker utility will help us create multiple containers from different images, &lt;a href="https://docs.docker.com/compose/networking/">connect them&lt;/a>, give them &lt;a href="https://docs.docker.com/compose/environment-variables/">environment variables&lt;/a> and even &lt;a href="https://docs.docker.com/storage/volumes/">volumes&lt;/a>.&lt;/p>
&lt;p>We will start by creating a file called &lt;code>docker-compose.yml&lt;/code>.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>touch docker-compose.yml
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>And on its first line we will specify which &lt;a href="https://docs.docker.com/compose/compose-file/#compose-and-docker-compatibility-matrix">version&lt;/a> of the tool we want to use, in this case we will use the most recent at the time of writing this article.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-yaml" data-lang="yaml">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">version&lt;/span>: &lt;span style="color:#a6d189">&amp;#39;3.8&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Next, we will indicate the services we want docker-compose to run, we will do this under the &lt;code>services&lt;/code> label. We will give each service a name, which will be important when we are configuring our image, so make sure to name it in a way that makes sense to you. Let&amp;rsquo;s start with the Postgres service, which we will call &lt;em>db&lt;/em>.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-yaml" data-lang="yaml">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">version&lt;/span>: &lt;span style="color:#a6d189">&amp;#39;3.8&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">services&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">db&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: postgres:latest
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">environment&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_DB=docker-rails-dev
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_PASSWORD=password
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">5432&lt;/span>:&lt;span style="color:#ef9f76">5432&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">volumes&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#a6d189">&amp;#39;dbdata:/var/lib/postgresql/data&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;blockquote>
&lt;p>YAML files are sensitive to indentation, so make sure everything is in order and indented correctly.&lt;/p>
&lt;/blockquote>
&lt;p>The &lt;code>db&lt;/code> tag is the name we gave to the service and within which we will specify all the configuration for it.&lt;/p>
&lt;p>The first thing we encounter is &lt;code>image&lt;/code>, which as its name indicates is the name of the image we want to use for that service, in this case it is the official Postgres image in its latest version (you can specify a version by replacing &lt;code>latest&lt;/code> with another valid version).&lt;/p>
&lt;p>Then we encounter &lt;code>container_name&lt;/code>, which is also self-explanatory and which will come in handy when checking our containers with &lt;code>docker ps&lt;/code>.&lt;/p>
&lt;p>&lt;code>environment&lt;/code> refers to the environment variables, and if we refer to the &lt;a href="https://hub.docker.com/_/postgres">Docker Postgres image documentation&lt;/a> we can see that the only mandatory variable is &lt;code>POSTGRES_PASSWORD&lt;/code> but we will also define &lt;code>POSTGRES_DB&lt;/code> to give a custom name to the database that the image creates by default.&lt;/p>
&lt;blockquote>
&lt;p>⚠️ Be sure to choose a secure password for the database!&lt;/p>
&lt;/blockquote>
&lt;p>&lt;code>ports&lt;/code> are the ports that we will need to pass from inside the container to our machine, the ones indicated in the file are the ones that Postgres uses by default.&lt;/p>
&lt;p>Finally, the &lt;code>volumes&lt;/code> are the persistent information we will need so as not to run the migrations every time we turn on the container, this is because Docker deletes all data once we shut down the information, if you want to learn more about this topic I recommend &lt;a href="https://docs.docker.com/storage/volumes/">this&lt;/a> section of the documentation.&lt;/p>
&lt;p>Now, the next service is Redis but we will not delve much into it as it only has a couple of labels which we have already reviewed, for more information you can visit &lt;a href="https://hub.docker.com/_/redis">the official image&lt;/a>.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-yaml" data-lang="yaml">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">version&lt;/span>: &lt;span style="color:#a6d189">&amp;#39;3.8&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">services&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">db&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: postgres:latest
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">environment&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_DB=docker-rails-dev
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_PASSWORD=password
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">5432&lt;/span>:&lt;span style="color:#ef9f76">5432&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">volumes&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#a6d189">&amp;#39;dbdata:/var/lib/postgresql/data&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">redis&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: redis:latest
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-redis
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">6379&lt;/span>:&lt;span style="color:#ef9f76">6379&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Our last service we will call &lt;code>web&lt;/code> and it will be the image we have built with our &lt;code>Dockerfile&lt;/code>.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-yaml" data-lang="yaml">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">version&lt;/span>: &lt;span style="color:#a6d189">&amp;#39;3.8&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">services&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">db&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: postgres:latest
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">environment&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_DB=docker-rails-dev
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_PASSWORD=password
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">5432&lt;/span>:&lt;span style="color:#ef9f76">5432&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">volumes&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#a6d189">&amp;#39;dbdata:/var/lib/postgresql/data&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">redis&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: redis:latest
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-redis
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">6379&lt;/span>:&lt;span style="color:#ef9f76">6379&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">web&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">build&lt;/span>: .
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: docker-rails
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-web
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">3000&lt;/span>:&lt;span style="color:#ef9f76">3000&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">depends_on&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - redis
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">environment&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_HOST=db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_USER=postgres
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_PASSWORD=password
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - REDIS_URL=redis://redis:6379
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>The first new tag we encounter is &lt;code>build&lt;/code>, which indicates the directory where our Dockerfile is located; since our Dockerfile is at the root we will only put &lt;code>.&lt;/code>; if your Dockerfile is not at the root or has another name it is advisable to read &lt;a href="https://docs.docker.com/compose/compose-file/compose-file-v3/#build">this&lt;/a> section of the documentation to make sure Compose finds it.&lt;/p>
&lt;p>The &lt;code>image&lt;/code> tag in this case will serve to name the image that Compose will build, since &lt;code>build&lt;/code> is present it will not go to the repository to look for a pre-built image.&lt;/p>
&lt;p>Finally, the &lt;code>depends_on&lt;/code> tag will inform Compose that it should not try to start the container until the &lt;code>db&lt;/code> and &lt;code>redis&lt;/code> services are created, as well as it will connect them internally so that we can access them through a URL (as can be seen in the Redis environment variable) or by their respective credentials (as is the case with Postgres), if you want to learn how Docker handles this you can read about &lt;a href="https://docs.docker.com/compose/networking/">Docker Network&lt;/a>.&lt;/p>
&lt;p>Now that we have finished with the services, the only thing we must do is list the volumes we will use and which we &lt;a href="https://docs.docker.com/compose/compose-file/compose-file-v3/#volumes">named&lt;/a> in the following way.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-yaml" data-lang="yaml">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">version&lt;/span>: &lt;span style="color:#a6d189">&amp;#39;3.8&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">services&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">db&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: postgres:latest
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">environment&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_DB=docker-rails-dev
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_PASSWORD=password
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">5432&lt;/span>:&lt;span style="color:#ef9f76">5432&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">volumes&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#a6d189">&amp;#39;dbdata:/var/lib/postgresql/data&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">redis&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: redis:latest
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-redis
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">6379&lt;/span>:&lt;span style="color:#ef9f76">6379&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">web&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">build&lt;/span>: .
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">image&lt;/span>: docker-rails
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">container_name&lt;/span>: docker-rails-web
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">ports&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - &lt;span style="color:#ef9f76">3000&lt;/span>:&lt;span style="color:#ef9f76">3000&lt;/span>
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">depends_on&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - redis
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">environment&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_HOST=db
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_USER=postgres
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - POSTGRES_PASSWORD=password
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - REDIS_URL=redis://redis:6379
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">volumes&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> - .:/app
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span>&lt;span style="color:#ca9ee6">volumes&lt;/span>:
&lt;/span>&lt;/span>&lt;span style="display:flex;">&lt;span> &lt;span style="color:#ca9ee6">dbdata&lt;/span>:
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>And that&amp;rsquo;s it! Our &lt;code>docker-compose.yml&lt;/code> is ready, now there&amp;rsquo;s only one step left to start creating our Docker-contained application.&lt;/p>
&lt;h2 id="out-of-sight-dockerignore-out-of-mind">Out of Sight, .dockerignore Out of Mind&lt;/h2>
&lt;p>Many times we do not want certain files to be in our Docker image because they are not necessary for its construction (or are generated in it) and only end up making the project larger than it needs to be, such as the &lt;code>node_modules&lt;/code> and &lt;code>.git&lt;/code> folder.
To save this space, we will create a file called &lt;code>.dockerignore&lt;/code> at the root of our project and add these two folders:&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>&lt;span style="color:#99d1db">echo&lt;/span> &lt;span style="color:#a6d189">&amp;#34;.git \n node_modules&amp;#34;&lt;/span> &amp;gt;&amp;gt; .dockerignore
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>For more information on what a &lt;code>.dockerignore&lt;/code> file can contain, you can consult the &lt;a href="https://docs.docker.com/engine/reference/builder/#dockerignore-file">official Docker documentation&lt;/a>&lt;/p>
&lt;h2 id="databases-2-go">Databases 2 Go&lt;/h2>
&lt;p>Before running the project it will be necessary to create the database that Rails expects, and creating it is so simple that it can be done in a single command.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>docker-compose run web db:create
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>This command tells Docker to use the image (which it will build) to run a command, in this case &lt;code>db:create&lt;/code>. Docker, with what is specified in the &lt;code>docker-compose.yml&lt;/code>, knows that since &lt;em>web&lt;/em> depends on &lt;em>db&lt;/em> it will have to run the Postgres instance first, so the database will be created in this container.&lt;/p>
&lt;blockquote>
&lt;p>Why only &lt;code>db:create&lt;/code> and not &lt;code>rails db:create&lt;/code> or &lt;code>rake db:create&lt;/code>? In our &lt;code>Dockerfile&lt;/code> we gave &lt;code>rails&lt;/code> as the entry point, so only the parameters are necessary. If we wanted to perform another command inside the container this would have to be through &lt;a href="https://docs.docker.com/engine/reference/commandline/exec/">docker exec&lt;/a>.&lt;/p>
&lt;/blockquote>
&lt;h2 id="our-application-in-a-container">Our Application in a Container&lt;/h2>
&lt;p>With the database created, there&amp;rsquo;s only one command left that will run the containers in &lt;a href="https://docs.docker.com/compose/reference/up/">detached mode&lt;/a> and we will be able to see the fruit of our labor.&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" style="color:#c6d0f5;background-color:#303446;-moz-tab-size:4;-o-tab-size:4;tab-size:4;">&lt;code class="language-bash" data-lang="bash">&lt;span style="display:flex;">&lt;span>docker-compose up -d
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>And that&amp;rsquo;s it! You can now access through your browser to &lt;a href="http://localhost:3000/">localhost:3000&lt;/a> and see the Rails welcome page.&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/post/docker-rails-1.png" alt="Welcome to Rails!">&lt;/p>
&lt;h2 id="conclusion">Conclusion&lt;/h2>
&lt;p>This whole process may be a bit intimidating at first, especially if you are not familiar with Docker, but the result is a much simpler development environment for everyone involved in the project, as now just by having Docker installed they can start programming; not to mention the benefits that this technology can bring to your production environment when combined with Kubernetes or Docker Swarm.&lt;/p>
&lt;p>I hope you found this useful, anything you can &lt;a href="https://luisangel.me/es/about">contact me&lt;/a> and I will respond as soon as possible.&lt;/p>
&lt;h2 id="references">References&lt;/h2>
&lt;ul>
&lt;li>&lt;a href="https://docs.docker.com/samples/rails/">Docker Docs&lt;/a>&lt;/li>
&lt;li>&lt;a href="https://gorails.com/episodes/docker-basics-for-gorails">Go Rails&lt;/a>&lt;/li>
&lt;/ul></description></item><item><title>Home Office or No Home Office? That is the Question</title><link>https://luisangel.me/post/2021/04/20/the-issue-with-home-office/</link><pubDate>Tue, 20 Apr 2021 15:07:57 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2021/04/20/the-issue-with-home-office/</guid><description>&lt;p>During this past weekend, I found myself in the middle of a family conversation, where the topic of &lt;em>home office&lt;/em> came up. My father commented that it wasn&amp;rsquo;t a good practice. &amp;ldquo;It&amp;rsquo;s not healthy,&amp;rdquo; he repeated several times while shaking his head from side to side in denial.&lt;/p>
&lt;p>My cousin and I did not agree with him, as both of us (who, by the way, both work in the IT field) have seen huge benefits from working from home. We tried to explain, but he continued to shake his head and finally we left the conversation at that.&lt;/p>
&lt;p>But since then, I haven&amp;rsquo;t been able to stop thinking about it. Is &lt;em>home office&lt;/em> really healthy? Does it really have the benefits that I claim? After a couple of days of reflection, I found that this topic, like everything in life, is complicated.&lt;/p>
&lt;p>We have already passed the first year mark of the &lt;a href="https://en.wikipedia.org/wiki/COVID-19_pandemic">pandemic&lt;/a>, and from my experience and privilege, &lt;em>home office&lt;/em> has brought a lot of benefits to my life (although here I only list 3).&lt;/p>
&lt;hr>
&lt;h3 id="the-good">The Good&lt;/h3>
&lt;ul>
&lt;li>&lt;strong>Job opportunities&lt;/strong>&lt;/li>
&lt;/ul>
&lt;p>This situation has allowed me to have a remote job, something that while possible before, I&amp;rsquo;m not sure I would have been given the opportunity so easily as a &lt;em>junior&lt;/em> developer.&lt;/p>
&lt;ul>
&lt;li>&lt;strong>More time for myself&lt;/strong>&lt;/li>
&lt;/ul>
&lt;p>I think this is the most obvious, as without having to travel (or even shower in the mornings) to go to an office I have been able to sleep more, spend more time with my family, and give myself time for me. I have been able to engage in more activities, which although are inside my house or with a limited number of people, I had not been able to try before; I didn&amp;rsquo;t know how much time of my life was only going in transport to other places.&lt;/p>
&lt;ul>
&lt;li>&lt;strong>Greater mental peace&lt;/strong>&lt;/li>
&lt;/ul>
&lt;p>This was the point I wanted to get to, because I believe not everyone has experienced this, but for me (after the initial shock of confinement) my mental health has improved considerably. See, I have &lt;a href="https://en.wikipedia.org/wiki/Generalized_anxiety_disorder">generalized anxiety disorder&lt;/a> and there are days that I am very, very bad. Those days, when I had to work in an office, were terrible. The workday seemed eternal, I&amp;rsquo;m sure I aged 4 years for each day that was like that; I couldn&amp;rsquo;t concentrate during those hours and I felt horrible about it, feeling that my work was not worth it and not sure what I was doing there. It was a time when neither my mind nor my body could escape from there, the most I could do was watch a couple of YouTube videos, talk to colleagues or go for a walk; but that was it, your colleagues can only talk so much with you before they have to return to their tasks and after a certain number of walks your boss starts to look at you weird (YouTube videos are infinite, for better or worse).&lt;/p>
&lt;p>But in the &lt;em>home office&lt;/em> I have the privilege of working from my room, where I have all the tools I need to deal with those bad days, which not only are no longer terrible, but have decreased in quantity and frequency! Although it took a couple of months to reach stability in my routine and have the discipline to work from home, now if I start having a particularly terrible day, I&amp;rsquo;ll take a quick shower, go out to the patio, and play with my pet; and that will work as a &lt;em>reset&lt;/em> to my body, where I didn&amp;rsquo;t lose the whole day trying to escape from my own mind, instead just 20 minutes in regaining composure. On less terrible but still difficult days, stopping each &lt;a href="https://en.wikipedia.org/wiki/Pomodoro_Technique">pomodoro&lt;/a> break to walk around the house or play a game as a reward for finishing a task serves as enough incentive to keep a good mood all day.&lt;/p>
&lt;hr>
&lt;h3 id="the-bad">The Bad&lt;/h3>
&lt;p>This is not to say that everything has been rosy, as I mentioned, it was a couple of months of work to get to this point. Also, I know I am speaking from a huge privilege, because not only was I lucky enough to have the equipment to work comfortably from home; but I had a place where to do it and a quiet environment, something that many people have not had.&lt;/p>
&lt;p>Even so, with all my privilege, there has been a big point and an important topic throughout the pandemic: socialization.&lt;/p>
&lt;ul>
&lt;li>&lt;strong>Socialization&lt;/strong>&lt;/li>
&lt;/ul>
&lt;p>As an &amp;ldquo;adult&amp;rdquo; that I am, I am starting to notice something that I had heard from older people: when you are an adult it is difficult to make friends. And in my first job in IT the best thing I took away were the friendships I made, because they are people that to this day I frequent and talk to daily; they went from being colleagues to close friends. Talking with them I like to tell them that really that office was not an office, but really we were in a &lt;em>reality show&lt;/em> style &lt;a href="https://en.wikipedia.org/wiki/The_Office">&lt;em>The Office&lt;/em>&lt;/a> where they recorded everything that happened.&lt;/p>
&lt;p>While, in the jobs/internships that I had during the pandemic I was able to meet incredible people, people I consider mentors, I can&amp;rsquo;t help but think that I would have a better relationship with them if I could have seen them in person more often. I also can&amp;rsquo;t deny that it is much easier to get help from someone if they are sitting next to you, even if it only serves as a &lt;a href="https://en.wikipedia.org/wiki/Rubber_duck_debugging">rubber duck&lt;/a>.&lt;/p>
&lt;p>In short, I miss very much the human warmth that working in an office brought and it would be a lie if I did not say that I worry about losing the ability to make friends if this model awaited me for the rest of my life.&lt;/p>
&lt;p>However, this is just one of the problems that working from home brings; I have not touched on things as important as that businesses save money if we are not physically in an office while we spend more by having to pay for the supplies we use to work without having a salary increase that reflects that saving on the part of the employer. This was not the point I wanted to touch on in this writing, but we should not take our finger off that topic.&lt;/p>
&lt;hr>
&lt;h2 id="what-i-propose">What I Propose&lt;/h2>
&lt;p>So what is the solution? What would be ideal? From my young and naive point of view, and considering that this is a solution to my specific problems; I believe that the solution would be a hybrid model, 2 days of face-to-face office and 3 days of work from home. It could work in reverse as well, but personally I prefer the first option.&lt;/p>
&lt;p>This would allow for an agile dynamic for situations such as meetings, planning or any other type of event that benefits from being physically in a room, leaving 3 days of space for the employee to work comfortably and in their own style from home. Also, if the office is already going to be open some days, why not allow employees who want to go work there? This could benefit, for example, someone who does not have good internet at home or someone who has children at home and does not have a suitable place to concentrate.&lt;/p>
&lt;p>In this last example it also works the other way around, it would allow (if things return to something that resembles the &lt;em>past&lt;/em>) for working parents to see their children more time after they get home from school, even allowing everyone to eat at the same time, at the same table.&lt;/p>
&lt;hr>
&lt;p>In the end, like many of the beautiful things in life, I think everything should be left to the free will of people; that they can choose the model that works best for them, because I believe that we as humans are much more than a piece of meat capable of making money for a company and &lt;em>home office&lt;/em> can be a support in our search for meaning and happiness.&lt;/p>
&lt;p>If you are interested in more about the topic of post-covid life, I recommend this &lt;a href="https://www.youtube.com/watch?v=6iILrpgbAMY">video&lt;/a> by Ophelia Pastrana.&lt;/p></description></item><item><title>A Teaspoon of Sun (Poem)</title><link>https://luisangel.me/post/2020/09/19/a-teaspoon-of-sun/</link><pubDate>Sat, 19 Sep 2020 15:15:49 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2020/09/19/a-teaspoon-of-sun/</guid><description>&lt;p>I am excited to share that my poem Una Cucharadita de Sol was selected as a winner in the Quarantine Poetry: Homemade Poems Competition in 2020! This piece was included in the international anthology Quarantine Poetry: 2020 Homemade Poems, where it was translated into English, French, Italian, and Indonesian. This recognition means a lot to me, as it captures a moment of reflection during an unprecedented time.&lt;/p>
&lt;p>Get it on &lt;a href="https://payhip.com/b/aqXmV">payhip.com&lt;/a> or on the &lt;a href="https://luisangel.me/docs/quarantine-poetry.pdf">mirror on this site&lt;/a>.&lt;/p></description></item><item><title>The Best Part of School Is Recess</title><link>https://luisangel.me/post/2020/08/11/the-best-part-of-school-is-recess/</link><pubDate>Tue, 11 Aug 2020 13:50:59 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2020/08/11/the-best-part-of-school-is-recess/</guid><description>&lt;p>Today I read a &lt;a href="https://www.escritas.org/es/t/4758/el-mediodia-en-la-calle-atropellando-angeles">poem&lt;/a> by Jaime Sabines, one of his verses said the following:&lt;/p>
&lt;p>    &lt;em>&amp;ldquo;The best part of school is recess,&amp;rdquo;&lt;/em>&lt;br>
    &lt;em>says Judit, and I think:&lt;/em>&lt;br>
    &lt;em>when will life give me a break?&lt;/em>&lt;br>
    &lt;em>Damn! I&amp;rsquo;m tired. I need&lt;/em>&lt;br>
    &lt;em>to die for at least a week.&lt;/em>&lt;/p>
&lt;p>These words echoed in me, I also want to die for a week so that I can wake up, and more importantly maintain, the spirits and mental clarity I experience from 8:30 to 9 in the morning, while I read (the time when I read this and other poems, by the way) and listen to music.&lt;/p>
&lt;p>But the truth is that I have been dead for more than a week, 140 days to be exact, or at least that&amp;rsquo;s how it feels. I want to go to recess, a break from this era of human history, and be able to feel euphoria for life again, not a constant fear of losing it.&lt;/p></description></item><item><title>The Sunday that Lasted a Summer</title><link>https://luisangel.me/post/2020/07/26/the-sunday-that-lasted-a-summer/</link><pubDate>Sun, 26 Jul 2020 13:34:27 -0500</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/post/2020/07/26/the-sunday-that-lasted-a-summer/</guid><description>&lt;p>There is a recurring feeling in my life. A feeling I associate with a time and a place. The feeling of a Sunday afternoon, which for some reason tastes of melancholy and even a bit of despair. As if the start of a new week signified the death of the being who lived in the week that just ended.
I have had this feeling since I can remember, at least since middle school.&lt;/p>
&lt;p>When I walked my dog on a Sunday afternoon, there was something about the calm and emptiness of the streets that made me uncomfortable.
At first, I feared this feeling since I didn&amp;rsquo;t understand it, but by the time I was in high school, I had accepted it. I got used to it. I simply called it &lt;em>the Sunday Sadness&lt;/em>.&lt;/p>
&lt;p>After a while I learned how to escape from it. By college I started going out with a girl, who would eventually become my girlfriend, on Sunday afternoons; one day I explained this to her and she understood.
With her, I discovered that as long as I was with company the feeling would disappear. With this, I began to appreciate the things that a Sunday afternoon brought: the beauty of the deserted streets at sunset, the distant sound of children playing in some park or the occasional &lt;a href="https://es.wikipedia.org/wiki/Kerm%C3%A9s">&lt;em>kermesse&lt;/em>&lt;/a> of some church celebrating something.&lt;/p>
&lt;p>As of writing this, it has been 125 days since the pandemic caused by &lt;a href="https://es.wikipedia.org/wiki/COVID-19">SARS-CoV-2&lt;/a> began, and I have just figured out how the quarentine makes me feel. It&amp;rsquo;s like a long Sunday afternoon, that bittersweet feeling prolonged throughout an entire summer. Just as sunset announces the end of a week and the beginning of a new one, every so often the end of the pandemic is announced with great fanfare, but so far it has not ended (nor have things improved, honestly). My family has been fortunate during this time, as we have not lost any loved ones to the disease, and the economic losses have been manageable so far; but not all of my close ones have been so lucky.&lt;/p>
&lt;p>So, yes, I write this because I feel like I&amp;rsquo;m back in high school. Unable to do anything to improve the situation, unable to see my friends, partner, or my family with the ease I had gotten used to. Constantly enclosed, surrounded by screens, and living &lt;a href="https://www.brainyquote.com/quotes/mitch_kapor_163583">that internet metaphor&lt;/a> day by day.&lt;/p>
&lt;p>Now I just look out the window at this eternal sunset, hoping soon to be able to see my grandparents again, walk hand in hand with the one I love through a park, and gather to laugh with my friends, because I simply miss them.&lt;/p></description></item><item><title>about me</title><link>https://luisangel.me/about/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/about/</guid><description>&lt;h2 id="whoami">whoami&lt;/h2>
&lt;p>I&amp;rsquo;m Luis Angel, a software developer and writter from Mexico. I&amp;rsquo;m a curious person, that has lead me to several things that I really enjoy like tech, films, music, videogames, literature, philosophy, gardening and gumpla. I write about a lot of those things in &lt;a href="https://luisangel.me/categories/">the writings section&lt;/a> of this page, so I encoruage you to check them out.&lt;/p>
&lt;p>&lt;img src="https://luisangel.me/images/about/i-really-like-computers.jpg" alt="i really like computers meme">&lt;/p>
&lt;h2 id="contact">contact&lt;/h2>
&lt;p>Nowdays I really don&amp;rsquo;t use social media that much, but I would love to talk! So the best way to get in touch is via email (&lt;a href="mailto:hey@luisangel.me">hey@luisangel.me&lt;/a>), Mastodon (&lt;a href="https://vmst.io/@link">@link@vmst.io&lt;/a>) or Bluesky (&lt;a href="https://bsky.app/profile/linksake.bsky.social">@linksake.bsky.social&lt;/a>) (￣▽￣)ノ&lt;/p></description></item><item><title>projects</title><link>https://luisangel.me/projects/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><author>hey@luisangel.me (Luis Angel Ortega)</author><guid>https://luisangel.me/projects/</guid><description>&lt;p>Over the years I&amp;rsquo;ve worked on several things, most of them are in spanish but here&amp;rsquo;s a list of them if you wanna check them out!&lt;/p>
&lt;h2 id="activeish">active(ish)&lt;/h2>
&lt;ul>
&lt;li>&lt;a href="https://uveg.edu.mx/index.php/es/info-mael">&lt;strong>Master&amp;rsquo;s degree (education)&lt;/strong>&lt;/a>: Currently I&amp;rsquo;m taking my masters on Education with a focus on Online Education on the Universidad Virtual de Guanajuato.&lt;/li>
&lt;li>&lt;a href="https://eltelar.xyz/posts/luis-angel-fomac-8/">&lt;strong>The Cave (book)&lt;/strong>&lt;/a>: I&amp;rsquo;m working on my first book named &amp;ldquo;La cueva&amp;rdquo;, more info soon(tm).&lt;/li>
&lt;li>&lt;a href="https://eltelar.xyz/">&lt;strong>El telar (colective)&lt;/strong>&lt;/a>: A group of writers based on Chihuahua, Mexico that gets together to read our work, give feedback. We want to do more, we&amp;rsquo;re working on it. Also, I maintain the website.&lt;/li>
&lt;li>&lt;a href="https://github.com/LinkSake/metwo">&lt;strong>luisangel.me v2 (website)&lt;/strong>&lt;/a>: The thing powering this words!&lt;/li>
&lt;/ul>
&lt;h2 id="paused">paused&lt;/h2>
&lt;ul>
&lt;li>&lt;a href="https://curcubita.art/">&lt;strong>Curcubita (colective)&lt;/strong>&lt;/a>: Art colective/studio founded along with some artist friends with the intention to have synergy with each other.&lt;/li>
&lt;/ul>
&lt;h2 id="archived">archived&lt;/h2>
&lt;ul>
&lt;li>&lt;a href="https://www.ivoox.com/podcast-nerdverse_sq_f1261615_1.html">&lt;strong>Nerdverse (podcast | 2015 - 2016)&lt;/strong>&lt;/a>: It was my first podcast, I did it as a part of a podcasting community named Estudio Geek / XLR Studio and we (some colaborators and myself) talked about comics, videogames, movies and pop culture.&lt;/li>
&lt;li>&lt;a href="https://linksake.github.io/DimeQuien/">&lt;strong>DimeQuien (website | 2018)&lt;/strong>&lt;/a>: A website in colaboration with &lt;a href="https://github.com/eagleera">Daniel Aguilera&lt;/a> and Wikipolitica to showcase the profile for different candidates for the local elections of that year.&lt;/li>
&lt;li>&lt;a href="https://www.youtube.com/@uwusuarios/featured">&lt;strong>uwusuarios (podcast | 2021 - 2022)&lt;/strong>&lt;/a>: My latest podcast where we didn&amp;rsquo;t had a main theme but we talked about the topics that where on our mind. I really enjoyed my time doing this with Nessie, hopefully someday we can give it another shot.&lt;/li>
&lt;li>&lt;a href="https://github.com/LinkSake/me">&lt;strong>luisangel.me v1 (website | 2020 - 2024)&lt;/strong>&lt;/a>: My previous webpage/blog made with Nextra.&lt;/li>
&lt;li>&lt;a href="https://github.com/LinkSake/startpage">&lt;strong>startpage (website | 2023)&lt;/strong>&lt;/a>: Minimal startpage based on several startpages I saw on &lt;a href="https://www.reddit.com/r/startpages/comments/12bobou/my_first_custom_start_page/">r/startpages&lt;/a>.&lt;/li>
&lt;/ul></description></item></channel></rss>