Astro + Vercel Serverless API

Daniel Macák - Sep 3 - - Dev Community

I recently decided to create a portfolio website and my requirements are pretty simple - I want mostly static content but also dynamic islands here and there. Namely I want to dynamically fetch and display my Dev.to blogposts, and I really don't care how I do it as long as I stay on the cheap side.

Since I mentioned islands, you probably guessed I picked Astro, and since I like using Vercel, I thought I could use an Edge Function to make the Dev.to articles fetch.

Edge Functions didn't work

I found this the hard way. Even though Vercel's docs mention Edge Functions don't work natively with Astro, in the same breath the say you can get it to work by following Functions Quickstart, but I just couldn't.

First of all the vercel cli, which apparently uses ts-node to compile the functions defined in /api in the project root just couldn't find the Astro's parent tsconfig.json. Secondly, when I just pasted the parent config directly into my tsconfig.json, it had a problem with the configuration since Astro's and Vercel's TS configs differ a lot. So I thought I'd create tsconfig.api.json but Vercel always only scans tsconfig.json and can't be configured otherwise.

At this point I thought this is was not a great DX to perform such a simple thing as define a function and deploy it and I looked for alternatives.

Serverless Functions to the rescue

It turned out the better supported way is to use Serverless Functions with a Vercel Adapter and it's easy to set up too. Following the link I had to do these steps:

pnpm astro add vercel
Enter fullscreen mode Exit fullscreen mode

And in my astro.config.ts:

import { defineConfig } from 'astro/config';
// Import /serverless for a Serverless SSR site
import vercelServerless from '@astrojs/vercel/serverless';

export default defineConfig({
  output: 'server', // don't be confused by "server", it's actually serverless
  adapter: vercelServerless(),
});
Enter fullscreen mode Exit fullscreen mode

I was at first spooked by the mentions of SSR in the docs since I thought one needs server for that, but apparently it can be done serverless too nowadays, cool!
And then I could happily define my functions not in /api but in pages like src/pages/blogposts.ts:

export async function GET() {
  const articlesResponse = await fetch("https://dev.to/api/articles/me", {
    headers: {
      "api-key": "[API_KEY]",
    },
  });
  const articles = await articlesResponse.json();

  return Response.json(articles);
}
Enter fullscreen mode Exit fullscreen mode

to which I can the just GET /blogposts and voila, there they are! The bonus is of course that I don't need any server with serverless (duh) and can stay on my Hobby Vercel plan, yay!

Wrap up

Of course I now feel naive that I went for Edge Functions at first because it's a very different thing to Serverless Functions deployment-wise, but the thing is I didn't care; I just wanted some quick and dirty API asap. Me not being very experienced in Astro + Vercel, it took me some time to wrap my head around the Vercel ecosystem and how to put things together so I hope this will help someone struggling with the same thing ❤️.

. . . . . . . . . . . .
Terabox Video Player