Sample Code
These examples use the routes that currently exist in the backend instead of placeholder endpoints.
Submit Records
const response = await fetch(
"https://metro2.switchlabs.dev/api/v1/submit-metro2-data",
{
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.METRO2_API_KEY}`,
},
body: JSON.stringify({
records: [
{
consumer_account_number: "ACCT-001",
portfolio_type: "I",
account_type: "00",
date_opened: "2024-01-15",
highest_credit_or_original_loan_amount: 25000,
terms_duration: "060",
terms_frequency: "M",
account_status: "11",
current_balance: 18500,
date_of_account_info: "2025-03-01",
surname: "Smith",
first_name: "Jane",
ecoa_code: "1",
address_1: "123 Main St",
city: "Austin",
state: "TX",
postal_code: "78701",
address_indicator: "C",
country_code: "US",
},
],
}),
},
);
const result = await response.json();Poll Batch Status
const statusResponse = await fetch(
`https://metro2.switchlabs.dev/api/v1/batch-status/${batchId}`,
{
headers: {
Authorization: `Bearer ${process.env.METRO2_API_KEY}`,
},
},
);
const status = await statusResponse.json();File Upload Flow
const createResponse = await fetch(
"https://metro2.switchlabs.dev/api/v1/files/upload-url",
{
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.METRO2_API_KEY}`,
},
body: JSON.stringify({
filename: "portfolio.csv",
contentType: "text/csv",
}),
},
);
const upload = await createResponse.json();
await fetch(upload.upload_url, {
method: "PUT",
headers: upload.headers,
body: csvBytes,
});
await fetch(
`https://metro2.switchlabs.dev/api/v1/files/${upload.file_id}/process`,
{
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.METRO2_API_KEY}`,
},
body: JSON.stringify({}),
},
);Additional Public Workflows
Webhooks, disputes, CRA response parsing, schedules, and audit retrieval are also available on the public `/api/v1` surface. See the reference and guide pages for the route-by-route contract.