Моя основная цель в этом модуле - загрузить изображение профиля пользователя в Firebase Storage и сохранить URL-адрес фотографии в Firestore (Cloud Firestore).
Примечание:
Я пробую следующий сценарий:
Это поле пользователя:
Это ошибка возникает, когда я пытаюсь загрузить изображение в хранилище Firebase:
update-profile.component.ts
userId: string;
fname: string;
studentId: string;
@ViewChild('filePicker') filePickerRef: ElementRef<HTMLInputElement>;
@Input() showPreview = true;
//The Selected Image in the File Explorer
selectedImage: any;
//The variable that holds Photo URL
uploadedImage: any;
constructor(private auth: AuthService,
private afs: AngularFirestore,
private loadingCtrl: LoadingController,
private toaster: ToastController,
private storage: AngularFireStorage,
private popOverCtrl: PopoverController) { }
ngOnInit() {
this.profileEditSub = this.auth.user$.subscribe(user => {
this.userId = user.userId;
this.fname = user.userName;
this.studentId = user.userSchoolId;
this.selectedImage = user.userPhoto;
});
}
onSubmit(form: NgForm){
const user = form.value.fname;
const studentId = form.value.studentId;
this.onUpdateUser(user, studentId);
}//
async onUpdateUser(name: string, studentNo: string){
const loading = await this.loadingCtrl.create({
message: 'Updating...',
spinner: 'crescent',
showBackdrop: true
});
//I call this method to upload the Image
this.uploadUserPhoto();
loading.present();
this.afs.collection('user').doc(this.userId).update({
'userName': name,
'userSchoolId': studentNo,
'userPhoto': this.uploadedImage, // Photo URL from Firebase Storage will be saved in here.
'editedAt': Date.now()
})
.then(() => {
loading.dismiss();
this.toast('Update Success', 'success');
this.closePopOver();
})
.catch(error => {
loading.dismiss();
this.toast(error.message, 'danger');
})
}//
//The method for uploading the photo.
uploadUserPhoto() {
var filePath = `${this.userId}/${this.selectedImage.name}_${new Date().getTime()}`;
const fileRef = this.storage.ref(filePath);
this.storage.upload(filePath, this.selectedImage).snapshotChanges().pipe(
finalize(() => {
fileRef.getDownloadURL().subscribe((url) => {
this.uploadedImage = url;
})
})
).subscribe();
}
onPickImage() {
this.filePickerRef.nativeElement.click();
}
onFileChosen(event: Event) {
const pickedFile = (event.target as HTMLInputElement).files[0];
if (!pickedFile) {
return;
}
const fr = new FileReader();
fr.onload = () => {
const dataUrl = fr.result.toString();
this.selectedImage = dataUrl;
};
fr.readAsDataURL(pickedFile);
}
update-profile.component.html
<!-- For the Image -->
<div class = "picker">
<img
class = "img"
[src] = "selectedImage"
*ngIf = "selectedImage && showPreview"
>
</div>
<input type = "file" accept = ".jpg,.png" *ngIf = "usePicker" #filePicker (change) = "onFileChosen($event)"/>
<ion-button class = "image-btn" (click) = "onPickImage()">
<ion-icon name = "camera" slot = "icon-only"></ion-icon>
</ion-button>
<!-- Other Textual Information -->
<form #f = "ngForm" (ngSubmit) = "onSubmit(f)">
<ion-list lines = "full">
<ion-item>
<ion-label position = "floating">Full Name:</ion-label>
<ion-input name = "fname" required type = "text" [(ngModel)] = "fname" #userCtrl = "ngModel"></ion-input>
</ion-item>
<ion-item>
<ion-label position = "floating">Student No:</ion-label>
<ion-input name = "studentId" required type = "number" [(ngModel)] = "studentId" #studentIds = "ngModel"></ion-input>
</ion-item>
<ion-button class = "ion-margin" type = "submit" expand = "block" shape = "round" [disabled] = "!f.valid">Edit User</ion-button>
</ion-list>
</form>
Спасибо тебе за это. Но я предполагаю, что проблема в том, что изображение не генерирует URL-адрес загрузки, потому что я проверяю переменную «uploadedImage» и ее значение undefined.
Но вы проверили, что он был загружен успешно? Вам всегда нужен обратный вызов ошибки, чтобы отловить ошибки в storage.upload
.
Я считаю, что вам не нужно использовать FileReader. Вы можете загрузить его напрямую. Проверьте это: stackoverflow.com/questions/46988902/…