Skip to main content
Version: v3.x (DDN)

How to Configure the RESTified Endpoints Plugin

Introduction

The RESTified GraphQL endpoints plugin allows you to add RESTified GraphQL endpoints to DDN. This can be used to add custom REST endpoints to DDN that would execute specified GraphQL query on the DDN GraphQL API and return the response.

This guide provides a step-by-step guide on how to configure and deploy the RESTified Endpoints Plugin for Hasura DDN using either of the two methods:

  1. Using a Docker image
  2. Using Cloudflare Wrangler

Using a Docker Image

In this example, we're going to use a Docker image to configure the RESTified Endpoints Plugin for Hasura DDN. You can use similar configurations to deploy the plugin using Kubernetes or any other container orchestration tool.

Step 1. Set up plugin for local development

Add the following service to your root-level docker-compose.yaml file (this is the one located at <project-root>/docker-compose.yaml). Add this new service at the same level as your existing services entries:

restified-endpoints:
build:
context: https://github.com/hasura/engine-plugin-restified-endpoint.git
ports:
- 8787:8787
environment:
- OTEL_EXPORTER_OTLP_ENDPOINT=https://gateway.otlp.hasura.io:443/v1/traces
- OTEL_EXPORTER_PAT=your-pat-here
- GRAPHQL_SERVER_URL=http://engine:3000
- HASURA_DDN_PLUGIN_CONFIG_PATH=plugin_config
volumes:
- ./restified-endpoints-config:/app/plugin_config

Here, we're building the image from the engine-plugin-restified-endpoint repository. We're also forwarding the plugin_config directory to the container. This directory will contain the configuration for the plugin. Here is the structure of the plugin_config directory:

plugin_config/
└── configuration.json

The configuration.json file is used to configure the plugin. Here's an example configuration:

{
"graphqlServer": {
"headers": {
"additional": {
"Content-Type": "application/json"
},
"forward": ["X-Hasura-Role", "Authorization", "X-Hasura-ddn-token"]
}
},
"headers": {
"hasura-m-auth": "zZkhKqFjqXR4g5MZCsJUZCnhCcoPyZ"
},
"restifiedEndpoints": [
{
"path": "/v1/api/rest/artistbyname/:name",
"methods": ["GET", "POST"],
"query": "query artistByName($name: String!) { artist(where: {name: {_eq: $name}}) { name }}"
},
{
"path": "/v1/api/rest/artists",
"methods": ["GET", "POST"],
"query": "query artists($limit: Int = 10, $offset: Int = 0) { artist(limit: $limit, offset: $offset) { name } }"
}
]
}

The RESTified endpoints configuration includes:

  • graphqlServer: Configuration for the GraphQL server:
    • headers: Configuration for the headers to be sent to the GraphQL server:
      • additional: Additional headers to be sent to the GraphQL server.
      • forward: Headers to be forwarded from the request to the GraphQL server.
  • headers.hasura-m-auth: The hasura-m-auth header is a custom header that is used to authenticate the requests to the plugin. You can use any strong key here to authenticate the plugin. DDN will automatically add this header to the requests to the plugin.
  • restifiedEndpoints: Configuration for the RESTified endpoints. Each endpoint includes:
    • path: The path of the endpoint (this can include path parameters like :name, which is used in the query as variables)
    • methods: The HTTP methods supported by the endpoint.
    • query: The GraphQL query to be executed when the endpoint is called.

Step 2. Add the plugin configuration

We'll let the engine know about the plugin and to execute it as a pre-route plugin by creating a new metadata file. In your global subgraph's metadata directory, create a new file named restified-endpoints.hml and add the following configuration.

kind: LifecyclePluginHook
version: v1
definition:
pre: route
name: restified_endpoints
url:
valueFromEnv: RESTIFIED_ENDPOINTS_URL
config:
matchPath: "/v1/api/rest/*"
matchMethods: ["GET", "POST"]
request:
method: GET
headers:
forward:
- Authorization
- x-hasura-role
- x-hasura-ddn-token
additional:
hasura-m-auth:
valueFromEnv: M_AUTH_KEY
rawRequest:
path: {}
query: {}
method: {}
body: {}
response:
headers:
additional:
content-type:
value: application/json
URL Match

The matchPath field is used to match the regex to the request path, while matchMethods specifies the HTTP methods to match. In this example, we're matching all GET and POST requests to /v1/api/rest/*. You can modify these to match any path and methods (GET/POST/PUT/PATCH/DELETE) you wish.

Also, note that we can not use the pre-defined DDN endpoints (like /graphql, /v1/sql, /v1/jsonapi, /v1/explain, /healthz and /metrics) in the matchPath field.

Moreover, on DDN cloud, for security reasons, only the /v1/api/rest/* path is allowed for the pre-route plugin.

Using environment variables

We've used valueFromEnv so that we can dynamically and securely add values from our environment variables. You can add these values to your root-level .env and then map them in the globals subgraph.yaml file. Alternatively, you can include raw strings here using value instead of valueFromEnv and passing the keys.

Next, update the subgraph.yaml file to include the environment variables.

kind: Subgraph
version: v2
definition:
name: globals
...
includePaths:
...
envMapping:
RESTIFIED_ENDPOINTS_URL:
fromEnv: RESTIFIED_ENDPOINTS_URL
M_AUTH_KEY:
fromEnv: M_AUTH_KEY

Finally, we need to add the environment variables to the .env file.

RESTIFIED_ENDPOINTS_URL="http://local.hasura.dev:8787"
M_AUTH_KEY="your-strong-m-auth-key"
M-Auth Key

The hasura-m-auth header is a custom header that is used to authenticate the requests to the allowlist plugin. You can use any strong key here to authenticate the plugin. DDN will automatically add this header to the requests to the plugin. Also, make sure to update the src/config.ts file (in step 5) with the same key.

Step 3. Run everything

At this point, you can run the following command to build and start local development:

ddn supergraph build local
ddn run docker-start

You can now test the plugin by making a request to the RESTified GraphQL endpoints defined in the plugin's configuration.

If you want to make changes to the plugin configuration, you can update the configuration.json file and restart the docker services.

Step 4. Deploy the plugin

The plugin can be deployed as a regular HTTP service using any container orchestration tool. When deployed, make sure to set the OTEL_EXPORTER_OTLP_ENDPOINT, OTEL_EXPORTER_PAT, GRAPHQL_SERVER_URL and HASURA_DDN_PLUGIN_CONFIG_PATH to appropriate values in .cloud.env. Note that the plugin must be visible from your Hasura deployment: if you are hosting for the Hasura Cloud, the plugin must be publicly visible.

Your plugin must be reachable

Since the RESTified endpoints plugin is a pre-parse plugin, it must be reachable from the Hasura deployment. If you are hosting for the Hasura Cloud, the plugin must be publicly visible.

Using Cloudflare Wrangler

In this example, we're using Cloudflare Wrangler to deploy our plugin as a Cloudflare Worker. You can get started with Wrangler here.

Step 1. Create a new plugin project

Create a new Cloudflare Worker project using the create-cloudflare command with the restified-endpoints plugin template:

npx create-cloudflare@latest restified-endpoints-plugin --template https://github.com/hasura/engine-plugin-restified-endpoint

This will create a new project with the required files and dependencies.

Step 2. Install dependencies

Navigate to the new directory and install the dependencies.

cd restified-endpoints-plugin
npm install

Start the local development server.

npm start

Step 3. Add the plugin configuration

Follow the steps in the docker image plugin configuration section to add the plugin configuration.

Step 4. Create a new build for local development

Create a new supergraph build.

ddn supergraph build local

Start the console for the local supergraph.

ddn console --local

You can now test the plugin by making a request to the RESTified GraphQL endpoints defined in the plugin's configuration.

Step 5. Update the plugin config

Update the src/config.ts file with the RESTified GraphQL endpoints that you want to add.

export const Config = {
graphqlServer: {
headers: {
additional: {
"Content-Type": "application/json",
},
// Please make sure to forward the authentication headers here
forward: ["hasura_cloud_pat", "x-hasura-ddn-token"],
},
},
headers: {
"hasura-m-auth": "your-strong-m-auth-key",
},
restifiedEndpoints: [
...,
{
path: "/v1/api/rest/users",
methods: ["GET", "POST"],
query: `
query MyQuery($limit: Int = 10, $offset: Int = 0) {
Users(limit: $limit, offset: $offset) {
Name
}
}
`,
}
],
};
Hot reloading

The local wrangler development server will automatically reload the plugin when you make changes to the code.

Step 6. Configure the plugin variables

Setup tracing

To enable tracing for the plugin, you need to update the wrangler.toml file with the required configurations. If you don't want to enable tracing for the plugin, you can skip this step.

In restified-endpoints-plugin directory, update the wrangler.toml file with the required configurations.

...
[vars]
OTEL_EXPORTER_OTLP_ENDPOINT = "https://gateway.otlp.hasura.io:443/v1/traces"
OTEL_EXPORTER_PAT = "<PAT>"
GRAPHQL_SERVER_URL = "<DDN_GRAPHQL_SERVER_URL>"

Replace <PAT> with the Personal Access Token (PAT) for the Hasura Cloud account. You can display this using the ddn auth print-access-token command.

Replace <DDN_GRAPHQL_SERVER_URL> with the URL of your DDN GraphQL server. You can find this in the DDN console under the Settings > Project Summary section.

Step 7. Deploy the plugin

For your plugin to be reachable by your hosted supergraph, we can deploy with any service that hosts HTTPS services. Here we will use Cloudflare Wrangler to deploy the plugin. The deploy command included in your plugin's package.json will do this automatically for you and return the hosted service's URL.

Note: Please also update the wrangler.toml with your cloud PAT for the tracing to work.

npm run deploy

This will deploy the plugin to Cloudflare Workers and return the URL of the hosted service. Next, update the .env.cloud file with the URL.

RESTIFIED_ENDPOINTS_URL="https://<your-deployed-plugin>.workers.dev"
M_AUTH_KEY="your-strong-m-auth-key"

Step 8. Create a new build

Create a new supergraph build on Hasura DDN to check your work in the cloud.

ddn supergraph build create
Cloud project required

In order for this command to succeed, you'll need a cloud project paired with your local metadata. If you don't already have one, you can create one using the CLI.

From the root of the project directory, run:
ddn project init .

Step 9. Apply the build

Apply the build to make it the default one served by your Hasura DDN project endpoint. You can do this from the DDN console by choosing the build from the Builds tab and clicking Apply Build.

The engine will execute the plugin for each requests to the RESTified GraphQL endpoints you defined.

As in the earlier example, you can test this by navigating to the endpoint for any paths you've set up in your plugin's configuration:
# E.g., https://profound-applet-5420.ddn.hasura.app/v1/api/rest/users
https://<your_Hasura_DDN_project_url_excluding_graphql>/v1/api/rest/<endpoint_path>