1
votes

Erreur de téléchargement d'image: TypeError [ERR_INVALID_ARG_TYPE]: l'argument "chemin" doit être de type chaîne

Je construis des fonctions backend avec node.js et firebase. J'ai utilisé BusBoy pour créer une fonction de téléchargement d'image;

Je vérifie mon code encore et encore, j'ai changé l'image avec une taille plus petite (comme 140 ko) et j'ai essayé de détecter le problème et à partir du code, je pensais que c'était un peu type de problème pour écrire le nom du chemin du fichier téléchargé, dans firebase serve cela donne l'erreur:

TypeError [ERR_INVALID_ARG_TYPE]: l'argument "chemin" doit être de type chaîne. Type reçu non défini

TypeError [ERR_INVALID_ARG_TYPE]: The "path" argument must be of type string.
Received type undefined 
> at validateString (internal/validators.js:125:11) 
> at Object.basename (path.js:1289:5) 
> at Bucket.upload (/Users/apple/Desktop/Oner/social_app/functions/node_modules/@google-cloud/storage/build/src/bucket.js:2237:38) 
> at PromiseCtor (/Users/apple/Desktop/Oner/social_app/functions/node_modules/@google-cloud/promisify/build/src/index.js:71:28)
> at new Promise (<anonymous>) 
> at Bucket.wrapper (/Users/apple/Desktop/Oner/social_app/functions/node_modules/@google-cloud/promisify/build/src/index.js:56:16) 
> at Busboy.busboy.on (/Users/apple/Desktop/Oner/social_app/functions/handlers/users.js:123:8) 
> at Busboy.emit (events.js:198:13) 
> at Busboy.emit (/Users/apple/Desktop/Oner/social_app/functions/node_modules/busboy/lib/main.js:37:33) 
> at /Users/apple/Desktop/Oner/social_app/functions/node_modules/busboy/lib/types/multipart.js:304:17

Quand je regarde les détails, je me suis rendu compte que le problème est dans cette ligne: .upload(imageToBeUploaded.filepath,

J'envoie une demande de publication de Postman

Y a-t-il quelqu'un pour m'aider?

Complet message d'erreur:

  exports.uploadImage = (req, res) => {
  const BusBoy = require('busboy');
  const path = require('path');
  const os = require('os');
  const fs = require('fs');

  const busboy = new BusBoy({ headers: req.headers });

  let imageToBeUploaded = {};
  let imageFileName;

  busboy.on('file', (fieldname, file, filename, encoding, mimetype) => {
    console.log(fieldname, file, filename, encoding, mimetype);
    if (mimetype !== 'image/jpeg' && mimetype !== 'image/png') {
      return res.status(400).json({ error: 'Wrong file type submitted' });
    }
    // my.image.png => ['my', 'image', 'png']
    const imageExtension = filename.split('.')[filename.split('.').length - 1];
    // 32756238461724837.png
    imageFileName = `${Math.round(
      Math.random() * 1000000000000
    ).toString()}.${imageExtension}`;
    const filepath = path.join(os.tmpdir(), imageFileName);
    imageToBeUploaded = { filepath, mimetype };
    file.pipe(fs.createWriteStream(filepath));
  });
  busboy.on('finish', () => {
    admin
      .storage()
      .bucket()
      .upload(imageToBeUploaded.filepath, {
        resumable: false,
        metadata: {
          metadata: {
            contentType: imageToBeUploaded.mimetype
          }
        }
      })
      .then(() => {
        const imageUrl = `https://firebasestorage.googleapis.com/v0/b/${
          config.storageBucket
        }/o/${imageFileName}?alt=media`;
        return db.doc(`/users/${req.user.handle}`).update({ imageUrl });
      })
      .then(() => {
        return res.json({ message: 'image uploaded successfully' });
      })
      .catch((err) => {
        console.error(err);
        return res.status(500).json({ error: 'something went wrong' });
      });
  });
  busboy.end(req.rawBody);
}; 


7 commentaires

Le rappel de fichier a-t-il été déclenché avant le rappel de finish ? Le type MIME était-il égal à l'un des spécifiés?


Je ne sais pas comment vérifier cela. J'envoie des demandes de courrier de Postman. Mais dans le message d'erreur, il est indiqué la 124e ligne, qui est admin.upload (imageToBeUploaded.filepath, {...})


Pouvez-vous voir les journaux dans la console? console.log (fieldname, fichier, nom de fichier, encodage, type MIME); Ou de n'importe quelle console.error ?


Je voulais dire dans la console du nœud, pas dans la console du facteur


Ok, j'imprime console.logs, il se connecte avant busboy.on mais pas après. Il semble que la méthode busboy.on ne se déclenche jamais et donne une erreur


Sur la base des informations données, je ne peux que vous conseiller d'ajouter un rappel de check in finish : if (! ImageToBeUploaded.filepath) return , mais ce n'est pas la solution que vous recherchez. imageToBeUploaded = {filepath, mimetype}; semble ne pas être exécuté, mais je ne peux pas dire pourquoi


J'ai une idée - regardez les exemples , ils ont tous req.pipe (busboy); où vous avez busboy.end (req.rawBody); - n'est-ce pas que vous appelez busboy.end et qu'il émet "terminer "omettre l'événement" fichier "?


3 Réponses :


1
votes

Toute personne ayant le même problème, pour le résoudre, vous devez restaurer firebase-tools vers la version précédente:

Dans le dossier functions

npm rm firebase-tools
npm i -g firebase-tools@6.8.0

Ensuite, ajoutez config .storageBucket au .bucket () dans le gestionnaire d'événements 'finish'.


0 commentaires

1
votes

Rien n'est faux dans votre code, supprimez simplement Content-Type des en-têtes du facteur. Cela a fonctionné pour moi


0 commentaires

0
votes

Je comprends que vous essayez de tester votre code dans Postman. J'ai fait face au même problème. Demande authentique: Essayez simplement d'ouvrir un nouvel onglet dans POSTMAN, pas de dupliquer, hérité d'un autre. ajoutez une image, ajoutez tout autre en-tête dépendant comme le jeton de porteur, etc. et appuyez sur envoyer.

Je ne sais vraiment pas ce qui s'est passé, mais je pense que différents en-têtes de postman sont ajoutés lorsque vous jouez avec le type de corps ... et cela pose des problèmes.


0 commentaires