0
0
Lập trình
Admin Team
Admin Teamtechmely

DevLog: Xây dựng GritPath OS - Ngày 1 với Convex

Đăng vào 1 ngày trước

• 8 phút đọc

DevLog: Xây dựng GritPath OS - Ngày 1 với Convex

Chào mọi người! Tôi là Creator X 👋

Như tôi đã hứa vào tuần trước, tôi sẽ chia sẻ hành trình xây dựng dự án mới nhất của mình với các bạn. Đầu tiên, tôi muốn gửi lời cảm ơn lớn đến Artem Lazarev - anh ấy cũng có kênh YouTube và đã hỗ trợ tôi rất nhiều trong dự án này. Hãy chắc chắn kiểm tra mẫu của anh ấy; nó thực sự tuyệt vời!

Tech Stack của Tôi

Dưới đây là các công nghệ mà tôi đang sử dụng cho dự án này:

  • Next.js - Framework React
  • Shadcn/Tailwind - Thành phần UI và phong cách
  • Convex - Cơ sở dữ liệu và backend
  • Clerk Auth - Xác thực người dùng
  • TypeScript - Đảm bảo kiểu dữ liệu
  • Python - (chưa được triển khai hoàn toàn)
  • Vercel - Triển khai

Kiểm Tra Nhanh

Bạn đang thế nào? Bạn có mục tiêu gì trong tuần này không? Có dự án mới nào mà bạn đang làm không? Hãy cho tôi biết trong phần bình luận!

Thiết Lập Next.js

Bắt đầu với những điều cơ bản. Đầu tiên, hãy tạo ứng dụng Next.js của bạn:

bash Copy
npx create-next-app@latest my-app

Bạn sẽ được hỏi một số câu hỏi:

  • Tên dự án của bạn là gì? my-app
  • Bạn có muốn sử dụng TypeScript không?
  • Bạn muốn sử dụng linter nào? ESLint
  • Bạn có muốn sử dụng Tailwind CSS không?
  • Bạn có muốn mã nguồn của mình nằm trong thư mục src/ không?
  • Bạn có muốn sử dụng App Router không? (được khuyến nghị)
  • Bạn có muốn sử dụng Turbopack không? (được khuyến nghị)
  • Bạn có muốn tùy chỉnh alias import không? Không

Thiết Lập Convex

Tiếp theo, cài đặt thư viện Convex:

bash Copy
npm install convex

Sau đó, chạy:

bash Copy
npx convex dev

Điều này sẽ thiết lập môi trường của bạn và yêu cầu bạn đăng nhập hoặc làm khách. Chỉ cần làm theo hướng dẫn để xác nhận tài khoản của bạn. Bạn có thể nhập một dự án hiện có từ bảng điều khiển Convex hoặc bắt đầu từ đầu. Khi hoàn tất, nó sẽ tạo một thư mục convex/ với một thư mục _generated/ bên trong.

Hành Trình của Tôi Từ Cơ Sở Dữ Liệu Truyền Thống Đến Convex

Chuyển từ các cơ sở dữ liệu truyền thống sang Convex thực sự là một điều khác biệt. Ban đầu, nó có thể gây bối rối, nhưng một khi bạn bắt đầu hiểu những điều cơ bản, mọi thứ sẽ trở nên rõ ràng.

Tạo Schema của Bạn

Đầu tiên, tôi đã tạo tệp schema.ts:

typescript Copy
// convex/schema.ts
import { defineSchema, defineTable } from "convex/server";
import { v } from "convex/values";

export default defineSchema({
  users: defineTable({
    // Các trường người dùng của bạn ở đây
  }),
  // Thêm nhiều bảng khi cần thiết
});

Mẹo chuyên nghiệp: Bạn cũng có thể sử dụng lệnh nhập nếu bạn có dữ liệu hiện có:

bash Copy
npx convex import --table tasks sampleData.jsonl

Tôi chỉ biết điều này sau! 😅

Hiểu Về Mutations (Khoảnh Khắc "Aha!" Của Tôi)

Đây là nơi tôi đã bị bối rối ban đầu. Convex sử dụng cái gọi là mutations, và đây là cách tôi hiểu chúng:

Mutations là các hàm xử lý các thao tác cơ sở dữ liệu của bạn - tạo, cập nhật và lấy dữ liệu. Chúng hoạt động như một cây cầu giữa frontend và cơ sở dữ liệu.

Hãy nghĩ theo cách này:

  • Trang .tsx của bạn có một biểu mẫu (frontend)
  • Mutation của bạn nhận dữ liệu từ biểu mẫu đó và lưu nó vào cơ sở dữ liệu
  • Mutation đó cũng có thể kéo dữ liệu trở lại để hiển thị

Chúng thường hoạt động theo cặp. Nếu bạn có business_profile.tsx, bạn sẽ có businessProfile.ts cho các mutations.

Ví Dụ Hoàn Chỉnh Về Mutation

Dưới đây là một ví dụ đơn giản, hoàn chỉnh về cách hoạt động của mutations:

Backend - Tệp Mutation (convex/tasks.ts):

typescript Copy
import { v } from "convex/values";
import { query, mutation } from "./_generated/server";

// Tạo một nhiệm vụ mới
export const createTask = mutation({
  args: {
    title: v.string(),
    description: v.string(),
  },
  handler: async (ctx, args) => {
    const taskId = await ctx.db.insert("tasks", {
      title: args.title,
      description: args.description,
      completed: false,
      createdAt: Date.now(),
    });
    return taskId;
  },
});

// Lấy tất cả nhiệm vụ
export const getAllTasks = query({
  args: {},
  handler: async (ctx) => {
    return await ctx.db.query("tasks").collect();
  },
});

Frontend - Thành phần React (app/tasks/page.tsx):

typescript Copy
"use client";
import React, { useState } from 'react';
import { useMutation, useQuery } from "convex/react";
import { api } from "@/convex/_generated/api";

export default function TasksPage() {
  const [title, setTitle] = useState("");
  const [description, setDescription] = useState("");

  const createTask = useMutation(api.tasks.createTask);
  const tasks = useQuery(api.tasks.getAllTasks);

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault();
    await createTask({ title, description });
    setTitle("");
    setDescription("");
  };

  return (
    <div>
      <form onSubmit={handleSubmit}>
        <input
          value={title}
          onChange={(e) => setTitle(e.target.value)}
          placeholder="Tiêu đề nhiệm vụ"
          required
        />
        <textarea
          value={description}
          onChange={(e) => setDescription(e.target.value)}
          placeholder="Mô tả nhiệm vụ"
        />
        <button type="submit">Thêm nhiệm vụ</button>
      </form>

      <div>
        {tasks?.map((task) => (
          <div key={task._id}>
            <h3>{task.title}</h3>
            <p>{task.description}</p>
          </div>
        ))}
      </div>
    </div>
  );
}

Schema (convex/schema.ts):

typescript Copy
import { defineSchema, defineTable } from "convex/server";
import { v } from "convex/values";

export default defineSchema({
  tasks: defineTable({
    title: v.string(),
    description: v.string(),
    completed: v.boolean(),
    createdAt: v.number(),
  }),
});

Lưu ý quan trọng: Tất cả mutations phải nằm trong thư mục convex/ của bạn để chúng được thêm vào _generated/.

Thiết Lập Client Provider

Tạo ConvexClientProvider.tsx trong thư mục app/ của bạn. Điều này cho phép ứng dụng của bạn giao tiếp với Convex:

typescript Copy
// Đây bao bọc ConvexProvider và truyền ConvexReactClient

Sau đó, bao bọc các con của bạn trong app/layout.tsx với <ConvexClientProvider>.

Hiển Thị Dữ Liệu

Để hiển thị dữ liệu của bạn trên frontend:

typescript Copy
import { useQuery } from "convex/react";
import { api } from "../convex/_generated/api";

Các Vấn Đề Thường Gặp Tôi Đã Gặp (Giúp Bạn Tiết Kiệm Thời Gian!)

  1. Chạy npx convex dev một cách chiến lược - Đừng chạy nó sau mỗi lần tạo tệp. Hãy tạo một vài trang trước, sau đó mới chạy nó. Bạn sẽ gặp ít lỗi hơn và dễ quản lý hơn.

  2. Thư mục _generated không được cập nhật? - Đôi khi sau khi chạy npx convex dev, thư mục _generated/ không cập nhật đúng cách. Nếu điều này xảy ra:

bash Copy
   rm -r _generated/
   npx convex dev

Nó an toàn để xóa - Convex sẽ tái tạo lại nó.

  1. Kiểm tra nhật ký bảng điều khiển - Nếu bạn gặp lỗi TypeScript không hợp lý, hãy kiểm tra nhật ký bảng điều khiển Convex. Chúng thường có thông tin lỗi chi tiết hơn.

  2. Kiểm tra các hàm của bạn - Tính năng thú vị: bạn có thể kiểm tra các hàm trực tiếp trong bảng điều khiển Convex! Chọn một hàm và nhấp vào "Chạy hàm" bên phải.

Biến Môi Trường và Triển Khai

Trong cài đặt Convex của bạn, bạn sẽ tìm thấy:

  • URL Triển khai
  • URL Hành động HTTP

Sao chép những điều này vào biến môi trường Vercel của bạn để chúng có thể giao tiếp đúng cách. Bạn cũng có thể thêm các biến môi trường khác làm việc với cơ sở dữ liệu Convex của bạn ở đó.

Những Suy Nghĩ Cuối Cùng

Thành thật mà nói, tôi từng ghét cơ sở dữ liệu một cách mãnh liệt. Tôi đã thử nhiều loại và thất bại thảm hại. Hai loại duy nhất mà tôi thực sự thích làm việc là PostgreSQL và giờ là Convex. Điều tôi thích ở Convex là cách mà nó trở nên đơn giản khi bạn hiểu những điều cơ bản.

Lời khuyên của tôi: hãy dành thời gian và tận hưởng quá trình. Đường cong học tập là xứng đáng!

Điều Gì Tiếp Theo?

Trong bài viết tiếp theo, tôi sẽ đi sâu vào xác thực Clerk và triển khai.

Dự án mà tôi đang xây dựng có tên là GritPath OS - một nền tảng giúp các doanh nghiệp tạo ra các bản thiết kế để phát triển. Tôi rất hào hứng khi nói rằng tôi cuối cùng đã đưa nó lên Product Hunt! 🎉

Đó là phần một của nhật ký phát triển của tôi, với nhiều điều thú vị hơn nữa sẽ đến.


Lưu ý: Những hướng dẫn này nhằm giúp những người mới bắt đầu. Nếu bạn có kinh nghiệm hơn với Convex, hãy chia sẻ quan điểm của bạn trong phần bình luận!

Cảm ơn bạn đã đọc, và đừng quên chào hỏi nhé! 👋


Bạn đã gặp những thách thức gì khi chuyển sang cơ sở dữ liệu mới? Hãy cho tôi biết trong phần bình luận!

Gợi ý câu hỏi phỏng vấn
Không có dữ liệu

Không có dữ liệu

Bài viết được đề xuất
Bài viết cùng tác giả

Bình luận

Chưa có bình luận nào

Chưa có bình luận nào