apollo-local-dev-loop

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Apollo Local Dev Loop

Apollo 本地开发循环

Overview

概述

Set up efficient local development workflow for Apollo.io integrations with proper environment management, testing, and debugging.
为Apollo.io集成搭建高效的本地开发工作流,包含完善的环境管理、测试与调试方案。

Prerequisites

前提条件

  • Completed
    apollo-install-auth
    setup
  • Node.js 18+ or Python 3.10+
  • Git repository initialized
  • 已完成
    apollo-install-auth
    配置
  • Node.js 18+ 或 Python 3.10+
  • 已初始化Git仓库

Instructions

操作步骤

Step 1: Environment Setup

步骤1:环境配置

bash
undefined
bash
undefined

Create environment files

创建环境文件

touch .env .env.example .env.test
touch .env .env.example .env.test

Add to .gitignore

添加到.gitignore

echo '.env' >> .gitignore echo '.env.local' >> .gitignore

```bash
echo '.env' >> .gitignore echo '.env.local' >> .gitignore

```bash

.env.example (commit this)

.env.example(需提交到仓库)

APOLLO_API_KEY=your-api-key-here APOLLO_RATE_LIMIT=100 APOLLO_ENV=development
undefined
APOLLO_API_KEY=your-api-key-here APOLLO_RATE_LIMIT=100 APOLLO_ENV=development
undefined

Step 2: Create Development Client

步骤2:创建开发客户端

typescript
// src/lib/apollo-dev.ts
import axios from 'axios';

const isDev = process.env.NODE_ENV !== 'production';

export const apolloClient = axios.create({
  baseURL: 'https://api.apollo.io/v1',
  params: { api_key: process.env.APOLLO_API_KEY },
});

// Add request logging in development
if (isDev) {
  apolloClient.interceptors.request.use((config) => {
    console.log(`[Apollo] ${config.method?.toUpperCase()} ${config.url}`);
    return config;
  });

  apolloClient.interceptors.response.use(
    (response) => {
      console.log(`[Apollo] Response: ${response.status}`);
      return response;
    },
    (error) => {
      console.error(`[Apollo] Error: ${error.response?.status}`, error.message);
      return Promise.reject(error);
    }
  );
}
typescript
// src/lib/apollo-dev.ts
import axios from 'axios';

const isDev = process.env.NODE_ENV !== 'production';

export const apolloClient = axios.create({
  baseURL: 'https://api.apollo.io/v1',
  params: { api_key: process.env.APOLLO_API_KEY },
});

// 在开发环境中添加请求日志
if (isDev) {
  apolloClient.interceptors.request.use((config) => {
    console.log(`[Apollo] ${config.method?.toUpperCase()} ${config.url}`);
    return config;
  });

  apolloClient.interceptors.response.use(
    (response) => {
      console.log(`[Apollo] 响应状态: ${response.status}`);
      return response;
    },
    (error) => {
      console.error(`[Apollo] 错误: ${error.response?.status}`, error.message);
      return Promise.reject(error);
    }
  );
}

Step 3: Create Mock Server for Testing

步骤3:创建测试用Mock服务器

typescript
// src/mocks/apollo-mock.ts
import { rest } from 'msw';

export const apolloHandlers = [
  rest.post('https://api.apollo.io/v1/people/search', (req, res, ctx) => {
    return res(
      ctx.json({
        people: [
          { id: '1', name: 'Test User', title: 'Engineer', email: 'test@example.com' },
        ],
        pagination: { page: 1, per_page: 10, total_entries: 1 },
      })
    );
  }),

  rest.get('https://api.apollo.io/v1/organizations/enrich', (req, res, ctx) => {
    return res(
      ctx.json({
        organization: {
          name: 'Test Company',
          domain: 'test.com',
          industry: 'Technology',
        },
      })
    );
  }),
];
typescript
// src/mocks/apollo-mock.ts
import { rest } from 'msw';

export const apolloHandlers = [
  rest.post('https://api.apollo.io/v1/people/search', (req, res, ctx) => {
    return res(
      ctx.json({
        people: [
          { id: '1', name: 'Test User', title: 'Engineer', email: 'test@example.com' },
        ],
        pagination: { page: 1, per_page: 10, total_entries: 1 },
      })
    );
  }),

  rest.get('https://api.apollo.io/v1/organizations/enrich', (req, res, ctx) => {
    return res(
      ctx.json({
        organization: {
          name: 'Test Company',
          domain: 'test.com',
          industry: 'Technology',
        },
      })
    );
  }),
];

Step 4: Development Scripts

步骤4:开发脚本配置

json
{
  "scripts": {
    "dev": "NODE_ENV=development tsx watch src/index.ts",
    "dev:mock": "MOCK_APOLLO=true npm run dev",
    "test:apollo": "vitest run src/**/*.apollo.test.ts",
    "apollo:quota": "tsx scripts/check-apollo-quota.ts"
  }
}
json
{
  "scripts": {
    "dev": "NODE_ENV=development tsx watch src/index.ts",
    "dev:mock": "MOCK_APOLLO=true npm run dev",
    "test:apollo": "vitest run src/**/*.apollo.test.ts",
    "apollo:quota": "tsx scripts/check-apollo-quota.ts"
  }
}

Step 5: Quota Monitoring Script

步骤5:配额监控脚本

typescript
// scripts/check-apollo-quota.ts
import { apolloClient } from '../src/lib/apollo-dev';

async function checkQuota() {
  try {
    const { data } = await apolloClient.get('/auth/health');
    console.log('API Status:', data);
    // Note: Apollo doesn't expose quota directly, track usage manually
  } catch (error: any) {
    if (error.response?.status === 429) {
      console.error('Rate limited! Wait before making more requests.');
    }
  }
}

checkQuota();
typescript
// scripts/check-apollo-quota.ts
import { apolloClient } from '../src/lib/apollo-dev';

async function checkQuota() {
  try {
    const { data } = await apolloClient.get('/auth/health');
    console.log('API状态:', data);
    // 注意:Apollo不直接暴露配额信息,需手动跟踪使用情况
  } catch (error: any) {
    if (error.response?.status === 429) {
      console.error('触发速率限制!请等待后再发起请求。');
    }
  }
}

checkQuota();

Output

输出结果

  • Environment file structure (.env, .env.example)
  • Development client with logging interceptors
  • Mock server for testing without API calls
  • npm scripts for development workflow
  • Quota monitoring utility
  • 环境文件结构(.env、.env.example)
  • 带有日志拦截器的开发客户端
  • 无需调用真实API的Mock测试服务器
  • 用于开发工作流的npm脚本
  • 配额监控工具

Error Handling

错误处理

ErrorCauseSolution
Missing API Key.env not loadedRun
source .env
or use dotenv
Mock Not WorkingMSW not configuredEnsure setupServer is called
Rate Limited in DevToo many test callsUse mock server for tests
Stale CredentialsKey rotatedUpdate .env with new key
错误原因解决方案
API密钥缺失.env文件未加载执行
source .env
或使用dotenv工具
Mock功能失效MSW未配置确保已调用setupServer
开发环境触发速率限制测试请求过多使用Mock服务器进行测试
凭证过期密钥已轮换更新.env文件中的密钥

Examples

示例

Watch Mode Development

监听模式开发

bash
undefined
bash
undefined

Terminal 1: Run dev server with watch

终端1:启动带监听的开发服务器

npm run dev
npm run dev

Terminal 2: Test API calls

终端2:测试API调用

curl -X POST http://localhost:3000/api/apollo/search
-H "Content-Type: application/json"
-d '{"domain": "stripe.com"}'
undefined
curl -X POST http://localhost:3000/api/apollo/search
-H "Content-Type: application/json"
-d '{"domain": "stripe.com"}'
undefined

Testing with Mocks

使用Mock进行测试

typescript
// src/services/apollo.apollo.test.ts
import { describe, it, expect, beforeAll, afterAll } from 'vitest';
import { setupServer } from 'msw/node';
import { apolloHandlers } from '../mocks/apollo-mock';
import { searchPeople } from './apollo';

const server = setupServer(...apolloHandlers);

beforeAll(() => server.listen());
afterAll(() => server.close());

describe('Apollo Service', () => {
  it('searches for people', async () => {
    const results = await searchPeople({ domain: 'test.com' });
    expect(results.people).toHaveLength(1);
    expect(results.people[0].name).toBe('Test User');
  });
});
typescript
// src/services/apollo.apollo.test.ts
import { describe, it, expect, beforeAll, afterAll } from 'vitest';
import { setupServer } from 'msw/node';
import { apolloHandlers } from '../mocks/apollo-mock';
import { searchPeople } from './apollo';

const server = setupServer(...apolloHandlers);

beforeAll(() => server.listen());
afterAll(() => server.close());

describe('Apollo 服务', () => {
  it('搜索人员信息', async () => {
    const results = await searchPeople({ domain: 'test.com' });
    expect(results.people).toHaveLength(1);
    expect(results.people[0].name).toBe('Test User');
  });
});

Resources

参考资源

Next Steps

下一步

Proceed to
apollo-sdk-patterns
for production-ready code patterns.
继续学习
apollo-sdk-patterns
以获取生产环境就绪的代码模式。