Upload files to Coinflow storage
Overview
This endpoint generates a secure, temporary upload URL that allows merchants to upload files directly to Coinflow’s storage. The presigned URL is valid for 1 hour.
Endpoint
POST /api/merchant/files/upload-url
Accepted File Types
| File Type | Content Type |
|---|---|
application/pdf | |
| PNG | image/png |
| JPEG | image/jpeg |
| GIF | image/gif |
| ZIP | application/zip |
| Word (.docx) | application/vnd.openxmlformats-officedocument.wordprocessingml.document |
| Excel (.xlsx) | application/vnd.openxmlformats-officedocument.spreadsheetml.sheet |
| CSV | text/csv |
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
fileName | string | Yes | Name of the file to upload (e.g., "evidence.pdf") |
contentType | string | Yes | MIME type of the file (e.g., "application/pdf") |
Response
| Field | Type | Description |
|---|---|---|
uploadUrl | string | Presigned S3-style URL for uploading the file (expires in 1 hour) |
fileKey | string | Identifier stored as: merchants/{merchantId}/{uuid}.{extension} |
Usage Flow
Step 1: Request Upload URL
$ curl --request POST \ > --url https://api-sandbox.coinflow.cash/api/merchant/files/upload-url \ > --header 'Authorization: YOUR_MERCHANT_API_KEY' \ > --header 'Content-Type: application/json' \ > --data '{ > "fileName": "chargeback-evidence.pdf", > "contentType": "application/pdf" > }' > > **Response** > { > "uploadUrl": "https://abc123.r2.cloudflarestorage.com/...&X-Amz-Credential=...", > "fileKey": "merchants/your-merchant-id/550e8400-e29b-41d4-a716-446655440000.pdf" > }
Step 2: Upload File to Presigned URL
$ curl --request PUT \ > --url "PASTE_UPLOAD_URL_HERE" \ > --header 'Content-Type: application/pdf' \ > --data-binary @/path/to/your/file.pdf
Step 3: Reference the Uploaded File in your API Calls
Example: Submit chargeback response with the uploaded file
$ curl --request POST \ > --url https://api-sandbox.coinflow.cash/api/merchant/chargebacks/PAYMENT_ID/respond \ > --header 'Authorization: YOUR_MERCHANT_API_KEY' \ > --header 'Content-Type: application/json' \ > --data '{ > "fileKey": "merchants/your-merchant-id/550e8400-e29b-41d4-a716-446655440000.pdf" > }'
Example: JavaScript / TypeScript
1 // Step 1: Get presigned upload URL 2 const getUploadUrl = async (fileName: string, file: File) => { 3 const response = await fetch( 4 'https://api-sandbox.coinflow.cash/api/merchant/files/upload-url', 5 { 6 method: 'POST', 7 headers: { 8 Authorization: `${YOUR_API_KEY}`, 9 'Content-Type': 'application/json', 10 }, 11 body: JSON.stringify({ 12 fileName, 13 contentType: file.type, 14 }), 15 } 16 ); 17 18 return response.json(); 19 }; 20 21 // Step 2: Upload file to Cloudflare R2 22 const uploadFile = async (uploadUrl: string, file: File) => { 23 await fetch(uploadUrl, { 24 method: 'PUT', 25 headers: { 'Content-Type': file.type }, 26 body: file, 27 }); 28 }; 29 30 // Step 3: Submit chargeback response using the uploaded file 31 const submitChargebackResponse = async (paymentId: string, fileKey: string) => { 32 const response = await fetch( 33 `https://api-sandbox.coinflow.cash/api/merchant/chargebacks/${paymentId}/respond`, 34 { 35 method: 'POST', 36 headers: { 37 Authorization: `${YOUR_API_KEY}`, 38 'Content-Type': 'application/json', 39 }, 40 body: JSON.stringify({ fileKey }), 41 } 42 ); 43 44 if (!response.ok) { 45 throw new Error(`Failed to submit chargeback response: ${response.statusText}`); 46 } 47 48 return response.json(); 49 }; 50 51 // Complete flow 52 const handleFileUploadAndSubmit = async (file: File, paymentId: string) => { 53 // Step 1: Get presigned URL 54 const { uploadUrl, fileKey } = await getUploadUrl(file.name, file); 55 56 // Step 2: Upload file 57 await uploadFile(uploadUrl, file); 58 59 console.log('File uploaded successfully! FileKey:', fileKey); 60 61 // Step 3: Submit chargeback response 62 const result = await submitChargebackResponse(paymentId, fileKey); 63 64 return result; 65 };

