Official TypeScript SDK for Client Commander CRM.
npm install @clientcommander/sdk
# or
pnpm add @clientcommander/sdk
# or
yarn add @clientcommander/sdkimport { ClientCommander } from '@clientcommander/sdk';
const cc = new ClientCommander({
apiKey: 'your_api_key_here',
});
// List contacts
const { data: contacts } = await cc.people.listPeople({ limit: 10 });
console.log(contacts);
// Create a contact
const response = await cc.people.createOrUpdatePerson({
firstName: 'John',
lastName: 'Doe',
email: 'john@example.com',
phone: '+1234567890',
});
// Search contacts
const { data: results } = await cc.people.searchPeople({ name: 'John' });// List contacts with pagination
cc.people.listPeople({ limit: 10, cursor: 'abc123' });
// Create or update a contact (upsert)
cc.people.createOrUpdatePerson({ firstName: 'John', lastName: 'Doe', email: 'john@example.com' });
// Search contacts by name, email, or phone
cc.people.searchPeople({ name: 'John' });
// Get a specific contact
cc.people.getPerson('contact_id');
// Update a contact
cc.people.updatePerson('contact_id', { firstName: 'Jane' });
// Delete a contact (soft delete)
cc.people.deletePerson('contact_id');
// Get contact tags
cc.people.getPersonTags('contact_id');
// Add tags to contact
cc.people.addPersonTags('contact_id', { tags: ['new', 'vip'] });// List tasks
cc.tasks.listTasks({ personId: 'contact_id' });
// Create a task
cc.tasks.createTask({ personId: 'contact_id', name: 'Follow up call', type: 'Call' });
// Get a task
cc.tasks.getTask('task_id');
// Update a task
cc.tasks.updateTask('task_id', { name: 'Updated task' });
// Mark task as complete
cc.tasks.markTaskAsComplete('task_id');
// Delete a task
cc.tasks.deleteTask('task_id');// List deals
cc.deals.listDeals({ pipelineId: 'pipeline_id' });
// Create a deal
cc.deals.createDeal({ title: 'New Deal', pipelineId: 'pipeline_id', stageId: 'stage_id' });
// Get a deal
cc.deals.getDeal('deal_id');
// Update a deal
cc.deals.updateDeal('deal_id', { title: 'Updated Deal' });
// Move deal to different stage
cc.deals.moveDealToStage('deal_id', { stageId: 'new_stage_id' });
// Delete a deal
cc.deals.deleteDeal('deal_id');// List activities for a contact
cc.activities.listActivities({ personId: 'contact_id' });
// Create an activity
cc.activities.createActivity({ personId: 'contact_id', type: 'note', content: 'Called and left voicemail' });
// Get an activity
cc.activities.getActivity('activity_id');
// Update an activity
cc.activities.updateActivity('activity_id', { content: 'Updated content' });
// Delete an activity
cc.activities.deleteActivity('activity_id');// List users in your company
cc.users.listUsers();
// Get current authenticated user
cc.users.getCurrentUser();For development or self-hosted instances:
const cc = new ClientCommander({
apiKey: 'your_api_key',
baseURL: 'https://your-instance.convex.site/v1',
});try {
const contact = await cc.people.getPerson('invalid_id');
} catch (error) {
if (error.status === 404) {
console.log('Contact not found');
} else if (error.status === 401) {
console.log('Invalid API key');
} else if (error.status === 429) {
console.log('Rate limited, retry after:', error.response.headers['retry-after']);
}
}Full TypeScript support with all types exported:
import type { Contact, Task, Deal, Activity } from '@clientcommander/sdk';
const contact: Contact = {
firstName: 'John',
lastName: 'Doe',
// Full autocomplete and type checking
};The API is rate-limited to 1000 requests per hour per API key. Rate limit info is included in response headers:
X-RateLimit-Limit: Maximum requests per hourX-RateLimit-Remaining: Remaining requestsX-RateLimit-Reset: Unix timestamp when limit resets
- Documentation: https://docs.clientcommander.com
- API Reference: https://clientcommander.readme.io
- Email: support@clientcommander.me
MIT