Now let's go ahead and let's protect our HONO API routes using Auth.js. So for that I want us to prepare a proper testing environment. So let's go ahead inside of source app API route catch all. And inside of here I want you to copy for example images and rename them to test and we're gonna go ahead and clear your get route so just make it an empty route and you can remove all imports besides HONO and let's simply return C.JSON with a success message. So just a very simple get route inside of a new test.ts file.
Now let's go back inside of route.ts and let's import that new test file. Let's chain it to our router under a test prefix. So now if you visit localhost 3000 slash API slash test you should see success true. Let's try it out. Localhost 3000 slash API slash test.
There we go. Success true. And now let's find a way to protect this route. So let's get back to Hono documentation here. And inside of the docs, inside of the menu, under the middleware section, you can find third-party middleware.
Inside of here select Auth.js. Let's go ahead and let's see what we have installed and what we don't have installed. So we already have Hono I believe, there we go, and I believe we have some auth but it looks like we don't have auth core. Now technically we don't need auth core ourselves because we use next auth package but nevertheless let's install these two. Hono, authjs and auth core.
I'm gonna go inside of the terminal and I'm gonna run bun add HonoAuthJS and AuthCore and after that you can do bun run dev again. As per configuration section we don't have to do anything we already have out secrets set up. Now inside of here they're gonna guide you to setting up next out for the first time but for us it's a different case. We already have a huge configuration so let's go ahead and separate that configuration into its own config. So this is how we're gonna do that.
Let's go ahead and close everything. Let's find our source auth.ts and on the same level as auth.ts create auth.config.ts. Go back to auth.ts and first of all let's copy all inputs here including the declare so all the way from declare to Zod copy everything and paste it instead of auth.config.ts And now inside of here go ahead and copy the entire next auth object. So basically everything inside of next auth here you're gonna have to copy that. So the entire object here.
I'm going to use Ctrl X to cut the object. And now I'm gonna go here and export default and paste that entire object here. And now I'm gonna go ahead and remove everything I don't need. So I don't need this declare, I don't need the credential schema, I don't need this and I don't need anything besides the next out import here. What I do need is the out config from at out dot config the new file we just created.
So let's go ahead and pass in out config here. The issue is now that we have some type errors. So let's go ahead and do the following. Let's go ahead and mark this export default method all the way here at the end using this satisfies TypeScript keyword. So we're gonna say satisfies nextOutConfig.
Make sure you add the import here. Next out from next out. And you can remove this and instead you can just import type next out config. There we go. So once you save this you can see that now there are no errors in this instance here.
So now let's go inside of app API route route.ts and inside of here we have to create a little method which we are going to call getOutConfig. It will accept context which is a type of context and make sure you import that here from Hono. And this getOutConfig will return OutConfig and you can import outconfig from athono.auth.js make sure you don't import it from some other package because I also think you can import it from out core but that should not be compatible with what we're trying to do here. So let's go ahead and let's return an object here. The first property we already have is the secret and we can use the context to grab that.
So context.environment.authSecret. So just make sure that you have the authSecret here in your .environment.local. And now what we have to do is we have to spread the authConfig from authConfig. But now we have an issue. We have an issue because in here we define that we return a type of outConfig.
But inside of our outConfig we are doing some module changes here. So when you hover over the return here and if you scroll down you're going to find that the property of token are incompatible. So I was kind of baffled by this error and it can easily be fixed I believe by simply marking this as any or marking this as any for example. There we go for example this can fix the issue but there is a way to actually resolve this in a bit of a nicer way and that is by adding another declare module here. So we're gonna add declare module Auth core jvt so that package which we just installed.
So why does this fix the issue? Well that's because this AuthConfig which comes from HonoAuth.js if you take a peek here actually uses auth core package and this is the JVT type that it uses. So auth core is the generic version of authjs. The version we are using is the one we are instructed to use from the documentation next out. So this still exists as a package.
So inside of our package JSON, if you remember when we set up authjs we were instructed to install nextout. Let me just find where it is. There we go. This is the package we installed in the beta version. So in the future I suppose we're just gonna have to install this package but at the moment the docs are still telling us to use next out.
Now I'm not sure exactly where Hono stands in all of this but it is a little bit confusing but I think that as long as we have these types compatible we are completely fine. So now let's go back inside of route.ts. We now have a working getOutConfig method. So now right here, I want to add app.use. For every route, let's add initOutConfig.
You can import this from addHono.js. And inside of initOutConfig, we can pass getOutConfig method from above. And there we go! No errors at all. Everything seems to be compatible here.
And now let's go ahead and let's go inside of test here. In order to try this out, I now want to be logged out first. So let me go ahead and go to slash API slash out sign out and I'm just gonna confirm my sign out here so I should get I believe redirected to login and we can still now go to localhost 3000 API test and there we go I get success true but now what we're gonna do is the following we're going to import verify auth from HonoAuth.js and we are going to add this right here as a middleware in between our route and our controller right here. So if I save this I think that already there we go I get back unauthorized. So let me go ahead and try and log in now.
I'm gonna go ahead and log in with GitHub and let's see if I am able to go to slash API slash test now there we go now I am able to go back so that's cool we now know how to protect our routes but how can I get the current active user? That's another thing we need to do. We can do that by doing the following. Const out will be context.get authUser right here and inside we can go ahead and simply define token as out that token. Let's try it out now.
So if I refresh this, there we go. You can see the currently logged in user and we also have the access to the ID which is what's going to be extremely useful for us on the backend because we're going to be able to query things by the currently logged in user. And let's go ahead and try this again by simply going to API Auth sign out. Let's sign out again. Let's try one more time to visit our API test and there we go.
It says unauthorized. Amazing! There is also an alternative way you can do this. So you don't have to use the middleware. You can also now check if there is no auth.token for example, you can return c.json error unauthorized and when you're returning errors in a form of JSON it's very important that you mark the error code here because it will default to 200.
So you can also try this. So now if I refresh... Oh looks like it's an internal server error. Okay so it looks like we do need the verify out middleware if we want to use get out user. My apologies, I thought that we don't need it.
Great, so let's just rely on the verify out. There we go. We got a proper unauthorized message here. Perfect. So now that works.
Let's go ahead and let's do one quick fix in the middleware now because our middleware is now invalid. So inside of here, oh, actually we have out here, my apologies, the middleware is perfectly fine. I thought that we had to change it because of our config but looks like it's just fine. So we just separated the config so that we can use it inside of our HONO. Great!
And now what I want to do is the following. I want to go inside of source app API route and I want to fix all these routes here. So I don't want the user to be able to remove background unless they are verified. So let's add verify auth from HonoAuthJS like this. And let me move the import here.
There we go. So verify auth here and let's also add that here. So only logged in users can now use these endpoints like remove background and generate image. Now let's go inside of the images and do the same thing. So I don't want any unauthorized user to use our Unsplash API.
There we go. And I'm just going to move that here. And for the users, Well, we don't need that because this is the register method. So this will only be used by unauthorized users. And we can now remove the test file.
We no longer need that. So go back to route here and remove the test route group and remove the test import. Great. So now what I want to do is I want to make sure that I'm logged in and that everything still works as intended. So let me go ahead and zoom things out a bit and expand this screen here.
So first of all, I'm going to continue with GitHub. There we go. I'm logged in. I'm now going to go to slash editor slash one, two, three. And I wanna check out these existing API routes that we have like generating an image for example, or something else.
So Let's just wait a second for the editor page to compile. There we go. So let's try the unsplash image. There we go. Works perfectly fine because we are logged in.
Now let's go ahead and let's try AI. So let's try an astronaut riding a horse on Mars. 3D HD cinematic. Let's click generate and let's see if this API is working. There we go, right here.
Now let's go ahead and let's try background removal. I'm not sure what kind of job it's going to do because this is quite a complex image so maybe it will mess up some things but we are just interested in seeing well it did a pretty good job great and it works and now there is another place which we completely forgot about and that is the file upload thing So let's go inside of source here inside of app API and we have upload thing here and I think it's inside of core. So we so far have a fake out method here so we can now remove this fake out method so let's remove it and since this is on the server and it's not inside of Hono we can actually do this. This is not exactly the user this is our session and we are using await out from out right here because we export out from here and we can use this for the server here. So just execute this method.
We now have session here. So if there's no session, we throw upload thing error. And we can return session.user.id Like this. There we go. Let's just confirm now that I can still upload images so I'm just gonna go ahead and try that out so we can wrap up the chapter.
So let me go ahead and upload my image here. Looks like it's working just fine And there we go. Looks like everything works. Perfect! So we are now ready to go ahead and further implement some functionality here such as actually saving our projects into the database.
Great, great job!