TS 예제
TS 예제 (Examples)
@libsql/client로 바로 돌려 볼 수 있는 TypeScript 예제 모음이에요. 배치 처리, 대화형 셸, 임베디드 레플리카 동기화, 벡터 검색까지 레시피 형태로 정리되어 있어요.
출처: 문서
본문
이 페이지의 예제는 모두 libsql-client-ts 리포지토리의 packages/libsql-client/examples 디렉터리에 있는 실행 가능한 스크립트예요. 클라이언트 패키지(@libsql/client)와 함께 제공되는 샘플이니까 클론해서 그대로 실행해 볼 수 있어요.
기본 예제: 배치와 파라미터 바인딩
테이블을 만들고 배치로 여러 SQL을 한 번에 실행한 다음, 위치 기반과 이름 붙은 플레이스홀더를 각각 쓰는 예제예요. example.js 파일 전체예요:
import { createClient } from "@libsql/client";
async function example() {
const config = {
url: process.env.URL ?? "file:local.db",
encryptionKey: process.env.ENCRYPTION_KEY,
};
const db = createClient(config);
await db.batch(
[
"CREATE TABLE IF NOT EXISTS users (email TEXT)",
"INSERT INTO users (email) VALUES ('[email protected]')",
"INSERT INTO users (email) VALUES ('[email protected]')",
],
"write",
);
await db.batch(
[
{
sql: "INSERT INTO users (email) VALUES (?)",
args: ["[email protected]"],
},
["INSERT INTO users (email) VALUES (?)", ["[email protected]"]],
{
sql: "INSERT INTO users (email) VALUES (:email)",
args: { email: "[email protected]" },
},
],
"write",
);
const rs = await db.execute("SELECT * FROM users");
console.log(rs);
}
await example();
연결 설정에서 URL은 환경 변수 URL로, 없으면 file:local.db를 써요. encryptionKey도 환경 변수로 넘길 수 있죠. 배치 안에서는 문자열 배열, sql/args 객체, [sql, args] 배열 세 가지 형태가 모두 허용되고, 위치 플레이스홀더 ?와 이름 붙은 플레이스홀더 :email을 섞어 쓸 수 있다는 점을 확인하세요.
대화형 SQL 셸
명령줄 인자로 받은 데이터베이스 URL에 접속해서 표준 입력으로 SQL을 계속 입력받아 실행하는 셸 예제예요. shell.js 파일 전체예요:
import * as readline from "node:readline/promises";
import { stdin, stdout, argv } from "node:process";
import * as libsql from "@libsql/client";
async function main() {
const url = argv[2];
if (!url) {
console.error("Please specify database URL as command-line argument");
return;
}
const client = libsql.createClient({ url });
const rl = readline.createInterface({ input: stdin, output: stdout });
for (;;) {
const sql = await rl.question("> ");
let rs;
try {
rs = await client.execute(sql);
} catch (e) {
if (e instanceof libsql.LibsqlError) {
console.error(e);
continue;
}
throw e;
}
console.log(JSON.stringify(rs.columns));
for (const row of rs.rows) {
console.log(JSON.stringify(Array.from(row)));
}
}
}
await main();
에러가 libsql.LibsqlError면 메시지를 출력하고 계속 진행해요. 그 외의 예외는 그대로 던져서 프로세스가 멈추게 두죠. 결과는 컬럼 이름 목록과 각 행을 JSON으로 출력해요.
임베디드 레플리카 동기화
로컬 파일 데이터베이스를 syncUrl에 연결하고, sync()를 호출할 때마다 프라이머리와 맞추는 예제예요. 방명록(guest book)에 코멘트를 남기는 흐름으로 구성되어 있어요. sync.js 파일 전체예요:
import { createClient } from "@libsql/client";
import reader from "readline-sync";
async function example() {
const config = {
url: process.env.URL ?? "file:local.db",
syncUrl: process.env.SYNC_URL,
authToken: process.env.AUTH_TOKEN,
};
const db = createClient(config);
await db.sync();
await db.execute(
"CREATE TABLE IF NOT EXISTS guest_book_entries (comment TEXT)",
);
const rep = await db.sync();
console.log("frames_synced: " + rep.frames_synced);
const comment = reader.question("Enter your comment: ");
await db.execute({
sql: "INSERT INTO guest_book_entries (comment) VALUES (?)",
args: [comment],
});
const rep2 = await db.sync();
console.log("frames_synced: " + rep2.frames_synced);
console.log("Guest book entries:");
const rs = await db.execute("SELECT * FROM guest_book_entries");
for (const row of rs.rows) {
console.log(" - " + row.comment);
}
}
example();
sync()가 반환하는 리포트의 frames_synced로 이번 동기화에서 몇 프레임을 가져왔는지 확인할 수 있어요.
오프라인 우선 동기화
offline: true 옵션을 켠 동기화 예제예요. 연결이 없어도 로컬 데이터베이스에서 바로 읽고 쓸 수 있다는 점이 위 예제와 달라요. sync_offline.js 파일 전체예요:
import { createClient } from "@libsql/client";
import reader from "readline-sync";
async function example() {
const config = {
url: process.env.URL ?? "file:local.db",
syncUrl: process.env.SYNC_URL,
authToken: process.env.AUTH_TOKEN,
offline: true,
};
const db = createClient(config);
console.log("Syncing database ...");
await db.sync();
await db.execute(
"CREATE TABLE IF NOT EXISTS guest_book_entries (comment TEXT)",
);
const comment = reader.question("Enter your comment: ");
await db.execute({
sql: "INSERT INTO guest_book_entries (comment) VALUES (?)",
args: [comment],
});
console.log("Syncing database ...");
const rep2 = await db.sync();
console.log("frames_synced: " + rep2.frames_synced);
console.log("Guest book entries:");
const rs = await db.execute("SELECT * FROM guest_book_entries");
for (const row of rs.rows) {
console.log(" - " + row.comment);
}
}
example();
벡터 검색과 함께 동기화
동기화되는 데이터베이스에서 벡터 임베딩을 저장하고 KNN(최근접 이웃) 검색을 하는 예제예요. 영화 제목과 4차원 임베딩을 저장하고, 벡터 인덱스를 만들어 유사한 영화를 찾아요. sync_vector.js 파일 전체예요:
import { createClient } from "@libsql/client";
import reader from "readline-sync";
async function example() {
const config = {
url: process.env.URL ?? "file:local.db",
syncUrl: process.env.SYNC_URL,
authToken: process.env.AUTH_TOKEN,
};
const db = createClient(config);
await db.sync();
await db.execute(
"CREATE TABLE IF NOT EXISTS movies (title TEXT, embedding FLOAT32(4))",
);
await db.execute(
"CREATE INDEX IF NOT EXISTS movies_idx ON movies (libsql_vector_idx(embedding))",
);
await db.sync();
const title = reader.question("Add movie (title): ");
const embedding = reader.question(
"Add movie (embedding, e.g. [1,2,3,4]): ",
);
await db.execute({
sql: "INSERT INTO movies (title, embedding) VALUES (?, vector32(?))",
args: [title, embedding],
});
await db.sync();
const all = await db.execute(
"SELECT title, vector_extract(embedding) as embedding FROM movies",
);
console.info("all movies:");
for (const row of all.rows) {
console.log(" - " + row.title + ": " + row.embedding);
}
const query = reader.question("KNN query (e.g. [1,2,3,4]): ");
const nn = await db.execute({
sql: "SELECT title, vector_extract(embedding) as embedding FROM vector_top_k('movies_idx', vector32(?), 2) as knn JOIN movies ON knn.id = movies.rowid",
args: [query],
});
console.info("nearest neighbors:");
for (const row of nn.rows) {
console.log(" - " + row.title + ": " + row.embedding);
}
}
example();
인덱스를 만들 때 libsql_vector_idx(embedding)을 쓰고, 검색 때는 vector_top_k('movies_idx', vector32(?), 2)로 상위 2개 이웃을 가져오는 흐름을 확인하세요.
예제 실행에 쓰는 package.json
예제 디렉터리의 package.json도 함께 참고하세요:
{
"name": "libsql-examples",
"type": "module",
"private": true,
"dependencies": {
"@libsql/client": "..",
"@libsql/core": "../../libsql-core",
"readline-sync": "^1.4.10"
}
}
더 알아보기 (Learn more)
이 페이지는 docs.turso.tech가 GitHub 리포지토리로 리다이렉트하는 페이지예요. 실행 가능한 최신 예제 코드는 libsql-client-ts 리포지토리의 examples 디렉터리에서, Turso 문서 전체 색인은 llms.txt에서 확인할 수 있어요.