File

src/app/core/entity/entity-actions/entity-edit.service.ts

Description

Bulk edit fields of multiple entities at once.

Extends

CascadingEntityAction

Index

Methods

Constructor

constructor(entityMapper: EntityMapperService, schemaService: EntitySchemaService, entityRelationsService: EntityRelationsService, matDialog: MatDialog, entityActionsService: EntityActionsService, unsavedChanges: UnsavedChangesService)
Parameters :
Name Type Optional
entityMapper EntityMapperService No
schemaService EntitySchemaService No
entityRelationsService EntityRelationsService No
matDialog MatDialog No
entityActionsService EntityActionsService No
unsavedChanges UnsavedChangesService No

Methods

Async edit
edit(entitiesToEdit: E | E[], entityType: EntityConstructor)
Type parameters :
  • E

Shows a confirmation dialog to the user and edit the entity if the user confirms.

This also triggers a toast message, enabling the user to undo the action.

Parameters :
Name Type Optional Description
entitiesToEdit E | E[] No

The entities to apply a bulk edit to.

entityType EntityConstructor No
Returns : Promise<boolean>
Async editEntity
editEntity(action: BulkEditAction, entitiesToEdit: E | E[])
Type parameters :
  • E
Parameters :
Name Type Optional
action BulkEditAction No
entitiesToEdit E | E[] No
Returns : Promise<literal type>
Protected Async cascadeActionToRelatedEntities
cascadeActionToRelatedEntities(entity: Entity, compositeAction: (relatedEntity: Entity,refField: string,entity: Entity) => void, aggregateAction: (relatedEntity: Entity,refField: string,entity: Entity) => void)
Inherited from CascadingEntityAction

Recursively call the given actions on all related entities that contain a reference to the given entity.

Returns an array of all affected related entities (excluding the given entity) in their state before the action to support an undo action.

Parameters :
Name Type Optional Description
entity Entity No
compositeAction function No

The method to be called on relationships with entityReferenceRole "composite"

aggregateAction function No

The method to be called on relationships with entityReferenceRole "aggregate" (this is also the default for any relationship)

import { Injectable } from "@angular/core";
import { EntityMapperService } from "../entity-mapper/entity-mapper.service";
import { Entity, EntityConstructor } from "../model/entity";
import { EntitySchemaService } from "../schema/entity-schema.service";
import { CascadingEntityAction } from "./cascading-entity-action";
import { UnsavedChangesService } from "app/core/entity-details/form/unsaved-changes.service";
import { lastValueFrom } from "rxjs";
import {
  BulkEditAction,
  EntityBulkEditComponent,
} from "./entity-bulk-edit/entity-bulk-edit.component";
import { MatDialog } from "@angular/material/dialog";
import { EntityActionsService } from "./entity-actions.service";
import { asArray } from "app/utils/asArray";
import { EntityRelationsService } from "../entity-mapper/entity-relations.service";

/**
 * Bulk edit fields of multiple entities at once.
 */
@Injectable({
  providedIn: "root",
})
export class EntityEditService extends CascadingEntityAction {
  constructor(
    protected override entityMapper: EntityMapperService,
    protected override schemaService: EntitySchemaService,
    protected override entityRelationsService: EntityRelationsService,
    private matDialog: MatDialog,
    private entityActionsService: EntityActionsService,
    private unsavedChanges: UnsavedChangesService,
  ) {
    super(entityMapper, schemaService, entityRelationsService);
  }

  /**
   * Shows a confirmation dialog to the user
   * and edit the entity if the user confirms.
   *
   * This also triggers a toast message, enabling the user to undo the action.
   *
   * @param entitiesToEdit The entities to apply a bulk edit to.
   * @param entityType
   */
  async edit<E extends Entity>(
    entitiesToEdit: E | E[],
    entityType: EntityConstructor,
  ): Promise<boolean> {
    let entities = asArray(entitiesToEdit);
    const dialogRef = this.matDialog.open(EntityBulkEditComponent, {
      maxHeight: "90vh",
      data: { entityConstructor: entityType, entitiesToEdit: entities },
    });
    const action: BulkEditAction = await lastValueFrom(dialogRef.afterClosed());

    if (action) {
      const result = await this.editEntity(action, entitiesToEdit);
      this.entityActionsService.showSnackbarConfirmationWithUndo(
        this.entityActionsService.generateMessageForConfirmationWithUndo(
          entities,
          $localize`:Entity action confirmation message verb:edited`,
        ),
        result.originalEntities,
      );
    }
    return true;
  }

  async editEntity<E extends Entity>(
    action: BulkEditAction,
    entitiesToEdit: E | E[],
  ): Promise<{ success: boolean; originalEntities: E[]; newEntities: E[] }> {
    if (!action) {
      return;
    }

    let originalEntities: E[] = Array.isArray(entitiesToEdit)
      ? entitiesToEdit
      : [entitiesToEdit];
    const newEntities: E[] = originalEntities.map((e) => e.copy());

    for (const e of newEntities) {
      e[action.selectedField] = action.value;
      await this.entityMapper.save(e);
    }

    this.unsavedChanges.pending = false;
    return {
      success: true,
      originalEntities,
      newEntities,
    };
  }
}

results matching ""

    No results matching ""