How to create and deploy an (express) Bridge app with Vercel
Tags: node, typescript, devops, webdev
Published: 2023-02-15 10:34:04

Vercel is a platform to host frontend applications and static sites but you can also host an express app using serverless functions. I've been using it for quite some time (mainly for frontend stuff) but it can also deploy your Expressjs backend!
We will see how to create a [Bridge app](https://bridge.codes) and deploy it to [Vercel](https://vercel.com).

[Repo](https://github.com/bridge-codes/deploy-vercel)

## About Bridge.

Bridge is a Typescript Nodejs framework that focuses on type-safety and developer experience. It aims to provide the best developer experience by simplifying the process of developing and integrating APIs.

This is done by heavily using the Typescript inference between elements from the backend such as data validation, routes and middlewares.

## Prerequisites

Having [Nodejs](https://nodejs.org/) and [Vercel CLI](https://vercel.com/docs/cli) installed on your machine.

## 1. Create your Bridge app

The easiest way it to use the **create-bridge-app** npm package.

You can do that by using:

```bash
npx create-bridge-app@latest
```

Then, enter your project name when prompted and select the "minimal-express" template. Once the app is created, navigate to the project directory and install the dependencies with the following command:

```
cd bridge-vercel && npm i
```

## Step 2: Prepare your app for deployment

By default, a Bridge app is not compatible with Vercel's serverless functions. To make it work, you need to make some changes to the app.

- Create a **vercel.json** file
- Edit the **index.ts** file
- Edit the **tsconfig.json** file
- Edit the **package.json** file

### vercel.json

Create a "vercel.json" file at the root of your project with the following content:
```json
{
  "rewrites": [
    {
      "source": "/api/:path+",
      "destination": "/api"
    }
  ],
  "redirects": [
    {
      "source": "/",
      "destination": "/api"
    }
  ]
}
```


This file configures Vercel to redirect all requests to the "/api" route.

### index.ts

To make it work, we'll also need to update our **index.ts** file and **initBridge** on the **/api** route. We additionnaly add a new route GET "/api/hello".

```ts
import { initBridge, handler, method } from 'bridge';
import express from 'express';

const app = express();

app.get('/api', (req, res) => res.send(`Welcome on Bridge API`));

const heyHandler = handler({
  resolve: () => {
    return 'Hey you!';
  },
});

const routes = {
  hey: method({ GET: heyHandler }),
};

app.use('/api', initBridge({ routes }).expressMiddleware());

app.listen(3000, () => {
  console.log(`Listening on port 3000`);
});

module.exports = app;
```

Don't forget to add the **module.exports = app** at the end of your file.

### package.json

Update your "package.json" file with the following.
```json
{
  "name": "bridge-vercel",
  "version": "1.0.0",
  "dependencies": {
    "bridge": "^2.0.45",
    "express": "^4.18.2",
    "ts-node": "^10.9.1"
  },
  "scripts": {
    "deploy": "tsc && vercel",
    "deploy-prod": "tsc && vercel --prod",
    "dev": "ts-node index.ts"
  },
  "devDependencies": {
    "@types/express": "^4.17.15",
    "@types/node": "^18.11.16",
    "typescript": "^4.9.4"
  }
}
```

- __npm run dev__ will run our development server on port 8080.
- __npm run vercel__ builds and deploys our app to vercel in preview
- __npm run deploy-prod__ build and deploys our app to vercel in production

### tsconfig.json

Finally, update your "tsconfig.json" file with the following content:

```json
{
  "compilerOptions": {
    "target": "es2016" /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */,
    "module": "commonjs" /* Specify what module code is generated. */,
    "outDir": "api" /* Specify an output folder for all emitted files. */,
    "esModuleInterop": true /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables 'allowSyntheticDefaultImports' for type compatibility. */,
    "forceConsistentCasingInFileNames": true /* Ensure that casing is correct in imports. */,
    "strict": true /* Enable all strict type-checking options. */,
    "skipLibCheck": true /* Skip type checking all .d.ts files. */
  }
}
```

Now everything should be ready for the deployment.

```
npm run deploy
```


Now you should have a fully working Bridge app deployed to Vercel. With Bridge, you can create complex APIs with a very good developer experience while using TypeScript and its type system to its fullest extent.

To read more about Bridge, check out [the documentation](https://bridge.codes/docs/handler).