Qu'est-ce qu'une URL blob et pourquoi est-elle utilisée?

352

J'ai beaucoup de problèmes avec l'URL blob.

Je cherchais srcun tag vidéo sur YouTube et j'ai trouvé que la vidéo srcétait comme:

src="blob:https://crap.crap"

J'ai ouvert l'URL de blob qui se trouvait dans srcla vidéo qui a donné une erreur. Je ne peux pas ouvrir le lien, mais cela fonctionnait avec la srcbalise. Comment est-ce possible?

Exigences:

  • Qu'est-ce que l'URL blob?
  • Pourquoi est-il utilisé?
  • Puis-je créer ma propre URL blob sur un serveur?
  • Si vous avez des détails supplémentaires
Waqas Tahir
la source
3
Interdit essentiellement le hotlinking. (comme youtube)
facepalm42

Réponses:

351

Les URL Blob (réf W3C , nom officiel) ou URL d'objet (réf. MDN et nom de méthode) sont utilisées avec un objet Blob ou File .

src = "blob: https: //crap.crap " J'ai ouvert l'URL de blob qui était en src de la vidéo, cela a donné une erreur et je ne peux pas l'ouvrir mais travaillais avec la balise src comment c'est possible?

Les URL d'objets blob ne peuvent être générées qu'en interne par le navigateur. URL.createObjectURL()créera une référence spéciale à l'objet Blob ou Fichier qui pourra être publié ultérieurement à l'aide de URL.revokeObjectURL(). Ces URL ne peuvent être utilisées que localement dans la seule instance du navigateur et dans la même session (c'est-à-dire la durée de vie de la page / du document).

Qu'est-ce que l'URL blob?
Pourquoi est-il utilisé?

URL Blob / URL URL est un pseudo protocole permettant aux objets Blob et Fichier d'être utilisés comme source d'URL pour des choses comme les images, les liens de téléchargement pour les données binaires, etc.

Par exemple, vous ne pouvez pas remettre des données d'octets brutes d'un objet Image car il ne saurait pas quoi en faire. Il nécessite par exemple des images (qui sont des données binaires) à charger via des URL. Cela s'applique à tout ce qui nécessite une URL comme source. Au lieu de télécharger les données binaires, puis de les renvoyer via une URL, il est préférable d'utiliser une étape locale supplémentaire pour pouvoir accéder directement aux données sans passer par un serveur.

C'est également une meilleure alternative à Data-URI qui sont des chaînes encodées en Base-64 . Le problème avec Data-URI est que chaque caractère prend deux octets en JavaScript. En plus de cela, un 33% est ajouté en raison de l'encodage Base-64. Les objets blob sont des tableaux d'octets binaires purs qui n'ont pas de surcharge significative comme Data-URI, ce qui les rend plus rapides et plus petits à gérer.

Puis-je créer ma propre URL blob sur un serveur?

Non, les URL Blob / URL d'objet ne peuvent être créées qu'en interne dans le navigateur. Vous pouvez créer des objets blob et obtenir un objet fichier via l'API File Reader, bien que BLOB signifie simplement un grand objet binaire et soit stocké sous forme de tableaux d'octets. Un client peut demander que les données soient envoyées en tant qu'ArrayBuffer ou en tant qu'objet blob. Le serveur doit envoyer les données sous forme de données binaires pures. Les bases de données utilisent souvent Blob pour décrire également les objets binaires, et nous parlons essentiellement de tableaux d'octets.

si vous avez alors des détails supplémentaires

Vous devez encapsuler les données binaires en tant qu'objet BLOB, puis utiliser URL.createObjectURL()pour générer une URL locale pour celui-ci:

var blob = new Blob([arrayBufferWithPNG], {type: "image/png"}),
    url = URL.createObjectURL(blob),
    img = new Image();

img.onload = function() {
    URL.revokeObjectURL(this.src);     // clean-up memory
    document.body.appendChild(this);   // add image to DOM
}

img.src = url;                         // can now "stream" the bytes

Notez que cela URLpeut être préfixé dans les navigateurs webkit, alors utilisez:

var url = (URL || webkitURL).createObjectURL(...);
Bakudan
la source
20
Au cours des 6 dernières heures, j'ai essayé de faire en sorte que PHP transforme une URL d'objet passée d'AJAX en un fichier image .. Ce n'est que lorsque j'ai lu votre explication que j'ai compris pourquoi il n'écrivait aucune donnée dans le fichier .. Votre explication concise et approfondie a mis fin à ma misère. Je vous remercie.
Partack le
4
@ K3N est-il possible d'obtenir la véritable source de l'URL de blob au lieu de l'URL générée? Nest cam génère une URL blob pour empêcher les gens d'enregistrer leurs propres caméras
Alex Kwitny
4
éveil pour moi "BLOB signifie simplement un grand objet binaire"
canbax
6
Est-il possible de récupérer le contenu de l'objet blob / fichier et de télécharger quoi que ce soit (image ou vidéo)?
DFSFOT
4
Cela pourrait être pertinent pour les personnes qui se demandent comment télécharger une vidéo blob: stackoverflow.com/q/42901942/1530508
ApproachingDarknessFish
10

Cette fonction Javascript prétend montrer la différence entre l' API de fichier Blob et l' API de données pour télécharger un fichier JSON dans le navigateur client:

/**
 * Save a text as file using HTML <a> temporary element and Blob
 * @author Loreto Parisi
 */

var saveAsFile = function(fileName, fileContents) {
    if (typeof(Blob) != 'undefined') { // Alternative 1: using Blob
        var textFileAsBlob = new Blob([fileContents], {type: 'text/plain'});
        var downloadLink = document.createElement("a");
        downloadLink.download = fileName;
        if (window.webkitURL != null) {
            downloadLink.href = window.webkitURL.createObjectURL(textFileAsBlob);
        } else {
            downloadLink.href = window.URL.createObjectURL(textFileAsBlob);
            downloadLink.onclick = document.body.removeChild(event.target);
            downloadLink.style.display = "none";
            document.body.appendChild(downloadLink);
        }
        downloadLink.click();
    } else { // Alternative 2: using Data
        var pp = document.createElement('a');
        pp.setAttribute('href', 'data:text/plain;charset=utf-8,' +
            encodeURIComponent(fileContents));
        pp.setAttribute('download', fileName);
        pp.onclick = document.body.removeChild(event.target);
        pp.click();
    }
} // saveAsFile

/* Example */
var jsonObject = {"name": "John", "age": 30, "car": null};
saveAsFile('out.json', JSON.stringify(jsonObject, null, 2));

La fonction est appelée comme saveAsFile('out.json', jsonString);. Il créera un ByteStream immédiatement reconnu par le navigateur qui téléchargera le fichier généré directement à l'aide de l'API File URL.createObjectURL.

Dans le else, il est possible de voir le même résultat obtenu via l' hrefélément plus l'API Data, mais cela a plusieurs limitations que l'API Blob n'a pas.

loretoparisi
la source
1
Pouvez-vous l'adapter pour enregistrer une vidéo à partir d'un tweet?
logicbloke
3

Qu'est-ce que l'URL blob? Pourquoi est-il utilisé?

BLOB n'est qu'une séquence d'octets. Le navigateur le reconnaît comme un flux d'octets. Il est utilisé pour obtenir un flux d'octets à partir de la source.

Un objet Blob représente un objet de type fichier de données brutes immuables. Les blobs représentent des données qui ne sont pas nécessairement dans un format natif JavaScript. L'interface de fichier est basée sur Blob, héritant de la fonctionnalité de blob et l'étendant pour prendre en charge les fichiers sur le système de l'utilisateur.

Puis-je créer ma propre URL blob sur un serveur?

Oui, vous pouvez le faire de plusieurs façons, par exemple essayez http://php.net/manual/en/function.ibase-blob-echo.php

En savoir plus sur

Robert
la source
2
Puis-je obtenir des avantages en utilisant l'URL BLOB?
Waqas Tahir
Vous pouvez lire ceci pour obtenir votre réponse. Évidemment, il y a des avantages et des inconvénients.
Robert
4
Vous mélangez des URL d'objet avec des BLOB. Object-URL est un pseudo-protocole permettant aux BLOB d'être utilisés comme source d'URI.
4
Il y a quelques défauts importants avec cette réponse. Principalement, comme indiqué dans un commentaire précédent, certains concepts très différents sont mélangés ... puis compressés en une réponse incomplète et incorrecte.
très
2

J'ai modifié la solution de travail pour gérer à la fois le cas .. lorsque la vidéo est téléchargée et lorsque l'image est téléchargée .. j'espère que cela aidera certains.

HTML

<input type="file" id="fileInput">
<div> duration: <span id='sp'></span><div>

Javascript

var fileEl = document.querySelector("input");

fileEl.onchange = function(e) {


    var file = e.target.files[0]; // selected file

    if (!file) {
        console.log("nothing here");
        return;
    }

    console.log(file);
    console.log('file.size-' + file.size);
    console.log('file.type-' + file.type);
    console.log('file.acutalName-' + file.name);

    let start = performance.now();

    var mime = file.type, // store mime for later
        rd = new FileReader(); // create a FileReader

    if (/video/.test(mime)) {

        rd.onload = function(e) { // when file has read:


            var blob = new Blob([e.target.result], {
                    type: mime
                }), // create a blob of buffer
                url = (URL || webkitURL).createObjectURL(blob), // create o-URL of blob
                video = document.createElement("video"); // create video element
            //console.log(blob);
            video.preload = "metadata"; // preload setting

            video.addEventListener("loadedmetadata", function() { // when enough data loads
                console.log('video.duration-' + video.duration);
                console.log('video.videoHeight-' + video.videoHeight);
                console.log('video.videoWidth-' + video.videoWidth);
                //document.querySelector("div")
                //  .innerHTML = "Duration: " + video.duration + "s" + " <br>Height: " + video.videoHeight; // show duration
                (URL || webkitURL).revokeObjectURL(url); // clean up

                console.log(start - performance.now());
                // ... continue from here ...

            });
            video.src = url; // start video load
        };
    } else if (/image/.test(mime)) {
        rd.onload = function(e) {

            var blob = new Blob([e.target.result], {
                    type: mime
                }),
                url = URL.createObjectURL(blob),
                img = new Image();

            img.onload = function() {
                console.log('iamge');
                console.dir('this.height-' + this.height);
                console.dir('this.width-' + this.width);
                URL.revokeObjectURL(this.src); // clean-up memory
                console.log(start - performance.now()); // add image to DOM
            }

            img.src = url;

        };
    }

    var chunk = file.slice(0, 1024 * 1024 * 10); // .5MB
    rd.readAsArrayBuffer(chunk); // read file object

};

URL jsFiddle

https://jsfiddle.net/PratapDessai/0sp3b159/

Pratap Dessai
la source
1. Quel est le but de l'indentation dans votre code? Tout le monde utilise l'indentation pour mettre en évidence la structure logique du code. 2. Votre JSFiddle ne fait rien. J'ai essayé de télécharger une image et une vidéo.
7vujy0f0hy