Shō y Hasshī están trabajando en algunos desarrollos interesantes utilizando Supabase. A diferencia del desarrollo en cascada tradicional, escucho hablar de la definición de requisitos funcionales desde la UI, ¡pero no puedo quedarme atrás!
Así que esta vez voy a crear una aplicación de notas simple e integrar Supabase con Prisma para guardar datos en la base de datos, resumiendo el proceso como referencia. Incluso usaré Gemini CLI!
Entorno: Next.js
No utilizamos Auth, Realtime ni RLS de Supabase; adoptamos Prisma para utilizar la funcionalidad de base de datos a través de la API. Dado que los datos se pueden tratar como objetos de JavaScript/TypeScript, creemos que los ingenieros de frontend podrán escribir código de una manera más familiar.
Prisma
Prisma ORM es una librería ORM (Object-Relational Mapping) que se puede utilizar con TypeScript y JavaScript.
En pocas palabras, es una herramienta que permite operar una base de datos mediante métodos definidos en objetos del lenguaje de programación, sin necesidad de escribir SQL.
Además, Prisma genera automáticamente tipos a partir del esquema de la base de datos, por lo que si intentas operar columnas que no existen en la base de datos o datos con tipos incorrectos, ¡podrás detectarlo mediante un error de compilación!
Supabase
Supabase es un servicio backend de pila completa que ha ganado atención como alternativa de código abierto a Firebase.
- Alta escalabilidad y confiabilidad basadas en la base de datos PostgreSQL
- Notificación automática de cambios de datos con funcionalidad de base de datos en tiempo real
- Compatibilidad con diversos métodos de autenticación (correo electrónico/contraseña, inicio de sesión social, autenticación por teléfono, etc.)
- Gestión eficiente de archivos de gran tamaño con funcionalidad de almacenamiento de archivos
- Desarrollo rápido mediante generación automática de API RESTful y API GraphQL
- Abundantes herramientas y SDK para desarrolladores, lo que facilita la configuración e implementación
Queremos priorizar los pasos de integración con Supabase, así que usaremos Gemini CLI para crear la parte visual. ¡Es increíblemente útil! ¡Qué suerte que la empresa usa Google Workspace!
Queremos crear una función de notas con Supabase y Prisma. Por favor, crea page.tsx en primer lugar.
De acuerdo, entonces queremos que cuando se ingrese contenido en el textarea y se presione el botón Save Memo, se agregue a la lista en Your Memos.
¡El aspecto se ve bien así! El contenido ingresado se agrega a la lista de abajo. Sin embargo, solo se está procesando con JavaScript, así que si recarga la página, la lista desaparecerá.
Para mantener el contenido ingresado, utilizaremos una base de datos.
Primero, crearemos un nuevo proyecto en Supabase.
Cree el proyecto desde el botón "New Project". Guarde la contraseña de la base de datos, ya que la necesitará al conectarse con Prisma.
A continuación, integraremos Prisma.
npm install prisma --save-dev
npx prisma init
Al ingresar estos comandos, Prisma se instalará y aparecerá la carpeta prisma.
Reemplace DATABASE_URL en el archivo .env con la URL de conexión de Supabase. Sustituya la parte [YOUR-PASSWORD] con la contraseña de la base de datos que configuró en Supabase.
DATABASE_URL="postgresql://postgres.odoaingwnxkhkeujwhtp:[YOUR-PASSWORD]@aws-1-ap-northeast-1.pooler.supabase.com:5432/postgres"
Luego, escriba el esquema (definición de estructura de base de datos) en /prisma/schema.prisma.
generator client {
provider = "prisma-client-js"
}
datasource db {
provider = "postgresql"
url = env("DATABASE_URL")
}
model Memo {
id Int @id @default(autoincrement())
content String
createdAt DateTime @default(now())
}
model ○○ se puede nombrar según lo desee.
Después de escribir el esquema, realizaremos una migración.
npx prisma migrate dev --name init
Se genera el archivo migration.sql y se crea la tabla de datos en el lado de Supabase.
Creación de API para conectarse a Supabase
Se crea una API de conexión para guardar los valores ingresados en Supabase.
Instalar Prisma Client en el proyecto.
npm install @prisma/client
Conexión a Supabase
/libs/prisma.ts
import { PrismaClient } from "@prisma/client";
const Prisma = new PrismaClient(); //インスタンス化
export const main = async () => {
try {
await Prisma.$connect();
} catch (error) {
return Error("DB接続に失敗しました");
}
};
API
/api/memos/route.ts
import { NextResponse } from "next/server";
import { prisma } from '@/lib/prisma';
export const GET = async (req: Request, res: NextResponse) => {
try {
await main();
const memos = await Prisma.memo.findMany();
return NextResponse.json(memos);
} catch (error) {
return NextResponse.json("エラーが発生しました");
} finally {
await Prisma.$disconnect();
}
};
export const POST = async (req: Request, res: NextResponse) => {
const { content } = await req.json();
try {
await main();
const memos = await Prisma.memo.**create**({
data: {
content: content,
},
});
return NextResponse.json(memos);
} catch (error) {
return NextResponse.json("エラーが発生しました");
} finally {
await Prisma.$disconnect();
}
};
La función GET es una API que obtiene todos los registros de la base de datos. El método findMany() recupera todos los registros que coinciden con las condiciones. En Prisma.memo.findMany(), «memo» es el nombre del esquema.
La función POST es una API que agrega datos a la base de datos y los crea con create().
También hay otros métodos para eliminar y actualizar, y se pueden operar como en JavaScript sin necesidad de escribir sentencias SQL.
Con esto, toda la preparación está completa.
Solo necesitas traer la API que escribiste anteriormente a page.tsx e integrarla.
'use client';
import React, { useState, useEffect } from 'react';
interface Memo {
id: number;
content: string;
createdAt: string;
}
export default function MemoApp() {
const [memos, setMemos] = useState<Memo[]>([]);
const [newMemo, setNewMemo] = useState('');
const fetchMemos = async () => {
const response = await fetch('/api/memos');
const data = await response.json();
setMemos(data);
};
useEffect(() => {
fetchMemos();
}, []);
const handleSaveMemo = async (e: React.FormEvent) => {
e.preventDefault();
if (newMemo.trim() !== '') {
await fetch('/api/memos', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({ content: newMemo }),
});
setNewMemo('');
fetchMemos();
}
};
return (
<div className="bg-white min-h-screen">
<div className="max-w-2xl mx-auto px-4 py-16">
<header className="text-center mb-12">
<h1 className="text-5xl font-extrabold text-gray-900">Memo</h1>
</header>
<main>
<div className="mb-12">
<form onSubmit={handleSaveMemo}>
<textarea
className="w-full p-4 text-gray-800 bg-gray-100 rounded-lg border-2 border-gray-200 focus:outline-none focus:ring-2 focus:ring-gray-400 focus:border-transparent transition"
placeholder="Create a new memo..."
rows={3}
value={newMemo}
onChange={(e) => setNewMemo(e.target.value)}
></textarea>
<div className="flex justify-end mt-4">
<button
type="submit"
className="px-6 py-2 bg-gray-800 text-white font-semibold rounded-lg hover:bg-gray-900 transition"
>
Save Memo
</button>
</div>
</form>
</div>
<section>
<h2 className="text-3xl font-bold text-gray-800 mb-6">Your Memos</h2>
<div className="space-y-4">
{memos.length > 0 ? (
memos.map((memo) => (
<div key={memo.id} className="bg-gray-50 p-6 rounded-lg shadow-sm">
<p className="text-gray-700">{memo.content}</p>
</div>
))
) : (
<div className="text-center text-gray-500">
<p>No memos yet. Add one above!</p>
</div>
)}
</div>
</section>
</main>
</div>
</div>
);
}
¡Se guarda en Supabase!
Esta vez confié en Gemini para crear una versión básica, pero si uso una base de datos para guardar valores, ¡las funciones y aplicaciones que puedo crear se expandirían mucho más!
Tenía la idea preconcebida de que el backend era algo difícil, pero con herramientas GUI para gestionar la base de datos es más comprensible, y las barreras para conectar con bases de datos bajaron considerablemente.
¡Yupi!
Me dedico al desarrollo frontend con enfoque en el marcado, utilizando JavaScript, React y Next.js. ¡Me alegra mucho cuando los sitios en los que he trabajado se publican exitosamente! Mi hobby es tocar la guitarra. Me encantan los gatos y los boniatos🐱🍠
Hiraitch
Ingeniero de frontend / Incorporado en 2022