Skip to main content

Frontend Development with Ductape

Ductape provides powerful frontend client libraries that make it easy to build real-time, data-driven applications. Our frontend SDKs give you direct access to databases, storage, features, agents, and more—all from the browser with built-in security and real-time synchronization.

Available Packages​

Ductape offers three complementary packages for frontend development:

@ductape/client​

The core client library that works with any JavaScript framework or vanilla JavaScript. Provides a simple, type-safe interface for all Ductape services.

Each topic page includes tabs for @ductape/client, React, and Vue 3 code samples — pick your stack on the same page.

Use when:

  • Building with vanilla JavaScript/TypeScript
  • Using frameworks not yet supported (Angular, Svelte, etc.)
  • You want full control over data fetching and state management
import { Ductape } from '@ductape/client';

const ductape = new Ductape({
publishableKey: 'your-publishable-key',
});

@ductape/react​

React hooks and components built on top of @ductape/client, providing a React-idiomatic way to work with Ductape.

Use when:

  • Building React applications (React 17+)
  • You want automatic loading states and error handling
  • You prefer declarative data fetching with hooks
import { DuctapeProvider, useDatabaseQuery } from '@ductape/react';
import { session } from './config'; // or from your auth (e.g. useSessionToken())

function UsersList() {
const { data, isLoading } = useDatabaseQuery('users', {
table: 'users',
limit: 10,
session, // required when using publishable key
});
}

@ductape/vue​

Vue 3 composables and plugin built on top of @ductape/client for Vue applications.

Use when:

  • Building Vue 3 applications
  • You want reactive data with Vue's composition API
  • You need seamless integration with Vue's ecosystem
<script setup>
import { useDatabaseQuery } from '@ductape/vue';

const sessionToken = useSessionToken(); // from your auth/backend
const { data, isLoading } = useDatabaseQuery(
['users'],
{ table: 'users', limit: 10, session: sessionToken }
);
</script>

Key Features​

Persisted settings​

A settings screen is complete only when it loads canonical state, persists changes through its owning registered Feature, and exposes loading, failure, and retry states. Generate or consume the frontend input type from the current Feature contract; do not invent payload keys from labels. Verify a real read-after-write round trip in the target environment before treating a local state change or success toast as proof of persistence.

For notification preferences, keep channel consent such as email, sms, and push separate from event-category subscriptions such as order or promotion updates. The submitted keys must match the Feature input schema exactly.

Real-time Subscriptions​

Subscribe to database changes, feature updates, and more with WebSocket-based real-time synchronization.

// Session token from your backend (e.g. after auth)
const sessionToken = getSessionFromYourBackend();

// Automatic real-time updates
const { data } = useDatabaseQuery('todos', {
table: 'todos',
where: { completed: false },
session: sessionToken,
});

// Subscribe to changes
ductape.databases.subscribe({
table: 'todos',
session: sessionToken,
onChange: (event) => console.log('Todo changed:', event)
});

Publishable key and session (required)​

When you use a publishable key (the normal frontend setup), the proxy requires a session as a second layer of validation:

  • Session in params: Every request must include a session property in the options object. The value is a session token issued by your backend (e.g. after user login). If session is missing or empty, the proxy rejects the request.
// Get session token from your backend (e.g. after auth)
const sessionToken = getSessionFromYourBackend();

// Include session in every Ductape request
const data = await ductape.databases.query({
table: 'orders',
limit: 10,
session: sessionToken, // required when using publishable key
});

await ductape.storage.upload({
storage: 'gcp-storage',
fileName: 'path/file.txt',
data: blob,
mimeType: 'text/plain',
session: sessionToken,
});
  • Session APIs are backend-only: When using a publishable key, you cannot call session methods (sessions.start, sessions.verify, sessions.refresh, sessions.revoke, etc.) from the client—they throw. Sessions must be started and managed only on your backend. Your backend returns a session token to the frontend; the frontend only passes that token as session in each request.

Type Safety​

Full TypeScript support with intelligent type inference for your database schemas and API responses.

const sessionToken = getSessionFromYourBackend();

interface User {
id: string;
name: string;
email: string;
}

const { data } = await ductape.databases.query<User>({
table: 'users',
where: { active: true },
session: sessionToken,
});
// data.rows is typed as User[]

Optimistic Updates​

Update your UI instantly while changes sync in the background.

const sessionToken = getSessionFromYourBackend();

const { mutate } = useDatabaseInsert({
onMutate: async (newTodo) => {
// Optimistically update UI
return { newTodo };
},
onError: (err, variables, context) => {
// Rollback on error
}
});

// When calling mutate, include session in the payload
mutate({ table: 'todos', data: newTodo, session: sessionToken });

What Can You Build?​

  • Real-time Dashboards: Live data visualization with automatic updates
  • Collaborative Apps: Multi-user applications with real-time sync
  • Chat Applications: Message brokers and presence tracking
  • File Sharing: Upload, download, and manage files
  • Data-Driven UIs: Complex queries with filtering, sorting, and pagination
  • AI-Powered Features: Run agents and features directly from the frontend
  • Graph Applications: Social networks, recommendation engines
  • Vector Search: Semantic search and AI features

Getting Started​

Choose a topic and switch tabs for your framework:

Architecture​

All three packages share a common architecture:

┌─────────────────────────────────────────┐
│ Your Application │
├─────────────────────────────────────────┤
│ @ductape/react or @ductape/vue │ ← Framework-specific bindings
├─────────────────────────────────────────┤
│ @ductape/client │ ← Core client SDK
├─────────────────────────────────────────┤
│ HTTP/WebSocket │ ← Transport layer
├─────────────────────────────────────────┤
│ Ductape Backend Services │ ← Your configured product
└─────────────────────────────────────────┘

The framework-specific packages (@ductape/react and @ductape/vue) are thin wrappers that provide idiomatic APIs for each framework while leveraging the full power of @ductape/client under the hood.

Next Steps​

  1. Install: Choose your package and install it
  2. Configure: Set up your client with access keys
  3. Connect: Initialize connection to your product
  4. Build: Start using databases, storage, features, and more

Explore the documentation for your chosen framework to learn more.