From 5e8476c7f5cac8f89a9c80e4433dadd0023d22c7 Mon Sep 17 00:00:00 2001 From: Bill Erickson <berickxx@gmail.com> Date: Tue, 26 Mar 2019 11:17:35 -0400 Subject: [PATCH] LP1821382 Add Items to Bucket menu action Includes changes to the existing record bucket dialog to support all bucket types. Signed-off-by: Bill Erickson <berickxx@gmail.com> Signed-off-by: Dan Wells <dbw2@calvin.edu> --- .../app/staff/cat/vandelay/queue.component.html | 4 +- .../staff/catalog/basket-actions.component.html | 4 +- .../app/staff/catalog/basket-actions.component.ts | 14 ++- .../staff/catalog/record/actions.component.html | 4 +- .../staff/catalog/record/holdings.component.html | 6 ++ .../app/staff/catalog/record/holdings.component.ts | 17 +++ .../app/staff/catalog/result/record.component.html | 12 --- Open-ILS/src/eg2/src/app/staff/common.module.ts | 6 +- ...component.html => bucket-dialog.component.html} | 24 ++--- ...log.component.ts => bucket-dialog.component.ts} | 118 ++++++++++++++------- 10 files changed, 128 insertions(+), 81 deletions(-) rename Open-ILS/src/eg2/src/app/staff/share/buckets/{record-bucket-dialog.component.html => bucket-dialog.component.html} (72%) rename Open-ILS/src/eg2/src/app/staff/share/buckets/{record-bucket-dialog.component.ts => bucket-dialog.component.ts} (56%) diff --git a/Open-ILS/src/eg2/src/app/staff/cat/vandelay/queue.component.html b/Open-ILS/src/eg2/src/app/staff/cat/vandelay/queue.component.html index e4ef84565b..2c1b3c3215 100644 --- a/Open-ILS/src/eg2/src/app/staff/cat/vandelay/queue.component.html +++ b/Open-ILS/src/eg2/src/app/staff/cat/vandelay/queue.component.html @@ -75,8 +75,8 @@ </li> <li class="list-group-item"> <div class="d-flex"> - <eg-record-bucket-dialog #bucketDialog [queueId]="queueId"> - </eg-record-bucket-dialog> + <eg-bucket-dialog #bucketDialog bucketClass="biblio" [fromBibQueue]="queueId"> + </eg-bucket-dialog> <div class="flex-1"> <a [routerLink]="" (click)="bucketDialog.open({size:'lg'})" i18n> Copy Queue To Bucket diff --git a/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.html b/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.html index 5837acee84..4857db8cc1 100644 --- a/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.html +++ b/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.html @@ -1,5 +1,5 @@ -<eg-record-bucket-dialog #addBasketToBucketDialog> -</eg-record-bucket-dialog> +<eg-bucket-dialog #addBasketToBucketDialog> +</eg-bucket-dialog> <div class="row"> <div class="col-lg-4 pr-1"> diff --git a/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.ts b/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.ts index e00a396d17..f96df6fd75 100644 --- a/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.ts +++ b/Open-ILS/src/eg2/src/app/staff/catalog/basket-actions.component.ts @@ -5,8 +5,8 @@ import {Router} from '@angular/router'; import {NetService} from '@eg/core/net.service'; import {AuthService} from '@eg/core/auth.service'; import {PrintService} from '@eg/share/print/print.service'; -import {RecordBucketDialogComponent - } from '@eg/staff/share/buckets/record-bucket-dialog.component'; +import {BucketDialogComponent + } from '@eg/staff/share/buckets/bucket-dialog.component'; @Component({ selector: 'eg-catalog-basket-actions', @@ -17,7 +17,7 @@ export class BasketActionsComponent implements OnInit { basketAction: string; @ViewChild('addBasketToBucketDialog') - addToBucketDialog: RecordBucketDialogComponent; + addToBucketDialog: BucketDialogComponent; constructor( private router: Router, @@ -89,8 +89,12 @@ export class BasketActionsComponent implements OnInit { case 'bucket': this.basket.getRecordIds().then(ids => { - this.addToBucketDialog.recordId = ids; - this.addToBucketDialog.open({size: 'lg'}); + this.addToBucketDialog.bucketClass = 'biblio'; + this.addToBucketDialog.itemIds = ids; + this.addToBucketDialog.open({size: 'lg'}).then( + ok => {}, + dismissed => {} + ); }); break; diff --git a/Open-ILS/src/eg2/src/app/staff/catalog/record/actions.component.html b/Open-ILS/src/eg2/src/app/staff/catalog/record/actions.component.html index c52609925e..7634103fd7 100644 --- a/Open-ILS/src/eg2/src/app/staff/catalog/record/actions.component.html +++ b/Open-ILS/src/eg2/src/app/staff/catalog/record/actions.component.html @@ -10,8 +10,8 @@ <eg-string key="catalog.record.toast.cleared" text="Record Marks Cleared"></eg-string> -<eg-record-bucket-dialog #recordBucketDialog [recordId]="recId"> -</eg-record-bucket-dialog> +<eg-bucket-dialog #recordBucketDialog bucketClass="biblio" [itemIds]="[recId]"> +</eg-bucket-dialog> <div class="row ml-0 mr-0"> diff --git a/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.html b/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.html index 42366eded1..dddba6ede2 100644 --- a/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.html +++ b/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.html @@ -49,6 +49,7 @@ <eg-copy-alerts-dialog #copyAlertsDialog></eg-copy-alerts-dialog> <eg-replace-barcode-dialog #replaceBarcode></eg-replace-barcode-dialog> <eg-delete-volcopy-dialog #deleteVolcopy></eg-delete-volcopy-dialog> +<eg-bucket-dialog #bucketDialog></eg-bucket-dialog> <!-- holdings grid --> <div class='eg-copies w-100 mt-3'> @@ -106,6 +107,11 @@ (onClick)="openItemNotes($event, 'create')"> </eg-grid-toolbar-action> + <eg-grid-toolbar-action + i18n-group group="Add" i18n-label label="Add Items To Bucket" + (onClick)="openBucketDialog($event)"> + Z</eg-grid-toolbar-action> + <!-- row actions: Edit --> <eg-grid-toolbar-action diff --git a/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.ts b/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.ts index fea6385403..75efc7a461 100644 --- a/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.ts +++ b/Open-ILS/src/eg2/src/app/staff/catalog/record/holdings.component.ts @@ -26,6 +26,8 @@ import {ReplaceBarcodeDialogComponent } from '@eg/staff/share/holdings/replace-barcode-dialog.component'; import {DeleteVolcopyDialogComponent } from '@eg/staff/share/holdings/delete-volcopy-dialog.component'; +import {BucketDialogComponent + } from '@eg/staff/share/buckets/bucket-dialog.component'; // The holdings grid models a single HoldingsTree, composed of HoldingsTreeNodes // flattened on-demand into a list of HoldingEntry objects. @@ -95,6 +97,8 @@ export class HoldingsMaintenanceComponent implements OnInit { private replaceBarcode: ReplaceBarcodeDialogComponent; @ViewChild('deleteVolcopy') private deleteVolcopy: DeleteVolcopyDialogComponent; + @ViewChild('bucketDialog') + private bucketDialog: BucketDialogComponent; holdingsTree: HoldingsTree; @@ -839,4 +843,17 @@ export class HoldingsMaintenanceComponent implements OnInit { const params = {target: copyIds, holdFor: 'staff'}; this.router.navigate(['/staff/catalog/hold/C'], {queryParams: params}); } + + openBucketDialog(rows: HoldingsEntry[]) { + const copyIds = this.selectedCopyIds(rows); + if (copyIds.length > 0) { + this.bucketDialog.bucketClass = 'copy'; + this.bucketDialog.itemIds = copyIds; + this.bucketDialog.open({size: 'lg'}).then( + // No need to reload the grid after adding items to buckets. + () => {}, + dismissed => {} + ); + } + } } diff --git a/Open-ILS/src/eg2/src/app/staff/catalog/result/record.component.html b/Open-ILS/src/eg2/src/app/staff/catalog/result/record.component.html index 90f066b1e9..9a65dafc60 100644 --- a/Open-ILS/src/eg2/src/app/staff/catalog/result/record.component.html +++ b/Open-ILS/src/eg2/src/app/staff/catalog/result/record.component.html @@ -3,8 +3,6 @@ routerLink's egDateFilter's --> -<eg-record-bucket-dialog #addToListDialog> -</eg-record-bucket-dialog> <div class="col-lg-12 card tight-card mb-2 bg-light"> <div class="card-body"> @@ -127,16 +125,6 @@ <span i18n>Place Hold</span> </button> </span> - <!-- - <span class="pl-1"> - <button - (click)="addToListDialog.recordId=summary.record.id(); addToListDialog.open({size: 'lg'})" - class="btn btn-sm btn-info label-with-material-icon small-text-1"> - <span class="material-icons">playlist_add_check</span> - <span i18n>Add to List</span> - </button> - </span> - --> </div> </div> </div> diff --git a/Open-ILS/src/eg2/src/app/staff/common.module.ts b/Open-ILS/src/eg2/src/app/staff/common.module.ts index 5a83f8ac29..9c822a2c6c 100644 --- a/Open-ILS/src/eg2/src/app/staff/common.module.ts +++ b/Open-ILS/src/eg2/src/app/staff/common.module.ts @@ -17,7 +17,7 @@ import {StringService} from '@eg/share/string/string.service'; import {TitleComponent} from '@eg/share/title/title.component'; import {FmRecordEditorComponent} from '@eg/share/fm-editor/fm-editor.component'; import {DateSelectComponent} from '@eg/share/date-select/date-select.component'; -import {RecordBucketDialogComponent} from '@eg/staff/share/buckets/record-bucket-dialog.component'; +import {BucketDialogComponent} from '@eg/staff/share/buckets/bucket-dialog.component'; import {BibSummaryComponent} from '@eg/staff/share/bib-summary/bib-summary.component'; import {TranslateComponent} from '@eg/staff/share/translate/translate.component'; import {AdminPageComponent} from '@eg/staff/share/admin-page/admin-page.component'; @@ -40,7 +40,7 @@ import {AdminPageComponent} from '@eg/staff/share/admin-page/admin-page.componen OpChangeComponent, FmRecordEditorComponent, DateSelectComponent, - RecordBucketDialogComponent, + BucketDialogComponent, BibSummaryComponent, TranslateComponent, AdminPageComponent @@ -64,7 +64,7 @@ import {AdminPageComponent} from '@eg/staff/share/admin-page/admin-page.componen OpChangeComponent, FmRecordEditorComponent, DateSelectComponent, - RecordBucketDialogComponent, + BucketDialogComponent, BibSummaryComponent, TranslateComponent, AdminPageComponent diff --git a/Open-ILS/src/eg2/src/app/staff/share/buckets/record-bucket-dialog.component.html b/Open-ILS/src/eg2/src/app/staff/share/buckets/bucket-dialog.component.html similarity index 72% rename from Open-ILS/src/eg2/src/app/staff/share/buckets/record-bucket-dialog.component.html rename to Open-ILS/src/eg2/src/app/staff/share/buckets/bucket-dialog.component.html index a2c88b8e34..32b6e2ec74 100644 --- a/Open-ILS/src/eg2/src/app/staff/share/buckets/record-bucket-dialog.component.html +++ b/Open-ILS/src/eg2/src/app/staff/share/buckets/bucket-dialog.component.html @@ -1,13 +1,13 @@ <ng-template #dialogContent> <div class="modal-header bg-info"> <h4 class="modal-title"> - <ng-container *ngIf="recIds.length > 0"> - <span *ngIf="recIds.length == 1" i18n> - Add Record #{{recIds[0]}} to Bucket</span> - <span *ngIf="recIds.length > 1" i18n> - Add {{recIds.length}} Record(s) to Bucket</span> + <ng-container *ngIf="itemIds.length > 0"> + <span *ngIf="itemIds.length == 1" i18n> + Add Item #{{itemIds[0]}} to Bucket</span> + <span *ngIf="itemIds.length > 1" i18n> + Add {{itemIds.length}} Items to Bucket</span> </ng-container> - <span *ngIf="qId" i18n>Add Records from queue #{{qId}} to Bucket</span> + <span *ngIf="fromBibQueue" i18n>Add Records from queue #{{fromBibQueue}} to Bucket</span> </h4> <button type="button" class="close" i18n-aria-label aria-label="Close" @@ -19,14 +19,10 @@ <div class="row"> <div class="col-lg-3 font-weight-bold" i18n>Name of existing bucket</div> <div class="col-lg-5"> - <select - class="form-control" - placeholder="Existing Bucket..." - i18n-placeholder - [(ngModel)]="selectedBucket"> - <option *ngFor="let bkt of buckets" - value="{{bkt.id()}}">{{bkt.name()}}</option> - </select> + <eg-combobox [entries]="formatBucketEntries()" + (onChange)="bucketChanged($event)" + placeholder="Existing Bucket..." i18n-placeholder> + </eg-combobox> </div> <div class="col-lg-4"> <button class="btn btn-info" (click)="addToSelected()" i18n diff --git a/Open-ILS/src/eg2/src/app/staff/share/buckets/record-bucket-dialog.component.ts b/Open-ILS/src/eg2/src/app/staff/share/buckets/bucket-dialog.component.ts similarity index 56% rename from Open-ILS/src/eg2/src/app/staff/share/buckets/record-bucket-dialog.component.ts rename to Open-ILS/src/eg2/src/app/staff/share/buckets/bucket-dialog.component.ts index f1f6f19cfa..1300f0f3e3 100644 --- a/Open-ILS/src/eg2/src/app/staff/share/buckets/record-bucket-dialog.component.ts +++ b/Open-ILS/src/eg2/src/app/staff/share/buckets/bucket-dialog.component.ts @@ -6,37 +6,36 @@ import {ToastService} from '@eg/share/toast/toast.service'; import {AuthService} from '@eg/core/auth.service'; import {DialogComponent} from '@eg/share/dialog/dialog.component'; import {NgbModal} from '@ng-bootstrap/ng-bootstrap'; +import {ComboboxEntry} from '@eg/share/combobox/combobox.component'; /** * Dialog for adding bib records to new and existing record buckets. */ @Component({ - selector: 'eg-record-bucket-dialog', - templateUrl: 'record-bucket-dialog.component.html' + selector: 'eg-bucket-dialog', + templateUrl: 'bucket-dialog.component.html' }) -export class RecordBucketDialogComponent - extends DialogComponent implements OnInit { +export class BucketDialogComponent extends DialogComponent implements OnInit { selectedBucket: number; newBucketName: string; newBucketDesc: string; buckets: any[]; - @Input() bucketType: string; + @Input() bucketClass: 'biblio' | 'user' | 'callnumber' | 'copy'; + @Input() bucketType: string; // e.g. staff_client - // Add one or more bib records to bucket by ID. - recIds: number[]; - @Input() set recordId(id: number | number[]) { - this.recIds = [].concat(id); - } + // ID's of items to add to the bucket + @Input() itemIds: number[]; - // Add items from a (vandelay) bib queue to a bucket - qId: number; - @Input() set queueId(id: number) { - this.qId = id; - } + // If set, itemIds will be derived from the records in a bib queue + @Input() fromBibQueue: number; + + // bucket item classes are these plus a following 'i'. + bucketFmClass: 'ccb' | 'ccnb' | 'cbreb' | 'cub'; + targetField: string; constructor( private modal: NgbModal, // required for passing to parent @@ -47,40 +46,77 @@ export class RecordBucketDialogComponent private evt: EventService, private auth: AuthService) { super(modal); // required for subclassing - this.recIds = []; + this.buckets = []; + this.itemIds = []; + this.fromBibQueue = null; } ngOnInit() { - - if (this.qId) { - this.bucketType = 'vandelay_queue'; - } else { - this.bucketType = 'staff_client'; - } - this.onOpen$.subscribe(ok => { - // Reset data on dialog open - - this.selectedBucket = null; - this.newBucketName = ''; - this.newBucketDesc = ''; - + this.reset(); // Reset data on dialog open this.net.request( 'open-ils.actor', 'open-ils.actor.container.retrieve_by_class.authoritative', this.auth.token(), this.auth.user().id(), - 'biblio', this.bucketType + this.bucketClass, this.bucketType ).subscribe(buckets => this.buckets = buckets); }); } + reset() { + this.selectedBucket = null; + this.newBucketName = ''; + this.newBucketDesc = ''; + + if (!this.bucketClass) { + this.bucketClass = 'biblio'; + } + + switch (this.bucketClass) { + case 'biblio': + if (this.fromBibQueue) { + this.bucketType = 'vandelay_queue'; + } + this.bucketFmClass = 'cbreb'; + this.targetField = 'target_biblio_record_entry'; + break; + case 'copy': + this.bucketFmClass = 'ccb'; + this.targetField = 'target_copy'; + break; + case 'callnumber': + this.bucketFmClass = 'ccnb'; + this.targetField = 'target_call_number'; + break; + case 'user': + this.bucketFmClass = 'cub'; + this.targetField = 'target_user'; + } + + if (!this.bucketType) { + this.bucketType = 'staff_client'; + } + } + addToSelected() { this.addToBucket(this.selectedBucket); } + bucketChanged(entry: ComboboxEntry) { + if (entry) { + this.selectedBucket = entry.id; + } else { + this.selectedBucket = null; + } + } + + formatBucketEntries(): ComboboxEntry[] { + return this.buckets.map(b => ({id: b.id(), label: b.name()})); + } + // Create a new bucket then add the record addToNew() { - const bucket = this.idl.create('cbreb'); + const bucket = this.idl.create(this.bucketFmClass); bucket.owner(this.auth.user().id()); bucket.name(this.newBucketName); @@ -90,7 +126,7 @@ export class RecordBucketDialogComponent this.net.request( 'open-ils.actor', 'open-ils.actor.container.create', - this.auth.token(), 'biblio', bucket + this.auth.token(), this.bucketClass, bucket ).subscribe(bktId => { const evt = this.evt.parse(bktId); if (evt) { @@ -106,27 +142,27 @@ export class RecordBucketDialogComponent } addToBucket(id: number) { - if (this.recIds.length > 0) { + if (this.itemIds.length > 0) { this.addRecordToBucket(id); - } else if (this.qId) { - this.addQueueToBucket(id); + } else if (this.fromBibQueue) { + this.addBibQueueToBucket(id); } } // Add the record(s) to the bucket with provided ID. addRecordToBucket(bucketId: number) { const items = []; - this.recIds.forEach(recId => { - const item = this.idl.create('cbrebi'); + this.itemIds.forEach(itemId => { + const item = this.idl.create(this.bucketFmClass + 'i'); item.bucket(bucketId); - item.target_biblio_record_entry(recId); + item[this.targetField](itemId); items.push(item); }); this.net.request( 'open-ils.actor', 'open-ils.actor.container.item.create', - this.auth.token(), 'biblio', items + this.auth.token(), this.bucketClass, items ).subscribe(resp => { const evt = this.evt.parse(resp); if (evt) { @@ -137,14 +173,14 @@ export class RecordBucketDialogComponent }); } - addQueueToBucket(bucketId: number) { + addBibQueueToBucket(bucketId: number) { const bucket = this.buckets.filter(b => b.id() === bucketId)[0]; if (!bucket) { return; } this.net.request( 'open-ils.vandelay', 'open-ils.vandelay.bib_queue.to_bucket', - this.auth.token(), this.qId, bucket.name() + this.auth.token(), this.fromBibQueue, bucket.name() ).toPromise().then(resp => { const evt = this.evt.parse(resp); if (evt) { -- 2.11.0