Points clés à retenir
- Conservez l’Auth Secret Transloadit dans un module
server-onlyet ne renvoyez que des options d’Assembly signées à courte durée de validité. - Contrôlez les autorisations et limitez le débit des requêtes du Route Handler de signature ; connaître une URL de l’application ne donne pas l’autorisation de téléverser.
- Verrouillez le Template enregistré, exigez des signatures et réappliquez les restrictions de fichiers côté client à un point de contrôle de confiance du traitement.
Sécuriser un téléversement depuis le navigateur ne se limite pas à déplacer l’Auth Secret dans une route API. Le serveur doit autoriser chaque demande de signature, la charge utile signée doit désigner un Template aux opérations limitées, le destinataire doit faire respecter la politique relative aux fichiers et l’application doit réconcilier l’état du traitement après que l’utilisateur a quitté la page. Cette architecture App Router rend chaque responsabilité explicite.
L’essentiel
- Créez une seule instance d’Uppy pour le composant client et laissez le plugin Transloadit maintenu coordonner le transfert avec reprise.
- Traitez la progression affichée dans le navigateur comme celle du transfert et utilisez des notifications vérifiées pour enregistrer durablement la fin du traitement.
- Stockez les informations d’identification pour le stockage d’un prestataire externe dans des ensembles d’informations d’identification de Template limités aux privilèges minimaux, plutôt que dans les champs de requête ou les variables d’environnement côté client.
Séparer l’autorisation applicative de l’exécution du téléversement
Le navigateur est un appelant non fiable, même lorsque l’interface fait partie de votre application Next.js. Un Client Component peut contenir l’Auth Key publique et un identifiant de Template, mais il ne doit jamais contenir l’Auth Secret du Workspace, des informations d’identification brutes pour le stockage ou le pouvoir de choisir arbitrairement des Steps de traitement. Gardez l’Auth Secret derrière un Route Handler et faites décider ce point de terminaison si l’utilisateur actuel de l’application peut lancer ce téléversement précis.
Cette décision est distincte de l’intégrité de la requête Transloadit. Une signature valide prouve que votre serveur a approuvé les paramètres sérialisés de l’Assembly pour une durée limitée ; elle ne prouve pas que la personne qui demande une signature à votre serveur possède un projet, reste dans les limites de son quota, a passé un contrôle CSRF ou peut publier le résultat. L’adaptateur d’autorisation applicative doit faire respecter ces règles avant de signer. Le Template enregistré limite ensuite ce que Transloadit exécutera.
Next.js
Le code applicatif authentifie la session, vérifie la propriété des ressources et la politique CSRF, applique des limites de débit ou de quota et émet des options signées propres à chaque usage.
Uppy
Prend en charge la sélection des fichiers, l’interface de téléversement accessible, les restrictions du navigateur, la progression, les nouvelles tentatives et l’orchestration des transferts avec reprise après interruption.
Transloadit
Crée l’Assembly, fait respecter la requête signée et le Template enregistré, inspecte les fichiers, exécute le traitement et exporte les résultats configurés.
Verrouiller le Template avant d’exposer le formulaire de téléversement
Créez le flux de traitement sous forme de Template enregistré. Définissez allow_steps_override sur false afin qu’un navigateur ne puisse pas soumettre des Steps de remplacement en même temps que template_id. Activez « Exiger une signature valide » sur ce Template, ou exigez des signatures correctes pour l’ensemble du Workspace. Il s’agit de contrôles distincts : le Template verrouillé fige le graphe de traitement, tandis que la validation obligatoire des signatures rejette les paramètres signés modifiés, expirés ou invalides pour toute autre raison. C’est toujours votre application qui décide quel utilisateur peut recevoir ces paramètres.
Répétez les contrôles peu coûteux de l’interface à l’entrée du traitement. L’exemple limite la taille totale attendue du téléversement de l’Assembly à 50 MiB, surcoût du corps de la requête compris, limite une Assembly à cinq fichiers et utilise /file/filter sur les métadonnées MIME détectées plutôt que de se fier au nom du fichier ou à la déclaration du navigateur. auth.max_size n’est pas une limite par fichier. Le paramètre maxTotalFileSize du navigateur ne vérifie que les octets des fichiers ; cet exemple le limite donc à 48 MiB, laissant une marge indicative de 2 MiB sous la limite du serveur. Le surcoût de la requête varie : le refus du serveur fait donc autorité même lorsque le navigateur accepte la sélection. Adaptez la liste exacte des éléments autorisés au produit. Ajoutez une vérification, une analyse antimalware, une mise en quarantaine ou un examen humain lorsque le risque lié au contenu l’exige ; aucun contrôle MIME à lui seul ne garantit la sûreté d’un contenu utilisateur arbitraire.
La valeur user_uploads désigne un ensemble d’informations d’identification de Template stocké dans le Workspace. N’accordez à cette identité externe que les opérations de stockage, le bucket et les chemins nécessaires à ce flux de travail. Utilisez un bucket privé avec Block Public Access activé. La valeur explicite acl: "bucket-default" remplace la valeur par défaut public-read du Robot et omet l’en-tête ACL, y compris pour les buckets dont les ACL sont désactivées ; les politiques du bucket et d’IAM continuent de contrôler l’accès. Le paramètre path maintient les exports sous uploads/ avec des clés propres à chaque Assembly et à chaque fichier. Le navigateur ne reçoit ni ne signe la clé d’accès sous-jacente. La rotation des informations d’identification peut alors se faire indépendamment du bundle Next.js, mais elle doit être coordonnée, car chaque Template qui référence cet ensemble est affecté.
{
"allow_steps_override": false,
"auth": {
"max_number_of_files": 5,
"max_size": 52428800
},
"notify_url": "https://app.example.com/api/transloadit-notifications",
"steps": {
":original": {
"robot": "/upload/handle"
},
"accepted_images": {
"use": ":original",
"robot": "/file/filter",
"accepts": [
["${file.mime}", "regex", "^(image/jpeg|image/png|image/webp)$"]
],
"error_on_decline": true,
"error_msg": "Only JPEG, PNG, and WebP images are accepted"
},
"stored": {
"use": "accepted_images",
"robot": "/s3/store",
"credentials": "user_uploads",
"acl": "bucket-default",
"path": "uploads/${assembly.id}/${file.id}/${file.url_name}"
}
}
}Signer une seule requête à courte durée de validité dans un module server-only
Conservez la configuration du serveur dans des variables d’environnement sans préfixe NEXT_PUBLIC_ et importez server-only en tête du module de signature. Next.js fera échouer la compilation si du code client importe ce module. Ce marqueur est un garde-fou utile, pas un gestionnaire de secrets : les politiques d’accès en production, le masquage des informations sensibles dans les journaux, l’isolation des environnements de prévisualisation et la rotation des informations d’identification restent essentiels.
Le SDK @transloadit/node ajoute l’Auth Key configurée, sérialise les paramètres et renvoie cette chaîne params exacte avec sa signature. Renvoyez les deux valeurs sans les modifier. Analyser la chaîne, ajouter un champ ou la sérialiser à nouveau dans un ordre différent après la signature produit une charge utile différente qui devrait être rejetée. L’exemple fixe une expiration de cinq minutes, car Uppy demande les options immédiatement avant la création de l’Assembly. Il ajoute également un nouveau params.nonce au niveau racine pour chaque autorisation.
Sélectionnez le Template sur le serveur. N’acceptez pas les valeurs template_id, steps, notify_url, les informations d’identification pour l’export ou des valeurs de transformation sans bornes provenant du corps de la requête pour les signer aveuglément. Si le produit propose effectivement plusieurs flux de téléversement, associez une opération applicative limitée, telle que avatar ou product-gallery, à un Template figurant dans une liste d’autorisation et à des limites, après avoir vérifié les permissions de l’utilisateur.
import 'server-only'
import { randomUUID } from 'node:crypto'
import { Transloadit } from '@transloadit/node'
export interface AssemblyOptions {
params: string
signature: string
}
type TransloaditEnvironmentName =
| 'TRANSLOADIT_KEY'
| 'TRANSLOADIT_SECRET'
| 'TRANSLOADIT_TEMPLATE_ID'
function readServerEnvironment(name: TransloaditEnvironmentName): string {
const value = process.env[name]
if (value == null || value === '') {
throw new Error('Missing Transloadit server configuration')
}
return value
}
const templateId = readServerEnvironment('TRANSLOADIT_TEMPLATE_ID')
const transloadit = new Transloadit({
authKey: readServerEnvironment('TRANSLOADIT_KEY'),
authSecret: readServerEnvironment('TRANSLOADIT_SECRET'),
})
export function createAssemblyOptions(): AssemblyOptions {
const requestParameters = {
auth: {
expires: new Date(Date.now() + 5 * 60 * 1000).toISOString(),
},
nonce: randomUUID(),
template_id: templateId,
}
return transloadit.calcSignature(requestParameters)
}Protéger le point de terminaison de signature App Router
Un Route Handler est accessible comme tout autre point de terminaison HTTP. La fonction authorizeUpload de l’exemple est volontairement propre à l’application : reliez-la à la bibliothèque de gestion des sessions existante du projet, aux contrôles de propriété des ressources, à la stratégie CSRF et au limiteur de débit partagé. Renvoyez le refus avant de générer la signature. Pour les applications multitenant, définissez les limites à la fois par tenant et par utilisateur, et vérifiez le tenant auquel appartiendra la ressource finale.
La route n’accepte aucun paramètre arbitraire d’Assembly et marque la réponse de succès avec no-store. Le message d’échec public reste volontairement générique. Consignez côté serveur un identifiant interne de requête ou de trace, la catégorie de décision et l’identifiant de l’acteur, mais ne renvoyez au navigateur ni traces de pile, ni identifiants de compte, ni corps de réponse de services tiers, ni informations d’identification. Laissez les échecs inattendus passer par la gestion centralisée des erreurs de l’application, qui en retire les données sensibles, plutôt que d’envelopper chaque appel dans un bloc catch bruyant.
Limiter la fréquence des appels à la route de signature contrôle la création des Assemblies, mais ne remplace ni les plafonds de facturation du compte, ni les limites de fichiers du Template, ni les quotas de l’application. Appliquez les trois. Une signature est une capacité d’accès de courte durée : toute personne qui obtient la charge utile signée complète peut tenter de la soumettre tant qu’elle reste valide. Transmettez-la donc uniquement via HTTPS et évitez les outils d’analyse, le stockage du navigateur, les URL et les journaux qui la conservent.
import type { NextRequest } from 'next/server'
import { NextResponse } from 'next/server'
import { authorizeUpload } from '../../../server/upload-authorization'
import {
type AssemblyOptions,
createAssemblyOptions,
} from '../../../server/transloadit-options'
interface ErrorResponse {
error: string
}
export async function POST(
request: NextRequest,
): Promise<NextResponse<AssemblyOptions | ErrorResponse>> {
const permission = await authorizeUpload(request)
if (!permission.allowed) {
return NextResponse.json({ error: 'Upload not allowed' }, { status: 403 })
}
return NextResponse.json(createAssemblyOptions(), {
headers: { 'Cache-Control': 'no-store' },
})
}Authentifier
Récupérez une session à jour côté serveur au lieu de faire confiance à un identifiant d’utilisateur ou de tenant fourni par le client.
Autoriser
Vérifiez que l’acteur est autorisé à téléverser pour la ressource et l’opération visées avant de créer la capacité d’accès signée.
Limiter
En plus des limites du Template, faites respecter les limites de fréquence par utilisateur et par tenant, les limites de traitement simultané, la politique de stockage et les quotas métier.
Monter Uppy une seule fois dans un Client Component
Uppy a besoin des API du navigateur ; l’outil de téléversement se trouve donc derrière une frontière use client. Créez l’instance Uppy dans un effet et détruisez cette même instance lors du nettoyage de cet effet. React StrictMode répète la mise en place et le nettoyage des effets en développement ; chaque mise en place doit créer une instance fonctionnelle au lieu de réutiliser une instance détruite par le nettoyage. L’état expose l’instance courante à Dashboard et la conserve lors des nouveaux rendus ordinaires. Si les téléversements doivent se poursuivre lors de la navigation entre les routes, déplacez ce cycle de vie dans un composant fournisseur côté client à durée de vie plus longue et détruisez son instance lorsque le cycle de vie de ce composant fournisseur prend fin.
La fonction asynchrone assemblyOptions appelle la route protégée pendant qu’Uppy prépare le téléversement. Elle vérifie response.ok, gère de manière sûre le JSON mal formé, valide la structure de la réponse et n’expose à l’utilisateur qu’un message d’erreur d’autorisation stable. Le Dashboard d’Uppy fournit l’interface de sélection, de progression, d’annulation et de gestion des erreurs, tandis que le plugin Transloadit crée l’Assembly et envoie les fichiers via une infrastructure de téléversement avec reprise. Le calendrier limité des nouvelles tentatives aide à surmonter les échecs temporaires sans réessayer indéfiniment.
Ces nouvelles tentatives fonctionnent tant que cette instance Uppy reste active. Elles ne permettent pas au composant présenté de récupérer les fichiers sélectionnés et l’état de l’Assembly après un rechargement de la page. Si la récupération après rechargement est une exigence du produit, configurez et testez Golden Retriever ou une autre architecture de persistance documentée avec le plugin Transloadit ; ne déduisez pas cette capacité de tus ou de retryDelays seuls.
Les restrictions du navigateur fournissent un retour rapide, mais ne constituent pas la frontière de sécurité. Un appelant peut contourner le composant, et les métadonnées des fichiers peuvent être fausses. Conservez dans le Template verrouillé les contrôles faisant autorité sur le nombre de fichiers, leur taille en octets et leur contenu détecté, ainsi que la politique d’export. Décidez également si une annulation dans le navigateur doit annuler uniquement le transfert, l’Assembly ou l’enregistrement du fichier dans l’application, puis testez ce choix au lieu de supposer que les trois états sont identiques.
'use client'
import Uppy from '@uppy/core'
import Dashboard from '@uppy/react/dashboard'
import Transloadit from '@uppy/transloadit'
import { type ReactNode, useEffect, useState } from 'react'
import { z } from 'zod'
import '@uppy/core/css/style.min.css'
import '@uppy/dashboard/css/style.min.css'
const assemblyOptionsSchema = z.object({
params: z.string().min(1),
signature: z.string().regex(/^(sha1|sha256|sha384):[0-9a-f]+$/),
})
async function fetchAssemblyOptions(): Promise<z.infer<typeof assemblyOptionsSchema>> {
const response = await fetch('/api/transloadit-params', {
method: 'POST',
headers: { Accept: 'application/json' },
})
if (!response.ok) {
throw new Error('Could not authorize this upload. Try again.')
}
const responseBody: unknown = await response.json().catch(() => null)
const parsedOptions = assemblyOptionsSchema.safeParse(responseBody)
if (!parsedOptions.success) {
throw new Error('Could not authorize this upload. Try again.')
}
return parsedOptions.data
}
function createUppy(): Uppy {
return new Uppy({
restrictions: {
allowedFileTypes: ['image/jpeg', 'image/png', 'image/webp'],
maxFileSize: 50 * 1024 * 1024,
maxNumberOfFiles: 5,
maxTotalFileSize: 48 * 1024 * 1024,
},
}).use(Transloadit, {
assemblyOptions: fetchAssemblyOptions,
retryDelays: [0, 1_000, 3_000, 5_000],
waitForEncoding: false,
})
}
export function UploadForm(): ReactNode {
const [uppy, setUppy] = useState<Uppy | null>(null)
useEffect(() => {
const instance = createUppy()
setUppy(instance)
return () => instance.destroy()
}, [])
return uppy == null ? null : (
<Dashboard height={420} proudlyDisplayPoweredByUppy={false} uppy={uppy} />
)
}Réconcilier la progression, les nouvelles tentatives et la fin du traitement
La progression du transfert et celle du traitement répondent à des questions différentes. Avec waitForEncoding: false, l’interface peut indiquer que l’opération est terminée après la réception des octets par Transloadit, alors que la validation, la transformation et l’export se poursuivent. Écoutez transloadit:assembly-created et associez l’identifiant de l’Assembly à un enregistrement en attente dans l’application. Une navigation peut alors interrompre le suivi dans le navigateur sans perdre l’identité nécessaire à la réconciliation des états.
Placez une valeur fixe pour notify_url dans le Template contrôlé par le serveur pour gérer la fin du traitement en mode asynchrone. Le gestionnaire de notifications doit vérifier la signature de la notification à l’aide de l’Auth Secret associé à l’Auth Key de l’Assembly, valider la charge utile, faire correspondre l’identifiant de l’Assembly à l’enregistrement en attente attendu et appliquer les résultats de manière idempotente avant de renvoyer une réponse de succès. Les notifications peuvent être renvoyées ; un doublon doit donc confirmer l’état terminal existant plutôt que créer un autre fichier ou événement de publication.
Utilisez waitForEncoding: true uniquement pour les flux de travail courts où l’utilisateur doit rester sur la page et où le code du navigateur a réellement besoin des résultats finaux. Même dans ce cas, conservez un mécanisme de récupération côté serveur, car les onglets se ferment et les connexions se coupent. Une tâche planifiée de réconciliation des états peut interroger les Assemblies dont l’état n’est pas terminal et dont les notifications n’ont pas été reçues. Adaptez la politique de nouvelle tentative au type d’échec : reprenez le transfert après une interruption réseau, demandez de nouvelles options signées lorsqu’elles expirent avant la création de l’Assembly et, en cas de rejet par une politique, arrêtez les tentatives jusqu’à ce que l’utilisateur change de fichier.
Sélectionné
Le navigateur dispose d’un fichier candidat ; aucun système de confiance ne l’a encore accepté.
Téléversé
Le destinataire dispose des octets, mais la validation faisant autorité, le traitement ou l’export peuvent encore échouer.
Prêt
Un résultat terminal vérifié a été enregistré de manière persistante et son utilisation prévue dans l’application est autorisée.
Tester les contrôles en tant qu’attaquant et en tant qu’utilisateur subissant une interruption
Testez le point de terminaison de signature sans session, avec le mauvais tenant, avec un jeton CSRF manquant ou invalide lorsque cela s’applique, au-delà de sa limite de fréquence et après la révocation des autorisations. Confirmez qu’aucune réponse ni aucun journal ne contient l’Auth Secret, les ensembles d’informations d’identification de Template, une trace de pile ou une erreur brute provenant d’une dépendance. Essayez de remplacer template_id, d’ajouter steps, de prolonger auth.expires et de soumettre des options signées après leur expiration ; la vérification de la signature ou l’application des règles du Template devrait rejeter la requête invalide.
Testez un JPEG autorisé, un type MIME interdit avec une extension d’image, un fichier trop volumineux, un nombre excessif de fichiers, un fichier de zéro octet, une perte de connexion à plusieurs positions du transfert, un rechargement du navigateur, une annulation, une autorisation expirée, une notification dupliquée, un refus de stockage et un échec de traitement après le téléversement. Confirmez que le comportement au rechargement correspond à la conception de la persistance au lieu de supposer une récupération automatique. Vérifiez l’accessibilité des annonces de progression et d’erreur au clavier et avec une technologie d’assistance, puis inspectez le stockage temporaire et les enregistrements de l’application pour détecter des fuites ou des états indéfiniment en attente.
Surveillez les refus de signature, les décisions de limitation du débit, les taux de création et d’échec des Assemblies, la reprise des téléversements, la latence du traitement, l’ancienneté des notifications, les erreurs de stockage et l’ancienneté des enregistrements en attente sans journaliser les charges utiles protégées. Déclenchez des alertes en cas de changements durables plutôt que pour des erreurs individuelles d’utilisateurs. Conservez l’identifiant du Template et une version du flux de traitement gérée par l’application dans les enregistrements d’exploitation, car un Template enregistré peut évoluer au fil du temps.
Détails techniques à connaître
- Un fichier
route.tsde l’App Router est un point de terminaison HTTP : il doit donc assurer lui-même l’authentification, l’autorisation, les contrôles contre les abus et la validation des entrées avant de renvoyer une signature. - Le marqueur de paquet
server-onlyprovoque une erreur de compilation si un module protégé est importé dans un Client Component, mais les secrets de déploiement nécessitent toujours une configuration correcte de la plateforme et des contrôles d’accès. - La méthode
calcSignaturedu SDK Node de Transloadit ajoute l’Auth Key lorsqu’elle est configurée, sérialise les paramètres de la requête et renvoie cette chaîneparamsexacte avec sa signature HMAC. - Signature Authentication couvre
auth.expireset le reste de la charge utile sérialisée de la requête ; modifier une valeur protégée après la signature invalide celle-ci. - Un Template peut accepter par défaut des substitutions de Steps à l’exécution ; les flux de traitement pilotés par le navigateur devraient donc définir
allow_steps_overridesurfalse, sauf si une substitution ayant fait l’objet d’un examen strictement délimité est intentionnelle. - Les restrictions d’Uppy fournissent un retour immédiat dans le navigateur, tandis que, côté Template,
auth.max_size,auth.max_number_of_fileset les Steps de traitement des fichiers font appliquer la politique une fois que le code du navigateur ne peut plus être considéré comme fiable. - Le plugin Transloadit accepte une fonction
assemblyOptionsasynchrone, crée une Assembly et configure des téléversements avec reprise vers le point de terminaison tus de l’Assembly. - Avec
waitForEncoding: false, Uppy termine son opération après le transfert plutôt qu’après le traitement ; l’application devrait conserver l’identifiant de l’Assembly et obtenir le résultat final au moyen d’une notification dont la signature a été vérifiée ou d’une consultation ultérieure de l’état. - L’exemple
retryDelaysassorti de limites reprend les transferts après des échecs transitoires tant que son instance Uppy reste active ; la reprise après un rechargement nécessite de conserver durablement l’état d’Uppy et de Transloadit, par exemple au moyen d’une intégration Golden Retriever configurée à cet effet. - Les ensembles d’informations d’identification de Template sont des enregistrements côté Workspace référencés par leur nom. Les secrets de stockage bruts n’apparaissent donc ni dans le JSON du Template enregistré, ni dans le bundle client, ni dans les paramètres signés de l’Assembly ; le Template contient uniquement le nom de l’ensemble d’informations d’identification.
Une approche pratique
- 1
Créez un Template verrouillé exigeant une signature, avec des limites de téléversement, des contrôles du contenu détecté et des ensembles d’informations d’identification de Template à portée restreinte.
- 2
Ajoutez une fonction utilitaire de signature réservée au serveur et un point de terminaison App Router authentifié, à débit limité et non cacheable.
- 3
Montez une seule instance Uppy dans un Client Component avec des restrictions cohérentes, des nouvelles tentatives et des messages d’échec d’autorisation expurgés.
- 4
Enregistrez durablement l’identifiant de l’Assembly, vérifiez les notifications de fin et testez les refus, les interruptions, l’expiration, la resoumission de requêtes signées capturées et les livraisons répétées.
Quand Transloadit est utile
Utilisez le plugin Transloadit maintenu pour Uppy lorsqu’un parcours Next.js dans le navigateur nécessite des téléversements avec reprise, suivis d’une validation, d’une transformation et d’un export gérés par le service. Un Template enregistré fixe le flux de travail autorisé, Signature Authentication protège les paramètres approuvés de la requête et son expiration, et les ensembles d’informations d’identification de Template gardent les secrets de stockage bruts hors des bundles clients Next.js et des paramètres d’Assembly.
Périmètre architectural
Votre application Next.js authentifie l’utilisateur et décide d’accorder ou non une autorisation de téléversement de courte durée. Uppy gère la sélection dans le navigateur, la progression et l’orchestration des transferts. Transloadit reçoit les octets, applique le Template de validation et de traitement configuré, puis communique les résultats. Aucune de ces couches ne remplace l’enregistrement persistant du fichier dans l’application ni sa politique de publication.
Questions fréquentes
Un Client Component Next.js peut-il contenir l’Auth Key Transloadit ?
L’Auth Key identifie le Workspace et peut figurer dans une requête signée, mais l’Auth Secret doit rester côté serveur. Exigez tout de même des signatures et limitez le Template, car une Auth Key exposée sans ces contrôles peut permettre des requêtes non autorisées.
Pourquoi utiliser un Route Handler plutôt que signer dans un Server Component ?
Uppy demande de nouvelles options d’Assembly depuis le code du navigateur juste avant le téléversement. Un Route Handler fournit cette interface HTTP, mais il doit authentifier et autoriser la requête comme tout autre point de terminaison qui modifie des données. Une Server Function pourrait fournir une interface similaire si l’intégration l’appelle de manière sécurisée.
Une requête signée pour un Template verrouillé empêche-t-elle toutes les formes d’abus de téléversement ?
Non. Elle protège l’intégrité de la requête et limite les opérations de traitement. Vous avez toujours besoin d’une autorisation au niveau de l’application, de limites de débit et de facturation, de limites du nombre de fichiers et d’octets, d’une validation du contenu détecté, d’un stockage respectant le principe du moindre privilège et de toute analyse de sécurité ou vérification exigée par le modèle de menace du produit.
Faut-il définir waitForEncoding sur true dans Next.js ?
Généralement pas pour les traitements longs. Avec false, l’utilisateur attend le transfert et l’application finalise le traitement au moyen d’une notification vérifiée. Définissez cette option sur true uniquement lorsque le flux de travail est court et que le code du navigateur a besoin des résultats finaux, tout en conservant une réconciliation des états côté serveur pour les onglets fermés et les connexions perdues.
Où stocker les informations d’identification pour S3 ou d’autres services de stockage ?
Stockez-les sous forme d’ensembles d’informations d’identification de Template Transloadit respectant le principe du moindre privilège et référencez l’ensemble par son nom depuis le Template enregistré. Ne placez pas les informations d’identification brutes du fournisseur dans les variables d’environnement publiques de Next.js, le code client, les champs de requêtes signées, les journaux ou les métadonnées des résultats.
Les restrictions de fichiers d’Uppy suffisent-elles à valider les téléversements ?
Non. Elles améliorent les retours fournis aux utilisateurs coopératifs. Réappliquez les limites du nombre d’octets et de fichiers dans le Template et inspectez les propriétés détectées des fichiers avec des Steps de traitement de confiance, car les appelants peuvent contourner le JavaScript du navigateur et les déclarations peuvent être trompeuses.