Skip to content
Santekno.com | Level Up Your Engineering Skills
ID
📖 0%
01 Aug 2025 · 5 mnt baca ·Artikel 32 / 125
Go

32 Setup ORM (gorm) di graphql-go

IH
Ihsan Arif
Penulis di Santekno · Backend Engineer

32 Setup ORM (gorm) di graphql-go: Panduan Terpadu untuk Engineer Backend

Bagi engineer backend di ekosistem Go (Golang), membangun API yang robust seringkali memerlukan integrasi antara database, ORM, dan schema GraphQL. Dua tools populer di dunia Go, yaitu gorm sebagai ORM dan graphql-go sebagai server GraphQL, menjadi pilihan utama banyak tim. Artikel ini akan membahas setup gorm dalam proyek graphql-go secara mendalam, dilengkapi contoh kode, simulasi, diagram alur, serta tips-tips engineer yang sudah matang.


🛠 Persiapan: Instalasi Dependency

Sebelum menulis kode, pastikan package berikut sudah terpasang:

sh
1go get github.com/jinzhu/gorm
2go get github.com/go-sql-driver/mysql
3go get github.com/graph-gophers/graphql-go
4go get github.com/graph-gophers/graphql-go/relay

Kita akan menggunakan MySQL pada contoh ini. Silakan ganti dengan driver lain sesuai kebutuhan (postgres, sqlite, dll).


👩‍💻 Skema & Requirement di Proyek

Kita bakal mensimulasikan skenario sederhana:

Use Case: Mengelola daftar user.

  • Setiap user punya: id, name, email.

Skema Database

sql
1CREATE TABLE users (
2  id INT AUTO_INCREMENT PRIMARY KEY,
3  name VARCHAR(100),
4  email VARCHAR(100) UNIQUE
5);

Skema GraphQL

graphql
 1type User {
 2  id: ID!
 3  name: String!
 4  email: String!
 5}
 6
 7type Query {
 8  users: [User!]!
 9  user(id: ID!): User
10}
11type Mutation {
12  createUser(name: String!, email: String!): User
13}

👨‍🔬 Integrasi gorm ke graphql-go, Step-by-step

Let’s break it down!

1. Model GORM untuk User

go
 1// models/user.go
 2package models
 3
 4import "github.com/jinzhu/gorm"
 5
 6type User struct {
 7    gorm.Model
 8    Name  string `gorm:"type:varchar(100)"`
 9    Email string `gorm:"type:varchar(100);unique"`
10}

2. Setup Database & Auto Migrate

go
 1// db/db.go
 2package db
 3
 4import (
 5    "github.com/jinzhu/gorm"
 6    _ "github.com/go-sql-driver/mysql"
 7    "log"
 8    "user-gql/models"
 9)
10
11func InitDB() *gorm.DB {
12    db, err := gorm.Open("mysql", "root:password@/userdb?charset=utf8&parseTime=True")
13    if err != nil {
14        log.Fatal(err)
15    }
16    db.AutoMigrate(&models.User{})
17    return db
18}

3. Resolver GraphQL

Resolver adalah ‘jembatan’ antara query/mutation GraphQL dan kode Go (termasuk ORM-nya).

go
 1// resolver/resolver.go
 2package resolver
 3
 4import (
 5    "context"
 6    "user-gql/models"
 7    "github.com/jinzhu/gorm"
 8)
 9
10type Resolver struct {
11    DB *gorm.DB
12}
13
14// Untuk users query
15func (r *Resolver) Users(ctx context.Context) ([]*UserResolver, error) {
16    var users []models.User
17    if err := r.DB.Find(&users).Error; err != nil {
18        return nil, err
19    }
20    resolvers := make([]*UserResolver, len(users))
21    for i, user := range users {
22        resolvers[i] = &UserResolver{user}
23    }
24    return resolvers, nil
25}
26
27// Query tunggal berdasarkan ID
28func (r *Resolver) User(ctx context.Context, args struct{ ID int32 }) (*UserResolver, error) {
29    var user models.User
30    if err := r.DB.First(&user, args.ID).Error; err != nil {
31        return nil, err
32    }
33    return &UserResolver{user}, nil
34}
35
36// Mutation
37func (r *Resolver) CreateUser(ctx context.Context, args struct{ Name string; Email string }) (*UserResolver, error) {
38    user := models.User{Name: args.Name, Email: args.Email}
39    if err := r.DB.Create(&user).Error; err != nil {
40        return nil, err
41    }
42    return &UserResolver{user}, nil
43}
44
45// Resolver untuk User type
46type UserResolver struct {
47    models.User
48}
49
50func (u *UserResolver) ID() graphql.ID     { return graphql.ID(fmt.Sprint(u.User.ID)) }
51func (u *UserResolver) Name() string       { return u.User.Name }
52func (u *UserResolver) Email() string      { return u.User.Email }

4. Schema GraphQL

Buat file schema.graphql dengan isi:

graphql
 1type User {
 2  id: ID!
 3  name: String!
 4  email: String!
 5}
 6
 7type Query {
 8  users: [User!]!
 9  user(id: ID!): User
10}
11type Mutation {
12  createUser(name: String!, email: String!): User
13}

5. Integrasi Handler HTTP

go
 1// main.go
 2package main
 3
 4import (
 5    "io/ioutil"
 6    "net/http"
 7    "user-gql/db"
 8    "user-gql/resolver"
 9
10    "github.com/graph-gophers/graphql-go"
11    "github.com/graph-gophers/graphql-go/relay"
12)
13
14func main() {
15    // Setup DB
16    database := db.InitDB()
17    defer database.Close()
18
19    // Load schema
20    schemaBytes, err := ioutil.ReadFile("schema.graphql")
21    if err != nil {
22        panic(err)
23    }
24
25    // Buat schema GraphQL
26    schema := graphql.MustParseSchema(
27        string(schemaBytes),
28        &resolver.Resolver{DB: database},
29    )
30
31    http.Handle("/query", &relay.Handler{Schema: schema})
32
33    // Live!
34    http.ListenAndServe(":8080", nil)
35}

🏃 Simulasi Query ke Server

1. Query Seluruh User

graphql
1query {
2  users {
3    id
4    name
5    email
6  }
7}

Respons:

json
1{
2  "data": {
3    "users": [
4      {"id": "1", "name": "Ridwan", "email": "ridwan@contoh.com"},
5      {"id": "2", "name": "Rahma", "email": "rahma@company.com"}
6    ]
7  }
8}

2. Mutation: Tambah User

graphql
1mutation {
2  createUser(name: "Bimo", email: "bimo@team.com") {
3    id
4    name
5  }
6}

📊 Tabel: Perbandingan GORM vs Raw SQL

FiturGORMRaw SQL
Query BuilderYES (ORM style)NO
Auto MigrationYESNO
RelationsYES (Preload, Joins)Manual (Join)
Struct MappingYES (Struct to Table)Handcrafted
Error HandlingTengah (ada error type)Manual/Error bawaan
ReadabilityLebih clean & idiomaticKadang verbose

🔖 Diagram Alur Setup

MERMAID
flowchart TD
    A[Inisiasi: Load Schema GraphQL] --> B[Init GORM DB]
    B --> C[Bind Resolver ke GORM DB]
    C --> D[GraphQL HTTP Handler aktif]
    D --> E[Receive HTTP Request /query]
    E --> F{Jenis Query}
    F -- Query user/users --> G[GORM query ke DB]
    F -- Mutation --> H[GORM transaksi ke DB]
    G & H --> I[Json Response via GraphQL]

⚡️ Engineering Tips

  • Connection Pool: Gunakan db.DB().SetMaxOpenConns(...) untuk optimasi performance.
  • Env Config: Simpan credential database di environment variable, bukan hardcoded.
  • Validation: Validasi input di mutation sebelum commit ke DB (jangan terlalu percaya kepada client!).
  • Migration: Jalankan migration secara terpisah di production, jangan dari main app.
  • Testing: Gunakan test DB untuk integration test, mocking GORM dengan library seperti go-sqlmock .

💬 Penutup

Dengan setup seperti di atas, kamu dapat menghubungkan orm GORM dan graphql-go dengan clean, rapi, dan maintainable. Kuncinya: selalu treat resolver sebagai lapisan bersih yang menghubungkan dunia GraphQL dengan ORM/db-mu.

Jangan ragu untuk mengadaptasi pattern ini ke kebutuhan proyekmu, baik untuk e-commerce, SaaS, atau skala enterprise. Jika ada pertanyaan atau butuh penjelasan lebih lanjut, drop di komentar 😉


References:

Selamat ngoding, backend warriors! 🚀

Artikel Terkait

💬 Komentar