skip to content
Podcast cover art for Shipping Web Applications with Dominic Saadi
Podcast

Shipping Web Applications with Dominic Saadi

Dominic Saadi shares his journey from biochemistry to web development and discusses his contributions to the Redwood framework community.

Open .md

Episode Description

Dominic Saadi shares his journey from biochemistry to web development and discusses his contributions to the Redwood framework community.

Episode Summary

In this episode, Dominic Saadi joins hosts Anthony Campolo and Christopher Burns to trace his unconventional path from biochemistry major to active Redwood JS contributor. Dom recounts how studying complex systems science in Boston led him to Python, data visualization, and eventually the browser, sparking a deep interest in web development. After experimenting with Vue and Nuxt without shipping a product, he discovered Redwood around its public launch in early 2020 and quickly became one of its most prolific contributors, starting with a scaffold improvement and progressing to Tailwind integration and the community newsletter. The conversation moves into technical territory around Prisma's foreign key syntax changes, the benefits of TypeScript for self-documenting code, and the evolving CSS landscape with Tailwind. A substantial portion of the discussion centers on Redwood's architecture, particularly the role of services as an abstraction layer beyond just Prisma, and the unresolved challenge of state management on the web side. Dom and Chris agree that while Redwood's API side is exceptionally well-designed, the front-end experience still needs more guidance, especially for developers building interactive, local-first applications. The episode closes with thoughts on Redwood's multi-sided architecture and the potential role of Deno in its future.

Chapters

00:00:00 - Meeting Dom and His Journey to Programming

Anthony introduces Dominic Saadi as a special guest, recounting how Dom was the very first person from the Redwood community he ever connected with through the newsletter. Dom shares his background, explaining how he started as a biochemistry major in college with only a brief, unhelpful high school programming class under his belt. He took some C++ courses but found the language dry and theoretical for a beginner.

After graduating, Dom worked at a cellular washing machine factory processing blood donations for research facilities, an experience that motivated him to be more intentional about his career. He then pivoted to studying complex systems science in Boston, which turned out to be heavily data-science oriented, requiring him to learn Python. Working in Jupyter notebooks daily and seeing a web team create stunning D3 visualizations sparked his curiosity about the browser and web development.

00:05:10 - From Python to the Browser and Discovering Redwood

Anthony and Christopher relate to Dom's journey, with Anthony noting the similar path from Python and Jupyter notebooks to web development, and Chris sharing his own difficult experience learning C++. The conversation shifts to how Dom discovered Redwood, recalling Tom Preston-Werner's initial tweet and Paul Graham's retweet. At the time, Dom was deep in Vue and Nuxt territory trying to build a note-taking app inspired by Roam Research, and switching to Redwood meant learning React—too big a leap at that moment.

Dom reflects on the trap of endlessly evaluating technology instead of building, admitting he never shipped anything with his Nuxt setup. He describes how working on a video game with his brother using the open-source Godot engine taught him Git fundamentals and the basics of contributing to open source. When he returned to web development with a clean slate, that experience made the jump to Redwood far more approachable. Chris pinpoints his own Redwood discovery to the Full Stack Radio episode with Tom on April 22nd, and Anthony notes the striking overlap between Redwood's public launch and the beginning of COVID lockdowns.

00:10:09 - Contributing to Redwood and Building Apps

Dom explains how going through the Redwood tutorial convinced him he had found the right tool, but he initially channeled his energy into contributing rather than building. His first contribution improved the scaffold command to support subdirectories, and the positive feedback loop of community appreciation kept him going. He acknowledges the need to shift toward building actual applications and describes his current calendar app project as a necessary step to make more meaningful contributions going forward.

The discussion turns to Dom's interest in local-first applications, where mutations happen on the client and sync to the server asynchronously rather than waiting for server confirmation. Chris explains this as "asynchronous UI," common in React Native due to unreliable mobile connections. Dom references Rich Harris's vision for SPAs competing with mobile apps, drawing a distinction between Redwood's goal of shipping interactive applications versus Next.js's focus on shipping pages. Chris adds a forward-looking note about React Native Web potentially converging with React, citing Twitter's web app as an example built with React Native for the web.

00:15:26 - Writing, the Newsletter, and the Redwood Community

Anthony raises the topic of writing culture in the Redwood community, and Dom shares that writing was his first passion, ignited by a college course on Nabokov. He views programming as a means to build better writing tools and still considers writing the higher creative pursuit. Anthony resonates deeply, describing how writing bridges the gap between the alien world of coding and human connection through language.

Dom then explains how the Redwood newsletter came about organically—he saw so many cool things happening in the community that he compiled forum highlights and pitched the idea to Tom, who immediately supported it. The newsletter's sole purpose is helping people use Redwood better by surfacing new features, contributions, and community work that might otherwise be buried in release notes. He specifically highlights the Prisma foreign key update as an example of an important change that could easily go unnoticed without a dedicated communication channel.

00:19:33 - Prisma Foreign Keys and TypeScript Benefits

Christopher asks why the Prisma foreign key update matters, launching a detailed technical discussion. Dom and Chris explain how connecting related models in Prisma previously required verbose nested object syntax with connect and create keywords, and how the update simplified this to a single key like author ID. Chris walks through the layered object structure that was previously required, and both agree the simplification is a significant developer experience improvement.

The conversation naturally flows into TypeScript's value, with Dom describing how exploring the generated types in node_modules made Prisma's capabilities crystal clear without needing documentation. Chris echoes this, recalling a conversation with Andy and David about how Command+Click on a type eliminates the need to read docs. Anthony summarizes the consensus that TypeScript's self-documenting nature through type introspection is consistently the top reason developers advocate for it, though Chris is quick to add that proper documentation remains essential.

00:25:23 - Tailwind CSS Integration and the Reusability Debate

Dom discusses his work integrating Tailwind with Redwood, humorously noting he was simply giving the community what it wanted rather than being a Tailwind evangelist. He praises Tailwind both as a CSS innovation and as a model for sustainable open-source business. Chris introduces Twin Macro, a project that bridges Tailwind syntax with styled components through Babel transpilation, which he used for CSS encapsulation on projects embedded in other websites.

The discussion evolves into a thoughtful debate about Tailwind's impact on DOM readability, with Chris questioning whether utility classes sacrifice the ability to identify components in the DOM tree. Dom pushes back on the emphasis on premature reusability in programming, arguing that Tailwind's approach of applying styles directly is more practical than designing abstractions from the start. Anthony draws a parallel to JSX, noting that both Tailwind and JSX faced initial skepticism simply for being different, with the common advice being to give each five minutes before judging.

00:31:40 - Understanding Redwood Services

Anthony brings up Dom's well-received forum post about Redwood services, a concept that confuses many newcomers. Dom explains that his key insight was thinking of Prisma as just another service rather than something uniquely special—it happens to be the default, but services should be understood as a general abstraction for any API integration, whether Stripe, Fauna, or anything else. He argues that tightly coupling the concept of services with Prisma is what causes confusion.

Chris shares his experience integrating Stripe and the challenge of knowing where to draw boundaries in the SDL file. Anthony adds his perspective from working with Fauna, where removing Prisma forced him to write services from scratch, which clarified their true purpose. Chris makes the important point that the perceived coupling with Prisma stems from generators being Prisma-specific rather than from the architecture itself, and Dom praises Redwood's API side as being beautifully designed and years ahead of where it might be expected given the project's age.

00:36:49 - State Management Challenges and Closing Thoughts

The group tackles what they see as Redwood's biggest front-end gap: state management guidance. Dom argues that the web side needs its own service-like patterns and that developers shouldn't underestimate the complexity involved. He critiques Apollo's attempt to serve as both data fetcher and state manager, noting a lack of clear real-world examples. Chris walks through the familiar React state escalation path from useState to prop drilling to context to external libraries, highlighting how daunting that crossroads can be for newcomers.

Both Dom and Chris agree that while Redwood shouldn't pick a single opinionated state manager, it needs to better communicate where its opinions end and developer responsibility begins. Dom emphasizes that the worst feeling is assuming there's a "Redwood way" to do something when there isn't one. In closing, Dom highlights Redwood's unique multi-sided architecture and speculates that Deno could play a role in its future, while Chris humorously expresses his loyalty to JavaScript and reluctance to move on. The episode wraps with mutual appreciation and excitement for Redwood's trajectory.

Transcript

00:00:00 - Anthony Campolo

All right. You guys want to get right into it? All right, Dom, I'm super excited to have you here as a podcast guest. Podcast guests are a bit like children. You're not really supposed to have favorites, but I've been really looking forward to getting you on because you are the very first person from the Redwood community that I ever interacted with. This was back, I think, in June. You had just put out the very first newsletter. We talked a little bit about that and went back and forth. You were super kind, super welcoming. I felt like it really set the tone for what the Redwood community is like. So I'm really happy to have you on here and to get to learn a little bit about you.

00:00:48 - Dominic Saadi

Thank you. I'm flattered by that. I definitely got the kindness from David and Rob, just how they welcomed me into the community. I just wanted to pay it forward. I feel like I don't even deserve to be anyone's favorite. There are so many cooler people in Redwood. David's done so much for helping us, kind of like any time we're feeling a little upset or uneasy. But that's cool. When you write the newsletter, you send it out, and you wonder who's reading it and what they're thinking. You were the first one to contact me. It was really cool. It's just amazing how many relationships have started from Redwood. I got into it just to do web dev, but I find I'm meeting all these crazy people. It's almost more worth it than anything I've made with it so far.

00:01:32 - Anthony Campolo

Yeah, that's what Kim said in her talk yesterday. Kim Adeline, she'll hopefully be on the show at some point too. She said, "I came for the contributions, but I stayed for the community."

00:01:43 - Dominic Saadi

Beautiful way to put it. Her talk was amazing.

00:01:45 - Anthony Campolo

Why don't you tell us a little bit about yourself? I'm kind of curious what your background is, how you got into programming. I think you were someone who didn't originally study computer science or anything like that, and you've kind of found your way to it a little bit like me. So why don't you give us a little bit of your background?

00:02:01 - Dominic Saadi

I think the first time I knew about programming was in high school. Maybe at the end of my senior year, I took a programming class. That was just an absolute joke. I don't think I learned anything at all. I think it was about Java, but I honestly couldn't tell you. And I went into college as a biochem major only because I liked both of those subjects and just planned on maybe going to med school. It was this hazy possibility, which I'm not sure. If you want to be a doctor, you should probably know a little bit more than an inkling. But I thought, okay, well, if I don't want to be a doctor, I should at least learn something about computers. I felt a little uncomfortable knowing nothing at all about programming and just how to use a computer because you use one every day. I decided to do a computing specialization. I made it through two out of the three classes, which were mainly C++. That was so dry and just all theoretical, you know, you're working with Visual Code or whatever.

[00:03:01] Visual Studio, not even Visual Studio Code. And they really set you up with almost industry-level stuff. You never see the light of day. It's just a tough language to give to a beginner. I think I dropped out of the third class because I was also a TA at the time, a teaching assistant. So I was giving a lecture for a class, and it was a lot of work. I graduated with biochem and went to work at a cellular washing machine factory, basically, where you would just mine for leukocytes from people who donated blood, and those white blood cells would be given to research facilities in Boston who bought them, like Novartis and stuff like that. So that's a huge business. Just, you know, you get that first job and then you realize that jobs kind of suck if you don't pick them or think about them at all. So you might as well think about it a little more and get stuck with something you like.

[00:03:55] I got into complex systems science just because the idea of studying real things like society, the idea of complexity, just was so appealing, scientifically speaking. It's a little bit antithetical to physics in that physics has this idea that you can reduce everything. You can understand something by reducing it down, and complexity kind of said you can't. If you reduce it down, you destroy what it is, and you've lost your chance of ever understanding it. I shipped over to Boston from LA and discovered that complex systems science was basically data science, so I had to learn Python. I was coding Python like every day for a year, just in my Jupyter notebook, hitting Control+Enter, you know, doing science. There was a web team there. They were doing all this crazy cool stuff with D3 and these animations, and I could understand data so much better like that. That really got me interested in what this thing called the browser was.

[00:04:54] And I remember when you first open the console and you're like, what? There's a REPL in here and all this other stuff. Like, what's going on? That's kind of how I got into web. From there to Redwood is another stretch, but that's how I went from being a biochem major.

00:05:10 - Anthony Campolo

Yeah, that's so similar to my journey because I also started doing Python, and same thing. You know, Jupyter notebooks, and you're in this very specific sort of environment that is easy to work with because it is a little bit like a REPL in the sense that you could just execute code. But then once you actually want to do anything with it, like you want to actually deploy something, you realize that this is not a very good way to do it, and then you start expanding out. And then I found that getting to web helped me actually see the base layer of some of this stuff. Like you said, it made it easier to think about how I would actually visualize some of these data points, because the data wasn't buried in this programming environment that was very foreign to you.

00:05:53 - Christopher Burns

I learned C++. It was my first C language. I hated it. Our assessment was to build a lovely C++ weather calculator. I know there are people out there that love C++, but to me it was just the worst experience I've ever had programming. I've never coded Python. I've opened a Python file and looked at it before, but I've never actually run a Python file.

00:06:21 - Anthony Campolo

Python's nice. Python's pretty simple. It's very readable. I think that if you're someone who already can program pretty well, you'll pick up Python really quickly if you wanted to. How did you discover Redwood? How'd you get into that? Because I know you've been around since almost the very beginning in terms of its public launch. We've talked about this with some of our other guests. There have been kind of many levels to Redwood's development, started just with Peter and Tom many years ago. And then they brought on David and Rob. And then March of this year is kind of when it launched and went public, and you've kind of been around since then, at least.

00:06:56 - Dominic Saadi

I remember when Tom first tweeted about it. I caught Paul Graham's retweets of it, like, hey, there's this thing called Redwood. Just hearing that news, I didn't want anything to do with it because I was already in Vue land, trying to get something to work with Nuxt and their whole ecosystem. At the time, I was trying to make a web app for taking notes because I was inspired by something similar to Roam Research, if you've heard of that. But that's a whole other rabbit hole. I was trying to do something like that, make taking notes a little more like a digital audio workspace, if you know what I mean, just a few more bells and whistles. So that was also the first time I was ever touching anything on the web. I was with Vue, and then this thing called Redwood came out, and switching to that at the time meant learning React and everything else. It was too big of a jump for me to make.

[00:07:50] And you can spend so much time picking the right tech that I knew I should focus on making whatever I was trying to make instead of finding the best piece of technology to use. But that obviously didn't work out because I never shipped anything with my Nuxt stack. It wasn't even a stack. I knew so little at the time. This was when I really didn't know anything about how web applications worked. I was so caught up in the React versus Vue debate, like in that podcast on Full Stack Radio. Retrospectively, that was me thinking React was a Rails competitor and I didn't even know what Rails was.

00:08:28 - Christopher Burns

Episode 136, Michael Chan. React is not a Rails competitor. I just looked up when I found out about Redwood, and I found out about Redwood the first day the Full Stack Radio episode with Tom Preston-Werner. And that was the 22nd of April. So that's when I found out about Redwood.

00:08:48 - Dominic Saadi

Yeah, it was early in the year, right? It's really crazy to think about. It feels like a long time ago, but it really hasn't been, just a few months.

00:08:56 - Anthony Campolo

I find it interesting how the history of Redwood tracks with the history of COVID. Think about the lockdown happening in the middle of March. And that's right around when the big Redwood announcement happened. So for me, the two are very interlinked together in terms of their timeline.

00:09:11 - Dominic Saadi

That's a good point. I'm not sure if that's something to brag about, but it is a fact. When I was trying to make something with Vue, it didn't exactly work. So I decided I needed to work with people, that that was the problem, right? I couldn't do it by myself. So I started working with my brother and my friend on a video game, actually, because I needed to find a team of people I could just make anything with at all. I'm sick of working by myself. So we were making a video game for maybe a few months using an engine called Godot, and that's actually open source. I tried my hand at contributing there. When I came back from that hiatus, all of a sudden I had a clean slate. I was willing to pick up any piece of technology, and I had tried to contribute. It kind of made the jump to Redwood a little more tractable because I could actually use Git on the command line, frankly, because that's not easy to do at all.

00:10:09 - Anthony Campolo

What type of stuff are you building with it?

00:10:11 - Dominic Saadi

I got into Redwood still with the idea that I was going to make this notes, digital audio workspace thing. Just even going through the tutorial made me realize, yes, this is what I need, you know, this idea of a back end at all. I kind of got swept up in the idea of learning web development because I finally could, because there was a way I could do it. So something that would teach me. And the easier thing for me to do when I first started the tutorial and got in the community was just contributing instead of actually building something. It was like at the time when the scaffold command, you would just run it and it would put all the files kind of in the base directory. And I thought, come on, why can't I say go to the admin subdirectory? You guys got so close, is how I felt. I decided, yeah, I'll make it happen.

[00:11:00] And I made that contribution. I just kept going, contribution after contribution after that. Because once you get one in and you realize people appreciate your work so much, and then other people use it, it's just a really addicting feeling. I'm definitely turning my attention to building stuff now that I've contributed so much. That's why we're here, right? Or that's why we got into Redwood, to build something with it. I'm starting with a more basic app besides the notes taking app I wanted to do. It's more of a little calendar app. I'll share the repo later, but I plan to release it this month. It's not a groundbreaking achievement or anything. It's just that as someone who's contributed so much, I need to build something with it to really move forward and make more meaningful contributions. And I'm definitely more interested in local-first apps. That kind of gets into one of the challenges of Redwood: this idea of state management, frankly, and the difference between state and caching, and Redwood's not really set up for local-first.

[00:12:01] It's just not obvious.

00:12:02 - Anthony Campolo

At least when you say local-first, what are you referring to by that?

00:12:05 - Dominic Saadi

With Apollo, you wait to hear back from the server before you consider data to be updated. That's not what I really want to do at all. I want to make the mutation locally, say, hey server, I did this, sync it whenever you can. The server is really just more of a persistence, like a data store. It's not doing that much else, at least at first, is it?

00:12:29 - Christopher Burns

Asynchronous UI is one of the terms people use to do it. For example, you click submit and your UI will then be like, I'm now going to wait until you've submitted this to the server and return something from the server, but instead you just carry on doing what you're doing. It's a lot more prevalent in React Native because obviously that's a mobile app where your connection could just drop out, for example.

00:12:53 - Dominic Saadi

Yeah, exactly. It is more like the experience of a mobile app. And if I can go back to Full Stack Radio again, that podcast with Rich Harris, I think the author of Svelte, and the idea that SPAs can be so much more. I'm definitely on the boat of SPAs competing with mobile applications. They should have that experience of you never really even know if your network is on or off. I look at Redwood as something to build applications with, whereas when I was listening to the Next conference, they described Next as shipping pages to the web, and I thought that was a really great description and a really great goal to have. But I look at Redwood as shipping these really interactive applications.

00:13:33 - Christopher Burns

We quickly touched on this whole concept with Tom. We're going to be seeing in a few years almost React taking a sidestep and React Native taking over. Expo is now fully supporting React Native for the web. While yes, it's React, but it's also React Native. The way certain things are done, like the routing, is all different. A good example of React Native for the web is Twitter's web app that's made with React Native for the web. This whole philosophy of you have React and then you have React Native, I think we're going to get to a point where one of them will take over. I think it's going to be React Native in the longer run, but we're just not there yet.

00:14:17 - Dominic Saadi

Yeah, that's a really interesting point. I had no idea you could use React Native to make a web application. So that's really cool.

00:14:24 - Christopher Burns

So React Native Web was started by a Twitter engineer. Nicholas was his username, but he moved on to work at Facebook on their React Native team. Expo is one of these platforms that say we're basically going to bridge the gap between native components and the JavaScript. They've now confirmed that they're taking on React Native Web into the main fold. But the problem with that currently is React Native Web sits behind the current branch of React Native, but the opportunities are opening. It's a really interesting look forward as well. You could build an application in React Native Web today, and I think you could get it working with Redwood using Apollo.

00:15:14 - Dominic Saadi

Well, we're just one PR away, it sounds like.

00:15:17 - Anthony Campolo

That's all it'll take.

00:15:18 - Christopher Burns

We are, but it needs a lot of Webpack, transpiling, and...

00:15:23 - Dominic Saadi

Whatever else happens in Webpack.

00:15:26 - Anthony Campolo

One of the things that I really enjoy about the Redwood community, there's a big emphasis on writing. For me, I always kind of experienced this tension between spending more time writing or spending more time coding or thinking of myself as a writer versus a programmer. And I know you spend a decent amount of time writing as well, so I'm curious if this is something you kind of think about as well.

00:15:49 - Dominic Saadi

This is a really interesting question. The roles you think of yourself as, it's not at the top of my consciousness, so to speak. Writing came first. And this love of writing and reading, towards the end of my senior year in college, I took a class on Nabokov. Before that, I was a reader, but I didn't really read any literature. But that class blew my mind. Some organ in my body could now sense why literature was so cool. And I still think it is, frankly. I definitely got into web development to make tools for writing. I don't write as much as I should, and I don't program as much as I should either. But writing was my first love, so to speak. Even now, I don't see myself that much as a programmer. I don't practice programming things just to practice them or do any [unclear] or study any algorithms.

[00:16:41] I still think programming is really cool. I guess I feel smarter when I'm writing and I have the peaks of my consciousness, or when I'm reading or writing. So I still think, at least for me, it's a higher activity that I want to pursue. And I'm using programming to make it even more so. I still don't know if that's the right way to do things or not. But part of the reason I got into Redwood was to build my own tools. It kind of falls in that category of I think there should be more tools, frankly, just at all. It's still easier for me to write with a paper and pencil, right? And that may never change. But I thought I should give a shot at making anything else. It just seems like very uncreative solutions keep popping up. There should be more as well.

00:17:32 - Anthony Campolo

Yeah, there is a point in time when on my Twitter it used to say, "A blogging programmer making programs for blogs," because I was kind of thinking the same thing as you know, making tools to write with. Writing to me just feels more human than coding. When you get really into it, it can be this whole world unto itself that can be very alien from anything else you're doing, and all your friends and family who don't do it, they have no idea what you're doing, and it's impossible for you to explain it to them. And so for me, writing was a way for me to bridge that gap and to connect with more of the human element of what I was doing. Because to me, language is just one of the most natural things that we do as people. It's why I love podcasts. I find language really, really interesting. So for me, writing kind of goes along with that. You write the Redwood newsletter, so how'd you fall into that?

00:18:22 - Dominic Saadi

So many people were doing so many cool things with Redwood. When I was learning Vue, there was a Vue newsletter that I would use a lot to find out about stuff I never would have found out about otherwise, like a new podcast or a new Vue library. And I wanted Redwood to have the same thing. I just took everything I saw on the forum and summed it up and gave it to Tom and said, this is cool, right? And he was like, yeah. That's how I kind of fell into it. My goal with that is just to help you use Redwood better. That's really the only goal it has. I just want to highlight the amazing work people are doing. And I want anyone, as a Redwood user, to know the latest thing about the framework because we're adding stuff all the time, and the 21, that Prisma foreign key thing, is huge.

[00:19:18] I just don't want things like that to go unnoticed because the release notes are where we're adding so many things in it. It's hard to keep up, really. So I just want to give you another way in to the top.

00:19:33 - Christopher Burns

Why is the foreign key Prisma update so important?

00:19:40 - Dominic Saadi

It's just really hard to make a generator. That syntax is quite a lot and it's a little unintuitive. It's a very big jump for people to make.

00:19:50 - Anthony Campolo

Can we explain what this is that we're talking about if we define this a little more clearly?

00:19:54 - Christopher Burns

You could probably explain it better than me. You'd probably use fancier terms than me. So here you go.

00:20:00 - Dominic Saadi

Well, whichever of us is more confused probably could explain it better, but it's just like in your Prisma schema, if you have a model that's connected in another way to another model, when you actually go about entering data with that and you want to make, say, you have a person or a people model and a post model, I guess author and post would be better here. If you want to make a new post with any kind of regular scaffold you'd use to update your data and you want to say, here's a new post and this is the author. The syntax for that is very verbose. You can't just say the author's name. You have to, in Prisma land, say author, and then that's an object, and you have to say connect. And you connect on a certain property of the model of the author, and it could be their name or their ID. They're trying to give you flexibility, but it's another step to make that just seems like, why can't I just give you their name?

[00:20:59] Why do we have to go through this contractual language?

00:21:03 - Christopher Burns

To just take it a step higher, if you've never actually worked with Prisma 2, what Prisma 2 basically is, is a CRUD builder. How you would start a query, say, for example, you wanted to get all the blog posts. You would say DB blog post dot find one, or find many, or create. For example, when you've got that dot create, that's when it becomes a function. And how do you start adding and removing data? It's all done through an object basis. So you start writing your object. And while there were multiple ways to do it, it tended to come down to clear, defined schema, such as where you would have the ID in the unique variables or data. And then when you wanted to connect, say, two tables together through this query builder, you would have to then open another object. And it comes down to two things: connect or create. They've simplified it to now just say if I'm going to say author ID, that means I'm going to be connecting this author. Previously you would have then had to do author and then write an object inside of author that says connect, and then another object inside of that that says ID and the author's ID. So really they've turned a three-layered object into one overall key. Is that a good explanation?

00:22:31 - Dominic Saadi

Yeah, you nailed it.

00:22:32 - Anthony Campolo

You can use fancy words, Chris.

00:22:34 - Christopher Burns

Well, that's just the fancy words that the object tells you to. And for me personally, this is where TypeScript shines and makes it so very easy to see what is available. But to what I understand, when you have jsconfig.json, that also tells VS Code to use the DB types.

00:22:57 - Dominic Saadi

Ah man, I wish I knew more TypeScript at all. I know for sure I can only understand Prisma because of what you're saying, because I hit Control+Space and it's like, okay, this is what I can do.

00:23:09 - Christopher Burns

Yeah. So if you don't know, that's TypeScript feature jsconfig.json. That's basically the same syntax of tsconfig, the TypeScript options file. So to what I understand, it's giving you the benefits of TypeScript without giving you TypeScript. Everything that I do is in TypeScript, so I don't truly know how well it gives you those typings.

00:23:37 - Dominic Saadi

It seems a little weird. You might as well just use TypeScript. It seems like why are we inventing these halfway points that are like, I don't know.

00:23:46 - Anthony Campolo

Yeah. It's like if you want to type your language, just type your language.

00:23:49 - Dominic Saadi

Yeah.

00:23:49 - Christopher Burns

This is where Prisma is really good in TypeScript, because what you can do is you can export types out of Prisma. For example, you know, you've got a data query, you're going to create an object, a blog post, and you're going to say there's going to be a title, a description, and a date, right? Instead of you writing that, you can extract that typing out of Prisma 2. So if it gets updated in the background later, it will automatically be updating your code without you having to manually code that type. So that's a really good feature of Prisma 2 as well, if you didn't know.

00:24:26 - Dominic Saadi

I kind of upgraded a little bit when I discovered how much Prisma relied on TypeScript, or how much the types could help me. When you go in your node_modules folder, there's like a .prisma or something, and it's just like everything you could do is in that folder and you don't have to go to their docs anymore. It's just very clear and straightforward. It's helpful to have that there.

00:24:48 - Christopher Burns

And that's the funny thing that you've just brought up. A few weeks ago, me and Andy were talking about TypeScript. I think it was with David, and it was like, why do you use TypeScript? It was like, because I can just Command+Click the type and totally understand what I need without looking at any documentation. It's great to know that other people have the same aha.

00:25:07 - Anthony Campolo

Yeah. When I hear people talk about why TypeScript is awesome, that's usually the very first thing they say is the introspection into your types and what you can actually do with them. So it's very self-documenting in that respect.

00:25:18 - Christopher Burns

But you still should document, don't get me wrong. You should still document.

00:25:23 - Anthony Campolo

Oh yeah. I want to talk about just a couple other things that you've contributed to the Redwood-verse. You've done a lot of work in integrating Tailwind with Redwood. Why Tailwind?

00:25:35 - Dominic Saadi

I just gave the people what they wanted, you know.

00:25:38 - Anthony Campolo

That's hilarious.

00:25:39 - Dominic Saadi

I'm not a Tailwind fanatic, per se, but there's so much interest. And honestly, I spin up new Redwood apps all the time, especially to try out something I'm contributing or if someone has a problem. So having a setup command for Tailwind just made a ton of sense because I don't want to open PostCSS config or whatever, and I'm just going to have to look that up every time. I think Tailwind is very interesting. It's probably the most interesting project in open source in some ways. In one aspect, it's innovative just in terms of what it's doing for CSS and rethinking best practices. But it's also innovative in that it's an open source project that is making money and has a team and is delivering amazing stuff. I think it's pointing in a direction for how to run a business that will help developers out but also keep you a little more than afloat.

[00:26:35] So you can do more for people in the way you want to. I've never used another CSS framework, like styled components or anything. I think I tried Bulma when I was with Vue. The idea of using Sass or CSS, and I forgot what the name of it is, like where you do the dash dash.

00:26:54 - Christopher Burns

BEM, block element modifier.

00:26:56 - Anthony Campolo

Yeah, BEM.

00:26:57 - Dominic Saadi

BEM. That's what I was thinking. Yeah, I feel like we could use a little bit of that in the sense of documenting what your HTML structure is, because I end up with a lot of divs or sections and it's not really clear why this is here, right? Tailwind has been amazing. In the same way that TypeScript, you just hover to see what's going on. Tailwind is the right amount of magic. The CSS really isn't too far away from you.

00:27:23 - Christopher Burns

You say you brought Tailwind to the people because they wanted it. Have you heard of a project called Twin Macro? And it's the crazy space where you say, I want Tailwind syntax to work with styled components.

00:27:41 - Anthony Campolo

Tailwind in JS. Whoa.

00:27:44 - Christopher Burns

Yeah. Tailwind in JS. It's really crazy because it works. But I had it built into my dashboard. So basically how you would integrate it is actually really ingenious. Instead of writing className equals bg blah blah blah, you would literally just write tw equals blah blah blah. And then that would transpile with Babel and styled components and build in the Tailwind CSS in JS. It was kind of crazy. I used it for encapsulation of CSS because I had a project that could go on other customers' websites, and you didn't want your CSS to be messed over by theirs. But I still wanted all the benefits of Tailwind. It's a really crazy good project to look up if you have a chance.

00:28:36 - Dominic Saadi

I'd love to see Redwood have more setup commands for CSS. I want to see what people are doing, and especially how to get better at it. Because I do feel like I'd probably still use Tailwind even if I knew more CSS. But I use Tailwind so that I don't have to learn CSS, frankly, so I can learn as much as I need to.

00:29:00 - Christopher Burns

What is more important when it comes to your DOM tree? Is it better to just write className equals bg, text, more? Or is it better to then abstract it to a CSS file with, this is a card? You then could look at the DOM and see the CSS tag of this is a card, but then you still get all the benefits of Tailwind. When I converted a project to Tailwind, you lost a lot of identity on the DOM tree of what it is. And if you didn't know what it was, you didn't know. I think the ultimate solution that makes no sense: className for Tailwind styles, and then ID to define what it actually is, even though you're not going to call the ID anywhere. If someone was to then look at the DOM, you would see the ID said card and the className says the Tailwind components. But I think this is a question across the whole Tailwind system that everybody's just trying to figure out, really.

00:30:08 - Dominic Saadi

I think Tailwind's answer right now is say, extract it all into a component, and then that component has a name and then you know what's going on. But I just haven't done that yet. I try to abstract as late as possible, almost always. And that's actually one thing I like about Tailwind a lot. I think the idea of reusability is a little overhyped in programming, unless you're making a library, which is explicitly for someone else to use. It's only slowed me down to try and design something with the intention of using it again later. I don't mean that in any sense of go agile programming or anything. Not that I have anything against it, but I think Tailwind got it right in terms of why are we designing for reusability at first or from the start, just sprinkling the tags on the DOM structure. It's more than okay. I just can't believe there was such a hard stigma around that for years, frankly, right.

00:31:03 - Anthony Campolo

It's like JSX, you know, all these things. Once you've done something for so long, anything that is different, you're instantly going to be like, hmm, I don't know about this. You don't think about, well, should I try it first and see if it's actually better or not? So I think Tailwind and JSX, both of those I've heard people describe as just give it five minutes, is what they say.

00:31:23 - Christopher Burns

Recently I've been having to build email templates and most of them are in Mustache and Handlebars. I'm like, this is still pretty cool that I can just do triple brackets. And why does React have this? And then you think because it's built completely different to have that functionality.

00:31:40 - Anthony Campolo

You have written a very well-received post on the community forums that we'll link to about services. And services are a Redwood feature that I know confuse a lot of people. It certainly confused me. Your post was kind of about the mental model for services, at least if I read it correctly, so I'd be kind of curious to hear what your thoughts are on services and what you're trying to accomplish with that post.

00:32:03 - Dominic Saadi

Yeah, it was around the time when I think Tom went on the Sam Selikoff podcast or Front End First with Ryan Toronto. And the interest in services blew up. It was always a super interesting abstraction. It's definitely the one thing that when he talks to Rails developers, they seem to really get into it, right? Like, oh man, services, this is so cool. So I can't relate to it because of that, because I was never a Rails developer. But the mental model for me that made services make more sense was thinking of Prisma as a service, because right now it has a very special place in a Redwood app. But it's more like a service that we just decided you should have pretty much always, or that's why you're using Redwood, because you want a database. But you shouldn't think of Prisma as being more special than another service that you could just integrate just as well.

[00:32:57] So like Stripe or something like that. I think Prisma is tied a little too closely to services, and that's why people get confused. They always think that a service means a Prisma model or something like that. A service is just an abstraction for making sure things stay maintainable in the long run. And I've never made a Redwood app that lasted more than a week or something. So there are other maintainability aspects that I still have to learn before I really, two years later, I'm like, thank God for services or something like that. The Jamstack is all about APIs, and I think services are the place for APIs because the APIs might change a lot. Jamstack is so young, the landscape is changing all the time, but Redwood has to think about making something to last a long time, right? That's why it's called Redwood. So services are kind of like the shield against the Jamstack ecosystem in a bit of a way. Call your service whatever you want and configure the APIs as you need them right now.

[00:33:54] Just because you change how your comment service works doesn't mean the rest of your app is going to suffer for it in any way.

00:34:01 - Christopher Burns

You brought up that you can use Stripe. I've done this in my application. You communicate through the Redwood API to Stripe, but if you look at how the Redwood tutorial, it helps you generate services through Prisma. But does Redwood help you generate a service for Stripe or a different third-party service? No. Now I need to look at the API that I'm trying to go to and create my own SDL file and create all that middle ground. When I integrated Stripe, the hardest point of that was saying where to cut Stripe's graph off because Stripe's API is interconnecting to the card machines to bitcoins. That takes a bit of experience to know where Redwood starts and Redwood ends. I used Prisma before I used Redwood, so I understood the glue that made it all magic. But if we think about your first time using it, Anthony, you can. I'm pretty sure you had this experience. You go, oh wow, this is really cool magic. I bet it's just Redwood doing it all.

00:35:10 - Anthony Campolo

Yeah. For me, I ran into this working with Fauna because when you use Fauna, basically, or the way I was doing it, you just rip out Prisma and then rewrite your services. And like you were saying, Dom, the services as they are now are very tied into Prisma. So by taking Prisma out and having to write your own services, that kind of gives you a better idea of what they're actually for. And yeah, it's about kind of reaching into Fauna's API and how do you interact with it?

00:35:37 - Christopher Burns

It's only linked with Prisma because the generators are currently linked with Prisma. If we could generate, say, Stripe code or Fauna code, then you could say the argument is no longer that it's just Prisma.

00:35:51 - Anthony Campolo

Or they're using the DB, find many, like they're using the Prisma commands in the services.

00:35:57 - Christopher Burns

Yes. See, this is the complex part. What is the service? I hear of my smart internet bank has 3000 microservices. And to what I understand of Redwood, every single file, you could say that's a microservice in the architecture of things.

00:36:16 - Dominic Saadi

That is definitely one of the hardest parts of Redwood. I do think that the API side is amazing. It's years ahead of where it should be when you really get into it. They knew exactly what they wanted. When you get into how the resolvers are tied to, it's just a thing of beauty, I guess.

00:36:35 - Christopher Burns

So I would say to me personally, the Redwood API side, ten out of ten. Perfect. The Redwood website, six out of ten. Still got a long way to go, but it's getting there.

00:36:49 - Dominic Saadi

I agree with you, and I think Peter would too. I've expressed concerns of, you know, just like, why haven't I shipped something? And it's definitely because front-end is hard. Redwood makes the hard possible, but we're still talking about hard stuff here. And I think that's where we have to remind ourselves. We're building a full-stack app. We're full-stack engineers at that point, and that is a crazy hard job. There's obviously parts of it that are still easy, but it's a hard endeavor.

00:37:14 - Christopher Burns

Redwood's getting there, but it's still got a long way to go in terms of how do we take all the processes of getting from the feature idea to the feature in production? I believe the API side of that is done right, that that's almost down to a point, but the website is... We're all still trying to figure it out as well.

00:37:35 - Dominic Saadi

In building my note-taking app, I had to learn a lot about state. I almost feel like the website needs its own set of services in a way. There's a lot more logic than you think. I brought in libraries like XState and things like that. And if you want to build a really feature-rich app, you have to understand why there are so many state management libraries and what they're all good at. You just can't skip it. It's actually pretty fun when you get into it and stop thinking that it's a chore. For some reason, we all think it's a chore, right? Like, oh my God, another state management library. And I've been kind of a critic of Apollo a little bit, just because they used to use Redux. So it was very clear that Apollo is getting your data and putting it in the state management library. And now it's like they're trying to do both. I'm not saying that it's impossible to do so, but I just don't see many clear examples of how it's done in a real-world app.

[00:38:32] And I just think we have to make that more clear because it's really not just like if you want to just use your scaffolds, you can, and I've seen apps like that. But for what I want to do, like a local-first app, scaffolds just aren't going to cut it. Or that's not fast enough, snappy enough for a user. How do you do that? Like, Redwood has to. I think we could do more for people building stuff.

00:38:55 - Christopher Burns

Do you think Redwood should have an opinionated state manager picked?

00:39:02 - Dominic Saadi

No.

00:39:03 - Christopher Burns

No.

00:39:04 - Dominic Saadi

I'd say no because state is too important depending on what you're building. I think you have to understand state. I just don't think you can skip it, is all I'm saying. And I think we have to just give people a few examples of this is the kind of app I'm building and I'm using this state management library. You know, there's just too many different front end apps you could make.

00:39:26 - Christopher Burns

State is one of these wide questions, right? Even I find it so gray of like, what's the right answer? In my Next.js app I use Pullstate because it's quite easy to interact with hooks and have a global state. But then in my Redwood app, I just focus on the state being replicated by the server. Is just using Apollo's state management through queries good enough?

00:39:55 - Dominic Saadi

Yeah, it's a hard question.

00:39:57 - Christopher Burns

Where do you start with state and where do you stop? I.e., how global do you go? Because React has these really cool hooks of useState and you're like, great, I can use state. But then you're like, yeah, but then I might want to change the menu from the nav bar, for example. And that's in a different component. Well, then I could do prop drilling. You're passing the prop down, but then you're like, ah, this is getting a bit complex. And then I feel like you're sitting at the crossroads of the hardest decision in your life. Will I go with React context, Redux, MobX, XState, or something else? And how do you make that decision? I do not know.

00:40:43 - Dominic Saadi

Yeah, it's a critical decision.

00:40:46 - Christopher Burns

You say it's critical. It's what do you want from it? Do you want to be able to say, I want to run this action that changes my state? Or do you just want to be a bit more wild west and just say, pull the hook and update it? To bring it back down to the point of Redwood web and the website, that side of the application of Redwood is not covered right now. And if Redwood is your first time using these technologies, that could hit you off guard massively.

00:41:19 - Dominic Saadi

Totally. I don't know if Redwood is doing it any worse than anything else, but for what Redwood wants to do, which is take care of you as a developer, really, it's kind of hanging you out to dry a little bit on the website. Yeah. When it comes to actually managing your state, it's hard to know, like, when is Redwood going to do this for me, and when does it have nothing for me? Right now as a developer using Redwood, I'm like, what's the way to do this? What's the Redwood way to do this? Where is it? So if Redwood doesn't have one, I'd like to know. And it's like, hey, you better figure this out because Redwood isn't going to figure it out for you. Just knowing when to make that mental switch, we need to communicate if there's ever going to be a point like that. I still think we can have opinions around state. But if Redwood is ever not going to take care of you, then we kind of have to explicitly say that because I think it's too easy to fall into the idea that there's a way to do this, and I'm doing it wrong.

[00:42:17] Right? That's not what you want to feel as a developer.

00:42:21 - Christopher Burns

Maybe the right answer here is we take a note out of Redwood Forms, if you understand what Redwood Forms is. Forms is a massive part of any React application. I prefer the raw interface of React Hook Form, but I understand the abstractions Redwood is doing on top of that. But you could say I don't like this way and go with Formik, and that's totally acceptable in Redwood web. So maybe the golden goose, the next module to be added to the npm repo, would be an opinionated state manager. Time will tell.

00:43:02 - Anthony Campolo

All right. Well, thanks so much for being here. Dom, do you have any closing thoughts? Things you're excited for, things you think the Redwood team should be thinking about?

00:43:11 - Dominic Saadi

Yeah. Thanks so much for having me. What you guys are doing is amazing, and I'm super looking forward to seeing you on Learn With Jason, Anthony. That is like blowing my mind for future Redwood. One thing that's easy to forget is Redwood is multi-side. That is pretty weird compared to all the other frameworks. I just think that is easy to forget, that we're ideally talking about making many different sides, and where it feels like other frameworks are just focusing on the web, we really have a lot more in mind. I think something like Deno might be really in the cards in the future because of that, but that is probably a whole other problem that hopefully won't be a problem for a while, but might be a bit of a pain to get integrated depending on what the future of Node is. But I think that's kind of on the horizon.

00:44:04 - Anthony Campolo

I got my eyes on Deno for sure.

00:44:06 - Christopher Burns

Deno scares me because I don't want TypeScript and JavaScript to die. I'm a JavaScript child. I do not want to move on to anything else. JavaScript for all. It's like the one ring in Lord of the Rings for me.

00:44:18 - Anthony Campolo

You can still write JavaScript in Deno.

00:44:20 - Christopher Burns

Don't even ask me how, that doesn't make sense in my head. I don't even know how that would work. I guess that's it for this episode. Thank you for your time, Dom.

00:44:30 - Dominic Saadi

Yeah, it's a pleasure.

On this pageJump to section