---
seo_title: JPEG to HEIC API: Convert JPG to HEIC in Code | EnConvert
meta_desc: Convert JPEG to HEIC with a REST API. POST /v1/convert/jpeg-to-heic encodes high-quality HEIC files and returns raw bytes or a presigned URL. Code examples.
keywords: jpeg to heic api, jpg to heic api, convert jpeg to heic programmatically, heic encoding api, jpg to heic converter api, heif conversion rest api, convert jpg to heic python
---

# JPEG to HEIC API

Convert JPEG images to HEIC (High Efficiency Image Container) programmatically with `POST /v1/convert/jpeg-to-heic`. The endpoint accepts a `.jpeg` or `.jpg` upload and produces a high-quality HEIC file using the HEIF codec. Responses return either raw image bytes for direct download or JSON metadata with a presigned download URL.

---

## Endpoint

```
POST /v1/convert/jpeg-to-heic
```

**Content-Type:** `multipart/form-data`

**Accepted input:** `.jpeg or .jpg` files

**Output format:** `.heic` (`image/heic`)

---

## Authentication

Requires either a private API key or a JWT token from a public key.

```
X-API-Key: sk_your_private_key
```

Or:

```
Authorization: Bearer <jwt_token>
```

---

## Request Parameters

| Parameter | Type | Required | Default | Description |
|-----------|------|----------|---------|-------------|
| `file` | file | Yes | -- | The `.jpeg or .jpg` image file to convert. |
| `output_filename` | `string` | No | Input filename | Custom output filename. The `.heic` extension is added automatically. |
| `direct_download` | `boolean` | No | `true` | When `true`, returns raw image bytes. When `false`, returns JSON metadata with a presigned download URL. |

---

## Conversion Details

- Uses **Pillow** with **pillow-heif** for HEIC encoding
- JPEG's RGB color data is preserved in the HEIC output
- Output quality is set to maximum (100)
- HEIC typically achieves smaller file sizes than JPEG at equivalent quality


---

## Response

### Direct Download (`direct_download=true`, default)

```
HTTP 200 OK
Content-Type: image/heic
Content-Disposition: inline; filename="photo_20260405_123456789.heic"
```

Returns raw image bytes.

### Metadata Response (`direct_download=false`)

```json
{
    "presigned_url": "https://spaces.example.com/...",
    "object_key": "env/files/{project_id}/jpeg-to-heic/photo_20260405_123456789.heic",
    "filename": "photo_20260405_123456789.heic",
    "file_size": 45678,
    "conversion_time_seconds": 0.5
}
```

---

## Code Examples

### Python

```python
import requests

with open("photo.jpg", "rb") as f:
    response = requests.post(
        "https://api.enconvert.com/v1/convert/jpeg-to-heic",
        headers={"X-API-Key": "sk_your_private_key"},
        files={"file": ("photo.jpg", f)}
    )

with open("photo_20260405_123456789.heic", "wb") as out:
    out.write(response.content)
```

### Node.js

```javascript
const form = new FormData();
form.append("file", fs.createReadStream("photo.jpg"));

const response = await fetch("https://api.enconvert.com/v1/convert/jpeg-to-heic", {
    method: "POST",
    headers: { "X-API-Key": "sk_your_private_key" },
    body: form
});

fs.writeFileSync("photo_20260405_123456789.heic", Buffer.from(await response.arrayBuffer()));
```

### PHP

```php
$ch = curl_init("https://api.enconvert.com/v1/convert/jpeg-to-heic");
curl_setopt_array($ch, [
    CURLOPT_POST => true,
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_HTTPHEADER => ["X-API-Key: sk_your_private_key"],
    CURLOPT_POSTFIELDS => ["file" => new CURLFile("photo.jpg")]
]);
$output = curl_exec($ch);
curl_close($ch);
file_put_contents("photo_20260405_123456789.heic", $output);
```

### Go

```go
body := &bytes.Buffer{}
writer := multipart.NewWriter(body)
part, _ := writer.CreateFormFile("file", "photo.jpg")
file, _ := os.Open("photo.jpg")
io.Copy(part, file)
writer.Close()

req, _ := http.NewRequest("POST", "https://api.enconvert.com/v1/convert/jpeg-to-heic", body)
req.Header.Set("Content-Type", writer.FormDataContentType())
req.Header.Set("X-API-Key", "sk_your_private_key")
resp, _ := http.DefaultClient.Do(req)
```

---

## Error Responses

| Status | Condition |
|--------|-----------|
| `400 Bad Request` | File is not a `.jpeg or .jpg` file |
| `400 Bad Request` | Image conversion failed (corrupt or unsupported file) |
| `401 Unauthorized` | Missing or invalid API key / JWT token |
| `402 Payment Required` | Monthly ops allowance exhausted |
| `402 Payment Required` | Storage limit reached |
| `413 Payload Too Large` | File exceeds plan's maximum file size |

---

## Limits

| Limit | Value |
|-------|-------|
| Max file size | Plan-dependent (Founding: 5 MB) |
| Output quality | Maximum (not configurable) |
| Monthly conversions | Plan-dependent |

---

## Frequently asked questions

### How do I convert a JPG to HEIC with a REST API?

Send a `multipart/form-data` POST request to `/v1/convert/jpeg-to-heic` with your `.jpeg` or `.jpg` file in the `file` field, authenticated via `X-API-Key` or a `Bearer` JWT token. By default the API responds with the raw HEIC bytes.

### Does converting JPEG to HEIC reduce file size?

Typically yes, because HEIC usually achieves smaller file sizes than JPEG at equivalent quality. This endpoint encodes at maximum quality (100) using Pillow with pillow-heif.

### Can I get a download URL instead of raw image bytes?

Yes. Set `direct_download=false` and the API returns JSON metadata including a `presigned_url`, `object_key`, `filename`, `file_size`, and `conversion_time_seconds`.

### Why does the API return 402 Payment Required?

A `402` means your plan's monthly ops allowance or storage limit has been reached. Files exceeding your plan's maximum file size return `413 Payload Too Large` instead.
