Building a Publish Extension for Canva and Cloudinary

With Canva being one of the hottest tools for creative and design projects, Cloudinary’s Igor Vorobeychik decided to build out a Canva-Cloudinary connector to help streamline work for those who use both platforms! This allows people to create their design in Canva, then publish it to Cloudinary for delivery onto websites, mobile apps and more.

Cloudinary’s Customer Education team will be walking through Igor’s Canva Publish Extension to show how he built it, and better understand how to create deep connections between mutually beneficial systems via code. Together, we will dive into his scripts that use Cloudinary’s Node.js SDK, Express, and more.

Sam Brace: [00:00:00] Hey there. Welcome to DevJams. This is where we talk with developers who are doing very interesting things. Maybe they’re projects that are pushing the boundaries of what’s possible with image and video management and delivery. Maybe they’re looking at things from a different perspective. Maybe it’s just things that we got really excited about here at Cloudinary, and that’s where we’re gonna be talking about the intersection of where developers are building awesome, amazing projects and how they’re incorporating Cloudinary into those projects.

My name is Sam Brace. I am the Senior Director of customer Education and Community here at Cloudinary. And in this DevJams episode, we’re gonna be talking with one of our very own employees, one of our solutions architects, Igor, and he has gone and developed an amazing project connecting [00:01:00] together Canva, one of the best, most widely used tools when it comes to creating content, specifically, maybe slides, maybe graphics, all sorts of things you can do with Canva.

It’s a tool that I personally love using, and I’m very excited to show how he created this connector between Canva and Cloudinary to really make sure that there’s a space for creating this overall content inside of Canva, and then making sure that it can be optimized, delivered perfectly for websites, mobile projects, and other various needs via Cloudinary.

Joining me for this episode is Becky Peltz. And Becky Peltz, of course, is somebody that you’ve seen in almost every Dev Jams episode, and she oversees our overall curriculum and learning opportunities at Cloudinary for our developers that are using Cloudinary. So Becky, it is wonderful to have you here for this episode.

Becky Peltz: Hey, I’m excited to be here. I used Canva as an instructional design [00:02:00] student for many years, and I was always downloading it from Canva, uploading it to Cloudinary, and so I love this project and it’s great to be here.

Sam Brace: I completely agree. What’s wonderful about this, as you’re pointing out, is that is a flow, but not only you have faced and I have faced, but it’s probably something that millions of Canva users have faced, is they probably have certain times where they say, I would love to have this delivered as a URL, and not only as a URL to make sure it’s optimized of all of the various things to make sure that it loads quickly and efficiently on people’s devices, on people’s browsers.

So it’s to say that this is not just a niche use case, and it’s something that excites maybe a portion of the population. To me, this is something that every Canva user can benefit from the work that Igor is gonna be showing us here today. So I’m very excited by that.

Becky Peltz: Yeah, and I think for developers we have a lot of integrations with a lot of [00:03:00] different tools, headless tools, image video tools.

But I think it’s interesting to be able to see how an integration is created, and in Igor’s process, he worked with the Canva documentation, and to just of see how how this integration is done using a node server. So I, there’s many different ways to integrate and this is an interesting one..

Sam Brace: Exactly. And I gotta tell you, if you’re a developer that is trying to figure out ways to connect two like-minded systems together, you’re gonna find an absolute amazing learning resource in this. But if you’re just a Canva user or a Cloudinary user and you’re trying to say huh, I’ve always wondered if those two systems can work together, there’s all sorts of things you’re gonna be able to extract from this.

So should be a great conversation with Igor. One thing I do wanna point out before we bring our friend Igor onto this to start talking all about his project, is we do wanna point out that all Cloudinary podcasts, including the one that you’re part of here today, which is DevJams, that is gonna be found at [00:04:00] cloudinary.com/podcasts.

And as we can see here on the screen, that is where you’re able to go through and review all of the previous podcasts that we have gone and issued across the many different programs that we do have. And of course you can dive into the episodes and watch them and listen to them as you so choose. And similarly, you can enjoy these on any of the services that you we happen to be on.

That includes our own Cloudinary Academy, YouTube, also in listening only mode for various services like Spotify, Apple Podcasts, Google Podcasts and more. And we’re gonna have some great conversations here today. But if you wanna continue those conversations, pass this episode, know that you can always head over to community.cloudinary.com and be part of all of those various discussions that are taking place so you can meet other users maybe those like Igor or maybe those that were previous guests on DevJams, or people that have never been on DevJams, but possibly could be because they’re doing great things with our overall service and pushing the [00:05:00] boundaries of what’s possible with image and video delivery and management programmatically.

So want to make sure everybody is aware of those things before we jump on over to talk with Igor. Igor, let’s have you come on to the program. Great to have you here.

Igor Vorobeychik: Hi there.

Sam Brace: Igor, let’s get a little bit of context here. So I gave you the audience some details saying you’re a Solutions Architect that works at Cloudinary.

I didn’t give anybody much more detail. So go ahead, give us a little bit of flavor about who is Igor and why are you here today.

Igor Vorobeychik: Thank you. Thank you Sam. Thank you Becky. And yes, I’m a new, relatively new solution architect in Cloudinary. Even though almost a year within the Cloudinary. And I’ve been in the industry since year 2000.

So been sometime in different roles as a web developer, team lead, as a managed [00:06:00] professional services, integrated lots of different systems during my career. Excited to be part of the Cloudinary family. And this is more or less my background.

Sam Brace: And what’s great about what’s happening here is that, of course, you’re a first guest that is really coming from the solutions team. We typically pro profile people from the outside, people that have done something with no ties to Cloudinary before, other than maybe reading the documentation, maybe being inspired by some of the training courses we have, and they go and build something. But you of course work with us and we get the chance to interact with you on a daily basis.

Tell us about why you decided as part of the getting to learn Cloudinary phase, being within Cloudinary and understanding what it’s about. What inspired to do this project that you have here today, connecting Canva and Cloudinary together?

Igor Vorobeychik: Sure. First of all before even I decided to join [00:07:00] Cloudinary, I was excited about Cloudinary onboarding process, right?

Which sounds for me, unique. Some companies doesn’t even have such a process. And part of this process was actually, that was clear to me from my manager, is that I will have to build some sort of a project. The project should be something real, not some, imaginary and unusable project project should be maybe even blog, something facing our customers. And I said, this company probably does something right if they want their own employees actually use the software, try it. And they actually later deliver it to the clients and customers. And I was excited already in this part. I was sold pretty much in the beginning. And eventually due to my background in [00:08:00] some building some online editors or involved in lots of integration, when I saw one of the projects or possibilities to build something with Canva, there was an easy choice for me.

Sam Brace: Well, and I think the great thing about being able to do this, is that, as you’re saying, it’s real. It’s code that people can use today to be able to bring these two systems that don’t have direct integrations, official integrations, together, but you are able to create something that really is gonna benefit so many users and also give essentially developers an answer when someone says, can you connect these systems together? You’ve given ’em a very clear pathway, which I love that was part of your graduation project as a good term that is out there. A way for you to say, I’m putting my work out into the world. This is my first way to tell people I’m working at Cloudinary. And be able to do that in an excellent way. So that was fantastic that you’ve been able to pull this off. But what inspired you to look at Canva? Was there ever [00:09:00] experiences working with it or seeing it out in the wild? Maybe personally, professionally? What got you to say I should link this to Cloudinary?

Igor Vorobeychik: So for the past 15 years I was actually working a lot with the a lot of Adobe products, right?

InDesign, Photoshop, a lot of personalization using InDesign servers and et cetera. We had lots of requirement from users to have something as powerful as Photoshop. Maybe not necessary as complex as Photoshop, but for the wide variety of customers, and have it online, right? And I would say about already maybe four or five years ago, the Canva, everybody was talking about Canva. I said, I need to look at the Canva. And by the way, my own previous job we had our own proprietary online editor. When I saw the Canva, just blew my mind. And this is a unique [00:10:00] Australian company which developed something unique.

And when I joined Cloudinary, I saw parallels that Canva was the best at what they do in the design space, right? And Cloudinary is the best of what they do with the media. And and for me it was interesting to combine those two. And actually I think you started your podcast with with something that millions of users are using Canva.

And I actually today Googled, I think I found that, again, it’s a bit old article, but in 2022, the projection was that they were gonna hit about 1 million user mark. So an amazing, so I always, I had some commercial way of looking at one new build, [00:11:00] right? One one way is to build something which can be useful, but that if our developers can also make it out of it, a successful product.

So I think to this connector can expose them, can expose their Cloudinary, maybe to a millions of users, right? It could be a business to business, it could be a B2C. So it just gives them ideas of how they can actually help millions of users to deliver media. And that’s what’s exciting, I think about it.

Becky Peltz: Yeah, I think this is interesting too. I was looking at the documentation from Canva and I noticed that we’ll be seeing movement from Canva into Cloudinary, but you can actually move both ways. So here you have these two kind of headless media companies able to exchange with each other and then of course other websites if needed.

So it’s just a really cool integration [00:12:00] between these two companies and their product.

Sam Brace: Absolutely. So Igor, let’s do a quick walkthrough of this so that way everybody understands what this is. Cause I think we’ve talked about conceptually enough where something’s happening in Canva, content creation, and then it’s gonna be delivered by Cloudinary.

But let’s see the overall flow of this thing. So I’m gonna bring your screen in here and maybe we can do a quick demonstration.

Igor Vorobeychik: Sure. Absolutely. So here I’m in Canva, right? And I want to create my design. Let’s assume it’s some Instagram post maybe, right? I can choose from variety of different designs, like templates, right?

And I don’t know, maybe this is an HR type of post like we are hiring or some other stuff. Maybe I want to to [00:13:00] customize it, right? Once I customize it, I would like probably to publish it, right? And this is where the a lot of customers will say, okay, what do I do? How do I make sure that it will be delivered in most optimized format?

How I will actually use this CDN also, so it’s gonna be cashed super fast and et cetera, et cetera. So millions of users can see this fast and et cetera. And this is where the integration. So all they need, if let’s say they have already a Cloudinary account, and they have an integration, then they just, in this case, I have this already integration in place.

I’m choosing the Cloudinary, it’s already connected to my particular cloud, right? And I can choose maybe some folder where I want to maybe organize something [00:14:00] like that. Maybe I can choose the format, one of the formats that’s available for me to save this. This is, by the way, configurable by your extension.

Maybe provide some message that can be used later on there, and save it. If all went well and my extension is up and running, first of all, you’re gonna get back already a URL, which can be shared, right? The version which we just customized, right? If those of you who know Cloudinary, you will see that this version include f_auto, q_auto, meaning is optimized format, optimized quality.

And again, we can go wild here and add more transformation even on top [00:15:00] of this asset, and if we will go to the Cloudinary, and let’s say go to this folder, we will find this asset now. And we also can notice that I applied some contextual metadata. I applied some tags to it, right?

So that can be also searchable within my my let’s say asset library to find something that has certain tags something that maybe has a contextual metadata we scan by id. So I can basically not only publish it, but also organize it in a certain way within the Cloudinary, right?

And obviously this [00:16:00] published URL now can be served in any systems can can be used on any website. So that’s the overall workflow final workflow which we see.

Sam Brace: It’s incredible and I think what’s amazing about it is that you’ve able to done do a few things that you’ve pointed out really is that if you wanna make sure that this is now easily searchable for inside of your Cloudinary system, you’ve now shown how adding something into the comments field be as searchable content that when it makes its way into Cloudinary as an asset.

I think it’s also where we didn’t have to wait long. This is a real-time demonstration. This wasn’t taped prior or anything like that. And then you add something where you created in Canva, you delivered it in to Cloudinary within a minute, if less it’s incredible what you just pulled off here at Igor.

Becky, I didn’t mean to interrupt you. You had a point there.

Becky Peltz: No problem. But yeah, I was struck by the, same thing. We’ve taken an [00:17:00] image that had really no context, no metadata, and made it into, put it into a place where it can be, have a high amount of context and be pulled in from many different data identifiers like the tag or the context metadata.

So I think that’s something to look for as we see how you implemented this Igor is how did you get that context associated with those images that you are pulling in?

Igor Vorobeychik: Yeah, absolutely. So this is where we can, we will need to already get in the bits and bytes of the integration. So I guess that would be a natural progression.

So for those that would like maybe later go a bit more detailed I do have a blog that you can find that describes how to build Canva extension give you pretty much [00:18:00] all the information you need. This is just like for your reference, right? So have you detailed here.

We may not be able to dive into all the aspects here. For this particular project and also the project that was facing the public, I decided to use Glitch. Glitch is a very easy way where you can create an application. You do not have to use any desktop id you pretty much, any student can use it.

He doesn’t have need to have a very powerful computer or any proprietary software. He can create a very powerful application. I use the, in this particular express framework. This is for for, to create my REST API influence that should [00:19:00] satisfy Canva publish extension.

We’re going to get into details a bit more. So I use Glitch as a platform where I develop the poc and also also something that is actually the, where I published my endpoint, right? So this is a development environment plus actual my endpoint resides on this system and can be accessed, right?

So it’s self-contained. Some of you may use some IDE Visual Studio Code. They maybe gonna use git or GitHub to, for their PUT versioning and eventually they may use, I don’t know, let’s say AWS to actually publish their lambda their endpoints. But this is more like self-contained.

A bit easier to understand. But I also love Glitch, its [00:20:00] an awesome company, which was acquired by Fastly, which is also a Cloudinary CDN partner. This is what I used for this particular project.

Becky Peltz: Hey, just not to interrupt you, but excuse me, Igor, but for this extension, now I, as I understand it, you need a base URL. So, whatever code that you, however you package it up, whether in Glitch or in serverless functions, you will need a base URL. So you get that automatically from Glitch, right?

Igor Vorobeychik: Exactly. So your like a unique name space, right? You call it a domain name. You obviously have a more robust version and pay for your CNAMEs and have but yes, it was [00:21:00] very easy to use because I got all my domain names, everything set up for me pretty much, right? You getting it. And it, it was very easy. Now, Canva also has tremendous documentation. And I actually when I look, looked at Canva documentation, look in Cloudinary and saw how we both create a very unique content in a very professional way.

So it was so easy for me being a new SA within Cloudinary just by reading some of the documentation, try the samples, right? Be able to achieve what you see here in, in a very few days. Literally.

Sam Brace: This was new to me because, like I’ve always thought, this is my ignorance, is that I [00:22:00] always thought of Canva as being a very UI based tool, but as I started going down the rabbit hole and being like, oh, but have great developer documentation and seeing this area, it was very enlightening for me to be able to see this project, but also to see the various layers that Canva has created to be able to create these types of connections that you’ve gone and showed here.

So I can see here on your screen the way that they’re calling this is a publication or a published extension. So what they’re ultimately doing is it’s getting added to the published menu of Canva and it becomes an app just like you chose it from in this space. And that’s what they’re encouraging developers to be creating.

Igor Vorobeychik: Exactly. So Canva has lots of out of the box extensions, but it also allow developers to create their own. And there are several types of extension. There are content extension. For example, one of the next steps maybe would be [00:23:00] bringing assets from Cloudinary, and that would be a content extension, right?

So this is, would be probably on the left when you do upload, that’s what it called content extension. Where you’re taking the extension from your asset from right where you selecting your asset. Not necessary. You start from design. Maybe you want to bring in us another type of extension is this is where you publish and it’s a publish extension.

So here you see my extension, but if I do more, you will see that a lot of connectors are already there. And those can, some of them are written by well known companies like Instagram and et cetera, right? But some of them, like mine was written by developers, right? So there is lots of extensions and there is a great [00:24:00] developer documentation that allow you pretty much, very quickly read about extension you want go with a quick start user guide, right?

There are examples here, and I, by the way, I choose Glitch, not just because it was also one of the easiest choices because I pretty much maybe get a project that I could have just click remix, right? And then start develop my own.

Becky Peltz: So its like a quick start here, huh? They’ve given you kind of a quick start for doing your extension.

Igor Vorobeychik: Exactly.

Becky Peltz: Giving you a sandbox.

Igor Vorobeychik: Exactly. Yeah. So maybe this sample is much simpler than the one that you see. Or actually, my example would be a combination of lots of samples that you will, you may find, and obviously a bit more [00:25:00] customized for Cloudinary needs, right? Or for, with the Cloudinary in mind.

But definitely the quick start user guides here, and by the way, on Cloudinary documentation, you will find a lot of also quickstart user guide samples also that use Glitch and some other systems that just allow you to play with the code, how you implement I dunno, Product Gallery Widget of Cloudinary etc…

So it’s today is very common where developers can quickly progress from documentation to some online sandbox where they can actually play with a tool before they, let’s say, purchase anything or before they decide or use this library another. So they, yeah, the, there is a very short path today from documentation to [00:26:00] actual actual sandbox and the prototype which our developers can build and that’s very exciting.

Sam Brace: Now, Igor, one thing that I know is a big thing that Becky and I always talk about in training, especially with Cloudinary, and I wanna address it in your project because I think you did a good job with being able to handle it well, is something called environment variables. And then basically making sure that’s not exposed to the public users in any way through something called a .env file.

Can you show me how you maybe did that? Maybe how Canva looks at that concept inside of your project?

Igor Vorobeychik: Yes. In order for us to build the extension, we need at least a few things. One of them obviously if we want to push asset to Cloudinary, we need to store Cloudinary application keys, right?

Basically how we execute the APIs. So in [00:27:00] my particular case, what I was doing, I was using the .env library, right? Which is using env file that allowed me to store pretty much different keys. So this is where I stored my keys. Now the interesting thing is if you will come here and and remix this project.

To make it of your own or you trying to view it as a different user, you will not going to see this information. You see it’s stripped out for you. To be honest, I was a bit worried in the beginning. That’s why I created, and I think in the blog post I created a, what I called public endpoint just for blog purposes where I [00:28:00] actually, in the instructions tell you create a .env I just given an extra layer of security there. I was afraid to store it there, but Glitch takes care of it, right? No worries. There, let’s go back to my Cloudinary endpoint, and let’s talk about the second key. Why do I have a, another value here is the Canva client secret.

So, Canva build with security in mind, right? When you start developing your application. And this is already, I already created, I can create new app right there in the Canva UI so you will see that one of the things is verification, and this is one of the actually things I really like, so your end point, Canva actually wants to ensure that whatever [00:29:00] you will develop be secure for its users, that endpoint will actually will implement the security measurements. Even if you can run the security tests and they actually will submit various client secret timestamps.

They will try to fail you and you should actually, your service should return a proper http response. If you do not, you will not be able to, let’s say, publish such extension, stuff like that.

Becky Peltz: Now, I noticed too that there’s a regenerate button there, so if anybody was trying to copy down your key when you showed it with the .env

Igor Vorobeychik: Obviously. Yeah, good point. Obviously right now…

Becky Peltz: Cloudinary has the same thing.

Igor Vorobeychik: Yeah. Obviously right now everybody will see this key and we are recording it, so obviously this is not something, so after the call will regenerate a new one and [00:30:00] then I will be able to use. But yes, the security in mind, this is great. This is by the way where I point to my own endpoint which is on Glitch.

And basically your project name will be the entry, right? The URL for your endpoint, right? And again awesome awesome very on one hand is simple, but everything in Canva is very so first of all you noticed that I had some user interface where I selected the folders.

Now since Canva wants to control kind of user experience, right? They don’t want that different plugins or [00:31:00] extensions look slightly different. They want some sort of unified look and feel, right? So they provide you pretty much with the user interface.

You just need to to write couple of endpoints to feed the information to the…

Becky Peltz: You’re gonna start out with an endpoint that is gonna go get you something, and then therefore they’re gonna have some UI that has lists or a single item.

Igor Vorobeychik: Yeah. And yes, Rebecca. Absolutely. So when you said word get, and this is exactly, actually, almost the name. Find and get the endpoint name. So even from the names of the endpoint, which Canva ask you to actually to write, it’s very easy to, it’s not some, special names. So for publishing, they using upload by the [00:32:00] way, I found that the upload endpoint. Is very similar to Cloudinary upload, right? So it’s an upload, which is mean published, and this is exactly what you do when you so a lot of similarity in terminology you say .And then yes, there are there is a find that’s basically something which loops through directories, right? So I used here a couple of Cloudinary APIs. In this case I used the sub folder API. And then eventually there is a get, once you find what you want, basically you are passing back the exact sub folder that you decide to place your item there, right?

The final URL. Now that was developed before Cloudinary I think had dynamic folders. Now we have dynamic [00:33:00] folders that maybe would do it differently, but again, the concept of structure or place your designs and organize it within the DAM still applies here.

Becky Peltz: Yeah, and it looks like inside there go and you get these resources and then you map them in your, I think it would be down a little bit from what I’m seeing, maybe line 120 or so where you were just, where you were at.

You, so down there at Oh, up a little bit. I see like line 115 there. So you take what you get out of the subfolder response and you map it to their object type id

Igor Vorobeychik: I will pass, yeah. All this information to their object so they can also build the UI, and eventually once something is selected, then they actually can already call the upload API, and pass what was selected because [00:34:00] it was done by different endpoint. The define and they get the actual path, let’s say, where you want to store it. And actually those few lines of code are responsible to push it to the cloud, right? And literally few lines of code as what we upload

I’m using the logs a lot in this just to debug and see what information is sent to me. That’s how I was able to understand exactly what type of let’s say body structure they sent to me, right? So I could access the URL of the asset, right? I can get a design id, right?

Canva, design id, which I decided using as a file name. And because I’m using a [00:35:00] default upload preset, even if I will reuse the same design id. But there is a unique unique characters are added by Cloudinary, so I do not override, again, I could have decided to override. It depends on the workflow.

Now right before actually I do provide some contextual metadata. I could have provided me maybe create structure metadata. Now right before, actually…

Sam Brace: Before you jump to that I wanna point out something that I love what you did there, because if you look at the context, if this is the connection of what we saw earlier in your demonstration where when you added in comments then how did those become searchable fields within Cloudinary when we were trying to find the files? And it’s because of its plus message that you see here, like the request body message. That’s that direct connection for us to know that we’re applying this as context metadata. So it’s, that was genius because you could see [00:36:00] people, adding lots of things, frankly, in the Canva UI to be able to explain what’s happening there and knowing that all of those become searchable keywords for people to find that asset later with Cloudinary. That’s a great feature that you added in there. It’s very smart.

Igor Vorobeychik: Yeah, thank you. And my personal favorite, actually, tags, right? Actually I had added just tags today. I when I joined the Cloudinary, I didn’t put much attention on the tags, but once I discovered the power of Cloudinary tags, it just blew my mind.

And also list APIs that are around it. Again, we probably need a different session on those, but that’s why I added this in another line here, just to add the tags. And obviously now in this case, you need to know the tag if you search by it, right? So if the design id is something generated by [00:37:00] Canva unique and basically has no particular structure it would be hard for you to guess that one, right? So you probably, when you are using the tags, this may be not the best field from design id from Canva to use. I would use here maybe something more more human readable or understandable or guessable, right? Let’s say some name or whatever.

But the idea is that you can apply tag and then doesn’t matter how many variations you will create of the same design, you can search by the same tag and then get all of those designs for you. So we can obviously very quickly demonstrate the same, we’ll just, let’s say create v2, right? Version two, right?

And then we will gonna share it again. And let’s say, I’m gonna put it even in the samples folder. I don’t [00:38:00] have to even put it in the same folder. Different message. By the way, this message in my case is required. You can make it not required. Just the configuration of the extension is on the published extension.

So now it’s saving. I want to show you, by the way, that when we saved all the information, I just put it in the log. Just easier to see. You will see here that I got all the information from Canva the file name, the type, the design id, right? So that’s the actual tag. And then I also store here response from from Cloudinary. Now let’s go back.

Becky Peltz: So just to [00:39:00] make it clear, you, this is where you’re calling our Cloudinary Upload API and pulling something from Canva, which is pulled in by its design ID into use as file name.

Igor Vorobeychik: I’m not pulling it per se. It’s more common when it calls the endpoint. It passes in the message that passes message body and message header.

The header is used for security to actually do some. You will see each method use validation of this post message. That’s what you use in the security. And remember the key which discuss Canva id and the body is a JSON body object that you can get an information from Canva take it from there and then pass it to Cloudinary.

That probably would be more accurate description of what happened. So if we go right now back to Cloudinary to [00:40:00] the, to Cloudinary and maybe go to, I don’t know, to advance search and maybe right now know the tag, but let’s say I’m just gonna apply the tag. So now I have two designs, right? Now this is v2 and this is actually marked as a new.

We see the nice preview here. This is v2, this is v1, right? Or basically our first creation, right? They have slightly different, I think message one has a test and another has, ah, they both have tests. I guess I, in both cases, wrote tests. But the idea is that I have two variations, right? But they all belong to the same design Id.

Then maybe later I can do something about it, right? Maybe in the future I will open up Canva from Cloudinary and load the design id, right? [00:41:00] Load design id, I just given the ideas where we can bring it to the future. The most important that you can tag, you can affect your file name.

You can do lots of stuff. You can organize your content and most important, you publish in it, in the multi-CDN environment of Cloudinary. And this later can be served in the most optimal optimized format and quality, any type of transformation.

Sam Brace: One thing I wanna do, let’s jump back to Glitch for a second cause I do want to unpackage one more thing that happens to be in your code that I think is gonna be very helpful for people when they’re working between these two systems.

Scroll down until we see resource type, I think it’s line 44 if I remember correctly. There we go. See it exposed. So Line 44. Resource type. So as we know, because we work at Cloudinary, This is where we’re saying, is this an [00:42:00] image? Is this a video or is this a raw file? And raw file could be any file tape that is not able to be transformed, meaning we’re not gonna resize it or crop it or change its format in other things that we can do.

There’s hundreds of things we can do with it, but it’s to say what I like that you’ve done here though, is you’ve called our auto resource type situation. Because when someone is working with a system like Canva, they’re gonna be bringing forward images like we saw. We’re gonna be bringing forward JPEGs, PNGs that were created in Canva, and then make sure we’re deliverable inside of Cloudinary.

But what’s also possible with a system like Canva is you might be bringing forward documents such as maybe a PowerPoint file or something that’s going to be, we consider them images the way that we work from the Cloudinary, but PDFs could be considered documents too. So it’s to say you don’t have to think about what’s coming from a system, it’ll just automatically detect it and make sure it applies the appropriate resource type.

So I thought that was very smart, once again to make sure this was future-proofing, this, making sure that all types of [00:43:00] users could benefit from this when they’re connecting these two systems together. So that was a good call on your code.

Igor Vorobeychik: Yeah. Thank you Sam. Yeah, and this was just for simplicity. You don’t have to think what type of the asset you have.

And as you saw in when we are actually posting something or let’s say, and sharing, we can decide on different type of format, right? And suddenly it can be become a PDF, right? And obviously in order not to have some if else statements or others, and maybe even on Cloudinary, you can use PDF as image and as raw.

So that’s where maybe you will need eventually get into the, those case or if statements, if you want really let’s say taking control, right? How you want those files be [00:44:00] accepted by Cloudinary, right? But if you don’t, then auto is a very good option to, to use. So now actually I’m gonna get back, and this is going to be in this case could be a PDF, but also we are going go to Cloudinary right now.

Let’s see, we’re gonna go through the Cloudinary and reload or refresh or now we have another asset, right? Image format, PDF, right? So, that’s just the power of Cloudinary.

Sam Brace: It is. Now one thing that I’m missing right now in the code situation and, I’d love for you to see it cause we’ve referenced this a few times, is this f_auto and q_auto that we keep talking about.

And of course f_auto means automatic format, so that way when you’re getting these as JPEGs or PNGs [00:45:00] from Canva, we at Cloudinary can deliver them in the most optimal format possible. So it may not stay as that JPEG or PNG, it might become a WebP as an example, or it might stay as that if we see that as most optimal.

But it’s allowing Cloudinary to help make the choice so that way the content is as lightweight as possible, but it’s only based on format. But, and q_auto is similar when it comes to the compression side, making sure that we’re providing the most optimal level of compression based on the person’s browser and and frankly, device as well.

But what I’m wondering is how are you applying this f_auto q_auto inside of your code? What’s making that be appended into the URL?

Igor Vorobeychik: Sure. In my particular, there is various techniques that you can use, right? I decided to use actually another Cloudinary method, right? That is basically the URL the method that allows me to [00:46:00] build the URL.

We also have a method that allows you actually to build the whole image tag, right? If we want the whole image tag, I use the URL here and within the URL, once I uploaded to Cloudinary and got back as part of the result, a public id, right? If you remember, I told you that I allow here to use a dynamic upload presets, which actually generates the unique name for these uploaded files.

It adds some characters. So I do not know, at this stage, what will be the public id. That’s why I need the response. Once the Cloudinary uploaded and I’m gonna get the public id. Now, once I get the public id, I can build the URL. And here again you can use any of your requirements. I do here very bare minimum,

I saying use version I don’t have to use version if I don’t want to. [00:47:00] I would like to use transformation. In this case, I’m saying I would like to use quality fetch format, which is auto, right? I could have specified particular format I want to use, right? I could have specified particular quality I would like to use, right?

I could have add all hundreds different transformations which Cloudinary supports and generate URL, right? So this is something that can be I’m not using here again, that was build when I just step into the Cloudinary world. You can use here name transformations, right?

Which is very powerful because then you actually give something of another like encapsulation. So basically let’s say if I would add here a name transformation, then I could have [00:48:00] used Cloudinary and build very complex name transformation, right? And give it to the no code user, right?

The user doesn’t have to write the code maybe later to change this name transformation, right? And use Cloudinary transformation builder for that, right?

Sam Brace: Hold on, Igor, I mean as big as you can make this, the fact that you are even able to apply just these two is so powerful too. So it’s to say yeah, you can always iterate, but this is pretty impressive in itself to be able to add f_auto q_auto to every URL.

And then Becky, make sure I’m understanding this correctly. So if I’m looking at this flow that we have here, we have it where we have the endpoint that’s using the Upload API. And then we’re calling, is this the URL helper method that’s taking place for all of this f_auto q_auto and URL generation take place?

Becky Peltz: Yeah. Yeah. So the Uploader, the API returns a [00:49:00] promise and Igor’s dealing that, dealing with that, using the, then so he gets the upload result back after the upload is successfully done and now he has access to the upload response, which contains lots of information. And some of that information is that public id.

So upload Result public ID is the unique identifier from Cloudinary upload result format was the original format that he used to upload version is the result version. So he’s able to pull in data out of the response and use that to generate a unique URL from the Cloudinary URL and there are other kind of, I call ’em helper methods.

This one builds a URL. There’s one that will build you an image tag. There’s one that will build you a video tag and they basically just produce strings. And then once you request that string in your browser, it goes through a lot of processing and eventually gets served off of a CDN. So [00:50:00] lot, a lot of things going on once you’ve got a Cloudinary URL that you can take advantage of.

Sam Brace: I love it. This is absolutely fantastic. Igor, you of course you wrote this or there’s so much we can unpackage, but whatever big things do we wanna make sure that people understand, like maybe was there any roadblocks that you came across? Was there any big learnings that you came when you were building this project that is worth unpackaging for the audience?

Igor Vorobeychik: Some little things which I found is maybe that I couldn’t actually find in documentation or wasn’t wasn’t clear. For example, when I used the subfolders API of Cloudinary the Cloudinary has also root folders of something API, which I didn’t want to use both.

And then I found the way, if I will just pass the back slash, that’s actually give me a route, the little things like that. [00:51:00] Also I found a bit not a clunky, but I spent some time on the not necessarily on Cloudinary end, but on the Canva around the validation, right? All of these validation of security which implemented here, which I advise to go and look at, right?

A bit more closely. What else? The rest is a, I wouldn’t say that other things are basically wasn’t that hard to implement. And again even if you new to node JS, if you are new to Cloudinary, new to Canva, you should using this blog and those few resources put this together in several days and already have your own Canva published extension. Now, my extension is not public [00:52:00] extension. This extension is of the it’s a team team extension, right? So when you publish it, you basically do not have to go through scrutiny of the Canva, which should make it available for millions of users.

Obviously there are there are some things that you will have to fulfill, but so it’s a bit easier to build your prototype to play with it. And then obviously expose it within your organization. So that’s what I was using here. I found this a very easy way of. If you, let’s say, building a new version, which you wanna point to, different end point.

Maybe this is fraud and you wanna point to staging, right? Or maybe you have pro too. Canva have out of the box, create new version. Now [00:53:00] it’s become draft of the new version, right? Which you maybe can repoint to some other place. You maybe even want to let’s say, remember I told you I’m forcing the message, right?

Maybe you don’t wanna force the message, right? Maybe you want to use different not allow, maybe PowerPoint whatever extension, right? Maybe you want to reconfigure it as well, right? And the interesting thing is using the same client secret, if you using the same endpoint, you just may be messing up with the descriptions with the UI, it doesn’t have to be changed within the code, right? So those type of things. And then you can even preview it. So right now I actually can maybe preview and you see now, I mean they have right now two [00:54:00] names I probably should have named the second one. This might be different. But if I’ll choose this one I by mistake, choose the designer, which I need to buy.

So let’s use something free and choose. And you will see right now that I don’t have this PowerPoint, right? Selected. I don’t have this message as something I have to use, right? And in this case, I’m using the same. So actually there is some error. I need to go dive. Maybe there was actually change in these secret key and et cetera, et cetera.

Sam Brace: Right, but you can test it and…

Igor Vorobeychik: Yeah, exactly. Exactly. And this is where the logs are coming into place. And there I should, or some public ID invalid name. So actually it was Cloudinary error. Probably not do doing a good job on the on these [00:55:00] naming convention. But again, this is how you are debugging the stuff actually intentionally wanted to show you.

So this is how you getting help from what are doing and perfecting your integration. And the great thing is the the Canva also makes it very easy for you to basically publish your draft. Now I have my new draft version, right? Which I can continue to edit, right? Or maybe I want to delete it, and once I’m done, I will be able to publish it and it’ll override my extension because this is a new version of v2.

So, again love what Canva did around extension love what they did around around security and even more excited about the Cloudinary, what we now, how we can help all these millions of Canva users to publish their [00:56:00] designs to deliver them across the globe in the most unified and optimized way.

Sam Brace: And to encapsulate everything. What I am really happy about of course, is that not only will people have this podcast episode to be able to reference, to understand all of the ins and outs of doing this, but you also have a fantastic blog post that’s published on Cloudinary’s main blog that highlights all of this.

It has clickable, usable links to be able to get access to a lot of this so you can remix exactly everything that you’ve gone ahead and built as anybody that’s working between these two platforms. So it’s a, you have plenty of resources available to the world to be able to make this Canva, Cloudinary connection, a real thing within their organizations.

So you’ve really empowered a lot of developers here at Igor. This is fantastic.

Igor Vorobeychik: Thank you. Excellent.

Sam Brace: So Igor, we’re gonna let you go, but have a wonderful day. This [00:57:00] is wonderful to have you here. And then me and Becky are gonna say some nice things about you. So yeah, have a wonderful one, Igor.

Igor Vorobeychik: Thank you, Sam. Thank you, Becky. Have a good day. Yeah, bye-bye. You too.

Sam Brace: Becky, what’s your key takeaways here? There’s a lot of things that we can unpackage of this project, but what are the things that are standing out to you?

Becky Peltz: I think the way that the documentation for Canva is set up, that they give you a Glitch starter.

You can take that and then just play around with all of the different, certainly Igor’s talk, generate a lot of ideas on built based on what he did and then what else you can do as far as you could maybe start bringing video in then you could bring, stuff from Cloudinary into Canva and just lots of different permutations there.

I think. It looks like a fun playground.

Sam Brace: I agree.

Becky Peltz: I would probably look into, building out some serverless functions [00:58:00] too, because as long as they all are posted at the same domain and you have that base URL, you can do that in a serverless mode as well. So lots of interesting paths that a developer might take with this.

Sam Brace: Yeah, I agree. And I think you’re touching on something that I think is really inspiring to me and it’s a move that I’ve seen Cloudinary starting to do with more quick starts, more ways to try it, exploring code. And Canva has something very like-minded where we have a lot of ours tied to Repl.it, which is a similar service with some differences of course, but similar service to what Glitch is providing.

And we have a lot of that in our documentation for people to try it out, to actually, let me quickly show our audience what I’m talking about here, but if we pop over to our documentation, you’ll see that we have quick starts, very similar to what they had here, where we can test out the node SDKs right from this area with a overall similar service to what they’re providing for this.

So people can expand and try [00:59:00] things out in a safe space. So it is where I like that Canva and Cloudinary are doing something very similar in that space, but it’s where they’re also encouraging everything that Igor did is they want more developers to create connections between this system and that system and the other system to Canva.

So if it’s inspired from a business perspective that they’ve embraced the creator and the developer within their overall product, which is very very cool to see.

Yeah. And I think a good developer experience is the one where there’s less code. So anytime they can supply you with a nice set of code that you can just put your specialty stuff on, that’s a good experience.

And they’re definitely in the right place as Cloudinary is too.

It is. And it was smart for Canva to use Node as a starter, frankly, because, think a lot of our coursework was written in Node intentionally, because it [01:00:00] is a framework, it is a way for people to be able to do things truly front end, back end because of the JavaScript connection between all of it.

So it is where it’s, if it’s a smart space for them to be in and, but it’s also to say that if someone were to try to replicate what Igor did, possibly in other SDKs, it might be possible. So version, there’s lots of connectivity there too, which is

Becky Peltz: Yeah. Just go home and talk to Chat GPT-4 and he’ll give you probably three or four ways to do it.

Sam Brace: Oh man, we like, it wouldn’t be a podcast if we didn’t mention Chat GPT in it, right? No, absolutely. But great stuff and to highlight of course, everything that we have talked about. Once again, on cloudinary.com/blog, you’ll see Igor’s post, we’ll have that of course in the show notes with all the associated links if you wanna follow along with everything that happened to be there.

So wonderful space for you to be at. And of course, before we do let our [01:01:00] audience go, we would do wanna point out that this is not the only Cloudinary podcast episode that has been out there. We have many, we have years now that we have produced of this. So you can always find every and all episodes of the podcast programs we produce.

There’s two: DevJams, as well as MX Matters, and you can see those at cloudinary.com/podcasts and that’s where you can dive into the episodes, watch and listen, and also have links to any of the associated podcast services that we happen to be subscribed to, such as Spotify, Apple Podcasts, Google Podcasts, YouTube, as well as our own training resource, the Cloudinary Academy.

And without making sure that we don’t continue the conversations, we have to continue the conversations and if someone has questions about anything we’ve covered at any program, or frankly, anything that is tickling their brain about what Cloudinary can provide, they can always go to community.cloudinary.com, where you’ll find our overall community forum and [01:02:00] it’s associated Discord server for you to continue with conversations.

So this is all good stuff now, Becky, any final thoughts about the Igor conversation?

Becky Peltz: No. It’s great to have Igor on and to be able to share some of the work that our own employees are doing. It’s, there’s a lot of creativity in the company and it’s nice to be able to pass that around.

Sam Brace: Absolutely. Absolutely. One last thing that we do wanna point out here is, this is actually somewhat of a bittersweet episode for us, because this is gonna be Becky Peltz last episode on DevJams. Becky’s moving on to some brand new adventures, which we’re really excited for her to be a part of, and it’s been amazing to have her as my co-host since we’ve launched this overall effort.

But it is to say that this will be the last time you have Becky on as our official co-host. Becky, I wanted to say thank you for the many years of helping our [01:03:00] developers, helping out the overall community to understand what is available with Cloudinary and expanding their knowledge. So thank you for being a part of this.

Becky Peltz: Hey, it’s been my pleasure and I’m happy to be here. I’ll have to check out what you’ve got going on next time.

Sam Brace: Absolutely. Absolutely. And that’s to say that we are still absolutely continuing the DevJams program. We’ll be out once again in the next few weeks with a future episode where we’re talking with another developer that is doing some amazing, innovative, inspiring things with the overall service.

So don’t worry, even though Becky won’t be with us, we’re still gonna be here. And of course, hopefully, Becky, you’re cheering for us from sidelines on this overall case too. Excellent. So on behalf of everybody here at Cloudinary, thank you for being a part of this episode and learning more about what our services can provide and we’ll see you at the next one.

Take care everybody.