August 2021 Summaries
11 posts from Hasura
Filter
Month:
Year:
Post Summaries
Back to Blog
In this tutorial, we learn how to integrate Hasura with Retool to create a moderator interface for flagging images and training tag accuracy. We modify the data layer shape and access controls in Hasura by adding a "flagged" column and defining new role permissions for updating tag ratings, deleting tag associations, and updating images. In Retool, we create an elegant UI with tabbed views, tables, and action buttons to handle flagging/unflagging, tag training, and deletion operations. We leverage Hasura's GraphQL support and Retool's features like resource triggers and tabs for a seamless integration.
Aug 27, 2021
906 words in the original blog post.
In this tutorial, we will learn how to integrate a Nest.js REST API into Hasura as an Action and also set up Event Triggers or Scheduled Trigger handlers using the @golevelup/nestjs-hasura module.
Firstly, let's install the necessary dependencies:
```bash
yarn add @nestjs/graphql graphql @nestjs/common @nestjs/core @nestjs/jwt @nestjs/passport @nestjs/typeorm bcryptjs class-validator dotenv express jsonwebtoken mongoose pg passport passport-jwt reflect-metadata
```
Next, we need to set up the environment variables. Create a `.env` file in your project root directory and add the following content:
```bash
DB_HOST=localhost
DB_PORT=5432
DB_USERNAME=postgres
DB_PASSWORD=mysecretpassword
DB_DATABASE=hasura-nestjs
JWT_SECRET=somesecret
```
Now, let's create a new Nest.js application:
```bash
yarn global add @nestjs/cli
nest new hasura-nestjs
cd hasura-nestjs
```
Next, we need to install the `@golevelup/nestjs-hasura` module and its peer dependencies:
```bash
yarn add @golevelup/nestjs-hasura graphql-tools graphql-typing-definitions graphql-relay-link graphql-subscriptions graphql-ws
```
Now, let's create a new module for handling payments:
```bash
nest generate service payment
```
This will generate the necessary files and folders. Now, we need to set up a fake payment handler that takes a `user_id`, `product_id`, and `quantity`, and then pretends to process a payment as a Hasura Action:
```typescript
// src/payment/payment.service.ts
import { Injectable } from '@nestjs/common';
@Injectable()
export class PaymentService {
private static products = [
{ id: 1, name: 'Milk', price: 2.5 },
{ id: 2, name: 'Apples', price: 1.25 },
{ id: 3, name: 'Eggs', price: 0.99 },
];
public calculateTotal(params: { product_id: number; quantity: number }): number {
return PaymentService.products.find((it) => it.id == params.product_id).price * params.quantity;
}
public processPayment(params: { total: number }): boolean {
console.log(`This is where you'd call a payment processor, and charge the customer for ${params.total}`);
return true;
}
}
```
Next, let's set up the `payment.controller.ts` to take a payload from a Hasura Action and call this service, returning `total`, `paymentResult`, and a fake `receiptNumber`:
```typescript
// src/payment/payment.controller.ts
import { Body, Controller, Post } from '@nestjs/common';
import { PaymentService } from './payment.service';
import { HasuraActionsPayload<Input extends {}, Session extends {}> } from '@golevelup/nestjs-hasura';
interface CreatePaymentForUserArgs {
user_id: number;
product_id: number;
quantity: number;
}
@Controller('payment')
export class PaymentController {
constructor(private readonly paymentService: PaymentService) {}
@Post('/createPaymentForUser')
createPaymentForUser(@Body() payload: HasuraActionsPayload<{ params: CreatePaymentForUserArgs }>>): any {
const total = this.paymentService.calculateTotal(payload.input.params);
const paymentResult = this.paymentService.processPayment({ total });
return {
total,
paymentResult,
receiptNumber: 1234567,
};
}
}
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
}
```
Then you should see output like this:
```bash
This is where you'd call a payment processor, and charge the customer for 25
```
Now if we boot up our app again, with `yarn start:dev` again, we should see in the output:
```bash
[Nest] 21396 - 08/24/2021, 3:30:42 PM LOG [RouterExplorer] Mapped {/payment/createPaymentForUser, POST} route +1ms
```
And if we try to make a request to that endpoint giving it the same payload it would receive if it were called by Hasura, as a Hasura Action, like this:
```bash
POST http://localhost:3000/payment/createPaymentForUser HTTP/1.1
content-type: application/json
{
"action": {
"name": "createPaymentForUser"
},
"input": {
"params": {
"user_id": 1,
"product_id": 2,
"quantity": 10
}
},
"session_variables": {}
Aug 25, 2021
4,104 words in the original blog post.
This article discusses how to approach various stages of development with Hasura, from localhost to staging -> going live to production and finally performing maintenance updates. It covers topics such as running Hasura via docker-compose, managing schema migrations, testing out Actions and Events with Hasura, setting up CI/CD, configuring environment variables, applying migrations and metadata, running tests - regression testing, securing endpoint with admin secret, disabling console, updating Hasura version, and more. The article also mentions the recommended hosting solution for Hasura as Hasura Cloud, which takes care of Infrastructure management automatically and provides advanced features like analytics/rate limiting.
Aug 25, 2021
2,307 words in the original blog post.
Hasura recently launched its cloud offering, which automates the management of GraphQL infrastructure. Migrating from self-hosted Hasura OSS to Hasura Cloud is straightforward and brings benefits such as automatic handling of infrastructure concerns and features like data caching and rate limiting. The migration process involves updating the current Hasura OSS server, taking a database backup and metadata snapshot, finding the connection string for the existing database, keeping HASURA_GRAPHQL_* environment variables ready, configuring necessary database permissions, creating a new project on Hasura Cloud, and applying metadata and migrations.
Aug 25, 2021
1,621 words in the original blog post.
The marketing operations team at Hasura has developed a real-time lead-to-account matching solution using Hasura, BigQuery, Zapier, and Salesforce. By leveraging Hasura's instant GraphQL & REST APIs on BigQuery and powerful querying abilities, the team was able to automate this workflow and make it real-time. The process involves mapping leads to accounts in Salesforce, with logic stored in Google BigQuery as a view. With the recent support for BigQuery by Hasura, the marketing operations team can now update lead information in Salesforce automatically every hour, ensuring that all relevant leads are matched to their corresponding accounts.
Aug 24, 2021
881 words in the original blog post.
In this tutorial, we will expand on the previous integration of Hasura project with Draftbit and build out a website presence for our application using Bubble. We will use Hasura's ability to create REST endpoints for saved GraphQL queries in the Hasura console and include an additional endpoint that allows us to upload content to Hasura. The tutorial covers the interface, workflow summary, and how Hasura Cloud helps with debugging serverless workflows.
Aug 17, 2021
1,908 words in the original blog post.
This tutorial guides users through building a simple and secure social media site using Magic and Hasura. The process involves creating an account and application with Magic, setting up a new project with Hasura, adding environment variables, and running the npx make-magic command to create a template for the project. The app allows users to share photos of their kittens and view other people's galleries. The tutorial covers building a Heroku PostgreSQL database, setting up user roles, creating tables, establishing relationships between them, and implementing object and array relationships. It also explains how to build a Next.js client with core UI components, integrate Magic authentication, create a GraphQL API, and log in or out of the application. The final result is an open-source social media site where users can share and view photos of kittens.
Aug 16, 2021
1,422 words in the original blog post.
This tutorial guides developers through using TypeScript in conjunction with GraphQL to leverage type safety benefits. It explains why type safety is advantageous and how it can be used effectively within the GraphQL ecosystem. The text also discusses reasons why not all developers are embracing type-safe languages, such as historical coupling of GraphQL and JavaScript, and boilerplate requirements. Furthermore, it provides a step-by-step guide on using Generative tooling with GraphQL Code Generator to generate TypeScript SDK for GraphQL API operations. The tutorial concludes by discussing how to iterate when using these types of SDKs and introduces an alternative tool called GraphQL Code Generator.
Aug 12, 2021
2,499 words in the original blog post.
In this tutorial, we will integrate Hasura with the low-code mobile app development tool Draftbit. We will scaffold a basic application with Draftbit, map the required data to a couple of GraphQL queries, and save those queries behind idiomatic REST endpoints in the Hasura console. The primary glue to integrate Hasura with Draftbit is creating idiomatic REST endpoints for GraphQL queries in the Hasura console. This will allow us to define a query for Draftbit (which doesn’t support GraphQL), on the Hasura side and save that behind a RESTful endpoint.
Aug 05, 2021
1,832 words in the original blog post.
This article explains how to set up webhooks in Hasura using Next.js API routes. It covers the basics of data models and APIs, introduces webhooks in Hasura, demonstrates setting up Hasura GraphQL engine, creating a table, setting up a Next.js project, deploying it to the cloud with ngrok, creating an event trigger, and testing the setup. The author also provides information about their background and experience as a software engineer.
Aug 05, 2021
1,210 words in the original blog post.
The text discusses three approaches to prevent users from creating/updating/deleting records in a table after a certain period of time. These include using Postgres triggers, Hasura's "Column Comparison" permission operators, and Postgres "Check Constraints". It provides detailed examples for each approach and highlights their pros and cons. The text also mentions that these solutions can be used to enforce data integrity within the bounds of Hasura's permission and roles system.
Aug 04, 2021
1,025 words in the original blog post.