SDK
SDK Node.js
Instal @sofia-post/node dan panggil API Sofia dari Node.js: publikasikan, jadwalkan, unggah media, dan baca statistik, dengan kesalahan bertipe.
SDK Node.js resmi membungkus Sofia API v1 dalam satu kelas, Sofia: satu metode per rute, permintaan dan jawaban bertipe, serta satu tipe kesalahan untuk setiap kegagalan. SDK ini tanpa dependensi dan berjalan di Node.js 20 atau lebih baru.
Instal
SDK ini dipublikasikan di npm sebagai paket @sofia-post/node. Bisa dipakai dengan import maupun require.
npm install @sofia-post/nodeMulai cepat
Buat klien dengan kunci Anda, temukan usaha yang akan dipublikasikan, lalu jadwalkan postingan di Instagram:
import { Sofia } from '@sofia-post/node';
const sofia = new Sofia(process.env.SOFIA_API_KEY);
const [establishment] = await sofia.establishments();
const post = await sofia.post({
establishmentId: establishment.id,
targets: [{ platform: 'instagram', text: 'Tarte tatin du jour 🍎' }],
scheduledAt: new Date('2026-12-01T09:00:00Z'),
});
console.log(post.id, post.status);Autentikasi
Konstruktor menerima kunci pribadi, yang dibuat di Pengaturan › API, tab Akses pribadi, atau token akses OAuth jika aplikasi Anda bertindak untuk pengguna Sofia lain (OAuth2). SDK mengirimnya sebagai Authorization: Bearer … pada setiap permintaan.
Klien berbicara ke https://api.sofia-post.com secara default. Argumen kedua mengubah URL dasar, atau fetch yang dipakai untuk mengirim permintaan:
const sofia = new Sofia(apiKey, { baseUrl: 'http://localhost:3008' });Metode
| Metode | Fungsinya |
|---|---|
me() | Untuk siapa kunci bertindak, scope-nya, dan apakah ini kunci uji |
platforms() | Aturan tiap jaringan: panjang teks, media, format |
establishments() | Usaha yang dijangkau kunci |
accounts(establishmentId) | Akun sosial yang terhubung ke sebuah usaha |
connectionLink(establishmentId, input) | Halaman yang dihosting Sofia tempat pengguna menghubungkan jaringan |
insights(establishmentId, period?) | Jangkauan, interaksi, dan pengikut, jaringan demi jaringan |
post(input, options?) | Publikasikan sekarang, jadwalkan dengan scheduledAt, atau simpan draf |
postList(filters?) | Satu halaman postingan, difilter menurut usaha, status, atau tanggal |
getPost(id) · updatePost(id, input) · deletePost(id) | Baca, ubah, atau tarik satu postingan |
upload(input) · uploadFromUrl(input) | Tambahkan file atau URL ke pustaka media usaha |
mediaList(filters) · getMedia(id) · deleteMedia(id) | Baca dan rapikan pustaka media |
createWebhook(input) · webhooks() · deleteWebhook(id) · testWebhook(id) | Diberi tahu saat postingan terbit atau gagal |
Postingan
Sebuah postingan punya satu target per jaringan, masing-masing dengan teks, media, dan format sendiri. Periksa dulu dengan dryRun: tidak ada yang ditulis, dan penolakan mencantumkan setiap aturan yang dilanggar. Sertakan idempotencyKey agar permintaan yang diulang tidak pernah memublikasikan dua kali. scheduledAt menerima Date atau string ISO 8601.
import type { PublishPostInput } from '@sofia-post/node';
const input: PublishPostInput = {
establishmentId,
targets: [
{ platform: 'instagram', text: 'Menu du jour', media: [{ id: media.id }] },
{ platform: 'facebook', text: 'Menu du jour : tarte tatin et café' },
],
};
await sofia.post(input, { dryRun: true });
await sofia.post(input, { idempotencyKey: crypto.randomUUID() });Media
Unggah file sekali, lalu masukkan id-nya ke media sebuah postingan. upload menerima Buffer, Uint8Array, atau Blob, dan membaca tipe konten dari nama file kecuali Anda memberikan contentType. Dengan uploadFromUrl, Sofia mengunduh filenya sendiri.
import { readFile } from 'node:fs/promises';
const media = await sofia.upload({
establishmentId,
file: await readFile('tarte-tatin.jpg'),
fileName: 'tarte-tatin.jpg',
});
const imported = await sofia.uploadFromUrl({ establishmentId, url: 'https://example.com/menu.png' });Paginasi
postList dan mediaList menjawab satu halaman setiap kali. Berikan nextCursor dari sebuah halaman sebagai cursor pada panggilan berikutnya; halaman terakhir tidak memilikinya.
let cursor: string | undefined;
do {
const page = await sofia.postList({ establishmentId, status: 'published', limit: 100, cursor });
page.data.forEach((post) => console.log(post.id));
cursor = page.nextCursor;
} while (cursor);Kesalahan
Setiap metode melempar SofiaApiError saat API menolak panggilan. Isinya mencakup status HTTP, code stabil dari amplop kesalahan, details (untuk postingan yang ditolak, setiap aturan jaringan yang dilanggar), requestId untuk diberikan ke dukungan, dan pada 429, retryAfterSeconds.
import { SofiaApiError } from '@sofia-post/node';
try {
await sofia.post(input);
} catch (error) {
if (!(error instanceof SofiaApiError)) throw error;
if (error.code === 'post_refused') console.log(error.details);
if (error.status === 429) await wait(error.retryAfterSeconds);
}Jika API sama sekali tidak dapat dijangkau, kesalahan memiliki kode network_error dan status 0. SDK tidak pernah mencoba ulang sendiri: tunggu retryAfterSeconds pada 429 dan beri jeda lebih lama pada 5xx.
TypeScript
Paket ini menyertakan tipenya: PublishPostInput, Post, Media, SocialAccount, EstablishmentInsights, dan lainnya diekspor di samping Sofia, sehingga editor Anda melengkapi setiap kolom dan setiap nilai enum.
Selanjutnya: referensi API menjelaskan setiap rute yang dipanggil SDK, dan CLI menjalankan API yang sama dari terminal.