mirror of
https://github.com/mealie-recipes/mealie.git
synced 2026-01-04 12:28:33 -05:00
Compare commits
8 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
70b5865dce | ||
|
|
3be7056f2c | ||
|
|
1b57310535 | ||
|
|
2b15d9a515 | ||
|
|
adc9c0b970 | ||
|
|
bec1708891 | ||
|
|
66bb545454 | ||
|
|
c1ebf04291 |
5
.gitignore
vendored
5
.gitignore
vendored
@@ -70,8 +70,11 @@ wheels/
|
||||
.installed.cfg
|
||||
*.egg
|
||||
|
||||
# packaged output - temporarily written here by `uv build`
|
||||
/mealie-*
|
||||
|
||||
# frontend copied into Python module for packaging purposes
|
||||
/mealie/frontend/
|
||||
/mealie/frontend
|
||||
|
||||
# PyInstaller
|
||||
# Usually these files are written by a python script from a template
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
###############################################
|
||||
# Frontend Build
|
||||
###############################################
|
||||
FROM node:24@sha256:20988bcdc6dc76690023eb2505dd273bdeefddcd0bde4bfd1efe4ebf8707f747 \
|
||||
FROM node:24@sha256:b52a8d1206132b36d60e51e413d9a81336e8a0206d3b648cabd6d5a49c4c0f54 \
|
||||
AS frontend-builder
|
||||
|
||||
WORKDIR /frontend
|
||||
|
||||
@@ -31,7 +31,7 @@ To deploy mealie on your local network, it is highly recommended to use Docker t
|
||||
We've gone through a few versions of Mealie v1 deployment targets. We have settled on a single container deployment, and we've begun publishing the nightly container on github containers. If you're looking to move from the old nightly (split containers _or_ the omni image) to the new nightly, there are a few things you need to do:
|
||||
|
||||
1. Take a backup just in case!
|
||||
2. Replace the image for the API container with `ghcr.io/mealie-recipes/mealie:v3.9.1`
|
||||
2. Replace the image for the API container with `ghcr.io/mealie-recipes/mealie:v3.9.2`
|
||||
3. Take the external port from the frontend container and set that as the port mapped to port `9000` on the new container. The frontend is now served on port 9000 from the new container, so it will need to be mapped for you to have access.
|
||||
4. Restart the container
|
||||
|
||||
|
||||
@@ -10,7 +10,7 @@ PostgreSQL might be considered if you need to support many concurrent users. In
|
||||
```yaml
|
||||
services:
|
||||
mealie:
|
||||
image: ghcr.io/mealie-recipes/mealie:v3.9.1 # (3)
|
||||
image: ghcr.io/mealie-recipes/mealie:v3.9.2 # (3)
|
||||
container_name: mealie
|
||||
restart: always
|
||||
ports:
|
||||
|
||||
@@ -11,7 +11,7 @@ SQLite is a popular, open source, self-contained, zero-configuration database th
|
||||
```yaml
|
||||
services:
|
||||
mealie:
|
||||
image: ghcr.io/mealie-recipes/mealie:v3.9.1 # (3)
|
||||
image: ghcr.io/mealie-recipes/mealie:v3.9.2 # (3)
|
||||
container_name: mealie
|
||||
restart: always
|
||||
ports:
|
||||
|
||||
@@ -10,11 +10,8 @@
|
||||
:label="$t('form.quantity-label-abbreviated')"
|
||||
:min="0"
|
||||
:precision="null"
|
||||
variant="plain"
|
||||
control-variant="stacked"
|
||||
inset
|
||||
density="compact"
|
||||
class="centered-number-input"
|
||||
style="width: 100px;"
|
||||
/>
|
||||
</div>
|
||||
@@ -242,10 +239,3 @@ export default defineNuxtComponent({
|
||||
},
|
||||
});
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.centered-number-input :deep(.v-field) {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -31,7 +31,7 @@ export default defineNuxtComponent({
|
||||
],
|
||||
ALLOWED_ATTR: [
|
||||
"href", "src", "alt", "height", "width", "class", "allow", "title", "allowfullscreen", "frameborder",
|
||||
"scrolling", "cite", "datetime", "name", "abbr", "target", "border",
|
||||
"scrolling", "cite", "datetime", "name", "abbr", "target", "border", "start",
|
||||
],
|
||||
});
|
||||
|
||||
|
||||
@@ -342,9 +342,9 @@
|
||||
"breakfast": "Café da manhã",
|
||||
"lunch": "Almoço",
|
||||
"dinner": "Jantar",
|
||||
"snack": "Snack",
|
||||
"drink": "Drink",
|
||||
"dessert": "Dessert",
|
||||
"snack": "Lanche",
|
||||
"drink": "Bebida",
|
||||
"dessert": "Sobremesa",
|
||||
"type-any": "Qualquer",
|
||||
"day-any": "Qualquer",
|
||||
"editor": "Editor",
|
||||
@@ -445,7 +445,7 @@
|
||||
"upload-a-recipe": "Enviar uma Receita",
|
||||
"upload-individual-zip-file": "Enviar um arquivo .zip individual exportado a partir de outra instância do Mealie.",
|
||||
"url-form-hint": "Copie e cole um link do seu site de receita favorito",
|
||||
"copy-and-paste-the-source-url-of-your-data-optional": "Copy and paste the source URL of your data (optional)",
|
||||
"copy-and-paste-the-source-url-of-your-data-optional": "Copie e cole o URL de origem dos seus dados (opcional)",
|
||||
"view-scraped-data": "Visualizar Dados Rastreados",
|
||||
"trim-whitespace-description": "Aparar o espaço em branco e à direita, bem como linhas em branco",
|
||||
"trim-prefix-description": "Aparar primeiro caractere de cada linha",
|
||||
@@ -637,8 +637,8 @@
|
||||
"scrape-recipe-suggest-bulk-importer": "Tente o importador em massa",
|
||||
"scrape-recipe-have-raw-html-or-json-data": "Tem dados HTML ou JSON brutos?",
|
||||
"scrape-recipe-you-can-import-from-raw-data-directly": "Você pode importar diretamente de dados brutos",
|
||||
"scrape-recipe-website-being-blocked": "Website being blocked?",
|
||||
"scrape-recipe-try-importing-raw-html-instead": "Try importing the raw HTML instead.",
|
||||
"scrape-recipe-website-being-blocked": "Site sendo bloqueado?",
|
||||
"scrape-recipe-try-importing-raw-html-instead": "Tente importar o HTML ao invés disso.",
|
||||
"import-original-keywords-as-tags": "Importar palavras-chave originais como marcadores",
|
||||
"stay-in-edit-mode": "Permanecer no modo de edição",
|
||||
"parse-recipe-ingredients-after-import": "Interpretar os ingredientes da receita após importar",
|
||||
@@ -1430,11 +1430,11 @@
|
||||
}
|
||||
},
|
||||
"validators": {
|
||||
"required": "This Field is Required",
|
||||
"invalid-email": "Email Must Be Valid",
|
||||
"invalid-url": "Must Be A Valid URL",
|
||||
"no-whitespace": "No Whitespace Allowed",
|
||||
"min-length": "Must Be At Least {min} Characters",
|
||||
"max-length": "Must Be At Most {max} Characters"
|
||||
"required": "Este campo é obrigatório",
|
||||
"invalid-email": "O e-mail deve ser válido",
|
||||
"invalid-url": "Precisa ser uma URL válida",
|
||||
"no-whitespace": "Nenhum espaço em branco é permitido",
|
||||
"min-length": "Precisa ter pelo menos {min} caracteres",
|
||||
"max-length": "Pode ter até {max} caracteres"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "mealie",
|
||||
"version": "3.9.1",
|
||||
"version": "3.9.2",
|
||||
"private": true,
|
||||
"scripts": {
|
||||
"dev": "nuxt dev",
|
||||
|
||||
@@ -5043,14 +5043,14 @@
|
||||
"hake": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "hake",
|
||||
"plural_name": "hakes"
|
||||
"name": "merlu",
|
||||
"plural_name": "merlus"
|
||||
},
|
||||
"pollock": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "pollock",
|
||||
"plural_name": "pollocks"
|
||||
"name": "lieu noir",
|
||||
"plural_name": "lieu noir"
|
||||
},
|
||||
"salt cod": {
|
||||
"aliases": [],
|
||||
@@ -5217,8 +5217,8 @@
|
||||
"pike": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "pike",
|
||||
"plural_name": "pikes"
|
||||
"name": "brochet",
|
||||
"plural_name": "brochets"
|
||||
},
|
||||
"pickled herring": {
|
||||
"aliases": [],
|
||||
@@ -5469,8 +5469,8 @@
|
||||
"tiny fish": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "tiny fish",
|
||||
"plural_name": "tiny fish"
|
||||
"name": "petit poisson",
|
||||
"plural_name": "petits poissons"
|
||||
},
|
||||
"tuna belly": {
|
||||
"aliases": [],
|
||||
@@ -5569,8 +5569,8 @@
|
||||
"crawfish": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "crawfish",
|
||||
"plural_name": "crawfish"
|
||||
"name": "écrevisse",
|
||||
"plural_name": "écrevisses"
|
||||
},
|
||||
"octopu": {
|
||||
"aliases": [],
|
||||
@@ -5635,8 +5635,8 @@
|
||||
"squid ink": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "squid ink",
|
||||
"plural_name": "squid inks"
|
||||
"name": "encre de seiche",
|
||||
"plural_name": "encres de seiches"
|
||||
},
|
||||
"dried prawn": {
|
||||
"aliases": [],
|
||||
@@ -5719,8 +5719,8 @@
|
||||
"sea urchin": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "sea urchin",
|
||||
"plural_name": "sea urchins"
|
||||
"name": "oursin",
|
||||
"plural_name": "oursins"
|
||||
},
|
||||
"abalone": {
|
||||
"aliases": [],
|
||||
@@ -5743,8 +5743,8 @@
|
||||
"smoked mussel": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "smoked mussel",
|
||||
"plural_name": "smoked mussels"
|
||||
"name": "moule fumée",
|
||||
"plural_name": "moules fumées"
|
||||
},
|
||||
"sea snail": {
|
||||
"aliases": [],
|
||||
@@ -5761,8 +5761,8 @@
|
||||
"prepared crab cake": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "prepared crab cake",
|
||||
"plural_name": "prepared crab cakes"
|
||||
"name": "gâteau de crabe",
|
||||
"plural_name": "gâteaux de crabe"
|
||||
},
|
||||
"sea lettuce": {
|
||||
"aliases": [],
|
||||
@@ -6095,8 +6095,8 @@
|
||||
"chipotle": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "chipotle",
|
||||
"plural_name": "chipotles"
|
||||
"name": "piment chipotle",
|
||||
"plural_name": "piments chipotles"
|
||||
},
|
||||
"fenugreek": {
|
||||
"aliases": [],
|
||||
@@ -6107,8 +6107,8 @@
|
||||
"onion flake": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "onion flake",
|
||||
"plural_name": "onion flakes"
|
||||
"name": "oignon émincé",
|
||||
"plural_name": "oignons émincés"
|
||||
},
|
||||
"matcha powder": {
|
||||
"aliases": [],
|
||||
@@ -6263,8 +6263,8 @@
|
||||
"garlic flake": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "garlic flake",
|
||||
"plural_name": "garlic flakes"
|
||||
"name": "ail émincé",
|
||||
"plural_name": "aulx émincés"
|
||||
},
|
||||
"dried cilantro": {
|
||||
"aliases": [],
|
||||
@@ -15705,7 +15705,7 @@
|
||||
"almond extract": {
|
||||
"aliases": [],
|
||||
"description": "",
|
||||
"name": "extrait d'amandes",
|
||||
"name": "extrait d'amande",
|
||||
"plural_name": "extraits d'amandes"
|
||||
},
|
||||
"food coloring": {
|
||||
|
||||
@@ -4,7 +4,7 @@ from concurrent.futures import ThreadPoolExecutor, as_completed
|
||||
from pathlib import Path
|
||||
|
||||
import sqlalchemy as sa
|
||||
from PIL import Image
|
||||
from PIL import Image, UnidentifiedImageError
|
||||
from pydantic import UUID4
|
||||
|
||||
from mealie.core import root_logger
|
||||
@@ -84,7 +84,12 @@ def reprocess_recipe_images(recipe_id: UUID4, force_all: bool = False) -> None:
|
||||
image_file = service.dir_image / image_filename
|
||||
image_file.unlink(missing_ok=True)
|
||||
|
||||
service.minifier.minify(original_image, force=True)
|
||||
try:
|
||||
service.minifier.minify(original_image, force=True)
|
||||
except UnidentifiedImageError:
|
||||
pass # source image is corrupted or invalid; skip
|
||||
except Exception:
|
||||
logger.exception(f"Failed to reprocess images for recipe {recipe_id}")
|
||||
|
||||
# Reprocess timeline event images
|
||||
timeline_dir = service.dir_image_timeline
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[project]
|
||||
name = "mealie"
|
||||
version = "3.9.1"
|
||||
version = "3.9.2"
|
||||
description = "A Recipe Manager"
|
||||
authors = [{ name = "Hayden", email = "hay-kot@pm.me" }]
|
||||
license = "AGPL-3.0-only"
|
||||
|
||||
Reference in New Issue
Block a user