Skip to content

JavaScript Examples

Learn how to use SheetsToJson with JavaScript and TypeScript in Node.js, browsers, and modern frameworks.

Installation

No installation required! Use the native fetch API available in:

  • Node.js 18+
  • All modern browsers
  • Deno, Bun, and other runtimes

For older Node.js versions, install node-fetch:

bash
npm install node-fetch

Basic Usage

Fetch All Rows

javascript
const API_KEY = 'your_api_key_here';
const SHEET_ID = 'your_sheet_id';
const BASE_URL = 'https://api.sheetstojson.com';

async function getAllUsers() {
  const response = await fetch(
    `${BASE_URL}/api/v1/${SHEET_ID}/Users`,
    {
      headers: {
        'X-API-Key': API_KEY
      }
    }
  );

  const result = await response.json();

  if (result.success) {
    console.log(`Found ${result.data.length} users`);
    return result.data;
  } else {
    throw new Error(result.message);
  }
}

// Usage
const users = await getAllUsers();
console.log(users);

Fetch Single Row

javascript
async function getUser(userId) {
  const response = await fetch(
    `${BASE_URL}/api/v1/${SHEET_ID}/Users/${userId}`,
    {
      headers: {
        'X-API-Key': API_KEY
      }
    }
  );

  const result = await response.json();
  return result.success ? result.data : null;
}

// Usage
const user = await getUser('123');
console.log(user);

Create Row

javascript
async function createUser(userData) {
  const response = await fetch(
    `${BASE_URL}/api/v1/${SHEET_ID}/Users`,
    {
      method: 'POST',
      headers: {
        'X-API-Key': API_KEY,
        'Content-Type': 'application/json'
      },
      body: JSON.stringify(userData)
    }
  );

  const result = await response.json();

  if (result.success) {
    console.log('User created:', result.data.rows[0]);
    return result.data.rows[0];
  } else {
    throw new Error(result.message);
  }
}

// Usage
const newUser = await createUser({
  name: 'Alice Johnson',
  email: '[email protected]',
  role: 'admin'
});

Update Row

javascript
async function updateUser(userId, updates) {
  const response = await fetch(
    `${BASE_URL}/api/v1/${SHEET_ID}/Users/${userId}`,
    {
      method: 'PUT',
      headers: {
        'X-API-Key': API_KEY,
        'Content-Type': 'application/json'
      },
      body: JSON.stringify(updates)
    }
  );

  const result = await response.json();
  return result.success ? result.data : null;
}

// Usage
const updated = await updateUser('123', {
  role: 'user',
  updated_at: new Date().toISOString()
});

Delete Row

javascript
async function deleteUser(userId) {
  const response = await fetch(
    `${BASE_URL}/api/v1/${SHEET_ID}/Users/${userId}`,
    {
      method: 'DELETE',
      headers: {
        'X-API-Key': API_KEY
      }
    }
  );

  const result = await response.json();
  return result.success;
}

// Usage
await deleteUser('123');
console.log('User deleted');

TypeScript

Add type safety with TypeScript:

typescript
interface User {
  id: string;
  name: string;
  email: string;
  role: 'admin' | 'user';
  created_at?: string;
}

interface ApiResponse<T> {
  success: boolean;
  data?: T;
  error?: string;
  message?: string;
}

class SheetsToJsonClient {
  constructor(
    private apiKey: string,
    private sheetId: string,
    private baseUrl = 'https://api.sheetstojson.com'
  ) {}

  private async request<T>(
    endpoint: string,
    options: RequestInit = {}
  ): Promise<ApiResponse<T>> {
    const response = await fetch(`${this.baseUrl}${endpoint}`, {
      ...options,
      headers: {
        'X-API-Key': this.apiKey,
        'Content-Type': 'application/json',
        ...options.headers
      }
    });

    return response.json();
  }

  async getAll<T>(tabName: string, params?: {
    limit?: number;
    offset?: number;
    sort?: string;
    order?: 'asc' | 'desc';
  }): Promise<T[]> {
    const query = new URLSearchParams(
      params as Record<string, string>
    ).toString();
    const endpoint = `/api/v1/${this.sheetId}/${tabName}${query ? `?${query}` : ''}`;

    const result = await this.request<T[]>(endpoint);
    return result.success && result.data ? result.data : [];
  }

  async getOne<T>(tabName: string, rowId: string): Promise<T | null> {
    const endpoint = `/api/v1/${this.sheetId}/${tabName}/${rowId}`;
    const result = await this.request<T>(endpoint);
    return result.success && result.data ? result.data : null;
  }

  async create<T>(tabName: string, data: Partial<T>): Promise<T | null> {
    const endpoint = `/api/v1/${this.sheetId}/${tabName}`;
    const result = await this.request<{ created: number; rows: T[] }>(endpoint, {
      method: 'POST',
      body: JSON.stringify(data)
    });
    return result.success && result.data ? result.data.rows[0] : null;
  }

  async update<T>(
    tabName: string,
    rowId: string,
    data: Partial<T>
  ): Promise<T | null> {
    const endpoint = `/api/v1/${this.sheetId}/${tabName}/${rowId}`;
    const result = await this.request<T>(endpoint, {
      method: 'PUT',
      body: JSON.stringify(data)
    });
    return result.success && result.data ? result.data : null;
  }

  async delete(tabName: string, rowId: string): Promise<boolean> {
    const endpoint = `/api/v1/${this.sheetId}/${tabName}/${rowId}`;
    const result = await this.request(endpoint, { method: 'DELETE' });
    return result.success;
  }
}

// Usage
const client = new SheetsToJsonClient('your_api_key', 'your_sheet_id');

const users = await client.getAll<User>('Users', { limit: 50 });
const user = await client.getOne<User>('Users', '123');
const created = await client.create<User>('Users', {
  name: 'Bob Smith',
  email: '[email protected]',
  role: 'user'
});

React Integration

Using React Query

typescript
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';

const API_KEY = process.env.REACT_APP_API_KEY;
const SHEET_ID = process.env.REACT_APP_SHEET_ID;
const BASE_URL = 'https://api.sheetstojson.com';

// Fetch users
function useUsers() {
  return useQuery({
    queryKey: ['users'],
    queryFn: async () => {
      const response = await fetch(
        `${BASE_URL}/api/v1/${SHEET_ID}/Users`,
        { headers: { 'X-API-Key': API_KEY } }
      );
      const result = await response.json();
      return result.data;
    }
  });
}

// Create user
function useCreateUser() {
  const queryClient = useQueryClient();

  return useMutation({
    mutationFn: async (userData) => {
      const response = await fetch(
        `${BASE_URL}/api/v1/${SHEET_ID}/Users`,
        {
          method: 'POST',
          headers: {
            'X-API-Key': API_KEY,
            'Content-Type': 'application/json'
          },
          body: JSON.stringify(userData)
        }
      );
      const result = await response.json();
      return result.data.rows[0];
    },
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ['users'] });
    }
  });
}

// Component
function UsersList() {
  const { data: users, isLoading, error } = useUsers();
  const createUser = useCreateUser();

  if (isLoading) return <div>Loading...</div>;
  if (error) return <div>Error: {error.message}</div>;

  const handleCreate = async () => {
    await createUser.mutateAsync({
      name: 'New User',
      email: '[email protected]'
    });
  };

  return (
    <div>
      <button onClick={handleCreate}>Add User</button>
      <ul>
        {users.map(user => (
          <li key={user.id}>{user.name} - {user.email}</li>
        ))}
      </ul>
    </div>
  );
}

Using SWR

typescript
import useSWR from 'swr';

const fetcher = (url: string) =>
  fetch(url, {
    headers: { 'X-API-Key': process.env.REACT_APP_API_KEY }
  }).then(r => r.json()).then(result => result.data);

function UsersList() {
  const { data: users, error, mutate } = useSWR(
    `${BASE_URL}/api/v1/${SHEET_ID}/Users`,
    fetcher
  );

  if (error) return <div>Failed to load</div>;
  if (!users) return <div>Loading...</div>;

  return (
    <ul>
      {users.map(user => (
        <li key={user.id}>{user.name}</li>
      ))}
    </ul>
  );
}

Next.js Integration

Server Component

typescript
// app/users/page.tsx
async function getUsers() {
  const response = await fetch(
    `${process.env.API_BASE_URL}/api/v1/${process.env.SHEET_ID}/Users`,
    {
      headers: {
        'X-API-Key': process.env.API_KEY!
      },
      next: { revalidate: 60 } // Cache for 60 seconds
    }
  );

  const result = await response.json();
  return result.data;
}

export default async function UsersPage() {
  const users = await getUsers();

  return (
    <div>
      <h1>Users</h1>
      <ul>
        {users.map(user => (
          <li key={user.id}>{user.name} - {user.email}</li>
        ))}
      </ul>
    </div>
  );
}

API Route

typescript
// app/api/users/route.ts
import { NextResponse } from 'next/server';

export async function GET() {
  const response = await fetch(
    `${process.env.API_BASE_URL}/api/v1/${process.env.SHEET_ID}/Users`,
    {
      headers: {
        'X-API-Key': process.env.API_KEY!
      }
    }
  );

  const result = await response.json();
  return NextResponse.json(result.data);
}

export async function POST(request: Request) {
  const body = await request.json();

  const response = await fetch(
    `${process.env.API_BASE_URL}/api/v1/${process.env.SHEET_ID}/Users`,
    {
      method: 'POST',
      headers: {
        'X-API-Key': process.env.API_KEY!,
        'Content-Type': 'application/json'
      },
      body: JSON.stringify(body)
    }
  );

  const result = await response.json();
  return NextResponse.json(result.data);
}

Error Handling

javascript
class SheetsAPIError extends Error {
  constructor(message, code, status) {
    super(message);
    this.code = code;
    this.status = status;
  }
}

async function apiRequest(url, options = {}) {
  try {
    const response = await fetch(url, {
      ...options,
      headers: {
        'X-API-Key': API_KEY,
        'Content-Type': 'application/json',
        ...options.headers
      }
    });

    const result = await response.json();

    if (!result.success) {
      throw new SheetsAPIError(
        result.message || 'Request failed',
        result.error,
        response.status
      );
    }

    return result.data;
  } catch (error) {
    if (error instanceof SheetsAPIError) {
      throw error;
    }

    // Network or parsing error
    throw new SheetsAPIError(
      error.message,
      'network_error',
      0
    );
  }
}

// Usage with error handling
try {
  const users = await apiRequest(`${BASE_URL}/api/v1/${SHEET_ID}/Users`);
  console.log(users);
} catch (error) {
  if (error.code === 'rate_limit_exceeded') {
    console.error('Rate limit hit, try again later');
  } else if (error.code === 'unauthorized') {
    console.error('Invalid API key');
  } else {
    console.error('Request failed:', error.message);
  }
}

Next Steps

Built with VitePress