# Dividir un PDF por tamaño de archivo

Divida un PDF en documentos más pequeños, cada uno sin superar un tamaño máximo en bytes.

Divida un documento PDF en varios documentos más pequeños, cada uno sin
superar un tamaño máximo de archivo en bytes. Esta acción devuelve varios
documentos, empaquetados en una sola respuesta según la cabecera `Accept`. La
API es *stateless*: su documento se procesa en la región y nunca se almacena.

## Endpoint

<Endpoint method="POST" path="/v1/split_by_size" />

Disponible en todas las regiones. Consulte [Regiones y residencia de
datos](/docs/api/regions-and-data-residency) para el enrutamiento y la
residencia de datos.

| Región           | URL                                                |
| ---------------- | -------------------------------------------------- |
| Global           | `https://api.pdfblocks.com/v1/split_by_size`       |
| Estados Unidos   | `https://us.api.pdfblocks.com/v1/split_by_size`    |
| HIPAA de EE. UU. | `https://hipaa.api.pdfblocks.com/v1/split_by_size` |
| Unión Europea    | `https://eu.api.pdfblocks.com/v1/split_by_size`    |
| Reino Unido      | `https://uk.api.pdfblocks.com/v1/split_by_size`    |
| Canadá           | `https://ca.api.pdfblocks.com/v1/split_by_size`    |
| Australia        | `https://au.api.pdfblocks.com/v1/split_by_size`    |
| Japón            | `https://jp.api.pdfblocks.com/v1/split_by_size`    |
| India            | `https://in.api.pdfblocks.com/v1/split_by_size`    |
| Brasil           | `https://br.api.pdfblocks.com/v1/split_by_size`    |

## Autenticación

Autentique cada solicitud con su clave de API secreta en la cabecera
`X-API-Key`, por HTTPS. Cree y administre sus claves desde el
[dashboard](https://dashboard.pdfblocks.com). Consulte
[Autenticación](/docs/api/authentication) para más detalles.

## Solicitud

El endpoint acepta un cuerpo de solicitud `multipart/form-data`.

<ParamField name="file" type="file" required>
  El documento PDF de entrada.
</ParamField>

<ParamField name="maximum_bytes" type="integer" required>
  El tamaño máximo, en bytes, de cada PDF de salida. Debe ser `1` o mayor.
</ParamField>

## Ejemplos

Divida un documento para que cada parte tenga como máximo 1 MB:

<CodeGroup>

```bash title="cURL"
curl https://api.pdfblocks.com/v1/split_by_size \
  -H 'X-API-Key: your_api_key' \
  -F file=@input.pdf \
  -F maximum_bytes=1048576 \
  -o parts.zip
```

```python title="Python"
# pip install requests
import requests

with open('input.pdf', 'rb') as file:
    response = requests.post(
        'https://api.pdfblocks.com/v1/split_by_size',
        headers={'X-API-Key': 'your_api_key'},
        files={'file': file},
        data={'maximum_bytes': 1048576},  # 1 MB
    )

response.raise_for_status()
with open('parts.zip', 'wb') as output:
    output.write(response.content)
```

```javascript title="Node.js"
// Node.js 18+
import { readFile, writeFile } from 'node:fs/promises';

const body = new FormData();
body.set('file', new Blob([await readFile('input.pdf')]), 'input.pdf');
body.set('maximum_bytes', '1048576'); // 1 MB

const response = await fetch('https://api.pdfblocks.com/v1/split_by_size', {
  method: 'POST',
  headers: { 'X-API-Key': 'your_api_key' },
  body,
});

if (!response.ok) throw new Error(`Request failed: ${response.status}`);
await writeFile('parts.zip', Buffer.from(await response.arrayBuffer()));
```

```php title="PHP"
<?php
$ch = curl_init('https://api.pdfblocks.com/v1/split_by_size');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_HTTPHEADER => ['X-API-Key: your_api_key'],
    CURLOPT_POST => true,
    CURLOPT_POSTFIELDS => [
        'file' => new CURLFile('input.pdf', 'application/pdf'),
        'maximum_bytes' => '1048576', // 1 MB
    ],
]);

$zip = curl_exec($ch);
if (curl_getinfo($ch, CURLINFO_HTTP_CODE) === 200) {
    file_put_contents('parts.zip', $zip);
}
```

```ruby title="Ruby"
# gem install http
require 'http'

response = HTTP
  .headers('X-API-Key' => 'your_api_key')
  .post('https://api.pdfblocks.com/v1/split_by_size', form: {
    file: HTTP::FormData::File.new('input.pdf'),
    maximum_bytes: '1048576', # 1 MB
  })

File.write('parts.zip', response.body) if response.status.success?
```

```go title="Go"
package main

import (
	"bytes"
	"io"
	"mime/multipart"
	"net/http"
	"os"
)

func main() {
	var buf bytes.Buffer
	form := multipart.NewWriter(&buf)

	file, _ := os.Open("input.pdf")
	defer file.Close()
	part, _ := form.CreateFormFile("file", "input.pdf")
	io.Copy(part, file)

	form.WriteField("maximum_bytes", "1048576") // 1 MB
	form.Close()

	req, _ := http.NewRequest("POST", "https://api.pdfblocks.com/v1/split_by_size", &buf)
	req.Header.Set("Content-Type", form.FormDataContentType())
	req.Header.Set("X-API-Key", "your_api_key")

	res, _ := http.DefaultClient.Do(req)
	defer res.Body.Close()

	out, _ := os.Create("parts.zip")
	defer out.Close()
	io.Copy(out, res.Body)
}
```

```csharp title="C#"
using var client = new HttpClient();
client.DefaultRequestHeaders.Add("X-API-Key", "your_api_key");

using var form = new MultipartFormDataContent
{
    { new ByteArrayContent(File.ReadAllBytes("input.pdf")), "file", "input.pdf" },
    { new StringContent("1048576"), "maximum_bytes" }, // 1 MB
};

var response = await client.PostAsync(
    "https://api.pdfblocks.com/v1/split_by_size", form);
response.EnsureSuccessStatusCode();
await File.WriteAllBytesAsync(
    "parts.zip", await response.Content.ReadAsByteArrayAsync());
```

</CodeGroup>

## Respuesta

Esta acción devuelve varios documentos, empaquetados en una sola respuesta
según la cabecera de solicitud `Accept`: consulte [Formatos de respuesta y
negociación de contenido](/docs/api/response-formats) para ver la referencia
completa de la negociación. Sin cabecera `Accept`, la opción predeterminada
es un archivo ZIP:

```http
HTTP/1.1 200 OK
Content-Type: application/zip
```

Seleccione el empaquetado con la cabecera `Accept`:

| Cabecera `Accept`    | Respuesta                                                      |
| -------------------- | -------------------------------------------------------------- |
| *(no se envía)*      | `application/zip`: la opción predeterminada                    |
| `application/zip`    | Un archivo ZIP con los PDF de salida                           |
| `application/json`   | Un sobre JSON con los documentos codificados en base64         |
| `multipart/mixed`    | Un PDF por parte                                               |
| cualquier otra cosa  | `406 Not Acceptable`                                           |

Los documentos de salida se llaman `00001.pdf`, `00002.pdf` y así
sucesivamente, en orden.

<Note>
  Cada parte se llena de páginas hasta quedar justo por debajo de
  `maximum_bytes` según el tamaño de salida generado, así que las partes se
  acercan al límite pero nunca lo superan. La excepción es una página cuyo propio tamaño ya
  supera `maximum_bytes`: se devuelve como una parte propia que excede el
  límite, porque una página nunca se divide.
</Note>

<Tip>
  Para ver código de principio a fin que llama a una acción de división y
  desempaqueta cada formato, ya sea extrayendo el ZIP, decodificando el sobre
  JSON o leyendo las partes multipart, consulte la guía [Dividir un
  PDF](/docs/api/splitting-a-pdf).
</Tip>

## Errores

Las solicitudes fallidas devuelven un cuerpo `application/problem+json`. El
error más habitual en este endpoint es un `400`, que se devuelve cuando falta
`maximum_bytes` o es menor que `1`, o cuando `file` no es un PDF legible: el
objeto `errors` nombra cada campo:

```json
{
  "type": "https://www.pdfblocks.com/docs/api/v1/error/400",
  "title": "One or more validation errors occurred.",
  "status": 400,
  "errors": {
    "maximum_bytes": ["The field maximum_bytes must be greater than or equal to 1."]
  }
}
```

Si la cabecera `Accept` no coincide con `application/zip`, `application/json`
ni `multipart/mixed`, por ejemplo `Accept: application/pdf`, la API responde
con `406 Not Acceptable`. Omita `Accept` para tomar el ZIP predeterminado, o
solicite uno de los tipos de medio admitidos. Una `X-API-Key` ausente o no
válida devuelve un `401`. Consulte [Errores](/docs/api/errors) para ver todos
los códigos de estado y la forma completa de la respuesta.

## Recetas

Una variante habitual. Despliéguela para ver el código en todos los
lenguajes.

<AccordionGroup>

<Accordion title="Recibir las partes como un sobre JSON">

Envíe `Accept: application/json` para recibir todas las partes en línea en
una sola respuesta y después decodifique de base64 el `content` de cada
entrada en un archivo con el nombre de su `name`:

<CodeGroup>

```bash title="cURL"
curl https://api.pdfblocks.com/v1/split_by_size \
  -H 'X-API-Key: your_api_key' \
  -H 'Accept: application/json' \
  -F file=@input.pdf \
  -F maximum_bytes=1048576 \
  | jq -r '.documents[] | .name + " " + .content' \
  | while read -r name content; do
      echo "$content" | base64 --decode > "$name"
    done
```

```python title="Python"
# pip install requests
import base64
import requests

with open('input.pdf', 'rb') as file:
    response = requests.post(
        'https://api.pdfblocks.com/v1/split_by_size',
        headers={
            'X-API-Key': 'your_api_key',
            'Accept': 'application/json',
        },
        files={'file': file},
        data={'maximum_bytes': 1048576},
    )

response.raise_for_status()
for document in response.json()['documents']:
    with open(document['name'], 'wb') as output:
        output.write(base64.b64decode(document['content']))
```

```javascript title="Node.js"
// Node.js 18+
import { readFile, writeFile } from 'node:fs/promises';

const body = new FormData();
body.set('file', new Blob([await readFile('input.pdf')]), 'input.pdf');
body.set('maximum_bytes', '1048576');

const response = await fetch('https://api.pdfblocks.com/v1/split_by_size', {
  method: 'POST',
  headers: { 'X-API-Key': 'your_api_key', Accept: 'application/json' },
  body,
});

if (!response.ok) throw new Error(`Request failed: ${response.status}`);
const { documents } = await response.json();
for (const doc of documents) {
  await writeFile(doc.name, Buffer.from(doc.content, 'base64'));
}
```

```php title="PHP"
<?php
$ch = curl_init('https://api.pdfblocks.com/v1/split_by_size');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_HTTPHEADER => [
        'X-API-Key: your_api_key',
        'Accept: application/json',
    ],
    CURLOPT_POST => true,
    CURLOPT_POSTFIELDS => [
        'file' => new CURLFile('input.pdf', 'application/pdf'),
        'maximum_bytes' => '1048576',
    ],
]);

$body = curl_exec($ch);
if (curl_getinfo($ch, CURLINFO_HTTP_CODE) === 200) {
    foreach (json_decode($body, true)['documents'] as $document) {
        file_put_contents($document['name'], base64_decode($document['content']));
    }
}
```

```ruby title="Ruby"
# gem install http
require 'base64'
require 'http'
require 'json'

response = HTTP
  .headers('X-API-Key' => 'your_api_key', 'Accept' => 'application/json')
  .post('https://api.pdfblocks.com/v1/split_by_size', form: {
    file: HTTP::FormData::File.new('input.pdf'),
    maximum_bytes: '1048576',
  })

if response.status.success?
  JSON.parse(response.body)['documents'].each do |document|
    File.write(document['name'], Base64.decode64(document['content']))
  end
end
```

```go title="Go"
package main

import (
	"bytes"
	"encoding/base64"
	"encoding/json"
	"io"
	"mime/multipart"
	"net/http"
	"os"
)

func main() {
	var buf bytes.Buffer
	form := multipart.NewWriter(&buf)

	file, _ := os.Open("input.pdf")
	defer file.Close()
	part, _ := form.CreateFormFile("file", "input.pdf")
	io.Copy(part, file)

	form.WriteField("maximum_bytes", "1048576")
	form.Close()

	req, _ := http.NewRequest("POST", "https://api.pdfblocks.com/v1/split_by_size", &buf)
	req.Header.Set("Content-Type", form.FormDataContentType())
	req.Header.Set("X-API-Key", "your_api_key")
	req.Header.Set("Accept", "application/json")

	res, _ := http.DefaultClient.Do(req)
	defer res.Body.Close()

	var result struct {
		Documents []struct {
			Name    string `json:"name"`
			Content string `json:"content"`
		} `json:"documents"`
	}
	json.NewDecoder(res.Body).Decode(&result)

	for _, doc := range result.Documents {
		data, _ := base64.StdEncoding.DecodeString(doc.Content)
		os.WriteFile(doc.Name, data, 0644)
	}
}
```

```csharp title="C#"
using System.Text.Json;

using var client = new HttpClient();
client.DefaultRequestHeaders.Add("X-API-Key", "your_api_key");
client.DefaultRequestHeaders.Add("Accept", "application/json");

using var form = new MultipartFormDataContent
{
    { new ByteArrayContent(File.ReadAllBytes("input.pdf")), "file", "input.pdf" },
    { new StringContent("1048576"), "maximum_bytes" },
};

var response = await client.PostAsync(
    "https://api.pdfblocks.com/v1/split_by_size", form);
response.EnsureSuccessStatusCode();

using var json = JsonDocument.Parse(
    await response.Content.ReadAsStringAsync());
foreach (var document in json.RootElement.GetProperty("documents").EnumerateArray())
{
    var name = document.GetProperty("name").GetString()!;
    var content = document.GetProperty("content").GetString()!;
    await File.WriteAllBytesAsync(name, Convert.FromBase64String(content));
}
```

</CodeGroup>

</Accordion>

</AccordionGroup>

## Acciones relacionadas

<CardGroup cols={2}>

<Card title="Dividir por número de páginas" href="/docs/api/split-pdf-by-page-count">
  Divida por número de páginas en lugar de por bytes.
</Card>

<Card title="Dividir en una página" href="/docs/api/split-pdf-at-page">
  Divida en dos documentos en un límite.
</Card>

<Card title="Dividir en grupos de páginas" href="/docs/api/split-pdf-into-page-groups">
  Defina a mano grupos de páginas arbitrarios.
</Card>

<Card title="Extraer páginas" href="/docs/api/extract-pages-from-pdf">
  Conserve un rango de páginas.
</Card>

</CardGroup>
