← Previous · All Episodes · Next →
Custom codegen for SDKs Episode 16

Custom codegen for SDKs

· 41:31

|

CJ: In this episode, Colin
and I talk about cogen and

how we use Cogen at Stripe.

We'll also mention a
conference talk at Ruby Conf.

That already happens, so if you're curious
and you wanna see that, head over to the

description and we'll have a link for you.

Enjoy the show.

Colin: Welcome to Build and Learn.

My name is Colin.

CJ: And I'm cj, and we weren't gonna
record today, but we're suddenly both free

Colin: Yep.

CJ: Yeah, Twitter was gonna
have a developer conference

called chirp, but it's canceled.

The entire conference is canceled.

Colin: It is canceled.

Yeah, we, I think we talked about it a
few episodes ago where we were pretty

excited to see, uh, Twitter getting back
to its developer roots, and they kind

of burned to the developer community a
few times over the last decade or more.

And this was looking like a good
sign that that would be different.

So if you're listening to this
in 2023, you already know about

all this, but obviously Elon
bought Twitter what, in October?

, I wouldn't have wanted to necessarily
be at that conference working at Twitter

and having to answer questions, right?

Like, imagine being a dev advocate, right?

and being asked all these questions
that you don't have answers to.

CJ: Right.

I don't think there are any more
develop, like all of the people.

at Twitter who were on the
developer advocacy team that

I was interacting with.

I don't know any of them
that are still there.

Like, uh, half of them or more
were laid off in the first round.

Some of them quit shortly after,
and I think the rest took the.

Opportunity to bail when Elon was
like, Hey, if you don't want to be

here and grind it out, then like,
you can, here's the door , and they

Colin: Yeah, he sent everyone
that email of, do You Like Me?

Yes or no?

Right.

CJ: yeah.

Circle yes or no.

Colin: uh, so, so chaotic, I think.

Yeah.

Chris Mesina tweeted that it was like
97% of the, I don't know if it's,

he said platform, so I don't know
if that means developer platform

and in like even the developers.

of the platform, including the developer,
obviously team are just not there anymore.

So that's gonna be interesting
to see where it goes.

CJ: Yeah.

There's also just a ton of people going
out in like flames of glory , you know,

like just calling out Elon on Twitter
for showing bad charts or using bad

metrics or, saying like, oh, I think
he said something like, oh, the A the

app is slow in certain countries because
it's doing thousands of RPC calls.

And then someone was like, not true.

I've been working on this for like six
years and , you know, blah, blah, blah.

And then, you know, five seconds
later that person's fired.

Just today I was watching some tos
where people were like counting

down until they got locked out.

And then, you know, they had champagne
ready to go when they got locked

outta their laptops and stuff.

Colin: I mean, even, uh, Justin
Jackson was sharing some tweets today

about how, like there's been on some
news posts that came out this morning

about how the building is locked
down again and no one can get in.

And then he shared a tweet from
someone who used to run their access

control and that Elon's calling him
back to help, like they're all locked

out of the building and that he needs
help getting back into the building.

It's

like, oh man.

, I don't know.

He should have bought it and not
touched it, I think is what it's like.

It's like a no make, don't make
any big decisions right after

you make a big purchase decision.

It's like

CJ: Yeah.

The way that I've been thinking about
it is that, He has started or made big

influential moves on the cultures of Tesla
and SpaceX and all these other companies

when they were really in their infancy.

And so the people I know who
work at SpaceX or worked at

SpaceX made the conscious
decision when they joined SpaceX.

To sleep in their van in the parking
lot because they knew they were gonna

have to work like 90 hours a week.

But they did that because they
wanted to be part of like this

thing that he was building.

But on the other hand, there was like
all of these people at Twitter who I

think were like really happy with the
quality of life and they chose Twitter

for, the community and like all of these,
great work-life balance benefits and,

working remotely and all this stuff.

And then he comes in and shifts the
culture from the top down and you.

, 80% of the people who worked
there didn't want to work in that

environment, and so it just kind
of like blew up in his face a bit.

But

Colin: Well, and I think the
rhetoric right now is that

they don't wanna work hard.

And it's just a different culture.

It's like there are definitely people
who got let go, who know how Very, very

specific things inside of Twitter were.

And now no one will know
how those things work.

And sure, that might be bad
documentation or whatever, but like

I'm looking at my Twitter right now.

I've been on Twitter since March of 2007.

There is more than 15 years
of culture that has already

been developed, at Twitter.

If people have been
there fr since that time.

Some people have been there only a
few years, but You could probably look

around at all the tech layoffs and
realize that yeah, everyone probably

overhired since the pandemic started.

Just wholesale cutting half of your
team, your company because you bought

something with a bunch of debt is
gonna have some waves for sure.

And I think everyone's trying to
figure out like, how do you make money?

And like we, we pay
for Twitter's api like.

I don't think a lot of people know that
there is a paid offering for the a p I.

And I think some people were like
making calls on Twitter for like, make

the a p I fully open again and let
us make as many calls as we want.

And it's does anyone remember what
it was like when that was the case?

Like fail whale was prevalent.

It wasn't a reliable api.

I, the guy who works, or probably
the team now that works on.

Tweet bot, you know, I've followed him for
years and just watched like their issues.

Cause they even were like limited
to the number of API keys.

They were allowed.

And so it's like when you buy Tweetbot,
you get one of our hundred thousand

p i keys and only a hundred thousand
people can use our Twitter client.

It's like in what world is that normal

CJ: Mm-hmm.

. Part of his thing early on was like,
there's too many bots on Twitter,

and so I could see him arguing for
just shutting the whole API down.

Like, you have to be a human
That's on the app that's tweeting

and we're only gonna let that.

Fly and not let people have API access.

But gosh, I don't want
that to be the world.

Colin: true.

And that's something that I'm
paying attention to cuz we integrate

heavily with Twitter at orbit, right?

So I'm like, okay, what
does this mean for us?

And some people are asking us
for Mastodon, integration now,

and we're looking at that.

But like some people, I still, I looked
at the API and it's pretty similar.

but, and this will get us into our
topic today, but the, the tricky

thing is it's just not a really
mature set of tools around it.

And Mastodon servers are just
melting right now because people

don't know how to host Mastodon.

People are realizing that a centralized
service with a whole DevOps team,

it turns out, is pretty important.

Instead of a bunch of, ma on fail whales,

CJ: So you are, are you on
Macedon, like as a user?

Colin: Yeah, I joined the Ruby
Social one, so ruby.social.

Um, I like it, you know, it's a
little, it's definitely rough.

You can tell it's an open source project.

CJ: Yeah.

.is it is it like implemented with Ruby?

Is it the Rails app?

Do you know?

Like,

Colin: I actually don't know.

Um,

CJ: Because there was someone
who posted in the Ruby social

Mastodon main feed or whatever.

also, I don't know what the
terms are, . I'm still trying

to figure out what, like this

Colin: Those toot toots,

CJ: yeah, you gotta make some toots,
someone tooted and, uh, , their toot

was about how like there's all these
issues on one of the master on repos

and they were basically making a call
to action for all the rubus that were

in ruby.social to help maintain it.

I was like, is this thing
like implemented in Ruby?

I don't know.

Colin: Well, I think, uh, Mike from
Sidekick runs the Ruby Social one.

Um, yeah, so if anyone knows
how to scale things, I think

he's gonna be pretty set there.

But yeah, I'll have to check and see.

It'd be interesting.

Maybe we, we should do a, a chat
and maybe even we find someone

who's more familiar with Mastodon to
talk about it in the next episode.

Actually getting Mike on the
show would be really good too.

Just talk about sidekick stuff eventually.

But with all that said, like
there is an API for Mastodon.

When we get into working with APIs, we
can work with those like raw and make API

calls, but most of us are using SDKs and
you're actually gonna be doing a talk.

I guess the talk will have happened
when this episode comes out, but, uh,

it'll probably be released on YouTube a
little bit after this podcast comes out.

So, um, let's dive into s TK
Generation and kind of what you're

gonna be chatting about at Ruby Comps.

CJ: Yeah.

So a lot of times if you're
implementing an api, , you can

have the API spit out an artifact
that has like the shape of the api.

A lot of times it's
like the open API spec.

Are you are, do you have
the open API spec for Orbit?

Uh,

Colin: Yeah, we use, uh, open api, which
I think is the same as swagger these days.

Right.

It's, yeah.

CJ: Swagger.

I think Swagger got like
renamed to open api.

Colin: Exactly.

Yeah.

CJ: So it could be open API speck, or it
could be, I think jsun API is another one.

And then, uh, or you could have
like G R P C proto buff, like your

proto buff schema definitions.

Could be like another artifact,
but basically you just want like,

or even in, in GraphQL too, right?

The GraphQL schema.

All of these are versions of some.

Sort of declarative thing that
gives you the shape of your api.

And it's usually like, what are
the endpoints, what are all the

different parameters it expects
what's required and not required.

And what you can do is take that
spec and then run it through a tool

to generate and spit out an sdk.

And if we really wind back the clocks
to, talking about like XML APIs.

Then, I don't know, did you
ever have to work with those SDS

Colin: I had to do.

I had to do soap APIs with wisdom files.

Yeah.

CJ: Yes, yes.

Yeah.

So, uh, way back in the day.

, this is like Prej, S o uh, a lot of APIs
were implemented with xml, and we had to

do this at my VR with, some of the big
booking engines or like listing platforms.

They, they didn't have JS O APIs.

They had XML APIs, and you could
get an X S D, which is a XML schema

definition, which is similar to an
open API spec or any of these things.

but then there were tools that could
take this schema definition and generate

bindings or an sdk, client library,
whatever, in a given programming language.

So in that case, we were, you know,
taking x sd, converting it to Python.

Um, and for the Stripe api we
spit out the open API spec.

And then we have this really,
really badass tooling that takes

the Open API spec and generates
all seven of our official support.

Server languages like the SDKs
for all of those languages.

So Ruby, Python, PHP,
node, go Java and.net.

We have Stripe SDKs for all
of those languages and they're

all now automatically generated
using the open API spec.

And I like, I know that I've
used Orbit Ruby or some sort

of Ruby clients for Orbit.

Are those also generated or are
those main maintained by hand?

Colin: You know, I think they
were written by hand and I would

say they're not maintained, so

CJ: Oh, they're not maintained at all.

Colin: like, I haven't touched
them since I've been here.

So, and yeah, the folks who built
them don't work here anymore.

So I think this is one of those things
where, you know, I wrote down here like,

what does SDK generation help to solve?

Because the a API I has changed, right?

And so we get to spit out at
this new artifact of a new

spec, a new open API doc.

And it would be really nice to have
that always be in sync right now.

Once that changes, the docs need to be
updated and the SDKs need to be updated.

And then you need to
communicate those SDK updates.

You know, if it's a gem, if it's a MPM
module, those need to make it out as

as version changes, you know, whether
they're breaking or non breaking changes.

Do you think that most s STKs today are
done automatically, or do you think that

a lot of people are still handwriting.

CJ: I.

. So there's a, there is an interesting
trade off when you're looking at Generat

like automatic generation, and that is
like if you want your SDK to be readable,

then using the automatic generation tools
don't really generate very readable code.

And so if you just take like the open API
spec and you run it through the Swagger

Code Gen or the Open API code cogen stuff,
it spits out like a giant, huge library.

it's automatically generated,
but it's really tough to use.

Um, and so your trade off is like, do
we want to use the automatic generation

and have like a really tough to use tool
or do we wanna write our own or do we

want to like build our own generation
tooling that does like a hybrid of

both?, so that's the tooling that I'm
excited to share and talk about is like

this hybrid of, of both worlds where
we've, we've built this pipeline, but.

The whole point of SDK generation
is to make sure that your s like

all of your client libraries are
staying up to date with the api.

And so, yeah, going back to the top of
the show, right, you're talking about

how like, yeah, we might just make API
calls directly to the API using Curl

or Postman or something like that.

But when we're integrating that into
our applications, we're gonna be

using Ruby code or JavaScript code
or whatever to make those API calls.

One option is to write your own like
class that represents a client of

the API and then use, HTP party, rest
client, whatever sort of built-in

library there is for making HTP calls
or to use a library that is provided

by the third party to integrate with.

For instance, transistor, the host,
the podcast host that we have for this

platform, I found like an unofficial
community, Ruby Library for it.

And I was like, ah, I don't think so.

. And so, um, I want to add a list of
all of our podcasts to my website.

I was like, oh, I'll just
use the transistor API and

you can like get an API key.

And so I just built, I wrote a class,
very simple transistor RV like Ruby class.

, has a couple of helper methods
on it that will just make the

request to fetch all the episodes
and page and iterate over those.

So that's the trade off between the
two is right, like you're gonna either

have, um, no, no SDK and you're expect
your all developers to go and implement

all of those helper methods themselves.

Or you have an SDK that's
auto-generated by a really generic.

Platform like swagger, cogen, you end
up with this massive, huge library

that is like really hard to read.

Or the third option is that you
build your own generation tooling.

Colin: And when you say it's hard to read,
you're talking like, I mean now it's just

as hard, like you're, you're having to
reference the docs all the time because

it's not nece, it's machine readable.

It's not necessarily like a, an
amazing developer experience.

CJ: exactly.

To make this more concrete.

If you take the Open API artifacts that
are spit out for the Stripe API and you

run it through swagger, cogen, one of the.

Like wrapper classes it gives
you is 30,000 lines of Ruby code.

And then for every single resource
in the API and all of its like sub

resources, it will generate CL classes
and files and there's like 2,200 files.

So it's like you're either reading through
this ridiculously massive like file

or like thousands of files to try to
figure out, you know, how do I construct

an API call with the right classes and
the right methods and things like that.

And so,

Colin: right?

Because you do also have to have like
docs for this new client library too.

When.

Could build that.

Right?

And Stripe is infamous for having very
good docs and, very human readable, SDKs.

And I think a lot of people think that to
get there, you have to have this huge docs

team and this huge s STK team and that
you're gonna write everything bespoke.

But you guys have kind of fallen in that
happy middle of generation plus some

hybrid, is that custom handwritten stuff
that's being done in the middle there?

CJ: So, Yes, and for a long time, for
like seven plus years, we manually

maintained and hand wrote all the SDKs.

So when a new feature would land in the
api, there was a Slack notification and

then, these volunteers would jump in and
start making prs to all of the different

SDKs in publishing, publishing those.

And that would take several
hours, sometimes a full day of.

To add the features, especially to
Stripe, Java, like Java's just so

verbose that you know, if you change
an eum, you've gotta go change and

update like six files in Stripe, Java.

And so we built this layer.

It took two years to migrate all
the SDKs to, and the other thing

was that we were trying to build the
generation so that it mirrored what

the handwritten versions were before.

So like you've gotta back
into your existing patterns.

And so we built this f.

Uh, this guy Alex Ratray, he runs
a company called stainless.dev that

does this like SDK generation and
developer experience as a service now.

So you can like hire stainless.dev.

And, uh, he built like the first
versions of this tool that we use

internally called Prettier Poet.

And Prettier poet is a react
like framework where you.

Components that are language specific,
and they give you things like method

calls or, you know, literals or strings
or, uh, as like, you know, in instance,

variable assignment or class definitions.

So you can use these,
language specific ones.

They also have like all
the tooling for comments.

And then when you build Your
high level react component.

You can use the open API spec as the data.

That's kind of like
your original data tree.

That's the input into that.

And so you can generate all the classes.

So in the Stripe api, there's
like customers and subscriptions

and payment intents.

Those are all defined
in the open API spec.

You can like iterate overall the resources
in the open API spec and have those feed

into this React component that is gonna be
like, oh, this is the resource component

and it knows how to generate the class.

And then it can use the spec to know
like what's the class name and what

are all the methods and what are my,
what are the documentation strings

that should be added to the top of the
class and to each of the methods and.

What's really cool about this is that
like at first we did it just for SDK

generation, but now we have like this
tooling that generates the Postman client.

It generates the API reference.

All of the code snippets that you see
in the docs we're generating like tons

and tons of those with this like higher
order markdoc.dev component called

cogen snippet, where you basically
say like, okay, this is a, an api.

To v1/customers it's a post request and
here's the arguments, and that will spit

out the code in all seven languages.

It shows the code in curl, it shows
how to do it with Stripe cli, and

that's like all autogenerated now.

And before that was all like just string
and interpolation in erb files, so

Colin: Wow.

Yeah.

I was gonna ask, because it sounds
very similar to Mark Docs, so you

guys have Mark Docs and your SDKs
are being fed by this generation,

if I'm, if I'm thinking
of the trees properly.

Right.

So you have your open API spec, which
then, feeds into prettier poet and then.

Generates those, those artifacts,
fors, stk, STKs, and your docs.

CJ: Yeah, exactly.

And even things like, we have
a visual studio code extension.

So if you install like the stripe
for VS code extension, then you get.

Snippet completion.

So you can type like stripe payment
intent, create and hit tab, and that

will auto complete a snippet in vs code.

Like that's also powered by this thing.

And so, uh, I think even like the stripe
shell, so if you go to the documentation

and you hit like tilde or whatever, it
pops open a little drawer at the bottom

that lets you have this interactive shell
for making API calls directly in the docs.

And all of that is backed by,

Colin: Wait, this.

is, this is in the docs that you

CJ: Yeah, if you go to like
stripe.com/docs and then hit . Yeah.

Hit like, you know, back tick
or whatever, it should pop open.

Stripe Shell which is like a
browser-based version of the Stripe c l

Colin: Oh, wow.

Yeah.

we're finding out all the secrets today.

Yeah.

The other one we just found, if you go to
the, uh, if you just go to customer.new

or do you know about this one?

CJ: No.

What is customer not new?

Colin: If you go to customer.new as
a, as a u r url, it launches into

Stripe and tries to create a new
customer if you're logged into Stripe.

Yeah, we've just found that cuz
we also, we have member new for

Orbit, so if you just like even
make a bookmark for member.new.

And click on it.

It just launches a little screen to
add a new member to your workspace.

But um, I think a lot of people are start,
there's like a whole list of all the

ones that you can do around the web now.

I'm sure there's like a notion,
page.new or something out there, but

CJ: so I definitely knew.

Okay, so invoice.new
works, subscription.new.

Works.

So there were a couple that I knew
about, I did not know about customer New

.
Colin: Yeah, it's whatever company gets
to the TLD before anyone else because

Now no one else can do subscription.new,
only, only Stripe powers that.

But yeah, fun little Easter
eggs for the internet.

I'm trying to think if we have any
other ones for, but I'll have to share

that console with, uh, with uh, Alex
who works on a lot of our Stripe stuff.

And even the, I didn't know that there was
a VS code extension, you know, cause in

my mind I was trying to think of like how
all this is really exciting when you think

about even the open API spec teaching.

GitHub co-pilot, right?

Like, just being able to be like,
I don't want to go, always look at

the docs for every little thing,
but like GitHub co-pilot or Stripe

cli, or Stripe, you know, vs.

Code extension helped me with
what I'm working on here.

And when I've used s STKs,
like some SDKs are just as.

Like, I would rather go just do curl
calls or like http party or something

like that, because I know what I'm
doing., there are some amazing ones.

I'm betting that the Discord one is
probably auto-generated, but what's

really cool is that like once you
get the table stakes of just good

s stk generation done, the discord,
client libraries also help you.

Rate limiting like automatically.

Um, and it's, so it's got a bunch of
like Texs and like backgrounding that

happens to make sure that you're, like,
you're not writing the code yourself to

make sure you're staying within those
rate limits, which is really nice.

But you probably don't get to work
on stuff like that if you're having

to hand write these things every
single time that the API changes.

And then you get the drift.

I mean honestly this conversation's
inspiring me to, go look at our Ruby.

I think we have a Ruby one
and a JavaScript one, and

I think that's probably it.

Um, but I do know that the JavaScript
one, it's like very opinionated

and I think that's the challenge.

It's like whoever wrote
that one, that's how you.

It's not necessarily how you might
write it or how I might write it.

And so there's like that kind of
like an opinion about the developer

experience instead of just saying taking
a customer object, if there's a class

for it, and being able to like add an
invoice really easily and let it fill

in all the parameters for customer and
do all that stuff behind the scenes.

Or do you have to go build each
object by hand and then send it to the

client in order to save those things?

CJ: Right, and I think sometimes
what's interesting about building this.

generation layer is say that you make
a choice early on when you're building

the SDK that you want to have people
interact with the API through like

class methods on some resource, right?

So you have like Stripe::Customer.Create
and that takes in some a hash that will

like pass those arguments to the api, but
later you decide that, oh, it's actually

way better if instead of having these
class methods globally available, That we

have a client where you can like new up
and say like, Stripe know, stripe.new, and

then you call like stripe.customers.Create
And so what's crazy is like you can

use the, these like generation layer to
implement both patterns and then you can

slowly start migrating people over to
this new pattern or just enable both.

Both like methods and.

If you look right now, there's
definitely parts of the stripe docs

that are still one foot in the old
world for like some of the SDKs,

like php, where we had all of the.

Documentation written as class
methods, but the API ref and all

of the auto-generated snippets
are now migrated over to this

like client and services pattern.

And so that is definitely
one of the benefits.

But yeah, if, if your original
authors took like one approach that

you disagree with and you don't wanna
break everyone, then it's ki it can

be challenging to like, Release a new
pattern and have everyone upgrade or,

Colin: yeah.

just alias.

Alias everything.

Yeah.

CJ: Yeah, exactly.

Colin: I think one of the considerations
that I've heard with SDK generation

is if you're not a rubus, for
example, and a Java person writes

a Ruby client library, right?

It's probably not gonna follow.

Ruby conventions.

And so like, this is something to consider
in your sstk generation, is that these

tools probably should know a little
bit about the standards in Java look

like this and Python looks like this.

Even just variable naming
and stuff like that.

Class names Camel Case, you know,
snake Case, all those kinds of

things where you can tell they're
like, oh, a Java person wrote this.

Or a JavaScript person type
script, whatever it looks like.

I'm just trying to think
through like pros and cons here.

It sounds like, you probably
have more contained like testing

and continuous deployment

and being able to have failures and tests
and all that kind of stuff along the way.

CJ: totally.

Yeah.

So what's cool is that if you have
patterns built into the api, then

you can test your generation layer
and be pretty confident that it's

gonna spit out the right code.

And if it's spitting out the wrong
code, then you can fix it at the

generation layer and that will fix it
all, like in all the downstream places.

So it fixes the docks and it
fixes the SDKs and it fixes

kind of everything ideally.

But yeah, it's, it's also important
I guess to mention that like we're

taking the open API spec and by itself
using the spec was really challenging

in order to go from like this giant
J s O object into all of these SDKs

and client libraries and whatever.

And so there is this like
intermediate step that we call,

like compiling the open API spec
into this thing called Stripe type.

And so I th we initially started with
Flow, but I think we're using Ty, uh,

type script now, where we take the,
uh, the original j s o blob that came

out of the open API spec, and then
we build all of these different like

discriminated types for what the high
level resources should all look like.

And then we use that as our
input into prettier poet and our

input into all these docs tools.

That way we have this much.

More like strongly typed and wired up
tool because the, the Open API spec

will actually give you back the resource
and here's the methods, but also

like down here is in a separate area.

Here's the responses, and you kind
of need to combine both of those in

order to have all the information to
implement a strongly typed language.

Go and see Sharp or whatever.

And there is that intermediate step and
if people are interested in, learning

more about that, Richard from our team did
a talk at Strange Loop last year, and so

we'll put a link to that, uh, on YouTube.

And it's super interesting
to watch, how that evolved.

But yeah, when you were, when you were
talking about how, like, like snake

case versus Camel case versus whatever,
have you ever used a Ruby motion?

Ruby Motion, like.

Colin: I'm.

CJ: Okay, so there was, I think, 20
12, 20 13 or something, you could use

Ruby to implement like iOS apps and
it had like some tooling to spit out.

I, it must have been like objective C
or something like this, but it was so

funny because the class ne like the
class names would be like, you know,

application on a knit with whatever.

You know, and completion block
or whatever, , like kind of

the apple, the apple like, uh,
objective seed name for the method.

But it was just like in Ruby, so
it was like deaf and then like

this 85 character method name.

But I think probably, uh, everyone
who's been around for a while has

encountered some SDK where you're
like, this is not, this was not like

implemented by Rubus based on all the
different weird names and stuff that are.

Colin: But I, what I like is
that everything is then in code.

You can commit, you can
add to a change log.

The change log goes out to
all the different s STKs.

So does that mean that you guys
release, when you release an

update to one s stk, you always
release an update to all of them?

Or is there some like, yeah, so there's
not really like, oh, we're only gonna

bump one because it affects all of them.

CJ: Yeah, so we will release.

So there are some changes that only impact
the strongly typed languages because we do

use some meta programming for some things.

And so like if there is a change
to an eum, like there's already an

existing eum and we're just adding
like a new value for that enum or

something, then it only needs to change.

Java go.net and the type definitions
for Stripe node, but it doesn't need

to change Ruby or Python or PHP because
those are all just gonna say like, ah, you

give me a string, you give me a string.

It must work . Because they're not
like checking types or anything,

As soon as a feature is generally
available, it kicks off this

domino chain that is pretty wild.

Like it will automatically generate
like all the internal versions

of it and tests and snapshot
tests and like all of this stuff.

And then it will also kick
off the Slack message.

And then the S STKs team goes
and runs like generate, generate,

generate, generate on all the SDKs.

And that all makes prs and
those prs get reviewed.

And once those are merged, those
all get deployed out to like,

you know, Ruby Gems and npm.

Maven and Gradle and whatever.

It's interesting to be the person
that's gonna tick the box that says

this is generally available now.

And it's like, you can't
take that back very easily.

Colin: Yeah, I was thinking like as
a small company or a smaller company,

it's like, whew, we're gonna be running
a lot of, we're gonna run a lot of

servers and spend a lot of money right
now when we took this box and a lot of

prs and CDs are gonna fire up and you're
gonna get a bunch of servers running

a bunch of code and now we got a bunch
of PRS to review and yeah, it's pretty

CJ: Yeah, that all that said, like
I think it is really valuable and

important to have features immediately
available in the SDKs because that

is like the main way that devs are
using and feeling stripe, right?

They're like, Their first impression
is, okay, I installed Stripe,

Ruby, and then I tried to make a
customer or something like that.

Like usually they're not, interacting
with the Stripe API directly.

The actual numbers of people who
. Are using the Stripe API directly

through official SDKs is massive.

Like, it's surprising how many
people use the SDKs instead

of just making raw requests.

Colin: Well, I mean, with Stripe
there's so many requests that you

need to chain together, right?

To do some things.

So I feel like that one
makes a lot of sense.

Cause a lot of people aren't used
to, you know, carrying around all the

responses and like, let's make this call.

Like I've done the, like, you know,
do the full process of checking

somebody out in Postman, right?

And it's like, okay, it's good to know
how it works, but man, a library really.

A lot more sense for this one, right?

With Orbit, it's like, okay, sending
an activity is just one call.

Now talking and pulling data outta orbit
requires a lot of chaining of APIs,

calls to get IDs and stuff like that.

And some of the things we're thinking
about is like, how do we, I really like

when APIs have like the side loading.

I think you guys have that with yours
where you can say like, This is an id,

but I want it to be the full object.

I don't want the ID of it.

I want the customer with the
invoice attached and those kinds of

things I'd really like us to have.

Cause right now it's like, here's
an organization id, you go get the

organization that it's attached to
and make another call when we already

know who that is and all that.

I think the thing that we're not talking
about here that we should probably talk

about in a future episode is that like,
This assumes you have an open API spec and

that you have like a well designed api.

Like this isn't designing
your API for you.

This is just the tooling around your api.

And you know, I've been thinking of what
RV two API I looks like so that we can

get a, a different API spec cuz our a
p is a J S O N api and it turns out J

S O API is really good for like machine
to machine computers understand it.

I mean it's most of these right?

Like a soap api.

Has a wisdom, like you were
talking about these X S D bindings,

um, all those kinds of things.

It's like teaches the computer what
it can call, but does not necessarily

always give the developer like a fun,
light bulb experience of sending a, an

SMS with Twilio or sending an email with
SendGrid or whatever those things are.

It's like it should be fun.

And I, you know, I, I've
always thought of APIs.

Turning on a light bulb across
the world, right, is it's just

fun to have that as a superpower.

And now we can charge a customer
and stripe or, you know, send an

activity to segment and have it
populate everywhere we need it.

CJ: So I was curious and I, I jumped
in, I did write a couple of orbit

integrations, like one for piping in
some dev.to blog post activity, and

another one for piping in YouTube.

and I was looking at like,
oh, did I just hit the a p I

directly or did I use the S D K?

And in one of them I used the, the
Orbit s d K, the other one I didn't

So yeah, I'm using Orbit activities
request and then passing in just

like a giant blob of arguments
and the body and everything.

Colin: Mm-hmm.

CJ: And then in the other one, I'm
using REST client to just hit, uh,

like orbit.love/api v1 or whatever.

Colin: Nice.

Yeah.

I mean, it's something that we all have to
make decisions when we, we actually have

our own Orbi HTTP client now, in Ruby and.

I think it'll be interesting.

I'll have to see if.

Coworker Steve has any interest
in eventually opening that up.

But it has a lot of that rate
limiting stuff built into

it like we had with Discord.

We sometimes will use official SDKs
for our integrations, but sometimes,

like if our API is only going to
ingest data and never create data,

some APIs don't give you API keys
that are read only, things like that.

So like we're like, we only.

The endpoints that get the data.

We do not want to even have a
method that lets us delete or

create or any of those things.

Um, but also just sometimes like, just
being able to standardize, re responses,

standardize what happens after, cuz
every sdk like we're talking about here,

the experience, the opinions of the
developer team that put together the sdk.

So like, Because of how we built
out our newer integrations.

They almost all use that Orbit
HTTP client, which I think is

a wrapper around rest client.

But there's just like a bunch of really
nice helpers and it's more declarative.

So you can just say these are the
end points and we're not rewriting.

Cause that's like the challenge
when you do a lot of integrations

is that you're doing the same thing.

And translating it to every API , and
being able to have some standards

once the response comes back,
we know what it looks like every

single time, which is really nice,

CJ: So this is the client that you're
using to integrate against other

third parties, not against the orbit?

Right.

Okay.

And then are, gosh, I, I almost wonder
if it's possible to like, Take the third

parties and see like, oh, do all of
them have open API specs or something

like that, that you could then use to

build that?

Like, yeah,

the, so like you have your H C D B
client, and then you could build like that

middle layer that we've talked so much
about, which is like the adapter layer.

And I, it sounded like you had
a pretty cool, uh, like pipeline

Colin: Mm-hmm.

CJ: Right.

But.

Colin: yeah.

Each integration essentially ends up
with its own like Stripe client for

example, that uses the Orbit HTTP client.

And it's just the methods we need
and because everything is built on

that client, we don't have to go
implement everything all over again.

It's just really like, is to get, what's
the endpoint slash customers or whatever.

Obviously once you release something
as like a public gem or whatever, now

you comes with a burden of supporting
it and documenting it and taking issues

and prs and all that kind of stuff.

So do you, you guys, I'm assuming,
don't take PRS necessarily

against these SDKs then, right?

CJ: So there are parts of
them that are not generated,

and we will take prs on that.

It's kind of like, I, I refer
to that as like the core.

So if it's, if it is that sort of,
um, item potency or retries layer or

interacting with, you know, SSL or, um,
the patterns, like, oh, is this a client?

Versus client services or
class method or whatever.

We will take PRS to modify that core.

But all of the pieces that are boiler
plate, that mirror the api, those are

all generated and it wouldn't make

sense for anyone to make a PR

Colin: But they can record an issue so
you guys can go check it out and see like,

oh yeah, that's actually not correct,

CJ: Exactly.

And I would love to see us
actually move the generation code

into the, into the open source.

Libraries.

The generation code right
now is all private sourced.

And I was looking at, AW s gem, I think
this might be the most popular Ruby gem

by downloads or something like that.

Uh, and they also generate this client.

But they're doing it in a
generator that's open source and

it's like part of the library.

And it was interesting to look at.

They have basically these giant
mustache templates and then they

iterate over some input, some input
that's like similar to open API spec.

They don't have this
intermediate stripe type.

Style compiler thing.

But, uh, I do love to see the generator
there because as an open source

contributor, you could make a change to
the generator that's like, oh, it would

be better if it was like this, or it'd
be more perf like performant if we use, I

don't know, yield instead of block.call.

You know, I don't know, like
the actual, you know, Ruby,

whatever, magic stuff, but.

Colin: And someone might learn from
this, uh, you know, AW S one and start

generating their own SDKs for their own.

Like, we, we would just end up
with better SDKs all around.

Right?

It's like putting it out there so that
more people do this as a, as a, as a norm.

Instead of it being like, you do what

CJ: Yeah.

, it's super hard to explain all
of the benefits of Prettier poet

in like the way that it looks
and feels and the shape of it.

So, . I'm hopeful that, uh, if this
is interesting to you or you're

inspired, you go, he head over and
like check out the talk on YouTube,

Colin: Nice

CJ: there will be like
code examples and such.

Colin: is Prettier poet open.

CJ: Prettier poet is not open and that's
another thing that I'm like hopeful

that we will eventually open source.

Colin: Yeah.

So you're

you're here in Nevada.

Here first, you know, or if you're
at Ruby Comp, you'll, you'll get

to hear some of this as well.

That's, uh, Ruby Comp is
the one that's in Texas.

Is that

CJ: Yes.

I'm gonna go to the, yeah, Ruby Comp
Texas, because the Ruby Comp Mini, that

was just in Rhode Island right down
the street, was gonna be the same time

as the develop like chirp developer

conference that we just missed.

So

Colin: Thanks Elon.

Thanks Elon.

Awesome.

Well, I think we're at time for
today, so it's awesome to kind of

dive into SDKs and all the stuff
you guys are doing at Stripe.

I'm definitely gonna go take a, take
a peek at our SDKs after this and

think about what we might need to do.

you said you wrote them
for seven years, were not.

At that point, like we're probably
gonna be handwriting ours for a while,

but at least getting some eyes on our s
STKs and just thinking about how we're

doing that would be, would be good.

CJ: totally.

The show notes for this episode
are available@buildandlearn.dev.

That wraps it for this episode.

Thanks everyone.

Colin: See ya.

View episode details


Creators and Guests

CJ Avilla
Host
CJ Avilla
Developer Advocate @StripeDev. Veteran. 📽 https://t.co/2UI0oEAnFK. Building with Ruby, Rails, JavaScript
Colin Loretz
Host
Colin Loretz
I like to build software and communities. Building software at @orbitmodel 🪐 Coworking at @renocollective 🎙Sharing software learnings on @buildandlearn_

Subscribe

Listen to Build and Learn using one of many popular podcasting apps or directories.

Apple Podcasts Spotify Overcast Pocket Casts Amazon Music
← Previous · All Episodes · Next →