Metadata-Version: 2.4
Name: coffeecode-cropper
Version: 1.0.0
Summary: Easy Python image thumbnail manager with on-disk cache and WebP output. Python fork of robsonvleite/cropper (PHP).
Project-URL: Homepage, https://github.com/kauelima21/coffeecode-cropper
Project-URL: Original PHP, https://github.com/robsonvleite/cropper
Project-URL: Issues, https://github.com/kauelima21/coffeecode-cropper/issues
Author-email: Kaue Leal <kaue.lima@totvs.com.br>
License: MIT
License-File: LICENSE
Keywords: cache,coffeecode,crop,fastapi,image,resize,thumbnail,webp
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Topic :: Multimedia :: Graphics
Requires-Python: >=3.9
Requires-Dist: pillow>=10.0.0
Provides-Extra: dev
Requires-Dist: pytest-cov>=4.0; extra == 'dev'
Requires-Dist: pytest>=7.0; extra == 'dev'
Description-Content-Type: text/markdown

# Cropper (Python)

Port em Python do pacote PHP [coffeecode/cropper](https://github.com/robsonvleite/cropper)
de Robson V. Leite. Gera **thumbnails JPG/PNG com cache em disco e saida WebP
por padrao**, com a mesma API de duas chamadas: `make()` e `flush()`. Pensado
para uso direto em Flask/FastAPI/scripts (sem dependencia de framework).

> Python port of the PHP package [coffeecode/cropper](https://github.com/robsonvleite/cropper)
> by Robson V. Leite. Generates JPG/PNG thumbnails with on-disk caching and
> WebP output by default. Two-method API (`make` and `flush`), framework-agnostic
> (Flask / FastAPI / scripts).

## Destaques

- API minima: `make(image, width[, height])` e `flush([image])`
- Cache no disco com chave por dimensao (regenera so quando muda)
- Saida WebP por padrao (opt-out com `webp=False`)
- Crop centralizado automatico quando `width` + `height` sao fornecidos
- Resize proporcional quando so `width`
- Pillow (substitui `ext-gd` + `webp-convert` do PHP)

## Instalacao

```bash
pip install coffeecode-cropper
```

Requer Python >= 3.9 e Pillow >= 10.

## Uso

```python
from coffeecode_cropper import Cropper

thumb = Cropper("cache", quality=75, compressor=5, webp=True)

# Resize proporcional pela largura
thumb.make("images/foto.jpg", 200)
# → "cache/foto-200-<hash>.webp"

# Crop centralizado para 400x400
thumb.make("images/foto.jpg", 400, 400)

# Banner widescreen
thumb.make("images/foto.jpg", 1200, 628)

# Limpa apenas as variacoes de uma imagem
thumb.flush("images/foto.jpg")

# Limpa todo o cache
thumb.flush()
```

### FastAPI

```python
from fastapi import FastAPI, HTTPException
from fastapi.responses import FileResponse
from coffeecode_cropper import Cropper, CropperException

app = FastAPI()
cropper = Cropper("cache", quality=80, webp=True)

@app.get("/thumb/{name}")
def thumb(name: str, w: int, h: int | None = None):
    try:
        return FileResponse(cropper.make(f"images/{name}", w, h))
    except CropperException as e:
        raise HTTPException(400, str(e))
```

Veja `example/fastapi_example.py` para versao com `flush()` exposto.

## API

### `Cropper(cache_path, quality=75, compressor=5, webp=True)`

| Parametro    | Tipo  | Descricao                                              |
|--------------|-------|--------------------------------------------------------|
| `cache_path` | `str \| Path` | Pasta onde os thumbs sao salvos. Criada se nao existir.|
| `quality`    | `int` | Qualidade JPEG (1-100), tambem usado para WebP.        |
| `compressor` | `int` | Nivel de compressao PNG (0-9).                         |
| `webp`       | `bool`| Converte saida para WebP (default `True`).             |

### `make(image_path, width, height=None) -> str`

Retorna o caminho do thumbnail (gera se nao existir, retorna do cache se sim).

- `width` apenas → resize proporcional
- `width` + `height` → crop centralizado para a proporcao alvo, depois resize

Excecoes:
- `ImageNotFoundError` — arquivo de origem nao existe
- `UnsupportedImageError` — origem nao e JPG/PNG
- `CropperException` — base; cobre arquivos corrompidos / falhas de I/O

### `flush(image_path=None) -> None`

- Sem argumentos: apaga todos os arquivos da pasta de cache.
- Com `image_path`: apaga apenas thumbs daquela imagem (matched via CRC32 do basename).

## Equivalencia com a versao PHP

| PHP                                         | Python                              |
|---------------------------------------------|-------------------------------------|
| `CoffeeCode\Cropper\Cropper`                | `coffeecode_cropper.Cropper`        |
| `make($img, $w, $h)`                        | `make(img, w, h)`                   |
| `flush($img)`                               | `flush(img)`                        |
| Erros como string ("Image not found")       | Excecoes (`ImageNotFoundError` etc.)|
| `ext-gd` + `rosell-dk/webp-convert`         | Pillow                              |
| `bool $webP = false` (default PHP)          | `webp: bool = True` (default Python)|

> **Diferencas intencionais:** errors viram excecoes (mais Pythonico) e o
> default de WebP foi promovido para `True` (alinhado com a recomendacao da v1.3+
> da versao PHP).

## Creditos

- API e design original: Robson V. Leite — [coffeecode/cropper](https://github.com/robsonvleite/cropper) (MIT)
- Port Python: Kaue Leal

## Licenca

MIT.
