如何在NodeJS中将二进制数据保存为JPG图片
Hey, I get it—curl makes saving binary media (like images) super straightforward with the -o flag, but Node.js needs a little extra care to handle that raw data correctly without corrupting the image. Let's walk through a couple of reliable ways to get this done, starting with no extra dependencies, then moving to a simpler library approach.
Using Node.js Native http/https Modules
If you don't want to install additional packages, Node's built-in http or https modules work perfectly. The key here is to stream the binary response directly to a file, which is efficient even for larger images.
const https = require('https'); // Use `http` instead if your API uses HTTP const fs = require('fs'); // Replace with your actual API endpoint const apiEndpoint = 'https://your-api-url.com/your-image-endpoint'; // Create a write stream to save the output image const outputStream = fs.createWriteStream('saved-image.jpg'); https.get(apiEndpoint, (response) => { // First, check if the request was successful if (response.statusCode !== 200) { console.error(`Request failed: Status code ${response.statusCode}`); outputStream.close(); return; } // Pipe the raw binary response directly to the file stream response.pipe(outputStream); // Handle completion and errors outputStream.on('finish', () => { outputStream.close(); console.log('Image saved successfully!'); }); }).on('error', (err) => { console.error('Failed to fetch the image:', err.message); outputStream.close(); });
Notes for this approach:
- If your API requires authentication headers (like a bearer token), add them to an options object instead of passing the URL directly:
const requestOptions = { hostname: 'your-api-url.com', path: '/your-image-endpoint', headers: { 'Authorization': 'Bearer your-auth-token', // Add any other required headers here } }; https.get(requestOptions, (response) => { /* ... */ }); - We use
pipe()because it handles backpressure automatically, which prevents memory issues with large files.
Using Axios (Simpler, with Dependencies)
If you prefer a more concise syntax, Axios is a great choice—just make sure to tell it to return binary data instead of trying to parse it as JSON or text.
First, install Axios if you haven't already:
npm install axios
Option 1: Stream the response (best for large images)
const axios = require('axios'); const fs = require('fs'); const apiEndpoint = 'https://your-api-url.com/your-image-endpoint'; axios.get(apiEndpoint, { responseType: 'stream' }) .then((response) => { const outputStream = fs.createWriteStream('saved-image.jpg'); response.data.pipe(outputStream); // Return a promise to handle finish/error events return new Promise((resolve, reject) => { outputStream.on('finish', resolve); outputStream.on('error', reject); }); }) .then(() => { console.log('Image saved successfully!'); }) .catch((err) => { console.error('Error saving image:', err.message); });
Option 2: Use ArrayBuffer (for smaller images)
If your image is small, you can fetch the data as an ArrayBuffer and write it directly to a file:
const axios = require('axios'); const fs = require('fs').promises; // Use promise-based fs for cleaner code const apiEndpoint = 'https://your-api-url.com/your-image-endpoint'; axios.get(apiEndpoint, { responseType: 'arraybuffer' }) .then(async (response) => { await fs.writeFile('saved-image.jpg', response.data); console.log('Image saved successfully!'); }) .catch((err) => { console.error('Error:', err.message); });
Critical Note for Axios:
Always set responseType to either stream or arraybuffer! If you skip this, Axios will default to parsing the response as UTF-8 text, which will corrupt your binary image data.
内容的提问来源于stack exchange,提问作者Amir Saleem

