amazon-seller-mcp
Version:
Model Context Protocol (MCP) client for Amazon Selling Partner API
227 lines • 8.01 kB
JavaScript
/**
* Reports API client for Amazon Selling Partner API
*/
// Third-party dependencies
import { z } from 'zod';
// Internal imports
import { BaseApiClient } from './base-client.js';
import { getLogger } from '../utils/logger.js';
/**
* Reports API client for Amazon Selling Partner API
*/
export class ReportsClient extends BaseApiClient {
/**
* API version
*/
apiVersion = 'reports/2021-06-30';
/**
* Create a new ReportsClient instance
*
* @param authConfig Authentication configuration
*/
constructor(authConfig) {
super(authConfig);
}
/**
* Create a report
*
* @param params Parameters for creating a report
* @returns Promise resolving to the create report result
*/
async createReport(params) {
const { reportType, marketplaceIds, dataStartTime, dataEndTime, reportOptions } = params;
// Validate create report parameters
this.validateCreateReportParams(params);
// Build request body
const requestBody = {
reportType,
marketplaceIds,
dataStartTime,
dataEndTime,
reportOptions,
};
// Make API request
const requestOptions = {
method: 'POST',
path: `/${this.apiVersion}/reports`,
data: requestBody,
};
const response = await this.request(requestOptions);
return response.data.payload;
}
/**
* Get a report
*
* @param params Parameters for getting a report
* @returns Promise resolving to the report
*/
async getReport(params) {
const { reportId } = params;
// Make API request
const requestOptions = {
method: 'GET',
path: `/${this.apiVersion}/reports/${reportId}`,
};
// Use cache for report (30 seconds TTL)
const cacheKey = `report:${reportId}`;
return this.withCache(cacheKey, async () => {
const response = await this.request(requestOptions);
return response.data.payload;
}, 30 // 30 seconds TTL
);
}
/**
* Get a report document
*
* @param params Parameters for getting a report document
* @returns Promise resolving to the report document
*/
async getReportDocument(params) {
const { reportDocumentId } = params;
// Make API request
const requestOptions = {
method: 'GET',
path: `/${this.apiVersion}/documents/${reportDocumentId}`,
};
// Use cache for report document (30 seconds TTL)
const cacheKey = `reportDocument:${reportDocumentId}`;
return this.withCache(cacheKey, async () => {
const response = await this.request(requestOptions);
return response.data.payload;
}, 30 // 30 seconds TTL
);
}
/**
* Get reports
*
* @param params Parameters for getting reports
* @returns Promise resolving to the get reports result
*/
async getReports(params = {}) {
const { reportTypes, processingStatuses, marketplaceIds, pageSize, createdSince, createdUntil, nextToken, } = params;
// Build query parameters
const query = {};
if (reportTypes && reportTypes.length > 0) {
query.reportTypes = reportTypes;
}
if (processingStatuses && processingStatuses.length > 0) {
query.processingStatuses = processingStatuses;
}
if (marketplaceIds && marketplaceIds.length > 0) {
query.marketplaceIds = marketplaceIds;
}
else {
// Default to the configured marketplace ID
query.marketplaceIds = [this.config.marketplaceId];
}
if (pageSize) {
query.pageSize = Math.min(100, Math.max(1, pageSize)); // Ensure pageSize is between 1 and 100
}
if (createdSince) {
query.createdSince = createdSince;
}
if (createdUntil) {
query.createdUntil = createdUntil;
}
if (nextToken) {
query.nextToken = nextToken;
}
// Make API request
const requestOptions = {
method: 'GET',
path: `/${this.apiVersion}/reports`,
query: query,
};
// Use cache for reports (30 seconds TTL)
const cacheKey = `reports:${this.config.marketplaceId}:${JSON.stringify(query)}`;
return this.withCache(cacheKey, async () => {
const response = await this.request(requestOptions);
return response.data.payload;
}, 30 // 30 seconds TTL
);
}
/**
* Cancel a report
*
* @param params Parameters for canceling a report
* @returns Promise resolving to void
*/
async cancelReport(params) {
const { reportId } = params;
// Make API request
const requestOptions = {
method: 'DELETE',
path: `/${this.apiVersion}/reports/${reportId}`,
};
await this.request(requestOptions);
// Clear cache for this report
this.clearCache(`report:${reportId}`);
}
/**
* Download a report document
*
* @param reportDocumentId Report document ID
* @returns Promise resolving to the report content
*/
async downloadReportDocument(reportDocumentId) {
// Get report document
const reportDocument = await this.getReportDocument({ reportDocumentId });
// Make request to download URL
const response = await fetch(reportDocument.url);
if (!response.ok) {
throw new Error(`Failed to download report document: ${response.statusText}`);
}
// Get content
const content = await response.text();
// Handle compression if needed
if (reportDocument.compressionAlgorithm === 'GZIP') {
// In a real implementation, we would decompress the content here
// For now, we'll just return the raw content with a warning
getLogger().warn('GZIP compression detected but not implemented. Returning raw content.');
}
return content;
}
/**
* Validate create report parameters
*
* @param params Parameters to validate
* @throws Error if validation fails
*/
validateCreateReportParams(params) {
// Define validation schema using zod
const schema = z.object({
reportType: z.string().min(1, 'Report type is required'),
marketplaceIds: z.array(z.string()).min(1, 'At least one marketplace ID is required'),
dataStartTime: z
.string()
.regex(/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}Z$/, 'Data start time must be in ISO 8601 format')
.optional(),
dataEndTime: z
.string()
.regex(/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}Z$/, 'Data end time must be in ISO 8601 format')
.optional(),
reportOptions: z.record(z.string()).optional(),
});
try {
schema.parse(params);
}
catch (error) {
if (error instanceof z.ZodError) {
const formattedErrors = error.errors
.map((err) => `${err.path.join('.')}: ${err.message}`)
.join(', ');
throw new Error(`Validation failed for create report: ${formattedErrors}`);
}
throw error;
}
// Additional validation for date range
if (params.dataStartTime && params.dataEndTime) {
const startTime = new Date(params.dataStartTime).getTime();
const endTime = new Date(params.dataEndTime).getTime();
if (startTime >= endTime) {
throw new Error('Data start time must be before data end time');
}
}
}
}
//# sourceMappingURL=reports-client.js.map