~/blog/crud-rest-api-nodejs-menggunakan-expressjs-mongodb
Published on

CRUD REST API Node.js Menggunakan Express.js dan MongoDB

book6 minutes read

Node.js rest api

source

Terkait tulisan saya yang kemarin Deploy Otomatis Node.js Dengan Menggunakan Github Actions di tulisan kali ini saya ingin membuat tutorial CRUD API aplikasi daftar yang ingin dilakukan (to-do list app) menggunakan Node.js dengan Web Framework Express.js dan MongoDB sebagai database.

Persiapan

Sebelumnya, daftar tool yang saya gunakan saat membuat tutorial ini yaitu:

node.js v15.0.1
npm v7.0.3
yarn v1.22.5
mongodb v3.6.3

Okee... langsung saja kita buat direktori baru dan inisiasi package.json untuk project nya

mkdir nodejs-todo-app
cd nodejs-todo-app
yarn init -y

Kemudian install paket yang dibutuhkan

yarn add express dotenv cors mongoose

Sebelum masuk ke langkah-langkahnya kita buat file .env dulu pada root direktori

PORT=1337
MONGODB=mongodb://localhost:27017/nama_database

Kita buat mundur saja yaa langkah demi langkah nya... yaitu dimulai dari membuat model, handler / controller (Proses untuk Create, Read, Update, Delete) kemudian route dan main file nya yaitu index.js.

Buat Model

Yang pertama kita buat model untuk project nya, disini kita menggunakan library mongoose untuk komunikasi ke MongoDB nya

Kita buat folder models pada direktori root

mkdir models

Kemudian buat file models/todo.js

// models/todo.js

const mongoose = require('mongoose');
const Schema = mongoose.Schema;

const model = new Schema({
  // field ini berisi tentang kegiatan yang ingin dilakukan
  text: {
    type: String,
    required: true
  },
  // field ini berisi apakah kegiatan sudah dilakukan belum
  checked: {
    type: Boolean,
    required: true
  }
}, {
  // opsi ini opsional sih
  // berfungsi agar membuat tanggal dibuat dan tanggal diupdate otomatis setiap pembuatan atau pembaruan dokumen
  timestamps: {
    createdAt: 'created_at',
    updatedAt: 'updated_at'
  }
});

module.exports = mongoose.model('todos', model);

Buat Handler

Yang kedua kita buat handler untuk memproses create, read, update dan delete data nya

Kita buat folder handlers pada direktori root

mkdir handlers

Kemudian buat file handlers/todo.js, dan import model yang sudah kita buat tadi

// handlers/todo.js

const modelTodo = require('../models/todo');

// Proses Create

// Proses Read All

// Proses Read By ID

// Proses Update

// Proses Delete

Create

Tambahkan fungsi create dengan menambahkan kode berikut

// Proses Create
exports.create = async (req, res) => {
  // ambil data dari nama field text dan checked
  const { text, checked } = req.body;

  try {
    // kirim respon error jika field text atau checked tidak ditemukan
    if (text === undefined || checked === undefined) {
      return res.status(422).json({ message: 'Parameter yang dimasukkan tidak lengkap.' });
    }

    // buat dokumen baru
    const todo = await modelTodo.create({ text, checked });

    // kirim respon dengan payload nya dokumen yang baru dibuat
    return res.status(201).json(todo);
  }
  catch (error) {
    console.log(error);
    return res.status(500).json(error);
  }
}

Read All

Tambahkan fungsi read all atau mengambil semua data yang ada dengan menambahkan kode berikut

// Proses Read All
exports.getAll = async (req, res) => {
  try {
    // ambil semua data
    const todos = await modelTodo.find();

    // disini jika kita tidak menambahkan .status(xxx) maka respon kodenya 200
    return res.json(todos);
  }
  catch (error) {
    console.log(error);
    return res.status(500).json(error);
  }
}

Read By ID

Tambahkan fungsi read by id atau mengambil data berdasarkan id dengan menambahkan kode berikut

// Proses Read By ID
exports.getOne = async (req, res) => {
  // kita ambil parameter id dari url
  const { id } = req.params;

  try {
    // jika parameter id tidak ada, kirim respon error
    if (id === undefined) {
      return res.status(422).json({ message: 'Parameter id tidak ditemukan.' });
    }
  
    // ambil data berdasar id
    const todo = await modelTodo.findOne({ _id: id });

    // jika data tidak ditemukan kirim respon status 404
    if ( ! todo) {
      return res.status(404).json({ message: 'Data tidak ditemukan.' });
    }
  
    return res.json(todo);
  }
  catch (error) {
    console.log(error);
    return res.status(500).json(error);
  }
}

Update

Proses update ini hampir sama dengan proses create, bedanya kita perlu mengambil parameter id untuk mencari dokumen yang ingin diubah

// Proses Update
exports.update = async (req, res) => {
  try {
    // ambil parameter id
    const { id } = req.params;

    // ambil data dari nama field text dan checked
    const { text, checked } = req.body;

    // kirim respon error jika field text atau checked tidak ditemukan
    if (text === undefined || checked === undefined) {
      return res.status(422).json({ message: 'Parameter yang dimasukkan tidak lengkap.' });
    }

    // update data
    const todo = await modelTodo.updateOne(
      {
        _id: id
      },
      {
        text,
        checked
      });

    // jika tidak ada perubahan pada suatu dokumen, berarti dokumen tidak ditemukan
    // kirim respon status 404
    if (todo.nModified === 0) {
      return res.status(404).json({ message: 'Data tidak ditemukan.' });
    }

    return res.json({ message: 'Sukses.' });
  }
  catch (error) {
    console.log(error);
    return res.status(500).json(error);
  }
}

Delete

Yang terakhir adalah proses delete

// Proses Delete
exports.delete = async (req, res) => {
  // ambil parameter id
  const { id } = req.params;

  try {
    // hapus data
    const todo = await modelTodo.deleteOne({ _id: id });

    // jika tidak ada dokumen yang berhasil dihapus, berarti data tidak ditemukan
    // kirim respon status 404
    if (todo.deletedCount === 0) {
      return res.status(404).json({ message: 'Data tidak ditemukan.' })
    }

    return res.json({ message: 'Sukses.' });
  }
  catch (error) {
    console.log(error);
    return res.status(500).json(error);
  }
}

Buat Route

Langkah selanjutnya kita buat routing nya, dengan membuat direktori routes dan membuat file index.js dan todo.js

mkdir routes

Buat file routes/todo.js

// routes/todo.js

const express = require('express');
const router = express.Router();

// import handler yang sudah kita buat tadi
const todoHandler = require('../handlers/todo');

// route ini mengarah ke http://localhost:1337/todos
router.route('/')
  // route untuk proses Read All
  .get(todoHandler.getAll)
  // route untuk proses Create
  .post(todoHandler.create);

// route yang ini mengarah ke http://localhost:1337/todos/:id
router.route('/:id')
  // route untuk proses Read By ID
  .get(todoHandler.getOne)
  // route untuk proses Update
  .put(todoHandler.update)
  // route untuk proses Delete
  .delete(todoHandler.delete);

module.exports = router;

Kemudian buat file routes/index.js

// routes/index.js

const express = require('express');
const router = express.Router();

// import route todo.js yang sudah kita buat tadi
const todoRoutes = require('./todo');

// route ini mengarah ke http://localhost:1337/
router.get('/', async (req, res) => {
  res.json({ message: 'Halo!' });
});
// route yang ini mengarah ke http://localhost:1337/todos
router.use('/todos', todoRoutes);

module.exports = router;

Buat Main File

Yang terakhir kita buat main file untuk menjalankan server kita. buat file index.js pada root direktori project kita

// ./index.js

// untuk meload file .env
require('dotenv').config()

const express = require('express');
const cors = require('cors');
const mongoose = require('mongoose');

const port = process.env.PORT || 1337;
const dbUrl = process.env.MONGODB;
// Import file route index.js yang sudah kita buat tadi
// jika ingin mengimport file index.js didalam folder, kita hanya perlu memanggil nama folder nya saja
const routes = require('./routes');

const app = express();
// buka koneksi ke mongodb
const mongooseOptions = {
  useNewUrlParser: true,
  useUnifiedTopology: true
};
mongoose.connect(dbUrl, mongooseOptions);

const db = mongoose.connection;
db.on('error', console.error.bind(console, 'connection error:'));
db.once('open', function() {
  // mongodb berhasil terkoneksi
  console.log('MongoDB berhasil tersambung!');
});
// selesai membuka koneksi

app.use(cors());
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(routes);

app.listen(port, () => {
  console.log('The magic happen on port :' + port);
});

Jalankan Server

Terakhir kita coba jalankan servernya bisa menggunakan node, pm2 atau nodemon

$ node index.js
The magic happen on port :1337
MongoDB berhasil tersambung!

Jika sudah muncul pesan tersebut, berarti sudah berhasil jalan servernya.

Testing

Nahh kita bisa test API nya dengan menggunakan postman, curl atau httpie.

Kebetulan saya sudah buatkan collection untuk postman supaya bisa memudahkan testing kalian, collection nya bisa diunduh disini.

Untuk repo project ini bisa dicek di github saya.

dahh sementara gitu aja, see yaa~