skip to content
Video cover art for Integrate APIs with StepZen GraphQL Studio - Frontend Horse
Video

Integrate APIs with StepZen GraphQL Studio - Frontend Horse

Anthony Campolo demos integrating multiple APIs into a unified GraphQL API using StepZen, showcasing its capabilities for simplifying backend dev

Open .md

Episode Description

Anthony Campolo demos StepZen, a GraphQL API gateway that unifies REST APIs, databases, and GraphQL endpoints into one queryable graph.

Episode Summary

In this final Frontend Horse live stream of 2021, host Alex Trost is joined by Anthony Campolo to explore StepZen, a hosted GraphQL API gateway that lets developers combine multiple backend data sources into a single GraphQL endpoint. The session begins with a boilerplate project returning mock data, then progressively layers in real data sources: first the JSON Placeholder REST API for user data, then the Rick and Morty GraphQL API for character data, followed by a Supabase Postgres database with both read and write capabilities. Anthony then walks through setting up a RedwoodJS full-stack app with Prisma and Railway's Postgres hosting, deploying it to Netlify as a serverless function, and feeding that custom GraphQL API back into the StepZen project. Throughout the build, Anthony explains how StepZen's custom directives — @rest, @graphql, @materializer, and @sequence — eliminate the need to write resolvers manually. The stream concludes with a tour of StepZen's GraphQL Studio, which offers pre-built integrations for services like Google Natural Language, Dev.to, Spotify, and Pokémon, demonstrating sentiment analysis on text input and showing how queries can be chained together for more complex use cases.

Chapters

00:00:00 - Introduction and Stream Setup

Alex Trost opens the final Frontend Horse live stream of 2021 and welcomes Anthony Campolo, a longtime community member and StepZen developer advocate. After some audio adjustments and shoutouts to chat regulars, Alex thanks StepZen for sponsoring the recent holiday charity show that raised $10,000 for Team Seas and removed 10,000 pounds of trash from the ocean.

The conversation sets the stage for the day's topic: a hands-on walkthrough of StepZen, which Anthony describes as a GraphQL API gateway. He explains the core concept — taking different backend services like REST APIs, databases, and other GraphQL APIs and unifying them into a single queryable GraphQL endpoint, comparing it to similar ideas like Gatsby's content mesh and The Guild's GraphQL Mesh, while noting StepZen's fully hosted deployment model.

00:07:28 - First Steps with the StepZen Boilerplate

Anthony guides Alex through the cloned StepZen boilerplate project, explaining the index.graphql entry point and the test.graphql file that defines basic GraphQL types including strings, integers, floats, JSON, and dates. They run stepzen start to deploy the endpoint and open the local GraphiQL editor to execute their first query against mock data.

The pair walks through fundamental GraphQL concepts like type definitions, field naming conventions, the non-nullable exclamation mark syntax, and how StepZen provides a live deployed endpoint rather than running everything on localhost. Anthony explains that the GraphiQL interface runs locally but queries a real hosted endpoint on StepZen's infrastructure, and mentions using tools like Insomnia or Postman to verify the endpoint independently.

00:21:24 - Connecting the JSON Placeholder REST API

With the mock data working, they move on to connecting a real data source by creating a users.graphql file that defines a User type with id, name, username, and email fields. Anthony introduces StepZen's @rest directive, which maps the REST endpoint to the GraphQL query automatically without requiring hand-written resolvers.

Alex queries the endpoint and gets back real user data from the JSON Placeholder API. Anthony explains that unlike Apollo Server where developers must write JavaScript resolvers to transform REST responses into GraphQL-compatible shapes, StepZen handles that mapping automatically based on the schema definition. He also mentions StepZen's JSON-to-GraphQL conversion tool that can auto-generate type definitions from API responses, making the process even more accessible for beginners.

00:30:03 - Adding the Rick and Morty GraphQL API

The next integration uses the Rick and Morty GraphQL API to demonstrate StepZen's @graphql directive for stitching in external GraphQL endpoints. Anthony walks Alex through creating a Character type and a nested Characters type that handles the API's paginated response structure, explaining how GraphQL types can contain fields that reference other types to form a graph.

A viewer asks whether the directives are StepZen-specific, and Anthony clarifies that @rest, @graphql, and all StepZen directives are custom additions built on GraphQL's spec-level directive capability, while the types, queries, and mutations remain standard GraphQL. They successfully query character data alongside the earlier user data, demonstrating how multiple data sources coexist in a single unified graph.

00:38:10 - Integrating a Supabase Database with Mutations

Anthony introduces database connectivity by having Alex spin up a new Supabase Postgres database. He explains Supabase's value proposition as a Firebase alternative built on open source technology, and briefly discusses the broader database landscape including Railway, PlanetScale, FaunaDB, and CockroachDB.

They create a books table, set up a config.yaml file for secure API key storage, and build a books.graphql schema that includes both a query and a mutation using the @rest directive with POST method and a post body. Alex successfully creates a book entry called "Old Man and the Sea" through the GraphiQL mutation explorer, verifies it appears in the Supabase dashboard, and then queries it back — demonstrating full read-write capability through StepZen's unified endpoint.

00:56:41 - Building a RedwoodJS Backend with Railway and Netlify

The session shifts to creating a custom GraphQL API using RedwoodJS, a full-stack JavaScript framework that bundles Prisma as its ORM. Anthony explains how Prisma translates JavaScript into SQL and manages database migrations, while Alex connects a Railway-hosted Postgres database to the new Redwood project.

They define a Post model in Prisma's schema, run a migration to create the database table, and use Redwood's scaffold generator to produce a full admin UI for managing posts. After deploying the Redwood app to Netlify as a serverless function, they wire the resulting GraphQL endpoint into the StepZen project, successfully querying posts alongside all previously connected data sources in one unified graph.

01:24:46 - The Mega Query and Linking Data Sources

With five data sources connected — mock data, JSON Placeholder users, Rick and Morty characters, Supabase books, and Redwood posts — Alex runs queries across all of them through the single StepZen endpoint. He reflects on the practical value this would have had at his previous agency job where combining review data, product information, and location services from different APIs was painful.

Anthony introduces two additional StepZen directives: @materializer for linking types across different APIs, and @sequence for chaining queries so the output of one feeds into the input of another. Alex draws parallels to real-world scenarios like connecting Shopify products with CMS content, inventory data, and review services, recognizing that StepZen's approach goes beyond simple aggregation to enable meaningful data relationships across backends.

01:31:26 - Exploring StepZen's GraphQL Studio

Anthony demonstrates StepZen's GraphQL Studio, a browser-based tool offering pre-built integrations for popular APIs. They connect the Google Cloud Natural Language API and run sentiment analysis queries, testing phrases like "I feel happy" versus "I feel sad" and observing polarity scores, which sparks an amusing exploration of how Google rates various emotional statements.

They also briefly explore the Dev.to API integration and browse other available connectors including Spotify, Pokémon, Twitter, Unsplash, and combined templates like outdoor dining search using Google Maps, OpenWeather, and Yelp. Anthony explains that all these integrations generate the same GraphQL schemas they'd been writing by hand, and projects can be exported and extended with custom code.

01:48:19 - Wrap-Up and Year-End Reflections

Anthony summarizes StepZen as "the front of the back end" — a tool that gives frontend developers access to backend capabilities and helps them become more full-stack. He notes that any framework capable of making a fetch request can integrate with a StepZen endpoint, and points to existing tutorials for React, Vue, and Svelte frontends.

Alex closes the final Frontend Horse stream of 2021 by thanking the community for a remarkable first year of streaming that grew from casual experiments into a thriving Discord community and culminated in a charity fundraiser. Anthony plugs StepZen, RedwoodJS, and his podcast FSJam, which covers many of the tools and projects discussed during the stream. The pair signs off wishing everyone a happy holiday and promising to return in January 2022.

Transcript

00:05:01 - Alex Trost

Hello and welcome to the last Frontend Horse live of the year. Happy 2021. I am so thrilled to be able to end it with our good friend Anthony. Anthony, it is so great to have you on, man. How's it going, buddy? I know you just hopped off from a different stream. You are in demand, my friend. How are you doing?

00:05:27 - Anthony Campolo

I'm feeling great. I'm really happy to be here. It's an honor to get to be on the show with you. I've been watching it for a while, been hanging out in the Discord for a while. So if you're a Frontend Horse regular, you've probably seen my little cartoon avatar popping around. Yeah, just super excited to get a chance to play around with some cool GraphQL stuff with you and get to show the audience what we're doing here at StepZen.

00:05:52 - Alex Trost

Yeah, it's awesome, man. And yes, you've been in the Discord as far as I can remember. I don't remember a time in the Discord without Anthony. I think you might have come in like the first or second week or something. Oh yes, thank you, Ben. I do need to —

00:06:08 - Anthony Campolo

Yeah, it was probably after maybe a month or two. When did the Discord actually start?

00:06:12 - Alex Trost

Hold on one sec. I just got — I have to boost you. We didn't get a chance to do a sound check. Yeah, I need to figure this out on the fly. Unfortunately. Thank you for saying that, Ben. I can drop myself. There we go. Gain. We're boosting that. All right, cool. Can you give me something, Anthony?

00:06:37 - Anthony Campolo

Yes. Check, check, check. One, two.

00:06:39 - Alex Trost

Let me go a little bit higher with you. Almost there, almost there. All right.

00:06:43 - Anthony Campolo

Okay. Hello.

00:06:45 - Alex Trost

Perfect. All right. That seems pretty good. All right. Also, StepZen, which is what we're going to be getting into, was one of the five big sponsors of our holiday show that we did on Friday, which helped raise $10,000 for Team Seas and removed 10,000 pounds of trash from the ocean. So thank you to you and to StepZen for sponsoring that. I really appreciate you guys coming through for that.

00:07:26 - Anthony Campolo

We're happy to do it.

00:07:28 - Alex Trost

Yeah. So StepZen is now an integral part of the Frontend Horse stream and the Frontend Horse community. Let's get into it. First off, what is StepZen? What are we even going to be doing today?

00:07:45 - Anthony Campolo

Yeah, it's hard to give a succinct definition of what StepZen is without using a couple of terms you need to define first. I would call it a GraphQL API gateway. An API gateway is something that sits between different services. So if you want to talk to a database, you'll usually do it through an API gateway — that's a very common pattern. AWS has a service literally called API Gateway, and that's usually a REST API. REST APIs have their own bespoke way of handling resources and mutations and stuff like that. Whereas GraphQL is a standard query language for APIs. So explaining StepZen requires explaining GraphQL also. But I know you have a little bit of GraphQL experience from doing Gatsby, and I think that's probably where frontend-heavy people will have seen it the most. The cool thing about GraphQL is it's actually a very simple, concise language where you just write either the word query or the word mutation, name it, and then specify what the query is and what you want back from it.

00:08:57 - Anthony Campolo

Everything we're going to be doing today is GraphQL, and then there'll be certain things that are specific to StepZen, because the point of StepZen is to take different kinds of backends and turn them into a GraphQL API. Whether that is a REST API, a database, or even another GraphQL API, it will stitch it all together into a single graph for you. If you've ever used Apollo, you may have had to figure out how to get a bunch of different data sources together and write resolvers that move throughout different pieces of the backend to find the right data and stitch them back together into a single object you can query. With StepZen, it does that for you automatically. You just write a bunch of schemas and then you can query it. What we're going to do is end with one giant mega query that's going to hit five or six backends all at once and get all the data in one go.

00:09:52 - Anthony Campolo

So that's kind of the high-level pitch — what is StepZen?

00:09:55 - Alex Trost

Got it. So it's my one-stop shop for all the data that my project needs, basically.

00:10:01 - Anthony Campolo

Yep, that is the idea. Whether that backend data is living in a CMS, a database, or just some random endpoint some developer gave you at some point in time — here you go.

00:10:13 - Alex Trost

Got it. Yeah. I know with my projects they might start out where I just have one source of data — maybe just Prismic, or even Markdown, or just Supabase. We just did a project that needed to fetch donations from Supabase. But as you continue to add onto that project, you keep piling on different data sources and it starts to get clunky. Like, I need the Supabase data to integrate with my Prismic data and all these different things. So if I have an API gateway that can handle that and manage the merger of that data for me, and I just have to talk to StepZen and not all these ten different data sources — that sounds like what I love about Gatsby. My interest is piqued.

00:11:21 - Anthony Campolo

Yeah. The terms "data mesh" and "content mesh" come up frequently with Gatsby. They were calling it a content mesh, and I think that's a really good term for it because it just kind of unifies everything into one fabric. You also hear the term GraphQL Mesh from The Guild, because they have an open source project that does a similar thing to StepZen — you can take all these different backends with different languages and types and put them all together into one thing. The main difference is that with StepZen you also get a fully hosted experience. When we build out the project, you'll be able to run a command that will deploy your endpoint, and that gives you a deployed endpoint that you can then use in any frontend you want. For someone who already knows how to work with a GraphQL API and knows how to send queries from whatever their favorite frontend framework is, you will immediately have an endpoint you can start querying and working with, which is really cool.

00:12:26 - Alex Trost

Great. Love it. So how do we want to get started here?

00:12:32 - Anthony Campolo

Yeah. So the first thing — I see Michael

00:12:34 - Alex Trost

Chan in the chat. Great to see you, my friend.

00:12:37 - Anthony Campolo

Always good, buddy.

00:12:39 - Alex Trost

Yeah, yeah.

00:12:40 - Anthony Campolo

Good to see you. While we start, you can clone the StepZen boilerplate that I had shared with you, because this will be a good way to —

00:12:48 - Alex Trost

I'm a step ahead, Anthony. I am ready. I'm here. So I did a few things to prep for the stream, just to fill in chat in case you're coming here looking to follow along. I cloned this down. Let me actually grab this repo for our friends. Yes, I want to go — I cloned this down, and then I installed the StepZen CLI.

00:13:24 - Anthony Campolo

Yep.

00:13:25 - Alex Trost

So those were kind of —

00:13:26 - Anthony Campolo

The CLI is what you're going to be using to actually deploy and interact with it. So it's really sweet because you just run a single command, stepzen start, and it does pretty much everything for you. Then why don't we look at each of the different files we have. So go to index.graphql — this is the entry point into your graph. Right now we have one single file, which is test.graphql, and that is going to be our graph. But as we go and add more data sources, we're going to create new files that will be brought in. Every time we create a new file, you have to remember to go back to your index.graphql and add the new filename. We're going to do that a handful of times.

00:14:10 - Alex Trost

Cool.

00:14:10 - Anthony Campolo

Right now it's just a single file. Basic project setup.

00:14:14 - Alex Trost

Great.

00:14:15 - Anthony Campolo

Then if you go to test.graphql —

00:14:17 - Alex Trost

Hold on, give me two seconds. I want to turn that bot off if I can manage it. Oh no, my keyboard is — see if I can turn that off super quick. Sorry about that. First stream since the fundraiser. Okay, it is off. Thank you for letting me do that.

00:14:36 - Anthony Campolo

Except for the snowtacular.

00:14:38 - Alex Trost

Yes, that was the donate link. You can still donate, but I don't want to spam. Trash.

00:14:45 - Anthony Campolo

I decided actually I really like trash now.

00:14:48 - Alex Trost

Yes. Cool. Sorry to cut you off. I just saw that pop up and wanted to nip it. Cool. I want to go where now?

00:14:58 - Anthony Campolo

test.graphql. Cool. This is our first basic GraphQL schema. This can also help anyone who doesn't know GraphQL — we can walk through it real quick. We're defining a test interface and it has some very basic types. You have a string, int, float, JSON, date, and datetime. And then we have a single query called getTest, and that query returns the test interface. Every StepZen schema you have is going to have a directive under the query that connects it to something. We don't have that right now because this is just set up to return mock data, just to make sure your GraphQL API is up and running. This is all you need to get started.

00:15:55 - Alex Trost

Got it. Cool.

00:15:56 - Anthony Campolo

And then go to stepzen.config.json. This will give us an endpoint name. Right now it's going to be api/stepzen-boilerplate.

00:16:07 - Alex Trost

So this is going to be preceded by like stepzen.com and my account name, and then I can determine what this is called beyond the hosted StepZen instance, right?

00:16:21 - Anthony Campolo

Yep, exactly. It's going to map to your name and your own custom domain. So anyone can deploy this and will have the same part at the end, but everyone will have their own part at the beginning because it's being hosted on their own account.

00:16:34 - Alex Trost

Cool. All right, great.

00:16:37 - Anthony Campolo

And then let's go ahead and run stepzen start and see what happens. This is where the magic happens — or the magic blows up and we die.

00:16:49 - Alex Trost

All right, so —

00:16:51 - Anthony Campolo

So you can see two things here right now. Before you go anywhere, this is important to explain because it confuses people when they start. We have a localhost:5001 running with a GraphiQL editor, but that is not the endpoint. The endpoint is not actually on localhost:5001. The endpoint itself is on stepzen.net — it's already a live endpoint, not running on localhost. But you have GraphiQL running on localhost to query that endpoint.

00:17:21 - Alex Trost

Got it.

00:17:21 - Anthony Campolo

Open up localhost:5001. This is also nice because GraphiQL is already giving you your StepZen keys in here, because if you want to hit this from a frontend — which we're probably not going to go into — you have StepZen keys, which I think you showed at the very beginning of your stream, by the way. So we might want to roll those.

00:17:38 - Alex Trost

Cool. Sounds good.

00:17:39 - Anthony Campolo

It was in your account. It was showing.

00:17:41 - Alex Trost

So they just show. Got it.

00:17:45 - Anthony Campolo

This is being included in your GraphiQL right now.

00:17:48 - Alex Trost

Got it. We might want to tuck those behind a little show button for future reference.

00:17:53 - Anthony Campolo

Yeah, it should be. I'm not sure why it isn't.

00:17:56 - Alex Trost

Oh, good.

00:17:58 - Anthony Campolo

So let's write — actually, first thing, open the Explorer.

00:18:02 - Alex Trost

Cool.

00:18:04 - Anthony Campolo

And then hit getTest and hit all the buttons except testMock.

00:18:10 - Alex Trost

Sounds good. Got it.

00:18:13 - Anthony Campolo

There you go. So there's our first GraphQL query. As you can see, we're getting back all of our different types. You have the date and you have a more specific datetime. You got your float, got your int, got your JSON. One is just an empty JSON object, so you have kind of two JSON test cases — like, what happens if they just throw an empty JSON object. So yeah, this is just our first get-up-and-go thing. Questions so far?

00:18:40 - Alex Trost

Not for me. This is making sense so far. So this is like — I had to make sure in my head — just because it's string: String, the first one is just the name and the second one is the type.

00:18:57 - Anthony Campolo

Yes. Yeah, that's a little confusing based on this example, but that's exactly it. You wouldn't necessarily have to call these the exact same thing. That's just so when the data pops out, you can see what's what. You could call it anything and it would return either the string, or the int, or the float.

00:19:13 - Alex Trost

So like, as long as — like that. And yeah, it'll — if I refresh, maybe it'll refresh and —

00:19:21 - Anthony Campolo

The Explorer will update. Yeah, so try name.

00:19:24 - Alex Trost

Yeah, name.

00:19:25 - Anthony Campolo

There it is, all the way at the bottom.

00:19:27 - Alex Trost

Yeah. So obviously that's not a real name, but I just want to point out — this is the key, here is what we're calling it, and that's the type. And then the exclamation mark means it's required. Is that correct?

00:19:40 - Anthony Campolo

Yep, exactly.

00:19:42 - Alex Trost

Awesome. Yeah.

00:19:42 - Anthony Campolo

Or non-nullable. Can't be null.

00:19:45 - Alex Trost

Got it. Cool. Thank you for that clarification. So this is good for me. We've got an endpoint and it is live — down at the bottom it has the stepzen.net URL. So that's already deployed and we can hit it as long as we send it an actual request.

00:20:12 - Anthony Campolo

Yeah. One thing I like to do is have Insomnia open where I'll test that endpoint with my StepZen keys in the header, just to get that verification — okay, it's working through the StepZen thing, but what if I just actually hit this from any API tool? Say, Postman. We did a Postman stream where they showed how to work with something like this using their GraphQL tooling. Most API tools now have GraphQL-specific tooling, autocomplete, and type checking, which is all pretty great.

00:20:51 - Alex Trost

Awesome.

00:20:52 - Anthony Campolo

All right, so the data was populated as just mock data. This is why I'm starting with this as the first example — the data is not coming from anywhere. This is just what StepZen does if you don't give it a real endpoint. The next one we're going to do will use the JSON Placeholder API, and that's where the data will be populated with real content. And then we're going to show how to do a database, so there's going to be data coming from lots of different places. Right now this data is nowhere — it's just built into StepZen as a mock test thing.

00:21:24 - Alex Trost

Cool. Awesome. So now what do we want to do?

00:21:30 - Anthony Campolo

Create another file and let's call this users.graphql.

00:21:41 - Alex Trost

Cool.

00:21:41 - Anthony Campolo

Yep. And then we're going to create a type this time — not an interface. So it's going to be type User, then curly braces, then we're going to have id: ID.

00:22:03 - Alex Trost

Like that or —

00:22:05 - Anthony Campolo

Yeah, both capitalized — both ID. Yeah, because that's another GraphQL thing, is that there's usually an ID for each type.

00:22:16 - Alex Trost

Hey, Steph.

00:22:17 - Anthony Campolo

Then we're going to add just a bunch of strings, which are going to be name, username, and email. The type has to match up with the API we're going to hit. So before we actually do that, we should show the JSON Placeholder API. Last one was email: String.

00:22:44 - Alex Trost

And do you want these non-nullable?

00:22:47 - Anthony Campolo

Let's put exclamation points after all of them.

00:22:49 - Alex Trost

Yeah, okay.

00:22:53 - Anthony Campolo

Cool.

00:22:53 - Alex Trost

All right.

00:22:54 - Anthony Campolo

And then let's do type Query now, outside of the type User block.

00:23:02 - Alex Trost

Yeah, my keyboard's being funky.

00:23:05 - Anthony Campolo

Yeah, luckily there's not a whole lot of typing we'll be doing. The stuff we're writing is going to be very concise. Cool. So we're going to do getMockUsers — camel case. Cool. Sorry, users, because it's going to return an array of users. Then do colon and then inside brackets do User. Basically what this means is that it's going to return an array of these User objects. That's the whole query. And now here's where the StepZen stuff comes in. So make another line under getMockUsers, indent two spaces — or tab if you're one of those people — and then do @rest. All lowercase, then parentheses, then endpoint: and then quotation marks. And inside there you're going to use the JSON Placeholder URL. Do you want me to read it out or do you want to just grab it? I dropped it in the chat.

00:24:28 - Alex Trost

Yeah, I'll grab it. Is it the gist? Where are you dropping it? Oh, did you drop it in the chat? Got it. Was not sure.

00:24:41 - Anthony Campolo

Yeah. Which is easier for you when I'm sending you stuff?

00:24:44 - Alex Trost

If you want to share it with chat — like if it's something like, hey, here you go, if you're following along — that works. If it's not something chat's really going to care about, then you can drop it in the DMs.

00:25:02 - Anthony Campolo

Either way, I'm going to drop a gist, which is essentially a script of what we're doing here. It can get confusing if you start looking ahead.

00:25:13 - Alex Trost

So I do this — like I drop all that in there?

00:25:17 - Anthony Campolo

No, no, no, no.

00:25:18 - Alex Trost

Okay.

00:25:18 - Anthony Campolo

Yeah, just the endpoint.

00:25:22 - Alex Trost

Yeah, okay. Just the URL.

00:25:24 - Anthony Campolo

Exactly.

00:25:24 - Alex Trost

Yeah, got it. Okay.

00:25:25 - Anthony Campolo

Exactly. Yeah. So what's going on here is this is essentially telling StepZen we are going to run a query with the type we've defined, and then it's going to resolve it with this endpoint.

00:25:39 - Alex Trost

Okay, got it.

00:25:41 - Anthony Campolo

Now let's save that and then go back to index.graphql because we have to add —

00:25:46 - Alex Trost

Add the file.

00:25:48 - Anthony Campolo

Yep, exactly. It'll be exactly like that — users.graphql. Cool. All right, you can go back to your GraphiQL editor. You should refresh anytime you change something so you'll have it in the Explorer. Cool. Yeah, so this is really great because you don't really even have to know how to write these queries. The problem right now, unfortunately, is your screen resolution. Normally it's not as big of an issue.

00:26:26 - Alex Trost

This is not a StepZen thing — this is a GraphiQL thing, the editor that you use.

00:26:31 - Anthony Campolo

Yeah, it's a popular open source library that we're just sticking our logo on top of.

00:26:36 - Alex Trost

Yeah. But I mean, that's what Gatsby and everyone does. Yeah, yeah, it's a wonderful tool.

00:26:43 - Anthony Campolo

We're going to go ahead, do all four of those. Yeah. Awesome.

00:26:48 - Alex Trost

Okay, so that is pulling from here, right? From this — Leanne Graham. Is that what it's doing?

00:26:56 - Anthony Campolo

Cool. Now you can see — if you've ever done GraphQL before, this is where you'd have to write resolvers in Apollo Server, because you'd have to hit the REST endpoint and then write JavaScript code to take the object and map it into something that makes sense to your schema. That's what StepZen is doing for you. It's letting you skip writing resolvers and just go with a schema and the query, and it figures out how to do the resolvers. Which is mind-blowing.

00:27:35 - Alex Trost

Yeah. So there's nothing special about this endpoint necessarily. I could have put in any REST API here and it would have taken care of it. It's not like you've explicitly mapped out the JSON Placeholder endpoints — it's already figured out.

00:27:58 - Anthony Campolo

The only thing we had to figure out was the User type itself. And we even have a tool that lets you convert JSON to GraphQL. I've done this enough that I can just look at an API and quickly figure out the types. But there's actually an auto-generating tool we have that can do that part for you, which is really great. This actually makes a lot of stuff more accessible to beginners. This is why I've been really passionate about this project, as someone who's still relatively new — StepZen is actually my first tech job. I was in a bootcamp before this. So having access to all these APIs really quickly because of the power it gives you is really, really cool. Having people wrap their minds around it is important to me. Because when you first look at StepZen, it can be hard to understand what it's really doing, because you're writing so little code.

00:29:05 - Anthony Campolo

But once you understand it, it's a very easy way to work with a lot of stuff all at once, which is really great especially with Jamstack. There's just so many services now and so many ways to connect to different stuff. But every API is different — every single API is different.

00:29:25 - Alex Trost

Yeah, that's why I'm just trying to make sure that this — yes, every API is different. So to make one solution that takes them all in feels near impossible to me. So I'm just clarifying — this isn't something you've already mapped out beforehand because it's a REST API in a certain format. When we can tell StepZen what that format is and what we're expecting, then we can work with that in our GraphQL API. Got it.

00:30:02 - Anthony Campolo

All right.

00:30:02 - Alex Trost

Okay.

00:30:03 - Anthony Campolo

So the next one we'll do is going to be almost identical, but instead of an @rest directive, it's going to be an @graphql directive.

00:30:11 - Alex Trost

Got it.

00:30:12 - Anthony Campolo

So we're moving to GraphQL. And we'll be using, of course, the ever-fantastic Rick and Morty GraphQL API. Are you a Rick and Morty fan?

00:30:22 - Alex Trost

I have — no, I'm not. I just haven't really gotten into it. The fan base keeps me away, to be honest.

00:30:31 - Anthony Campolo

Oh, that's too bad. I'm a fan of the show, but I've been a fan of lots of things with terrible fan bases. I used to like Tool, so I get it.

00:30:41 - Alex Trost

Yeah, I mean, it's not that I'm explicitly against it or anything, just haven't dipped my toes in too far. All right, cool.

00:30:49 - Anthony Campolo

It can be pretty aggro. So yeah, let's create a file called characters.graphql.

00:30:59 - Alex Trost

Cool. We're going to do a type here.

00:31:01 - Anthony Campolo

And then let's go ahead and add that into our index.graphql right now.

00:31:03 - Alex Trost

All right, characters.

00:31:09 - Anthony Campolo

Austin knows what I'm talking about.

00:31:12 - Alex Trost

Yeah. Austin, how's it going? Good to see you. And yeah, that was an excellent quote — used to like Tool. All right, cool.

00:31:23 - Anthony Campolo

Type Character.

00:31:26 - Alex Trost

Cool.

00:31:27 - Anthony Campolo

With an ID field of type ID again. And then name and image, which will both be strings. One of the things I'm doing here is not having you write out the entire schema — I want to show the directives, which is the important part.

00:31:51 - Alex Trost

Cool.

00:31:51 - Anthony Campolo

If you really want to work with something like this and send any kind of query, you'd have to get the entire schema. But we also have auto-generating tools to introspect a GraphQL schema. One of the great things about GraphQL schemas is that they usually — if it's a public one — will let you introspect them and basically say, "what are the types?" and they just tell you. We've built tools that will let you do that as well. I'll drop that link in the chat too. You can introspect —

00:32:26 - Alex Trost

Yeah. It's good to see you, Mike. Welcome to the chat, buddy. Hello. Okay, cool.

00:32:34 - Anthony Campolo

We're not going to do that right now though, because it'll give us like a 10,000-line file.

00:32:39 - Alex Trost

No worries.

00:32:41 - Anthony Campolo

Yeah. Cool.

00:32:42 - Alex Trost

Back to this. All right, so we got a Character with ID and name.

00:32:45 - Anthony Campolo

All good. Yeah. And then we're going to create a type Characters. This is because the Rick and Morty API is kind of nested — the thing we really want is going to be the characters, but to get there we have to do this. So do results, all lowercase, then colon, then in brackets Character. Yeah, exactly. So now what happens is the field is — this is a little more GraphQL jargon here — the types have fields, and the fields can return other types. This is why it's a graph: you can have things nested within each other as much as you want. Now we're going to write a query that returns Characters, but without wrapping it in brackets.

00:33:51 - Alex Trost

Okay, not following yet, but I will once it comes back.

00:33:54 - Anthony Campolo

Sure. Yeah. So just do type Query outside of the Characters type, and then characters, all lowercase, returning Characters with a capital C. We're not putting it in brackets because it's already going to return an array — the array is within the results field. So that's why we just return the Characters type. This is just a little bit of GraphQL stuff you need to know. And there's a question in the chat: are the REST directives unique to StepZen? Yes, all of the directives we're showing here are unique to StepZen. The @rest one was unique, and now we're about to do an @graphql one. These are the special sauce of StepZen, because everything else — you're still writing queries and types, your schema is pretty much unchanged — but the directive is what does all the stitching together of the endpoint to those queries. The ability to write directives and give them custom behavior has been in the GraphQL spec from the beginning. You just don't see it that often because people typically build GraphQL projects from scratch. This is a nice way to have StepZen-specific built-in conventions.

00:35:28 - Anthony Campolo

Built-in conventions into GraphQL that are StepZen-specific.

00:35:33 - Alex Trost

Awesome. Great questions, Cynthia. Really appreciate it.

00:35:39 - Anthony Campolo

Yeah, definitely. Keep the questions coming. I'm always a fan of explaining. I used to be a teacher, so that's actually one thing you and I haven't touched on.

00:35:46 - Alex Trost

Yeah.

00:35:48 - Anthony Campolo

And then now we're going to do @graphql, all lowercase, and then exactly like the other one — parentheses, then endpoint:. Yeah. And then make sure to save.

00:36:03 - Alex Trost

Yep, hit save. Heading to our characters results — ID, image, name. Okay, there we go.

00:36:15 - Anthony Campolo

Cool. Yep. So now that's coming from the Rick and Morty API. And now yeah, let's hit a couple of these.

00:36:23 - Alex Trost

Yeah. Kind of want to — so you have our characters up here at the top, and then a little bit further we have our mock users. And then getTest was in the middle. All right. Got it. Perfect.

00:36:42 - Anthony Campolo

Awesome. Cool. Right, yeah. Now we're able to basically work with the entire thing as if it's one unified graph and write any kind of queries we want to get any sort of data. This was the promise of GraphQL from the beginning — that you would be able to do this from the frontend. The creators of GraphQL, who worked at Facebook at the time, have said they started from the mental model of a frontend developer and worked backwards. They basically said, what is the nicest possible query we could write, and then created an entire language to facilitate writing those kinds of queries. So StepZen really leans into that.

00:37:22 - Alex Trost

And you can do stuff like this, right, where if I want it to have a different name — there's just lots of small details in GraphQL that make it really nice to work with. I can't believe we've already got two different APIs built into this.

00:38:04 - Anthony Campolo

Yeah, two APIs and some mock data. Now we're going to get a database.

00:38:10 - Alex Trost

Okay. All right. Nice. Checking off the GraphQL API. We're fine.

00:38:14 - Anthony Campolo

It can't just be any kind of database. It needs to be a Supabase database.

00:38:19 - Alex Trost

Supabase database. Got it. Nice. Awesome.

00:38:24 - Anthony Campolo

You already know how to use Supabase at least a little bit — at least spin it up — because it takes a minute or two, and then we'll start writing code.

00:38:32 - Alex Trost

How do you want me to do that? You want me to use one of mine?

00:38:38 - Anthony Campolo

I mean, if you want, you can just make a brand new one, or I can make a new one. If you hit your limit, you just make a new organization and then you can make more.

00:38:45 - Alex Trost

Yeah, I mean, I can spin one up. Give me one sec.

00:38:50 - Anthony Campolo

Yeah. And then I can talk a little about — for people in chat who may not know all the new dev tool companies out there — Supabase is a way to host a Postgres database with a really nice UI, because they want to essentially mirror the functionality of Firebase but with a relational Postgres database. If you've ever used Firebase before, you know it's not just a database — it's also a querying language and client libraries and authentication and storage and serverless functions. Supabase is the equivalent of that, built on an entirely open source stack. I'm a really big fan because I like using Postgres. I've been using Redwood, so I'm very familiar with Postgres. Having the ability to spin up a Postgres database in a minute or two and just start using it is really, really powerful, because you'll never need to install Postgres locally ever again. These things just work so well, and they're free for the most part.

00:40:00 - Anthony Campolo

It's great for beginners who just want to get their hands on a database but don't want to worry about breaking something or paying a $40 bill to Amazon because their database was the wrong type and all that kind of stuff.

00:40:12 - Alex Trost

Yeah. And everything includes auth, storage — they've got a whole bunch of stuff now. It's just great. And there's a few of them too. Like I've been using Supabase, but PlanetScale is another one that's kind of up and coming. FaunaDB, right?

00:40:32 - Anthony Campolo

Yeah, I've used almost all of them. I'm actually a really big fan of Railway because Railway supports Postgres, MySQL, Redis, and MongoDB, so you can use any of those just as an add-on. You can actually have multiple different types of databases all at the same time, which is really weird but works pretty well. CockroachDB also has a serverless offering. So if you're into databases, this is like the golden age of databases right now.

00:41:01 - Alex Trost

CockroachDB — I just don't understand why they would name it that. Because the database can't die, right? But I mean, not a lot of people like that thing. I don't know. Anyway, Egad says Railway is dope. Yeah. I think we might be trying to play with it after Supabase. Is that right?

00:41:27 - Anthony Campolo

We'll see if we end up with enough time. Because I have another example that will involve a Redwood backend with Railway. So yeah, see if we get to that.

00:41:38 - Alex Trost

So I do have Supabase up. Would it be fine if we use the data from the donations project we just worked on Friday? Or do I do something totally different?

00:41:51 - Anthony Campolo

We're going to want a fresh database, because what we're going to do is show how to essentially hook into the RESTful API. So yeah, we're going to want a fresh table on a database.

00:42:05 - Alex Trost

So do a fresh table. All right, do we want anything — pull this over. This should all be fine. Anything here that we want to —

00:42:20 - Anthony Campolo

So yeah, just add a column and have that column say name, then make it text.

00:42:37 - Alex Trost

Okay.

00:42:37 - Anthony Campolo

Yep. That should be good. Save. Yep.

00:42:42 - Alex Trost

All right. Creating new table.

00:42:48 - Anthony Campolo

Okay. And then there's going to be some code I'm going to send you privately. We're going to need your API key, which you probably want to grab off stream. And then we're going to want the endpoint. Because Supabase gives you an endpoint that exposes a RESTful API. This is something people may not necessarily know about Supabase — they include this library called PostgREST, which is an auto-generating REST API for your tables. Pretty interesting.

00:43:31 - Alex Trost

So where do I put this configuration thing that you just sent me?

00:43:35 - Anthony Campolo

You're going to create a new file called config.yaml. Yep.

00:43:41 - Alex Trost

Okay.

00:43:42 - Anthony Campolo

Yep. And that's where it's going to go. Where the XXXX is, that's going to be your API key that you get from your Supabase dashboard. That's what you need to make sure you don't expose.

00:43:52 - Alex Trost

And where does the endpoint go? We're going to use that in the GraphQL query like we've been doing.

00:43:59 - Anthony Campolo

Yeah. I just sent you another chunk of code. Make a new file called books.graphql.

00:44:06 - Alex Trost

Okay. So do we want the public key or the secret one? Just probably the public one, right? For the API key there's always two. The secret one has like unlimited power. And then the public key you can —

00:44:22 - Anthony Campolo

I'm pretty sure it's the public one.

00:44:24 - Alex Trost

Cool.

00:44:24 - Anthony Campolo

Yeah.

00:44:25 - Alex Trost

All right. Saved that. And the public one's kind of fine to expose honestly — for the most part I've got it locked down anyway. Okay, so I got that done. Egad said — how do you miss the holiday party? What if we're going to do that today? Yeah. Great to have you. Thank you so much for coming through. This is the last stream of the year, so you're just in time. Let me go over and grab this. So type Book { id: — all right. What do we want to call this file?

00:45:02 - Anthony Campolo

Yeah, let's just call it books.graphql. And I'm realizing now because of how we named the table, we might have to modify this a bit. So instead of books, the endpoint path is going to be stepzen.

00:45:19 - Alex Trost

Okay. So typically, chat, you're going to name your thing not after the company that you're working with.

00:45:27 - Anthony Campolo

Can we go back? Let's see — can we rename the table?

00:45:30 - Alex Trost

Honestly, one thing that's been a pain with Supabase has been renaming tables and changing stuff, so I'm skeptical.

00:45:38 - Anthony Campolo

Okay, just delete that table and then create a new one called books.

00:45:42 - Alex Trost

Okay, well let me try it because I don't want to totally count them out. Let me refresh and make sure this actually worked. It seems like we were successful. Yeah, books. Got it. Awesome.

00:46:06 - Anthony Campolo

The only other thing you need to fill in is the XXXX in your endpoint URL. That's something you'll be able to get — since you're already having that REST API exposed, they give you this endpoint and then all you do is add a route for the name of the table. So cool. I think if you also already got your key in your config.yaml, that should be everything we need. This should restart. I should actually explain some of this code though. There's a lot happening here that wasn't in the others, so go back to books.graphql.

00:46:44 - Alex Trost

Sounds good. To do that.

00:46:46 - Anthony Campolo

Yeah. So the first thing we have here is that we're including now a configuration along with the endpoint. If you look at the @rest below books, it's very similar to the other one where it has the endpoint — but now we also have headers with an API key. This is where when you're building real projects, you're going to have API keys, auth headers, all this stuff, which can be hard and confusing to manage. Basically, all of your secret stuff will always be in config.yaml. Everything that's not in config.yaml should not be secret. Then actually, real quick, let's make a .gitignore just as good practice and put your config.yaml in that .gitignore file.

00:47:45 - Alex Trost

Thank you for the follow. Welcome to the stream. Good to have you.

00:47:52 - Anthony Campolo

Cool. Then the other thing — now we're writing a mutation and not just a query. Again, GraphQL: you write queries to get data and mutations to change data. We have the endpoint with the configuration and the headers, but we also specify the method, which is going to be POST, and then we're going to do a post body. The post body code is the one area where things get a little hairy, and it's going to be useful to have a StepZen example already written because I've figured out how to write this somewhat complex thing. It does a lot of character escaping. Basically it grabs the name, which is what we're going to input into our createBook mutation — we want to give the book a name when we create it. We write a GraphiQL query to create a book, give it the name, and it maps that to the post body. If we go back to our GraphiQL editor now —

00:48:53 - Anthony Campolo

Let's clear all this out. Yeah. Oh, we didn't add the file. Yeah, we forget at least once.

00:49:01 - Alex Trost

books.graphql. All right, cool.

00:49:10 - Anthony Campolo

Takes a second to save. Cool.

00:49:13 - Alex Trost

Good. Nice.

00:49:14 - Anthony Campolo

Yep.

00:49:14 - Alex Trost

"I'll say from the start, I'm no coder, but very much an ideas man. Background is Domino technical architect."

00:49:20 - Anthony Campolo

Interesting.

00:49:22 - Alex Trost

A Domino technical architect. I'm interested in what that is like — Domino's pizza?

00:49:27 - Anthony Campolo

Domino's? Or Domino — guessing it's Lotus Notes.

00:49:35 - Alex Trost

I've heard of those. All right, I've heard of that, but that's really interesting. It's great to have you, though. Always great. I'm a big believer in outside perspectives. Both Anthony and I come from different backgrounds as well. We are not classically trained developers, so yeah, definitely welcome the outside experience.

00:50:00 - Anthony Campolo

Okay, hold up.

00:50:01 - Alex Trost

Yeah, sorry, I got clicky.

00:50:04 - Anthony Campolo

Yeah. But there should be a createBook. Oh, I know why — because we're only looking at queries right now.

00:50:10 - Alex Trost

Yeah.

00:50:10 - Anthony Campolo

Underneath your stream thing — you can't quite see it because you pulled up the — yeah, there you go. Yeah, you select your mutations.

00:50:22 - Alex Trost

Okay.

00:50:23 - Anthony Campolo

And then hit the plus button. Cool. There we go. Now we're talking. Yeah.

00:50:33 - Alex Trost

Oh, okay. So I'm going to get rid of the query. Is that right?

00:50:37 - Anthony Campolo

Yep, correct. And then you can write the name in on the left or in the query itself. "Old Man and the Sea" — that is a book. And then just return the ID and name. Let's see.

00:50:52 - Alex Trost

All right.

00:50:53 - Anthony Campolo

How it does with that. Okay, so that's fine. But if we go back to our Supabase table now —

00:51:03 - Alex Trost

I'm sorry, what did you just say, Anthony? Did you say "super base"?

00:51:09 - Anthony Campolo

Oh, Supabase.

00:51:12 - Alex Trost

Thank you. Hey, look at that. It got in there.

00:51:16 - Anthony Campolo

Yeah, there's a slight bug there — it should actually be returning the ID and name. Something for me to figure out one day. But it actually does write it to the database. That is the far more important part.

00:51:27 - Alex Trost

That's really cool.

00:51:28 - Anthony Campolo

Now if we do the books query again, we should get back the book.

00:51:32 - Alex Trost

Oh nice. Okay, so how do I close out of the mutation? How do I get the queries back?

00:51:42 - Anthony Campolo

Yeah, I think you need to go back to the bottom and hit plus on query.

00:51:46 - Alex Trost

Yeah, I just closed.

00:51:47 - Anthony Campolo

Yeah. When you're working with both queries and mutations, the explorer gets a little dicier.

00:51:51 - Alex Trost

Got it. All right, so books — I should be able to get that back. Awesome. All right, nice. So with StepZen, I can create mutations that work with these same databases that I'm able to query from, and just through the one tool. I can't tell you how much I enjoy just using one thing, learning one thing. Through StepZen, I'm able to not only query all my data but maybe update user data. Or, as we just showed, if I'm doing a personal library app and I also want to call in reviews from Amazon and connect it to a books database and something else — I can have all of that coming in through one API.

00:52:44 - Anthony Campolo

Exactly.

00:52:44 - Alex Trost

That's really nice.

00:52:51 - Anthony Campolo

Watching GX Ray's snow tackling infrastructure in real time.

00:52:55 - Alex Trost

Yeah, right. Because that's kind of what we had to do. Team Seas — the charity we raised all the money for — had an API that was open, we didn't need to authenticate or anything. But it also wasn't documented, so we didn't know how to use it beyond a quick request for the Frontend Horse total. It was paginating at 150 and we had no idea how to go beyond the first page of results. So we set up Supabase to hold all of the donations just in case we went over 150. We were close — we were at like 125 or something. So it was a good call to have that as a backup. We had to combine those two different sources of data, and yeah, it was a little bit of a pain. Having something like StepZen to manage all those things is super cool.

00:54:14 - Alex Trost

"Can I ask your advice on something? Can wait till later if you're busy."

00:54:18 - Anthony Campolo

Yeah. Feel free to drop any questions in the chat. Always happy to help.

00:54:22 - Alex Trost

It's not just Anthony and I here — we've got some fantastic, much more knowledgeable people in the chat, so absolutely ask away. If it's something I'd like to give a more fleshed-out response to, either we can take it to the Discord or I'll let you know. But there's a good chance that people like Ben and Michael and everyone else can help.

00:54:46 - Anthony Campolo

You've got quite the hive mind built up in chat.

00:54:49 - Alex Trost

Yeah, there's good folks there. Awesome. So we connected a database, and not only to read from — I didn't expect us to be able to write to it so easily. It was a bit of copy-paste, but not a ton of code. That's awesome.

00:55:08 - Anthony Campolo

Where we're at right now, with time, we'll probably skip over the FaunaDB one. But people can check out the gist — there's an example where we would have done the exact same thing with Supabase but with FaunaDB. And there you're just writing regular native GraphQL mutations, and you don't have to do that weird post body thing. That's like the next step, and even nicer. But yeah, if you want to just go down to the FaunaDB section — yeah, there you go. So FaunaDB will give you a bunch of mock data for a store. You create a store type, and then you can find a store by ID, return all stores, create a store, update a store, delete a store. I think people pretty much get the idea at this point of the GraphQL endpoint and the config and all that. All right, well, that's a long one.

00:56:07 - Alex Trost

Yeah.

00:56:09 - Anthony Campolo

"Basic code, but needed touching up. As I'm no coder, I gotta flower it up, so to speak. I paid five grand. Whoa. That's a lot."

00:56:16 - Alex Trost

We can — I think we can come back to that in a bit, Anthony. I don't want to cut you off. But I think maybe Ben in chat or someone can help. Yeah, it seems like a detailed question that I definitely want to help with. Mostly Disco, just don't want to derail this entirely, but I appreciate you bringing it here. So what do we want to do next, Anthony?

00:56:41 - Anthony Campolo

Yeah, next I want to show you how Redwood works. So follow along with the Redwood API with Netlify functions. If you scroll down just a little bit more —

00:56:53 - Alex Trost

Cool.

00:56:54 - Anthony Campolo

There's a command right there. And then baby —

00:57:01 - Alex Trost

All right. I did actually — no, I did not. Okay. Should I do it in the boilerplate or outside?

00:57:12 - Anthony Campolo

Outside the boilerplate.

00:57:13 - Alex Trost

Okay.

00:57:13 - Anthony Campolo

Yeah.

00:57:16 - Alex Trost

yarn create redwood-app horse-zen-redwood. Yeah.

00:57:18 - Anthony Campolo

Actually, you should —

00:57:21 - Alex Trost

I can stop it. I can stop it.

00:57:23 - Anthony Campolo

No, no. Well, now this might create a folder you're going to want to delete. So first delete that folder if it created one, and then get a new VS Code window open.

00:57:34 - Alex Trost

It did not create a folder. We are good.

00:57:36 - Anthony Campolo

Okay, great. So just get a new VS Code window open.

00:57:39 - Alex Trost

Okay.

00:57:39 - Anthony Campolo

And then keep this one where it is. You can have your Redwood project and your StepZen projects both open at the same time. But yeah, to simplify our lives, we just keep them separate.

00:57:47 - Alex Trost

Okay, cool.

00:58:06 - Alex Trost

Correct, yes.

00:58:09 - Anthony Campolo

Redwood is actually how I got into the whole open source coding world in general. My job at StepZen was actually a direct result of the work I was doing on Redwood. It's a full-stack JavaScript framework for apps, and it says here it's for startups — but honestly, you can use it for all sorts of things. The idea is that it's a great tool for getting going really fast with a full-stack project. And when people say full-stack these days, it's not always clear what they mean — people refer to things like Next.js as a full-stack framework. But the real difference with Redwood is that it includes an ORM, which is Prisma. Have you ever used Prisma?

00:59:03 - Alex Trost

No, but I have used ORMs before. And thank you for the bits, Mostly Disco. I appreciate it. I will be reading and checking that out. Thank you.

00:59:13 - Anthony Campolo

Yeah, this will be great then, because we've got a Prisma employee in the chat — Austin.

00:59:18 - Alex Trost

Austin, yeah. Okay.

00:59:20 - Anthony Campolo

Yeah, yeah. And so Prisma is —

00:59:22 - Alex Trost

We've got to talk, buddy.

00:59:24 - Anthony Campolo

Yeah, you should definitely get him on to show you some Prisma stuff. So it's a way to turn JavaScript into SQL, because we all know we just want to write JavaScript. No one wants to write SQL, even though they probably should learn. I should learn at least a little SQL.

00:59:43 - Alex Trost

I should learn more. There's so many things I should learn, though.

00:59:47 - Anthony Campolo

But the great thing about Prisma is that you don't necessarily have to worry about writing SQL ever again. And you'll also be able to use it to do migrations on your database. This is part of the real power you get — the ability to set up your database programmatically. The thing we did manually through Supabase's UI, we're going to do programmatically through Prisma now.

01:00:14 - Alex Trost

Oh, nice. Got it. Okay. My ORM experience, just so you know where I'm coming from, is mainly through Django, the Python framework.

01:00:26 - Anthony Campolo

Great.

01:00:26 - Alex Trost

Yeah. So I really enjoyed their ORM that stopped me from having to do a whole bunch of SQL stuff, and that was a joy on my first web dev project. ORMs are very nice, I'm a fan. Should we check on that install and see if we're still running?

01:00:47 - Anthony Campolo

Cool.

01:00:47 - Alex Trost

Oh, Redwood has Prisma under the hood, is that correct?

01:00:51 - Anthony Campolo

Yes. So Redwood is bundling Prisma for you. You can use Prisma by itself and bring it into a Next.js project — this is common with Remix too, the docs show you how to bring in Prisma as well. Redwood is saying: we want to assume from the beginning that you want Prisma and actually bake it into the CLI itself. So we're going to run some commands that are prefixed with rw, but are actually just aliasing to a Prisma command. When you're learning Redwood, knowing where the boundary between Redwood and Prisma actually is can be a little fuzzy until you've gotten through the process of, like, ripping Prisma out and seeing what breaks — which is a fun experiment but not really recommended. When you're learning, just stick with using Prisma as Redwood provides it. You don't need to figure out how to integrate Prisma into your project; it's just assumed by default, and there are a lot of nice downstream effects of that.

01:01:50 - Anthony Campolo

Cool. While that's still going though, let's open up Railway.

01:01:53 - Alex Trost

We are here. It looks like we're good.

01:01:56 - Anthony Campolo

It takes longer on Windows than Mac unfortunately. Normally that would take about half the time if you ran it on an M1.

01:02:04 - Alex Trost

I don't know why my code thing broke — ever since, I can't open VS Code the fun way. So horse-zen-redwood. Okay. Yarn Redwood dev. Open folder. Is it horse-zen or is it horse-zen-redwood?

01:02:24 - Anthony Campolo

It was horse-zen-redwood.

01:02:28 - Alex Trost

There we go.

01:02:29 - Anthony Campolo

Cool.

01:02:30 - Alex Trost

Select folder. All right, nice. We are in.

01:02:32 - Anthony Campolo

Yep.

01:02:33 - Alex Trost

All right. And should we do yarn now?

01:02:35 - Anthony Campolo

yarn redwood dev. Yeah, this will kick off our dev server.

01:02:39 - Alex Trost

All right.

01:02:39 - Anthony Campolo

And it'll just give us a nice little splash page. Don't worry about that.

01:02:45 - Alex Trost

Okay, cool.

01:02:45 - Anthony Campolo

Yeah. Don't use the Redwood IDE. It tells you to check it out, but honestly that's kind of a weird beta project that doesn't actually work that well. So don't use redwood ide.

01:02:57 - Alex Trost

Good tip. All right, cool.

01:02:58 - Anthony Campolo

It will be very cool one day. That day is not today.

01:03:02 - Alex Trost

Got it. All right, so kicked off a localhost. Yeah.

01:03:06 - Anthony Campolo

And then this is going to give us a splash page. It'll get there, don't worry.

01:03:13 - Alex Trost

Cool. All right. Nice.

01:03:16 - Anthony Campolo

There we go. Yeah. Cool. Now we got that set up. We want a database we can use in our Redwood project. If you go to Railway, we're going to show how to do Railway. Cool about Railway is it spins up a database in 10 seconds. Unlike Supabase, which does take about a minute or so. This is really the fastest way to get a Postgres database up and running. So go ahead and do new project.

01:03:43 - Alex Trost

Okay.

01:03:45 - Anthony Campolo

What do we want to deploy? Provision PostgreSQL. Yeah. This will assume you already want Postgres when it sets up. Do you have many WordPress people in?

01:03:58 - Alex Trost

We have a couple, but we tend to lean more Jamstack, which you can do with WordPress — but typically more headless CMSs. I work for a headless CMS called Prismic, so I don't have a ton of WordPress experience. I've been mainly using headless CMSs. But we definitely have some people around who are at least familiar with WordPress. My friend Colby Fayock is really good with WordPress. "Web dev has let you down. Sorry to hear that."

01:04:41 - Anthony Campolo

If you go to Postgres on the left, then a little bit further down, go to Connect. This will hide your keys for you. We're going to want the bottom one — there are two things here. There's the psql command, which will let you directly connect to your database, but we don't need that because we're going to connect through Prisma. So we just need the connection URL.

01:05:10 - Alex Trost

Okay.

01:05:10 - Anthony Campolo

So you should go off screen for a second.

01:05:13 - Alex Trost

All right. And then with this, or with my code — with this. Right?

01:05:20 - Anthony Campolo

Yeah. You'll be able to copy this without exposing it, but you're going to have to drop it into your project in your .env file.

01:05:30 - Alex Trost

Yep, just the .env. Yeah, that makes sense.

01:05:34 - Anthony Campolo

Yeah. In .env, it'll have a commented-out part where it says DATABASE_URL. So you want to uncomment that and put the connection string in there.

01:05:45 - Alex Trost

Cool. DATABASE_URL. TEST_DATABASE_URL. Which one do I want?

01:05:51 - Anthony Campolo

DATABASE_URL, not TEST_DATABASE_URL. You can keep everything else commented out.

01:05:57 - Alex Trost

And I'm going to turn on — nope, didn't mean to do that.

01:06:04 - Anthony Campolo

Those mask-your-keys things.

01:06:07 - Alex Trost

So we've got that in there — just so chat can see, there is stuff here, it's just masked out. So save that. That is set. Do I need to restart the dev server?

01:06:23 - Anthony Campolo

Yes. Then keep the dev server off for a second.

01:06:30 - Alex Trost

Okay.

01:06:31 - Anthony Campolo

Then go back to — so first, let's set up our schema. Go to the api folder.

01:06:39 - Alex Trost

API. Okay.

01:06:41 - Anthony Campolo

Yep. And then db/ and then schema.prisma. Yeah, so let's change the default model — change it to say Post instead of User. Just a single word, Post. Yep.

01:07:01 - Alex Trost

Cool.

01:07:02 - Anthony Campolo

Yep. And then change email to title. And then get rid of the unique constraint. And then get rid of name: String. Yeah, and that should be good. We could add a createdAt field or something like that, but that's not really important to what we're demonstrating right now. So let's keep it simple. Save that. And then run: yarn rw prisma migrate dev --name posts. Let me explain this before you run it. What's happening is we're telling Redwood to run the Prisma command, and the Prisma command is migrate dev, and we're creating a migration named "posts." This is going to create a table in our Railway database for our posts, as specified with the Post model we just wrote.

01:08:25 - Alex Trost

Got it. I'll be honest, the word "migrate" just gave me a little — oh right, I remember the stuff I didn't like about databases and ORMs. The stuff I struggled with as a first-time developer in my Python app, breaking stuff. Migrations can go poorly once you have a lot of data and you don't know what you're doing. So that word hit me. I had to roll back to snapshots and all that kind of stuff. Sorry, just took a mental trip back in time.

01:09:04 - Anthony Campolo

That's a great point though. When you ran migrations in Django, were you able to see the SQL it was actually using to set up the database?

01:09:13 - Alex Trost

Maybe. But this was maybe like three years ago.

01:09:17 - Anthony Campolo

Great. So run this command. I'm going to show you something really cool. Oh, we forgot one other thing — change SQLite to PostgreSQL at the second line. Yeah. So this is because you could originally just do a SQLite database, but we already have Postgres. What's really cool about the way Prisma handles migrations is that it's going to spit out a SQL file and show you exactly what that is. It's very transparent about what the migration is doing. And I don't think we had Copilot doing anything — there's Copilot working.

01:10:10 - Alex Trost

Copilot.

01:10:10 - Anthony Campolo

Yeah, Copilot.

01:10:11 - Alex Trost

It's on. I mean, it tried to help me finish the Postgres bit.

01:10:16 - Anthony Campolo

Oh, nice.

01:10:19 - Alex Trost

Yeah.

01:10:20 - Anthony Campolo

Oh yeah, that's cool.

01:10:22 - Alex Trost

Did help me.

01:10:23 - Anthony Campolo

Now if we look at the migrations folder in db/, we can see that migration. There's the SQL it's going to write for us.

01:10:32 - Alex Trost

Okay, cool. Very cool.

01:10:35 - Anthony Campolo

All right, and now we're going to do one more command: yarn rw g scaffold post.

01:10:53 - Alex Trost

Okay. Run it.

01:10:55 - Anthony Campolo

Yep. And what this is going to do is give us a whole admin UI for our posts. So now go back — run yarn redwood dev again.

01:11:07 - Alex Trost

Okay. I do like the built-in admin UI that Django had. So if you have that, that's wonderful. yarn redwood dev.

01:11:17 - Anthony Campolo

Yep, yep. And then we're going to go to localhost:8910/posts/new.

01:11:32 - Alex Trost

localhost:8910/posts.

01:11:37 - Anthony Campolo

Oh, yep. Yep.

01:11:43 - Alex Trost

Create a post title. "Anthony is super cool." Wow.

01:11:53 - Anthony Campolo

And then that's our thing. Right now this isn't set up to actually work with the frontend at all because the frontend is not really important for this project. Because what we're going to do now is deploy this to Netlify and it's going to put the API into a serverless function. It basically takes your entire Redwood backend and bundles it into one giant function, exposing that through a Netlify function. And then we feed that into StepZen.

01:12:21 - Alex Trost

That is wild. Okay.

01:12:23 - Anthony Campolo

Wow.

01:12:24 - Alex Trost

Okay. I'm trying to wrap my head around it. That's really cool. I just like getting free admin stuff — this can come in handy in so many different ways. And this is just a layer over my Prisma database. Wait, who owns the Prisma database? Is Prisma always — oh, it's Railway. Sorry.

01:12:54 - Anthony Campolo

Yeah, yeah, yeah. Moving pieces here.

01:12:57 - Alex Trost

We grabbed that. Yeah.

01:12:59 - Anthony Campolo

It was right there in your Railway dashboard. So yep. And then the post —

01:13:06 - Alex Trost

"Anthony is super cool." All right, cool. I love that. I really love that. That's just a nice little abstraction that I get for free on top of — that's so good. Awesome. All right, so we want to deploy. This is what you said, right?

01:13:23 - Anthony Campolo

So you want to get it on a git repo and then connect that git repo to — oh sorry, one more command. So you got to set up the deployment. You can turn your dev server off. We're not going to need that.

01:13:37 - Alex Trost

Am I even in — there we go.

01:13:41 - Anthony Campolo

Yeah. So then do yarn rw setup deploy netlify.

01:13:55 - Alex Trost

It's off screen a little bit. Let me —

01:13:58 - Anthony Campolo

Yeah, yeah, that's good. So then run that and this will generate a netlify.toml file for us. Cool, cool. Yep. So you scroll down to netlify.toml. Yep. Yeah. And so this gives us a command and it's going to deploy all of our things. So then all you have to do now is get this in a git repo, connect that repo to Netlify, and then you'll also have to include your database URL. I'll let you know how to do that once we get there.

01:14:34 - Alex Trost

Cool. Do you know how to use the GitHub CLI?

01:14:42 - Anthony Campolo

I do. So okay, gh repo create [name] --public. It used to just work like this, but now you got to do --public.

01:14:59 - Alex Trost

Okay.

01:15:00 - Anthony Campolo

And then hit enter and that should do it.

01:15:02 - Alex Trost

Yeah, I realize you can't see it again. There we are. All right.

01:15:07 - Anthony Campolo

Yep. I've started using this HTTPS — I guess, authenticate git?

01:15:22 - Alex Trost

With a web browser. Sure. Should I be showing this on stream? I don't even know.

01:15:31 - Anthony Campolo

Probably not.

01:15:35 - Alex Trost

Device activation. All right. Should be good. Authentication complete. Awesome. I'm going to run that again. Cool. git init.

01:15:58 - Anthony Campolo

No.

01:15:59 - Alex Trost

An origin. git remote add origin to local repository. Yes. We didn't get a git init. Cool. git init — that's not how you say that.

01:16:09 - Anthony Campolo

Git ignition.

01:16:13 - Alex Trost

All right, cool. So now we just git push. I know we did add and commit. Cool.

01:16:32 - Anthony Campolo

Do git add . Just git add .. Yep. And then git commit -m and then give it a message.

01:16:41 - Alex Trost

I already committed everything. Yeah.

01:16:43 - Anthony Campolo

Oh, you did? Okay.

01:16:44 - Alex Trost

Yeah. It just says publish branch because we're on master and I think it —

01:16:49 - Anthony Campolo

Maybe do a git status real quick. Okay, great.

01:16:54 - Alex Trost

Yeah.

01:16:54 - Anthony Campolo

Push it. Or set the remote and then push it.

01:16:59 - Alex Trost

Just git remote set-url.

01:17:02 - Anthony Campolo

This is the one I always blank on.

01:17:04 - Alex Trost

Yeah. Honestly, I always just copy and paste from GitHub.

01:17:07 - Anthony Campolo

Yeah.

01:17:07 - Alex Trost

Yeah. Let me —

01:17:11 - Anthony Campolo

Yeah, because you should have a blank repo there now.

01:17:13 - Alex Trost

Yeah. I'm not sure if I'm logged in. I am logged in. Cool. So horse-zen. Nope. Find. Yeah, horse-zen-redwood. Cool.

01:17:21 - Anthony Campolo

Yep. Perfect. Yep. So it's those last two commands.

01:17:33 - Alex Trost

All right. Should be good, I think.

01:17:35 - Anthony Campolo

Okay, cool. Great.

01:17:36 - Alex Trost

Sweet.

01:17:37 - Anthony Campolo

I think the GitHub CLI set it for you already.

01:17:40 - Alex Trost

Awesome. Now Netlify — I should probably log in. Pull this off just in case I need to do anything.

01:17:49 - Anthony Campolo

Can you refresh that just to make sure the project is there. The GitHub one. Yeah.

01:17:56 - Alex Trost

Add new site, import an existing project.

01:17:59 - Anthony Campolo

Cool.

01:18:00 - Alex Trost

Adding from GitHub. Authorized. Sweet. horse-zen-redwood. Sweet. Okay, so now it's probably going to —

01:18:11 - Anthony Campolo

And then here's where you're going to add your database. Under Show Advanced. Everything is good, don't change anything, and then add a new variable — that's where you'll grab the DATABASE_URL and put it in. Cool.

01:18:25 - Alex Trost

All right, so I'm going to do a little bit of this off screen. Actually, you know what, I'll do it this way so it's a little bit easier, chat. There's not much else to show. This is just easier. I'm in the wrong repo in general. All right, so that was under my .env, DATABASE_URL.

01:18:49 - Anthony Campolo

Getting the URL — the whole gamut of services today.

01:18:55 - Alex Trost

Yeah. Right. Okay. So it is in and it's hidden. So we can actually — the cool thing is I could have done that on camera.

01:19:04 - Anthony Campolo

Because Netlify has the extension to hide it for you.

01:19:07 - Alex Trost

Yeah, I'm hiding it here and they're hiding it there. So I could have done that. Sorry, chat. You didn't miss much though. All right, cool. So it looks like it's detected the build command already because we have the netlify.toml. Right, because that is what it's reading. Awesome. So deploy.

01:19:27 - Anthony Campolo

Yep, deploy. And then this will take probably five to ten minutes. We're going to set up the StepZen schema. So let's go back to our StepZen project.

01:19:41 - Alex Trost

Is that going to be five to ten minutes every time I push a change to Redwood?

01:19:49 - Anthony Campolo

It kind of depends what the change is and what needs to change. This first time it has to build a whole bunch of stuff, including the API. If you're just changing the frontend, that won't necessarily need to rebuild.

01:20:04 - Alex Trost

It'll cache certain things and just —

01:20:07 - Anthony Campolo

At least I think so. I may be talking out of my butt, but it's usually a situation where you're not really deploying your Redwood app multiple times a day, because you're not creating fast-changing blog content with it. You're setting up an API, and the API is handling when data is updating. So you're not constantly rebuilding lots of pages all the time, because that's not really what Redwood's for. That's why the build time itself is not a huge issue.

01:20:47 - Alex Trost

Right. It shouldn't be compared to, like, 11ty builds this fast, because it's a very different beast. The same thing that you're building in Eleventy, you wouldn't build with Redwood.

01:21:00 - Anthony Campolo

Right. Exactly. Yeah.

01:21:01 - Alex Trost

Cool. Awesome. All right, so we've got that. Did you say you wanted to do something in the meantime?

01:21:10 - Anthony Campolo

So yeah, let's go back to the StepZen project.

01:21:15 - Alex Trost

StepZen. Here we go.

01:21:17 - Anthony Campolo

Yep.

01:21:18 - Alex Trost

Cool.

01:21:20 - Anthony Campolo

Then let's create another file called posts.graphql.

01:21:27 - Alex Trost

posts.graphql.

01:21:27 - Anthony Campolo

Let's add that to index.graphql.

01:21:38 - Alex Trost

Got it.

01:21:41 - Anthony Campolo

And then now this will be type Post. Yep. Which will have an ID, which is just Int!.

01:21:53 - Alex Trost

Cool.

01:21:54 - Anthony Campolo

And then title — let's say title — that'll be a String!. And then we'll have a query. type Query. Yep. And that'll be posts, all lowercase. Yep. Which will then return an array with Post. Yeah.

01:22:18 - Alex Trost

Cool.

01:22:18 - Anthony Campolo

And then add @graphql after that. Yep.

01:22:25 - Alex Trost

Okay.

01:22:26 - Anthony Campolo

And then endpoint:. And that is where the Netlify function URL goes.

01:22:34 - Alex Trost

Got it. So should I grab what this is going to be?

01:22:36 - Anthony Campolo

Let's first give it a nice name. So go to your site settings and just change the domain settings. I usually just call it the same thing as the repo for simplicity's sake.

01:22:47 - Alex Trost

horse-zen-redwood. What was it?

01:22:50 - Anthony Campolo

Redwood, yeah. horse-zen-redwood. Yep. And then save that. If we go to the site —

01:22:58 - Alex Trost

Name is already taken. Did you already grab it?

01:23:01 - Anthony Campolo

Yeah. Okay, so give it a slightly different name. Cool. Actually, you don't need to grab that first. Just save it. And then go to Functions — the fourth tab at the very top. Not quite there. Scroll all the way up to the top and go to Functions. And then click graphql. There you go. That is your function endpoint. I don't think it's done building yet, but you can go ahead and pop that in your StepZen endpoint.

01:23:34 - Alex Trost

Cool.

01:23:35 - Anthony Campolo

Now this is the thing we haven't done yet — this is why we just went through that whole rigmarole to get to this point. Because what we have done now is deployed our own custom GraphQL API connected to our own custom database, that we can now feed into our StepZen project. We're not connecting to an API that's being given to us by Supabase — we actually created our own API with Redwood.

01:24:03 - Alex Trost

Right. And so now we can pull that in once that's built. Published.

01:24:12 - Anthony Campolo

All right, cool, great.

01:24:13 - Alex Trost

404 pages.

01:24:14 - Anthony Campolo

So let's see if we can run that.

01:24:17 - Alex Trost

To be expected.

01:24:18 - Anthony Campolo

That's to be expected because we did not build a frontend. Right now we are just accessing the serverless function. We could have created a frontend with a cell that queries our backend and shows it, but that would have added another ten minutes or so.

01:24:30 - Alex Trost

So this will only show on dev. This isn't going to show on production, in other words.

01:24:36 - Anthony Campolo

Yeah, exactly.

01:24:37 - Alex Trost

Cool. Okay, cool.

01:24:38 - Anthony Campolo

If you want to actually show someone something, you would just create a frontend pretty quickly. But right now we're only working with the Redwood API via the serverless function.

01:24:46 - Alex Trost

Sounds good. Okay, cool. So now I've saved this.

01:24:51 - Anthony Campolo

Is our StepZen server still running? Yeah. So I do stepzen start here. And then if the Redwood one works, might want to kick that off and just try it again. Oh, that's interesting. Oh, you're in the wrong directory.

01:25:16 - Alex Trost

Ah, good call. cd into the stepzen boilerplate. Cool.

01:25:22 - Anthony Campolo

There we go. Okay.

01:25:23 - Alex Trost

Yeah, we did leave it to create that other thing. Cool. All right, deploy.

01:25:28 - Anthony Campolo

If the Redwood query works, then we can run the mega query, which will be all the queries.

01:25:33 - Alex Trost

All right, nice.

01:25:33 - Anthony Campolo

This is posts. Yep. ID, title. And then did it work?

01:25:43 - Alex Trost

Wow, cool. So that's coming from Railway through our RedwoodJS API through our Netlify function. Yeah. Wow, that's wild. I added that in with the Redwood admin thing and there it is. We also have our test data — that's coming from StepZen's mock service, correct?

01:26:19 - Anthony Campolo

Yeah.

01:26:21 - Alex Trost

Then we also have our mock users, which is coming from the public REST API. We get a bunch of users back from that. We also have the Rick and Morty API here with a whole bunch of characters that we can query — we get Educator Rick, lots of characters. And then books — we should get "Old Man and the Sea" in here too. That was the one where we wired up a mutation with Supabase and created it in the GraphiQL explorer itself. We used that in the same kind of way we used the RedwoodJS admin to create an item. Wow. Now here's the question — is there anything nice that we can do either with GraphQL or with StepZen where all of this data was more interconnected? I'm thinking of use cases where — whoa. Cynthia, thank you so much for the sub. Really appreciate it. It's great to have you here, and I really appreciate the support. Thank you so much.

01:27:57 - Anthony Campolo

So if I have linked types together through APIs and things like that?

01:28:01 - Alex Trost

Yeah. Say I have a product that's in Shopify and I want the content I've written about it in Prismic to be linked to it, coming in from the Shopify API. And I also want to check my database to see how many sales we have on it, or check some review service, and bring all of that together so I can just request "give me information about this shoe" and not have to make all these different requests. Just pull that in with StepZen. Is that something that StepZen does, or is it something that GraphQL natively does but StepZen unlocks because it's giving me this one API to hit?

01:28:44 - Anthony Campolo

Yeah, there are a couple of directives we didn't talk about that I included in the chat — particularly @materializer and @sequence. @materializer lets you link types together, and @sequence lets you feed the output of one query into the input of another query.

01:29:03 - Alex Trost

Okay.

01:29:04 - Anthony Campolo

So you can chain queries together. There are other things built in that let you do more complex stuff like that.

01:29:13 - Alex Trost

Awesome. Okay, so is @sequence — I think Cynthia asked earlier — is that a StepZen-specific thing or a GraphQL thing?

01:29:30 - Anthony Campolo

Yeah, so all of the directives are the StepZen-specific part. Anytime you're writing the @ symbol and then a directive and feeding something into it, that is something StepZen is doing for you. Anytime you're writing types or queries or mutations, you're just writing GraphQL. So the boundary between the two is actually pretty clear once you start working with them.

01:29:49 - Alex Trost

Got it. So that's a StepZen thing. Okay, cool. Because that, to me, is where our example here gets powerful. We can get books and Rick and Morty characters and it's fun, but the real power comes from having all these different services. At the agency I worked at, we had to pull in review data about a pet food, but also hit another API to see where that pet food was sold — all these different services. That's a big thing with Jamstack, where you're connecting all these different things. There's not typically one service that handles all of that. But we had to connect all these things and it wasn't fun to do as a frontend developer. I wanted to focus on other things. So StepZen as a service — to not only combine all of those things into one API but also allow me to through @sequence and —

01:30:54 - Anthony Campolo

@materializer.

01:30:55 - Alex Trost

Yeah, @materializer. Allow me to combine that into one query — "give me this specific pet food item" and I get back the reviews for it, where it's sold, its locations, how much is in stock — all the things I need to display on the frontend. That is kind of the dream, and that is really, really nice that I can do that with StepZen.

01:31:26 - Anthony Campolo

Yeah. And so there's just one more thing I want to show with our remaining time here. Imagine now that everything we did — creating schemas, hooking in endpoints, all of that — imagine all of that was already done for you, and you could just literally write a query and get stuff back. That is the StepZen GraphQL Studio. Whoops, not that. Can you delete that?

01:31:52 - Alex Trost

Actually, I don't know, Ben. Can we delete that?

01:31:58 - Anthony Campolo

Those are not super important. I can roll both of those. That was not supposed to end up in my keyboard when I copy-pasted that.

01:32:06 - Alex Trost

I don't know how to do it from my interface.

01:32:10 - Anthony Campolo

Yeah.

01:32:11 - Alex Trost

Ben Myers deleted the message. Ben, you are great. Mod of the year, my friend. Really appreciate you.

01:32:18 - Anthony Campolo

That is by far the dumbest thing I've ever done on stream.

01:32:22 - Alex Trost

You'll have to — oh, good call. Still on the thing. There we go. The GraphQL Studio. Can I click here? The GraphQL Studio. Yep, that's it.

01:32:38 - Anthony Campolo

Cool.

01:32:39 - Alex Trost

Get started with GraphQL Studio. Ben, thank you again, I greatly appreciate you. You'll still need to reroll those, but at least harder to copy-paste now. Yeah.

01:32:55 - Anthony Campolo

Yeah.

01:32:56 - Alex Trost

I don't know how you did it. You'll have to teach me. Cool. So get started with the GraphQL Studio. "Create your own GraphQL API in just a few clicks. No resolvers to write, no data connections to code, no servers to build. Your API runs on StepZen." Okay, I'm intrigued, but I'm not fully appreciating it yet. So what should I do here? Just hit next?

01:33:25 - Anthony Campolo

Yeah, so let's hit next and then keep hitting next.

01:33:30 - Alex Trost

All right. Build a studio.

01:33:33 - Anthony Campolo

Build a studio. All right, so what we've got here is basically all the different integrations on the left. So hit "No thanks" there actually.

01:33:45 - Alex Trost

Okay.

01:33:46 - Anthony Campolo

Yeah, so these are all the different things we can connect to right now. These are pre-built integrations that you can just click and get going with. We're going to start with the Google Natural Language API.

01:34:06 - Alex Trost

Cloud Natural Language API. Yeah, cool. Just hit plus.

01:34:10 - Anthony Campolo

Yeah. This one will need some keys — which is actually what I accidentally dropped into the stream. So I just sent you a message. And we're going to end up rolling these afterwards anyway, so I don't really worry about taking anything off screen at this point.

01:34:27 - Alex Trost

Sounds good. Where am I?

01:34:30 - Anthony Campolo

This is one of the nice things actually about having API keys that are easy to roll. If you're working with a service that does not let you easily roll your API keys, that should be a huge red flag, because these things are really easy to expose.

01:34:41 - Alex Trost

Yeah, newsletter API keys are not re-rollable. And I'm like, that's not good.

01:34:50 - Anthony Campolo

Yeah, that's not good.

01:34:51 - Alex Trost

Yeah. Where am I putting these keys?

01:34:54 - Anthony Campolo

Where it says Configure, yes — top left, right next to the name. Yeah, yeah. All right, I think I'll just drop it in there.

01:35:05 - Alex Trost

Is that going to hide?

01:35:06 - Anthony Campolo

I think right now it's hiding it. So I'll show it. Yeah, there you go.

01:35:08 - Alex Trost

My keys.

01:35:09 - Anthony Campolo

Just save, don't hit Create Account. Thank you. Yeah. And then so I've got a query that I need to —

01:35:20 - Alex Trost

So what is the Google Cloud Natural Language API? I'm not even familiar with it.

01:35:26 - Anthony Campolo

Yeah. It's basically Google exposing their natural language processing capabilities through an API. Google has tons of things like TensorFlow and all these deep learning services on their cloud. This is a way that you can use those without needing to know how to train a model yourself and do all that stuff.

01:35:53 - Alex Trost

Got it. Cool. All right, so am I still going to run this, or —

01:35:59 - Anthony Campolo

Hold on one second.

01:36:00 - Alex Trost

Sorry, I had to click the button. I couldn't not click the button.

01:36:06 - Anthony Campolo

Yeah, see what it's spitting out for you?

01:36:09 - Alex Trost

So, "classify text." Oh, so I'm asking Google to use its big brain and tell me what this text is about. The content — "the weekend side of our hard-working hoodies with a relaxed fit and ultra spongy fabric, 100% cotton, French Terry, blah, blah, blah." So Google comes back — and chat, there's not a great way for me to make this big and have you see things. I can't minimize this site or anything. So I'm going to make it a little smaller and read it.

01:36:39 - Anthony Campolo

Grab the query I just dropped in your Discord messages and run that, because this is going to show us exactly what we want.

01:36:47 - Alex Trost

Austin, I'm so sorry. Sorry, I'm triggering Frugal Homes. Gotta be careful. Sorry about that, Austin. That's my fault. All right, so I did grab the query. Drop it in here or schema?

01:37:05 - Anthony Campolo

Yeah, no, in query.

01:37:07 - Alex Trost

Okay, cool. All right.

01:37:10 - Anthony Campolo

So what this is going to do is send the message "I feel happy," and it will let us know how happy it actually feels. Yes. So now change the word "happy" to "sad" and rerun it.

01:37:23 - Alex Trost

This is how they become sentient. Interesting.

01:37:27 - Anthony Campolo

So what it's doing is giving you what's called the polarity of your speech. It basically looks at the words and says whether it's positive or negative, and how strongly so. "I feel..." — I usually try to feel exactly in the middle. Yeah, this is funny.

01:37:45 - Alex Trost

Even "neutral." If I say "I feel neutral," that's still somewhat positive. "I feel —"

01:37:51 - Anthony Campolo

I feel exactly in the middle.

01:37:54 - Alex Trost

"I feel nothing." "Meh" is worse than nothing. "I feel nothing" is pretty dark to me, but Google thinks it's not as bad as "meh." All right. I'm learning a lot about humans and people and about Ben.

01:38:14 - Alex Trost

Wait, hold on. Let's see what we got. All right. "It's a step in the right direction." I wonder if spaces matter. Nope. This is interesting. Still a nine. All right, let's make some marks. So what is special about what we just did? Can you explain what's neat about this?

01:38:57 - Anthony Campolo

Yeah. If you click over to where it says the schema now, so next to query — yeah. What you see here is what we have been writing throughout this whole episode. We've been writing these GraphQL schemas. And if you keep going down to query, eventually you'll see where it's actually feeding in the endpoint itself. All of this GraphQL code has been written for you. So if you don't want to connect your own bespoke API and just want to deal with these already-known services, the schemas are all there for you. You don't have to write a single line of GraphQL to do this.

01:39:33 - Alex Trost

Got it. Okay, so basically — if I'm understanding this correctly — is there a way to make this part bigger? No. So this is like, hey, you're almost doing an "if this, then that" or a Zapier kind of thing where these are all popular APIs that you might want to hit, and here's that integration. Now you can write the queries without having to come up with the schema itself. It feels like where Zapier is a no-code solution, this is still a code solution, but a lower-code solution. Like, I would love to integrate with Trello and Spotify, but I need more than what Zapier would give me. I need a bit more nuanced querying. But I don't want to go through the pains of actually integrating with Spotify — and assume this is going to — oh, whoa. Did that just — oh, wow. Is that going to actually work?

01:40:53 - Anthony Campolo

So you might need a Spotify key.

01:40:56 - Alex Trost

So that's what I thought. Yeah, yeah. Absolutely, would need to configure. I was just clicking around. But that's awesome.

01:41:06 - Anthony Campolo

And so there was one other one I wanted to show. So add in the Dev.to one.

01:41:09 - Alex Trost

Dev.to.

01:41:11 - Anthony Campolo

Yeah.

01:41:11 - Alex Trost

This is great — "configure Dev.to API keys." Should I go grab one or did you drop me one?

01:41:18 - Anthony Campolo

I dropped you one? Yeah.

01:41:19 - Alex Trost

Cool. I thought I did see it in chat earlier.

01:41:22 - Anthony Campolo

Nope. Yep. Cool. And then I have a query too. So for this one, basically what you do is you have a "get comments by" — yeah, let's try that one. So what I'm going to do is have it return comments on an article specified with the article ID. The reasoning for that is — the goal here, what I've already showed how to do in a blog post, is that you are able to chain the query that gets you your blog comments into the — I have another one I was testing, but the comment it shows actually has a swear word in it. So I don't want that popping up on screen right now. I think it's just because of the ID we're feeding it.

01:42:47 - Alex Trost

Click what Ben dropped in chat. I have no shock. Yeah, that was definitely the mood there, Ben. I agree. All right, we're here. Interesting. Did you drop me something yet? Wasn't sure.

01:43:11 - Anthony Campolo

Yeah, this is fine. This gets across the idea. So go to the thing I just linked. I'm just going to kind of walk through it. Since we're almost out of time, the next step you can do is export this project and extend it with anything you want. What this is is basically what we just walked through here. So keep going, keep going — and then where it says @sequence. Yeah, right there. And if you bump up your font a little bit.

01:43:57 - Alex Trost

Yeah, okay, awesome.

01:43:59 - Anthony Campolo

This is essentially taking the first query — the "get comments by article ID" query — and feeding it into the "get natural language analyze sentiment" query, mapping the body HTML to the content. Now, that's not going to work — no, yeah, because this needs to be in the schema. This is why you would need to export the project and then add it in and spin up stepzen start. There is a bit of friction there. But if you scroll down a little more, then you'll see — there you can feed in the comment, and this is a positive one, so it's giving 0.8. And if you scroll down a little more, it's an article I wrote where there are some salty comments, so it has a polarity of -0.04.

01:44:55 - Alex Trost

That's funny. That's really interesting that you can use that bit of AI to assess which of your posts made people the most happy — not just, did they engage with it. And do people engage more with the stuff they're angry at or the stuff they enjoy? Based on social media and the world today, I'm willing to bet they engage more with the negative comments. I'm not encouraging that — I'm just saying. It's very interesting what you can do with things like this, and really cool that StepZen allows you to pipe one into the next and surface it all in one API. That's great. "How do you add a secret, e.g., OpenWeather?" It's over on the left under config.

01:45:49 - Anthony Campolo

That was the configure button we were clicking earlier.

01:45:54 - Alex Trost

Got it.

01:45:54 - Anthony Campolo

Yeah. Any time you click an integration that needs a key, you'll have a configure button next to it, and you just add it in.

01:46:02 - Alex Trost

Really cool. And then the Pokémon one is open, right? So we can just query for Pokémon. "Deploying your endpoint." That happens so quick I barely even noticed.

01:46:23 - Anthony Campolo

You gotta get your Pokémon.

01:46:25 - Alex Trost

Gotta. Pokémon abilities. Pokémon. Snow — so it gives me all the abilities and it gives me ten actual Pokémon, the first ten. Really cool. And then so with @sequence, I can get one, maybe put the description of a Pokémon into the Google Natural Language and see what they think about how friendly that one is or something. Lots of stuff you can do here. And then you can also eject — this is what you said.

01:47:07 - Anthony Campolo

Yeah, exactly. If you click the publish button, it'll publish it for you, and then basically that just spits out a project that is like the one we were creating throughout the first hour.

01:47:17 - Alex Trost

Got it. Oh, and then you have pre-built combinations.

01:47:20 - Anthony Campolo

So these are already kind of combined. So like the social media sentiment analysis brings in some other sentiment analysis stuff. And you can do currency conversions. You can do image search. All sorts of stuff.

01:47:33 - Alex Trost

Oh, this is cool. Yeah — Twitter and Unsplash contextual image search. Outdoor dining search: Google Maps plus OpenWeather plus Yelp. Really cool stuff. But it doesn't lock you in the way that an "if this, then that" — or a no-code solution like Zapier — would. This is a way to search and combine different sources of data and also connect your own. This is so cool, man.

01:48:19 - Anthony Campolo

Yeah, awesome. I'm glad you're enjoying it. I hope you'll find use for it and possibly use it for something. It would definitely be super fun to just get to hack on some of this stuff together and build something actually useful, because we don't want this to just be a theoretical project — people build actual real useful things with this. I'm always happy to get a chance to show it off and see people's reactions. This has been really, really fun. If anyone has any other questions, feel free to drop them in the chat. But that's essentially everything I wanted to show. I didn't show how to build out a frontend and connect it to a StepZen API, but we have lots of tutorials for that — whether it's a React, Vue, or Svelte frontend. Anything that can make a fetch request can integrate with this. It's a really great tool. The front of the back end — that's what I think of it as. People always talk about the front of the front end and the back of the front end.

01:49:19 - Anthony Campolo

This is the front of the back end. It's a cool tool to give you access to a lot of backend powers and make you more full-stack as a frontend dev.

01:49:29 - Alex Trost

That's great. Awesome, man. Thank you so much. Chat, do we have any questions? I think we've been mostly answering them as we go. Has anyone wondered anything? No, I did not plug it and I didn't see anyone do that. So I apologize for not — makes sense.

01:49:50 - Anthony Campolo

All good.

01:49:50 - Alex Trost

Yeah, seems pretty clear.

01:49:51 - Anthony Campolo

Seems pretty clear.

01:49:53 - Alex Trost

It's awesome.

01:49:53 - Anthony Campolo

Good to hear. Because this thing confused the crap out of me when I first learned StepZen — made no sense for like a month or two. Glad I can hopefully make it a little more comprehensible to people.

01:50:05 - Alex Trost

Cynthia says it's great. It's awesome. Disco, are you still here by chance? Because maybe we can take that one offline. Don't want to —

01:50:13 - Anthony Campolo

Yeah, he was asking about money things.

01:50:15 - Alex Trost

Yeah. I don't know if I'm going to be the best person for that. Sorry — "give them the dude, share the profits." Especially if there's real money involved.

01:50:32 - Anthony Campolo

Yeah, you should talk to a legal expert.

01:50:34 - Alex Trost

"Made me around 2.5 mil. Yeah, he's had around $250,000." Yeah. There's this much money involved — it's going to come down mainly to lawyers and proof unfortunately. And I know that's not fun. Sorry that you're going through that.

01:51:03 - Anthony Campolo

Alex Trost told me.

01:51:05 - Alex Trost

I mean yeah — but Anthony, this was really cool. Thank you. Chat, you were all fantastic. Really appreciated the questions and just having you all here. And Ben, thank you for saving our butts with that quick deletion. You are top pro. Igad, thank you. Folks, this is — in case you didn't hear me say it before — the last stream of the year. And I just want to say, wow, it has been a phenomenal year. We started really streaming in February. We haven't even been streaming for a full year yet. We did a couple of streams the year before, but not really. So I just want to say thank you so much for everything — for showing up, for being so supportive, for asking questions, and for all of this. It's been an honor to make it to the end of the last stream. Amit, great to see you, my friend. Brent, great to see you. So yeah, thank you for a phenomenal year. And Anthony, and everyone like Amit and like Ben and others who have come on and given us their time and energy and taught us so much this year.

01:52:34 - Alex Trost

We've had a lot of episodes and yeah, just really want to say thank you for an awesome year. We will be back in January.

01:52:41 - Anthony Campolo

Thank you for hosting and for putting it all together and doing the thing.

01:52:45 - Alex Trost

Of course, man.

01:52:46 - Anthony Campolo

The community very much appreciates you.

01:52:48 - Alex Trost

Thank you. Yeah, it's honestly been a joy. Did not expect all of this coming into the new year. Came into a new job, and the stream kind of — oh yeah, we can mess around with the stream — and then it seemed like we needed a Discord, and it's just been this incredible community thing that ended the year with us doing a good thing for the world as a community. So I'm excited to see what happens next year, and just appreciate all of you. Hope everyone out there has a wonderful holiday and wonderful new year. Whoa. Ben, thank you so much for those gifted subs. Really appreciate you. So kind, my friend. Super generous. Thank you so much. But yeah, hope everyone has a phenomenal holiday and great new year. I'll see you in 2022. If you're not in the Discord, I would love to see you before then. So join the Discord. Let me see if I have the button here. I do — that's the Discord. There's the button. Thank you so much. And Anthony, you want to plug anything before we head out?

01:53:55 - Anthony Campolo

Oh, I mean, stepzen.com for StepZen stuff, redwoodjs.com for Redwood stuff. And then I'd be remiss not to mention fsjam.org — this is my podcast. We've had the great Alex Trost as a guest, along with Ben and other people. Had Cassie Evans just very recently. So fsjam.org is my podcast that I've been doing with Christopher Burns for over a year now. We started October of last year, so we're about a year and two months in. We've got about 60 episodes right now. That's a very fun, fulfilling thing for me to do. We have lots of conversations with people from — like we've had people from Supabase and a lot of the tech we've shown here. If this interests you, if you think these projects are cool and you want to learn more, it's a really great resource to dig into this huge cornucopia of stuff that we've looked at today.

01:54:57 - Alex Trost

Great. Awesome. Yes, definitely check out fsjam.org. And you were so much fun to talk to, so I really appreciate it. And Cynthia says she's gonna check it out. Thank you so much, Cynthia. So folks, that's it. Hope you have a great day and we will see you later. Take care. Let's find someone to raid — let's go drop by there and have a great new year. Bye.

01:55:43 - Anthony Campolo

[unclear]

On this pageJump to section