add api actions to attachments page

This commit is contained in:
Kyle Spearrin 2018-01-31 21:56:47 -05:00
parent 99b0b57a5e
commit 77d1d272cc
2 changed files with 36 additions and 19 deletions

View File

@ -1,6 +1,6 @@
<div class="modal fade"> <div class="modal fade">
<div class="modal-dialog"> <div class="modal-dialog">
<div class="modal-content"> <form class="modal-content" #form (ngSubmit)="submit()" [appApiAction]="formPromise">
<div class="modal-body"> <div class="modal-body">
<div class="box" *ngIf="cipher && cipher.hasAttachments"> <div class="box" *ngIf="cipher && cipher.hasAttachments">
<div class="box-header"> <div class="box-header">
@ -14,8 +14,9 @@
<small class="row-sub-label">{{a.sizeName}}</small> <small class="row-sub-label">{{a.sizeName}}</small>
<div class="action-buttons no-pad"> <div class="action-buttons no-pad">
<a class="row-btn" href="#" appStopClick appBlurClick title="{{'delete' | i18n}}" <a class="row-btn" href="#" appStopClick appBlurClick title="{{'delete' | i18n}}"
(click)="delete(a)"> (click)="delete(a)" #deleteBtn [appApiAction]="deletePromises[a.id]">
<i class="fa fa-lg fa-trash-o"></i> <i class="fa fa-trash-o fa-lg fa-fw" [hidden]="deleteBtn.loading"></i>
<i class="fa fa-spinner fa-spin fa-lg fa-fw" [hidden]="!deleteBtn.loading"></i>
</a> </a>
</div> </div>
</div> </div>
@ -28,7 +29,7 @@
<div class="box-content no-hover"> <div class="box-content no-hover">
<div class="box-content-row"> <div class="box-content-row">
<label for="file">{{'file' | i18n}}</label> <label for="file">{{'file' | i18n}}</label>
<input type="file" id="file" name="file"> <input type="file" id="file" name="file" required>
</div> </div>
</div> </div>
<div class="box-footer"> <div class="box-footer">
@ -37,11 +38,12 @@
</div> </div>
</div> </div>
<div class="modal-footer"> <div class="modal-footer">
<button type="button" class="primary" appBlurClick (click)="save()"> <button appBlurClick type="submit" class="primary" title="{{'save' | i18n}}" [disabled]="form.loading">
<i class="fa fa-lg fa-save"></i> {{'save' | i18n}} <i class="fa fa-save fa-lg fa-fw" [hidden]="form.loading"></i>
<i class="fa fa-spinner fa-spin fa-lg fa-fw" [hidden]="!form.loading"></i>
</button> </button>
<button type="button" data-dismiss="modal">{{'close' | i18n}}</button> <button type="button" data-dismiss="modal">{{'close' | i18n}}</button>
</div> </div>
</div> </form>
</div> </div>
</div> </div>

View File

@ -32,6 +32,8 @@ export class AttachmentsComponent implements OnInit {
cipherDomain: Cipher; cipherDomain: Cipher;
hasUpdatedKey: boolean; hasUpdatedKey: boolean;
canAccessAttachments: boolean; canAccessAttachments: boolean;
formPromise: Promise<any>;
deletePromises: { [id: string]: Promise<any>; } = {};
constructor(private cipherService: CipherService, private analytics: Angulartics2, constructor(private cipherService: CipherService, private analytics: Angulartics2,
private toasterService: ToasterService, private i18nService: I18nService, private toasterService: ToasterService, private i18nService: I18nService,
@ -53,7 +55,7 @@ export class AttachmentsComponent implements OnInit {
} }
} }
async save() { async submit() {
if (!this.hasUpdatedKey) { if (!this.hasUpdatedKey) {
this.toasterService.popAsync('error', this.i18nService.t('errorOccurred'), this.toasterService.popAsync('error', this.i18nService.t('errorOccurred'),
this.i18nService.t('updateKey')); this.i18nService.t('updateKey'));
@ -74,10 +76,13 @@ export class AttachmentsComponent implements OnInit {
return; return;
} }
this.cipherDomain = await this.cipherService.saveAttachmentWithServer(this.cipherDomain, files[0]); try {
this.cipher = await this.cipherDomain.decrypt(); this.formPromise = this.cipherService.saveAttachmentWithServer(this.cipherDomain, files[0]);
this.analytics.eventTrack.next({ action: 'Added Attachment' }); this.cipherDomain = await this.formPromise;
this.toasterService.popAsync('success', null, this.i18nService.t('attachmentSaved')); this.cipher = await this.cipherDomain.decrypt();
this.analytics.eventTrack.next({ action: 'Added Attachment' });
this.toasterService.popAsync('success', null, this.i18nService.t('attachmentSaved'));
} catch { }
// reset file input // reset file input
// ref: https://stackoverflow.com/a/20552042 // ref: https://stackoverflow.com/a/20552042
@ -87,16 +92,26 @@ export class AttachmentsComponent implements OnInit {
} }
async delete(attachment: AttachmentView) { async delete(attachment: AttachmentView) {
if (this.deletePromises[attachment.id] != null) {
return;
}
if (!confirm(this.i18nService.t('deleteAttachmentConfirmation'))) { if (!confirm(this.i18nService.t('deleteAttachmentConfirmation'))) {
return; return;
} }
await this.cipherService.deleteAttachmentWithServer(this.cipher.id, attachment.id); try {
this.analytics.eventTrack.next({ action: 'Deleted Attachment' }); this.deletePromises[attachment.id] = this.cipherService.deleteAttachmentWithServer(
this.toasterService.popAsync('success', null, this.i18nService.t('deletedAttachment')); this.cipher.id, attachment.id);
const i = this.cipher.attachments.indexOf(attachment); await this.deletePromises[attachment.id];
if (i > -1) { this.analytics.eventTrack.next({ action: 'Deleted Attachment' });
this.cipher.attachments.splice(i, 1); this.toasterService.popAsync('success', null, this.i18nService.t('deletedAttachment'));
} const i = this.cipher.attachments.indexOf(attachment);
if (i > -1) {
this.cipher.attachments.splice(i, 1);
}
} catch { }
this.deletePromises[attachment.id] = null;
} }
} }