Come ottenere un elenco di tutti i file in Cloud Storage in un'app Firebase?


102

Sto lavorando al caricamento delle immagini, tutto funziona alla grande, ma ho 100 immagini e vorrei mostrarle tutte nel mio View, poiché ottengo l'elenco completo delle immagini in una cartella, non riesco a trovare nessuna API per questo lavoro.


Puoi pubblicare una soluzione di codice completa?
ISS

Risposte:


92

Dal momento che Firebase SDK per JavaScript versione 6.1 , iOS versione 6.4 e versione Android 18.1 hanno tutti un metodo per elencare i file.

La documentazione è un po 'scarsa finora, quindi consiglio di controllare la risposta di Rosário per i dettagli.


Risposta precedente, poiché questo approccio può essere ancora utile a volte:

Al momento non è presente alcuna chiamata API nell'SDK Firebase per elencare tutti i file in una cartella Cloud Storage dall'interno di un'app. Se hai bisogno di tale funzionalità, dovresti memorizzare i metadati dei file (come gli URL di download) in un posto dove puoi elencarli. Il database Firebase in tempo reale e cloud Firestore sono perfetti per questo e ti permette di condividere facilmente anche gli URL con gli altri.

Puoi trovare un buon (ma un po 'complicato) esempio di questo nella nostra app di esempio FriendlyPix . Il codice rilevante per la versione web è qui , ma ci sono anche versioni per iOS e Android.


8
Lo implementerai su Firebase?
Molo

55
Se ho bisogno di mantenere gli URL di tutti i miei file di archiviazione in Realtime Database, qual è lo scopo di avere la gerarchia delle cartelle in Archiviazione? tutti i file, con un nome univoco, possono essere archiviati nello stesso livello, senza bisogno di cartelle !!! vedi, è una contraddizione !!! Fondamentalmente, la logica principale alla base della gerarchia delle cartelle sono le query con caratteri jolly senza la conoscenza preliminare di ciò che si trova in una cartella, che non si fornisce ragionevolmente.
abedfar

7
Firebase Storage è basato su Google Cloud Storage, che fa esattamente quello che dici: memorizza tutti gli oggetti in un lungo elenco. Firebase Storage modella una gerarchia su questo, certamente come un'astrazione che perde. I motivi comuni per utilizzare la cartella in Firebase Storage sono la separazione logica dei dati e la creazione di regole di sicurezza basate sulla struttura delle cartelle.
Frank van Puffelen

8
Cosa succede se la connessione dell'utente viene persa dopo il caricamento e prima di salvare downloadUrl nel database? Come scopriamo i file esistenti in una cartella in quel caso?
Oswaldo

10
E adesso? Esiste un'API diretta per questo nel 2018?
Diaz diaz

48

A partire da maggio 2019, la versione 6.1.0 di Firebase SDK per Cloud Storage ora supporta l'elenco di tutti gli oggetti da un bucket. Devi semplicemente chiamare listAll()un Reference:

    // Since you mentioned your images are in a folder,
    // we'll create a Reference to that folder:
    var storageRef = firebase.storage().ref("your_folder");


    // Now we get the references of these images
    storageRef.listAll().then(function(result) {
      result.items.forEach(function(imageRef) {
        // And finally display them
        displayImage(imageRef);
      });
    }).catch(function(error) {
      // Handle any errors
    });

    function displayImage(imageRef) {
      imageRef.getDownloadURL().then(function(url) {
        // TODO: Display the image on the UI
      }).catch(function(error) {
        // Handle any errors
      });
    }

Tieni presente che per utilizzare questa funzione, devi aderire alla versione 2 delle regole di sicurezza , che può essere eseguita inserendo rules_version = '2';la prima riga delle regole di sicurezza:

    rules_version = '2';
    service firebase.storage {
      match /b/{bucket}/o {
        match /{allPaths=**} {

Consiglierei di controllare i documenti per ulteriori riferimenti.

Inoltre, in base alla configurazione , al passaggio 5, questo script non è consentito Node.jspoiché require("firebase/app");non tornerà firebase.storage()come funzione. Ciò si ottiene solo utilizzando import * as firebase from 'firebase/app';.


quale plugin stai usando
azheen

@azheen Presumo tu stia usando Flutter. Sfortunatamente, questo non è ancora disponibile su flutterfire. Puoi seguirlo su questo numero
Rosário Pereira Fernandes,

33

Da marzo 2017: con l'aggiunta di Firebase Cloud Functions e l'integrazione più profonda di Firebase con Google Cloud, ora è possibile.

Con Cloud Functions puoi utilizzare il pacchetto Google Cloud Node per eseguire operazioni epiche su Cloud Storage. Di seguito è riportato un esempio che ottiene tutti gli URL dei file in un array da Cloud Storage. Questa funzione verrà attivata ogni volta che qualcosa viene salvato nell'archivio cloud di Google.

Nota 1 : questa è un'operazione piuttosto costosa dal punto di vista computazionale, in quanto deve scorrere tutti i file in un bucket / cartella.

Nota 2 : ho scritto questo solo come esempio, senza pagare molti dettagli in promesse, ecc. Solo per dare un'idea.

const functions = require('firebase-functions');
const gcs = require('@google-cloud/storage')();

// let's trigger this function with a file upload to google cloud storage

exports.fileUploaded = functions.storage.object().onChange(event => {

  const object = event.data; // the object that was just uploaded
  const bucket = gcs.bucket(object.bucket);
  const signedUrlConfig = { action: 'read', expires: '03-17-2025' }; // this is a signed url configuration object

  var fileURLs = []; // array to hold all file urls 

  // this is just for the sake of this example. Ideally you should get the path from the object that is uploaded :)
  const folderPath = "a/path/you/want/its/folder/size/calculated";

  bucket.getFiles({ prefix: folderPath }, function(err, files) {
    // files = array of file objects
    // not the contents of these files, we're not downloading the files. 

    files.forEach(function(file) {
      file.getSignedUrl(signedUrlConfig, function(err, fileURL) {
        console.log(fileURL);
        fileURLs.push(fileURL);
      });
    });

  });

});

Spero che questo ti dia l'idea generale. Per esempi di funzioni cloud migliori, controlla il repository Github di Google pieno di esempi di Cloud Functions per Firebase . Verificate anche la documentazione API di Google Cloud Nodo


35
Questo è troppo stupido che Firebase non si limiti ad aggiungere questa API in Firebase SDK
Thaina

4
@Thaina penso che abbia a che fare con la scala. Devono pensare non solo alle piccole app ma anche ai giganti. E se un percorso avesse migliaia di file. Questa operazione consumerebbe molta potenza di calcolo e dovrebbe fare riferimento a un database per ogni chiamata apparentemente innocente e semplice. Più mi sono addentrato nell'uso di Firebase su larga scala, meglio capisco perché sono stati fatti alcuni compromessi.
johnozbay

1
In questa API gcs ha anche limite e impaginazione, quindi è responsabilità del consumatore API conoscere il rischio e provare a scegliere un metodo che potrebbe scalare. Ma essere iperprotettivi, quindi tagliare la nostra opzione non è una buona decisione. Possono addebitare un carico pesante se costa davvero
Thaina

1
questa dovrebbe essere la risposta migliore! Grazie per il testa a testa. Attualmente, la sintassi è diversa dal tuo esempio. Invece di inviare un callback come parametro, devi concatenare un .thencome questo:this.bucket .getFiles({ prefix: 'path/to/directory' }) .then((arr) => {})
JP Lew

1
@JPLew Sei il benvenuto :) Per quanto riguarda la sintassi, restituiscono una promessa solo se la richiamata è esclusa. Quindi è sicuro usare quello che preferisci. Vedi un esempio qui: cloud.google.com/nodejs/docs/reference/storage/1.3.x/…
johnozbay

20

Poiché non è elencata alcuna lingua, risponderò in Swift. Consigliamo vivamente di utilizzare Firebase Storage e Firebase Realtime Database insieme per realizzare elenchi di download:

Condivisa:

// Firebase services
var database: FIRDatabase!
var storage: FIRStorage!
...
// Initialize Database, Auth, Storage
database = FIRDatabase.database()
storage = FIRStorage.storage()
...
// Initialize an array for your pictures
var picArray: [UIImage]()

Caricare:

let fileData = NSData() // get data...
let storageRef = storage.reference().child("myFiles/myFile")
storageRef.putData(fileData).observeStatus(.Success) { (snapshot) in
  // When the image has successfully uploaded, we get it's download URL
  let downloadURL = snapshot.metadata?.downloadURL()?.absoluteString
  // Write the download URL to the Realtime Database
  let dbRef = database.reference().child("myFiles/myFile")
  dbRef.setValue(downloadURL)
}

Scarica:

let dbRef = database.reference().child("myFiles")
dbRef.observeEventType(.ChildAdded, withBlock: { (snapshot) in
  // Get download URL from snapshot
  let downloadURL = snapshot.value() as! String
  // Create a storage reference from the URL
  let storageRef = storage.referenceFromURL(downloadURL)
  // Download the data, assuming a max size of 1MB (you can change this as necessary)
  storageRef.dataWithMaxSize(1 * 1024 * 1024) { (data, error) -> Void in
    // Create a UIImage, add it to the array
    let pic = UIImage(data: data)
    picArray.append(pic)
  })
})

Per ulteriori informazioni, consulta Zero to App: Develop with Firebase e il codice sorgente associato , per un esempio pratico di come eseguire questa operazione.


3
Ma come ottengo lo stesso risultato con Cloud Firestore?)
Max Kraev

5

Una soluzione alternativa può essere quella di creare un file (es. List.txt) senza niente all'interno, in questo file è possibile impostare i metadati personalizzati (ovvero una mappa <String, String>) con l'elenco di tutti gli URL del file.
Quindi, se è necessario scaricare tutti i file in un fodler, scaricare prima i metadati del file list.txt, quindi scorrere i dati personalizzati e scaricare tutti i file con gli URL nella mappa.


4
Sì, questa è una soluzione alternativa, ma non è possibile gestire scritture simultanee su un singolo
list.txt

5

Ho riscontrato questo problema anche mentre stavo lavorando al mio progetto. Vorrei davvero che fornissero un metodo api finale. Ad ogni modo, è così che ho fatto: quando carichi un'immagine nell'archivio Firebase, crea un oggetto e passa questo oggetto al database Firebase allo stesso tempo. Questo oggetto contiene l'URI di download dell'immagine.

trailsRef.putFile(file).addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>() {
        @Override
        public void onSuccess(UploadTask.TaskSnapshot taskSnapshot) {
            Uri downloadUri = taskSnapshot.getDownloadUrl();
            DatabaseReference myRef = database.getReference().child("trails").child(trail.getUnique_id()).push();
            Image img = new Image(trail.getUnique_id(), downloadUri.toString());
            myRef.setValue(img);
        }
    });

Successivamente, quando si desidera scaricare immagini da una cartella, è sufficiente scorrere i file in quella cartella. Questa cartella ha lo stesso nome della "cartella" nello spazio di archiviazione di Firebase, ma puoi denominarle come preferisci. Li ho messi in thread separati.

 @Override
protected List<Image> doInBackground(Trail... params) {

    String trialId = params[0].getUnique_id();
    mDatabase = FirebaseDatabase.getInstance().getReference();
    mDatabase.child("trails").child(trialId).addValueEventListener(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            images = new ArrayList<>();
            Iterator<DataSnapshot> iter = dataSnapshot.getChildren().iterator();
            while (iter.hasNext()) {
                Image img = iter.next().getValue(Image.class);
                images.add(img);
            }
            isFinished = true;
        }

        @Override
        public void onCancelled(DatabaseError databaseError) {

        }
    });

Ora ho un elenco di oggetti contenenti gli URI di ciascuna immagine, posso fare tutto ciò che voglio fare con loro. Per caricarli in imageView, ho creato un altro thread.

    @Override
protected List<Bitmap> doInBackground(List<Image>... params) {

    List<Bitmap> bitmaps = new ArrayList<>();

    for (int i = 0; i < params[0].size(); i++) {
        try {
            URL url = new URL(params[0].get(i).getImgUrl());
            Bitmap bmp = BitmapFactory.decodeStream(url.openConnection().getInputStream());
            bitmaps.add(bmp);
        } catch (MalformedURLException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    return bitmaps;
}

Questo restituisce un elenco di bitmap, quando finisce li allego semplicemente a ImageView nell'attività principale. I metodi seguenti sono @Override perché ho interfacce create e ascolto il completamento in altri thread.

    @Override
public void processFinishForBitmap(List<Bitmap> bitmaps) {
    List<ImageView> imageViews = new ArrayList<>();
    View v;
    for (int i = 0; i < bitmaps.size(); i++) {
        v = mInflater.inflate(R.layout.gallery_item, mGallery, false);
        imageViews.add((ImageView) v.findViewById(R.id.id_index_gallery_item_image));
        imageViews.get(i).setImageBitmap(bitmaps.get(i));
        mGallery.addView(v);
    }
}

Nota che devo prima aspettare che venga restituita l'immagine dell'elenco e quindi chiamare il thread per lavorare su List Bitmap. In questo caso, Image contiene l'URI.

    @Override
public void processFinish(List<Image> results) {
    Log.e(TAG, "get back " + results.size());

    LoadImageFromUrlTask loadImageFromUrlTask =  new LoadImageFromUrlTask();
    loadImageFromUrlTask.delegate = this;
    loadImageFromUrlTask.execute(results);
}

Si spera che qualcuno lo trovi utile. Servirà anche come linea di gilda per me anche in futuro.


5

Un altro modo per aggiungere l'immagine al database utilizzando la funzione Cloud per tenere traccia di ogni immagine caricata e memorizzarla nel database.

exports.fileUploaded = functions.storage.object().onChange(event => {

    const object = event.data; // the object that was just uploaded
    const contentType = event.data.contentType; // This is the image Mimme type\

    // Exit if this is triggered on a file that is not an image.
    if (!contentType.startsWith('image/')) {
        console.log('This is not an image.');
        return null;
    }

    // Get the Signed URLs for the thumbnail and original image.
    const config = {
        action: 'read',
        expires: '03-01-2500'
    };

    const bucket = gcs.bucket(event.data.bucket);
    const filePath = event.data.name;
    const file = bucket.file(filePath);

    file.getSignedUrl(config, function(err, fileURL) {
        console.log(fileURL);
        admin.database().ref('images').push({
            src: fileURL
        });
    });
});

Codice completo qui: https://gist.github.com/bossly/fb03686f2cb1699c2717a0359880cf84


5

Per il nodo js, ​​ho usato questo codice

const Storage = require('@google-cloud/storage');
const storage = new Storage({projectId: 'PROJECT_ID', keyFilename: 'D:\\keyFileName.json'});
const bucket = storage.bucket('project.appspot.com'); //gs://project.appspot.com
bucket.getFiles().then(results => {
    const files = results[0];
    console.log('Total files:', files.length);
    files.forEach(file => {
      file.download({destination: `D:\\${file}`}).catch(error => console.log('Error: ', error))
    });
}).catch(err => {
    console.error('ERROR:', err);
  });

Mi hai appena salvato la giornata !!
hugo blanc


3

In realtà questo è possibile ma solo con un'API di Google Cloud invece di una di Firebase. È perché un Firebase Storage è un Google Cloud Storage Bucket che può essere raggiunto facilmente con le API di Google Cloud, tuttavia è necessario utilizzare OAuth per l'autenticazione invece di Firebase.


3

Ho affrontato lo stesso problema, il mio è ancora più complicato.

L'amministratore caricherà i file audio e pdf nella memoria:

  • audio / stagione1, stagione2 ... / classe1, file di classe 2 / .mp3

  • libri / file .pdf

L'app Android deve ottenere l'elenco di sottocartelle e file.

La soluzione è catturare l'evento di caricamento in archivio e creare la stessa struttura su Firestore utilizzando la funzione cloud.

Passaggio 1: crea manualmente la raccolta "archiviazione" e il documento "audio / libri" su firestore

inserisci qui la descrizione dell'immagine

Passaggio 2: configurazione della funzione cloud

Potrebbero essere necessari circa 15 minuti: https://www.youtube.com/watch?v=DYfP-UIKxH0&list=PLl-K7zZEsYLkPZHe41m4jfAxUi0JjLgSM&index=1

Passaggio 3: cattura l'evento di caricamento utilizzando la funzione cloud

import * as functions from 'firebase-functions';
import * as admin from 'firebase-admin';
admin.initializeApp(functions.config().firebase);
const path = require('path');

export const onFileUpload = functions.storage.object().onFinalize(async (object) => {
        let filePath = object.name; // File path in the bucket.
        const contentType = object.contentType; // File content type.
        const metageneration = object.metageneration; // Number of times metadata has been generated. New objects have a value of 1.
        if (metageneration !== "1") return;

        // Get the file name.
        const fileName = path.basename(filePath);
        filePath = filePath.substring(0, filePath.length - 1);
        console.log('contentType ' + contentType);
        console.log('fileName ' + fileName);
        console.log('filePath ' + filePath);
        console.log('path.dirname(filePath) ' + path.dirname(filePath));
        filePath = path.dirname(filePath);
        const pathArray = filePath.split("/");
        let ref = '';
        for (const item of pathArray) {
            if (ref.length === 0) {
                ref = item;
            }
            else {
                ref = ref.concat('/sub/').concat(item);
            }
        }

        ref = 'storage/'.concat(ref).concat('/sub')
        admin.firestore().collection(ref).doc(fileName).create({})
                .then(result => {console.log('onFileUpload:updated')})
                .catch(error => {
                    console.log(error);
                });
    });

Passaggio 4: recupera l'elenco di cartelle / file sull'app Android utilizzando firestore

private static final String STORAGE_DOC = "storage/";
    public static void getMediaCollection(String path, OnCompleteListener onCompleteListener) {
        String[] pathArray = path.split("/");
        String doc = null;
        for (String item : pathArray) {
            if (TextUtils.isEmpty(doc)) doc = STORAGE_DOC.concat(item);
            else doc = doc.concat("/sub/").concat(item);
        }
        doc = doc.concat("/sub");

        getFirestore().collection(doc).get().addOnCompleteListener(onCompleteListener);
    }

Passaggio 5: ottieni l'URL di download

public static void downloadMediaFile(String path, OnCompleteListener<Uri> onCompleteListener) {
        getStorage().getReference().child(path).getDownloadUrl().addOnCompleteListener(onCompleteListener);
    }

Nota

Dobbiamo mettere una raccolta "sotto" per ogni elemento poiché firestore non supporta il recupero dell'elenco della raccolta.

Mi ci sono voluti 3 giorni per trovare la soluzione, spero che impiegherai al massimo 3 ore.

Saluti.


Esattamente lo stesso scenario su cui sto lavorando. Qualcuno può inviarmi codice flutter? perché devo solo caricare batch di file, non scaricare.
Mahesh Peri

Flutter SDK (linguaggio freccette)
Mahesh Peri

1
cloud firestore non supporta ancora flutter firebase.google.com/docs/firestore . L'approccio rapido è scrivere API utilizzando la funzione cloud, quindi accedere a queste API tramite riposante come al solito. Potrebbero essere necessarie diverse ore per acquisire familiarità con la funzione cloud, questi video di formazione sono abbastanza facili da digerire: D youtube.com/…
thanhbinh84

3

Estendendo la risposta di Rosário Pereira Fernandes , per una soluzione JavaScript:

  1. Installa Firebase sulla tua macchina
npm install -g firebase-tools

  1. Su Firebase init impostato JavaScriptcome lingua predefinita
  2. Nella cartella principale del progetto creato eseguire le installazioni di npm
   npm install --save firebase
   npm install @google-cloud/storage
   npm install @google-cloud/firestore
   ... <any other dependency needed>
  1. Aggiungi dipendenze non predefinite al tuo progetto come
    "firebase": "^6.3.3",
    "@google-cloud/storage": "^3.0.3"

functions / package.json

{
  "name": "functions",
  "description": "Cloud Functions for Firebase",
  "scripts": {
    "lint": "eslint .",
    "serve": "firebase serve --only functions",
    "shell": "firebase functions:shell",
    "start": "npm run shell",
    "deploy": "firebase deploy --only functions",
    "logs": "firebase functions:log"
  },
  "engines": {
    "node": "10"
  },
  "dependencies": {
    "@google-cloud/storage": "^3.0.3",
    "firebase": "^6.3.3",
    "firebase-admin": "^8.0.0",
    "firebase-functions": "^3.1.0"
  },
  "devDependencies": {
    "eslint": "^5.12.0",
    "eslint-plugin-promise": "^4.0.1",
    "firebase-functions-test": "^0.1.6"
  },
  "private": true
}

  1. Crea una sorta di listAllfunzione

index.js

var serviceAccount = require("./key.json");
const functions = require('firebase-functions');

const images = require('./images.js');

var admin = require("firebase-admin");

admin.initializeApp({
    credential: admin.credential.cert(serviceAccount),
    databaseURL: "https://<my_project>.firebaseio.com"
});

const bucket = admin.storage().bucket('<my_bucket>.appspot.com')

exports.getImages = functions.https.onRequest((request, response) => {
    images.getImages(bucket)
        .then(urls => response.status(200).send({ data: { urls } }))
        .catch(err => console.error(err));
})

images.js

module.exports = {
    getImages
}

const query = {
    directory: 'images'
};

function getImages(bucket) {
    return bucket.getFiles(query)
        .then(response => getUrls(response))
        .catch(err => console.error(err));
}

function getUrls(response) {
    const promises = []
    response.forEach( files => {
        files.forEach (file => {
            promises.push(getSignedUrl(file));
        });
    });
    return Promise.all(promises).then(result => getParsedUrls(result));
}

function getSignedUrl(file) {
    return file.getSignedUrl({
        action: 'read',
        expires: '09-01-2019'
    })
}

function getParsedUrls(result) {
    return JSON.stringify(result.map(mediaLink => createMedia(mediaLink)));
}

function createMedia(mediaLink) {
    const reference = {};
    reference.mediaLink = mediaLink[0];
    return reference;
}

  1. Esegui firebase deployper caricare la tua funzione cloud
  2. Chiama la tua funzione personalizzata dalla tua app

build.gradle

dependencies {
...
  implementation 'com.google.firebase:firebase-functions:18.1.0'
...
}

classe kotlin

  private val functions = FirebaseFunctions.getInstance()
  val cloudFunction = functions.getHttpsCallable("getImages")
  cloudFunction.call().addOnSuccessListener {...}

Per quanto riguarda l'ulteriore sviluppo di questa funzionalità, mi sono imbattuto in alcuni problemi che potrebbero trovarsi qui .


2

Per farlo con JS

Puoi aggiungerli direttamente al tuo contenitore div o puoi inviarli a un array. Di seguito viene mostrato come aggiungerli al tuo div.

1) Quando archivi le tue immagini nella memoria, crea un riferimento all'immagine nel tuo database Firebase con la seguente struttura

/images/(imageName){
   description: "" , 
   imageSrc : (imageSource) 
}

2) Quando carichi il documento, estrai tutti gli URL di origine dell'immagine dal database anziché dalla memoria con il codice seguente

$(document).ready(function(){

var query = firebase.database().ref('images/').orderByKey();
query.once("value").then(function(snapshot){

    snapshot.forEach(function(childSnapshot){

        var imageName = childSnapshot.key;
        var childData = childSnapshot.val();
        var imageSource = childData.url;

        $('#imageGallery').append("<div><img src='"+imageSource+"'/></div>");

    })
})
});

2

Puoi usare il codice seguente. Qui sto caricando l'immagine nella memoria di Firebase e poi sto memorizzando l'URL di download dell'immagine nel database di Firebase.

//getting the storage reference
            StorageReference sRef = storageReference.child(Constants.STORAGE_PATH_UPLOADS + System.currentTimeMillis() + "." + getFileExtension(filePath));

            //adding the file to reference 
            sRef.putFile(filePath)
                    .addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>() {
                        @Override
                        public void onSuccess(UploadTask.TaskSnapshot taskSnapshot) {
                            //dismissing the progress dialog
                            progressDialog.dismiss();

                            //displaying success toast 
                            Toast.makeText(getApplicationContext(), "File Uploaded ", Toast.LENGTH_LONG).show();

                            //creating the upload object to store uploaded image details 
                            Upload upload = new Upload(editTextName.getText().toString().trim(), taskSnapshot.getDownloadUrl().toString());

                            //adding an upload to firebase database 
                            String uploadId = mDatabase.push().getKey();
                            mDatabase.child(uploadId).setValue(upload);
                        }
                    })
                    .addOnFailureListener(new OnFailureListener() {
                        @Override
                        public void onFailure(@NonNull Exception exception) {
                            progressDialog.dismiss();
                            Toast.makeText(getApplicationContext(), exception.getMessage(), Toast.LENGTH_LONG).show();
                        }
                    })
                    .addOnProgressListener(new OnProgressListener<UploadTask.TaskSnapshot>() {
                        @Override
                        public void onProgress(UploadTask.TaskSnapshot taskSnapshot) {
                            //displaying the upload progress 
                            double progress = (100.0 * taskSnapshot.getBytesTransferred()) / taskSnapshot.getTotalByteCount();
                            progressDialog.setMessage("Uploaded " + ((int) progress) + "%...");
                        }
                    });

Ora per recuperare tutte le immagini memorizzate nel database di Firebase puoi usare

//adding an event listener to fetch values
        mDatabase.addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot snapshot) {
                //dismissing the progress dialog 
                progressDialog.dismiss();

                //iterating through all the values in database
                for (DataSnapshot postSnapshot : snapshot.getChildren()) {
                    Upload upload = postSnapshot.getValue(Upload.class);
                    uploads.add(upload);
                }
                //creating adapter
                adapter = new MyAdapter(getApplicationContext(), uploads);

                //adding adapter to recyclerview
                recyclerView.setAdapter(adapter);
            }

            @Override
            public void onCancelled(DatabaseError databaseError) {
                progressDialog.dismiss();
            }
        });

Per maggiori dettagli puoi vedere il mio post Firebase Storage Example .


Ho seguito il tuo esempio nel collegamento, ma le immagini non vengono visualizzate da Firebase in RecyclerView
Wolfiebae

1

Quindi avevo un progetto che richiedeva il download di risorse dall'archivio Firebase, quindi ho dovuto risolvere questo problema da solo. Ecco come:

1- Per prima cosa, crea un modello di dati, ad esempio class Choice{}, In quella classe definisce una variabile String chiamata Nome immagine, quindi sarà così

class Choice {
    .....
    String imageName;
}

2- da un database / database firebase, vai e codifica i nomi delle immagini negli oggetti, quindi se hai un nome immagine chiamato Apple.png, crea l'oggetto da

Choice myChoice = new Choice(...,....,"Apple.png");

3- Ora, ottieni il link per le risorse nel tuo archivio Firebase che sarà qualcosa del genere

gs://your-project-name.appspot.com/

come questo

4- infine, inizializza il tuo riferimento di archiviazione Firebase e inizia a ottenere i file da un ciclo del genere

storageRef = storage.getReferenceFromUrl(firebaseRefURL).child(imagePath);

File localFile = File.createTempFile("images", "png");
storageRef.getFile(localFile).addOnSuccessListener(new OnSuccessListener<FileDownloadTask.TaskSnapshot>() {

@Override
public void onSuccess(FileDownloadTask.TaskSnapshot taskSnapshot) {
    //Dismiss Progress Dialog\\
}

5- questo è tutto


1
#In Python

import firebase_admin
from firebase_admin import credentials
from firebase_admin import storage
import datetime
import urllib.request


def image_download(url, name_img) :
    urllib.request.urlretrieve(url, name_img)

cred = credentials.Certificate("credentials.json")

# Initialize the app with a service account, granting admin privileges
app = firebase_admin.initialize_app(cred, {
    'storageBucket': 'YOURSTORAGEBUCKETNAME.appspot.com',
})
url_img = "gs://YOURSTORAGEBUCKETNAME.appspot.com/"
bucket_1 = storage.bucket(app=app)
image_urls = []

for blob in bucket_1.list_blobs():
    name = str(blob.name)
    #print(name)
    blob_img = bucket_1.blob(name)
    X_url = blob_img.generate_signed_url(datetime.timedelta(seconds = 300), method='GET')
    #print(X_url)
    image_urls.append(X_url)


PATH = ['Where you want to save the image']
for path in PATH:
    i = 1
    for url  in image_urls:
        name_img = str(path + "image"+str(i)+".jpg")
        image_download(url, name_img)
        i+=1

Non c'è bisogno di API, basta una semplice classe Python e la parola chiave blob
Milan Hazra,

0

Sto usando AngularFiree utilizzo quanto segue per ottenere tutti i filedownloadURL

getPhotos(id: string): Observable<string[]> {
    const ref = this.storage.ref(`photos/${id}`)
    return ref.listAll().pipe(switchMap(list => {
      const calls: Promise<string>[] = [];
      list.items.forEach(item => calls.push(item.getDownloadURL()))
      return Promise.all(calls)
    }));
}

-1

Per Android la migliore pratica è usare FirebaseUI e Glide.

Devi aggiungerlo sulla tua gradle / app per ottenere la libreria. Nota che ha già Glide su di esso!

implementation 'com.firebaseui:firebase-ui-storage:4.1.0'

E poi nel tuo codice usa

// Reference to an image file in Cloud Storage
StorageReference storageReference = FirebaseStorage.getInstance().getReference();

// ImageView in your Activity
ImageView imageView = findViewById(R.id.imageView);

// Download directly from StorageReference using Glide
// (See MyAppGlideModule for Loader registration)
GlideApp.with(this /* context */)
        .load(storageReference)
        .into(imageView);
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.