Fix download with restrictive permissions

This commit is contained in:
rubikscraft 2022-04-21 17:53:02 +02:00
parent cd7c3b387c
commit 779c9f44d2
No known key found for this signature in database
GPG key ID: 1463EBE9200A5CD4
6 changed files with 68 additions and 15 deletions

View file

@ -40,7 +40,7 @@ export class ViewComponent implements OnInit {
}
share() {
this.utilService.shareLink(this.imageLinks.source);
this.utilService.shareFile(this.imageLinks.source);
}
goBackHome() {

View file

@ -1,17 +1,17 @@
import { Component, Inject } from '@angular/core';
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';
export interface DialogButton {
export interface ConfirmDialogButton {
text: string;
name: string;
color: string;
}
export interface DialogData {
export interface ConfirmDialogData {
title: string;
description?: string;
buttons: DialogButton[];
buttons: ConfirmDialogButton[];
}
@Component({
@ -22,7 +22,7 @@ export interface DialogData {
export class ConfirmDialogComponent {
constructor(
public dialogRef: MatDialogRef<ConfirmDialogComponent>,
@Inject(MAT_DIALOG_DATA) public data: DialogData,
@Inject(MAT_DIALOG_DATA) public data: ConfirmDialogData,
) {}
onButton(name: string) {

View file

@ -0,0 +1,4 @@
<div class="centered">
<h2>Downloading {{ data.name }}...</h2>
<mat-progress-bar mode="indeterminate" color="accent"></mat-progress-bar>
</div>

View file

@ -0,0 +1,18 @@
import { Component, Inject } from '@angular/core';
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';
export interface DownloadDialogData {
name: string;
}
@Component({
selector: 'download-dialog',
templateUrl: './download-dialog.component.html',
})
export class DownloadDialogComponent {
constructor(
public dialogRef: MatDialogRef<DownloadDialogComponent>,
@Inject(MAT_DIALOG_DATA) public data: DownloadDialogData,
) {}
}

View file

@ -2,6 +2,7 @@ import { CommonModule } from '@angular/common';
import { ModuleWithProviders, NgModule } from '@angular/core';
import { MatButtonModule } from '@angular/material/button';
import { MatDialogModule } from '@angular/material/dialog';
import { MatProgressBarModule } from '@angular/material/progress-bar';
import {
MatSnackBarModule,
MAT_SNACK_BAR_DEFAULT_OPTIONS
@ -9,6 +10,7 @@ import {
import { RouterModule } from '@angular/router';
import { ApiErrorService } from './api-error.service';
import { ConfirmDialogComponent } from './confirm-dialog/confirm-dialog.component';
import { DownloadDialogComponent } from './download-dialog/download-dialog.component';
@NgModule({
imports: [
@ -16,9 +18,10 @@ import { ConfirmDialogComponent } from './confirm-dialog/confirm-dialog.componen
MatSnackBarModule,
MatDialogModule,
MatButtonModule,
MatProgressBarModule,
RouterModule,
],
declarations: [ConfirmDialogComponent],
declarations: [ConfirmDialogComponent, DownloadDialogComponent],
})
export class UtilModule {
static forRoot(): ModuleWithProviders<UtilModule> {

View file

@ -11,8 +11,9 @@ import { Logger } from 'src/app/services/logger/logger.service';
import { SnackBarType } from '../../models/dto/snack-bar-type.dto';
import {
ConfirmDialogComponent,
DialogData
ConfirmDialogData
} from './confirm-dialog/confirm-dialog.component';
import { DownloadDialogComponent } from './download-dialog/download-dialog.component';
@Injectable({
providedIn: 'root',
@ -77,11 +78,14 @@ export class UtilService {
});
}
public async showDialog(options: DialogData): Promise<string | undefined> {
public async showDialog(
options: ConfirmDialogData
): Promise<string | undefined> {
return new Promise((resolve, reject) => {
const ref = this.dialog.open(ConfirmDialogComponent, {
data: options,
disableClose: true,
closeOnNavigation: false,
});
const subscription = ref.beforeClosed().subscribe((result) => {
subscription.unsubscribe();
@ -90,13 +94,37 @@ export class UtilService {
});
}
public downloadFile(url: string) {
const link = document.createElement('a');
link.href = url;
link.download = url.split('/').pop() ?? '';
link.click();
public showDownloadDialog(filename: string): () => void {
const ref = this.dialog.open(DownloadDialogComponent, {
data: { name: filename },
disableClose: true,
closeOnNavigation: false,
});
link.remove();
return () => ref.close();
}
public async downloadFile(url: string) {
const closeDialog = this.showDownloadDialog('image');
const file = await this.api.getBuffer(url);
if (HasFailed(file)) {
closeDialog();
this.logger.error(file.getReason());
this.showSnackBar('Error while downloading image', SnackBarType.Error);
return;
}
// Download with the browser
const a = document.createElement('a');
a.href = URL.createObjectURL(
new Blob([file.buffer], { type: file.mimeType })
);
a.download = file.name;
a.click();
closeDialog();
this.showSnackBar('Image downloaded', SnackBarType.Info);
}
public canShare(): boolean {
@ -121,7 +149,7 @@ export class UtilService {
return testShare;
}
public async shareLink(url: string) {
public async shareFile(url: string) {
if (!this.canShare()) {
this.showSnackBar(
'Sharing is not supported on your device',