Skip to content

[ETASK-23] Dynamic view configuration#333

Open
Retoocs wants to merge 35 commits into
release/6.5.0from
ETASK-23
Open

[ETASK-23] Dynamic view configuration#333
Retoocs wants to merge 35 commits into
release/6.5.0from
ETASK-23

Conversation

@Retoocs
Copy link
Copy Markdown
Contributor

@Retoocs Retoocs commented Jun 2, 2026

Description

Fixes

  • fixed initialization of allowed nets in task-view
  • header component button behavior logic
  • export all double drawer components

New features / improvements

  • introduced new configurable header options: meta-processIdentifier, meta-petriNetId
  • you can configure all allowed nets for the views by menu items
  • changed menu item URL to contain encoded case id instead of raw task id
  • enabled translation of create case button text
  • some new configuration options for views
  • expand possible configuration view options for double drawer

Other changes:

  • reworked parsing of filters in menu items
  • removed code for filter API since the filter process was deleted

Implements ETASK-23

Dependencies

No new dependencies were introduced

Third party dependencies

No new dependencies were introduced

Blocking Pull requests

Depends on #332

How Has Been This Tested?

Manually and by unit tests

Test Configuration

Name Tested on
OS Ubuntu 24.04.1 LTS
Runtime Node 23.6.1
Dependency Manager NPM 11.0.0
Framework version Angular 19.2.2
Run parameters
Other configuration

Checklist:

  • My code follows the style guidelines of this project
  • I have performed a self-review of my own code
  • My changes have been checked, personally or remotely, with @...
  • I have commented my code, particularly in hard-to-understand areas
  • I have resolved all conflicts with the target branch of the PR
  • I have updated and synced my code with the target branch
  • I have added tests that prove my fix is effective or that my feature works
  • New and existing tests pass locally with my changes:
    • Lint test
    • Unit tests
    • Integration tests
  • I have checked my contribution with code analysis tools:
  • I have made corresponding changes to the documentation:
    • Developer documentation
    • User Guides
    • Migration Guides

Summary by CodeRabbit

  • New Features

    • Configurable empty-state messages and icons across lists and paginators
    • Case header now shows Process Identifier and Petri Net ID
    • New simple case view and updated default navigation views
  • Bug Fixes & Improvements

    • Improved navigation, breadcrumbs and tab/case opening flows
    • Enhanced language-aware empty-text resolution and header behavior
    • Streamlined resource handling for more consistent UI
  • Removed Features

    • Filter save/load dialogs and related side‑menu integrations removed

Retoocs and others added 30 commits May 4, 2026 08:51
- update data field value
- export I18nFieldValue from core
- fix opening menu items
- add base64 encoding for menu item id
- fix ticket view
- implement filter resolving in single task view
- make single task view as a primary view
- update single task view configurations
- use untabbed single task view in menu
- implement menu item configurations in default simple task view
- fix header
- introduce default simple case view
- introduce navigation-item-new-case-configuration-factory.ts
- provide new case creation data token in default-simple-case-view.component.ts
- update case meta fields for header
- fix breadcrumbs redirect
- fix opening default view when clicking on breadcrumbs
- introduce empty content configuration
- fix data resolving
- fix getEmptyContentText
- fix new case button title translation
- improve filter allowed nets handling
- update default headers parsing
- use allAllowedNets metadata for filter
- update allowed nets logic for task view
- update filter parsing according to backend changes
- remove filter case implementations
- fix 99% of tests
- add todos
# Conflicts:
#	projects/netgrif-components-core/src/lib/navigation/utility/filter-extraction.service.ts
#	projects/netgrif-components-core/src/lib/utility/navigation-item-task-filter-factory.ts
#	projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/model/factory-methods.ts
#	projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/refs/default-case-ref-list-view/default-case-ref-list-view.component.html
#	projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/refs/default-case-ref-list-view/default-case-ref-list-view.component.ts
#	projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-case-view/default-tabbed-case-view.component.ts
- fix allow export menu item configuration
- create new filter field as text field for filter query
- introduce new field types
# Conflicts:
#	projects/netgrif-components-core/src/lib/filter/user-filters.service.ts
- rework allowed nets parsing
- fix filter type initialiazation
- rework search categories initialization
- update default component exports
Retoocs added 3 commits June 2, 2026 08:06
- fix bread crumbs
- implement task field's component headers configuration
@Retoocs Retoocs self-assigned this Jun 2, 2026
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Jun 2, 2026

Review Change Stack

Walkthrough

Switch navigation to menu-backed item data with Base64 itemCaseId routing; remove saved-filter services and dialogs; refactor filter/allowed-nets extraction and group-navigation constants; add filter-string query field and handleDataGroups utility; add localized empty-state inputs and extend header/case metadata; update views, modules, and tests.

Changes

Menu-driven navigation, filter refactor, and UI updates

Layer / File(s) Summary
Menu-based routing & resolver
nae.json, .../breadcrumbs/*, .../group-navigation-component-resolver/*, .../resources/engine-endpoint/menu-resource.service.ts
Adds menu resource entry, MenuResourceService, changes routing to Base64 itemCaseId, updates breadcrumbs to decode/encode item ids, and rewires resolver to load/inject NAE_NAVIGATION_ITEM_TASK_DATA.
Filter constants & extraction, allowed-nets factories
.../navigation/model/group-navigation-constants.ts, .../navigation/utility/*, .../allowed-nets/*, .../utility/navigation-item-task-filter-factory.ts
Splits/renames navigation constants for case/task, refactors extractCompleteFilterFromData to accept fieldId/filterType, updates navigationItemTaskFilterFactory and allowed-nets factories to accept navigation item data and inheritance flags.
Remove saved-filter flows & UI
.../filter/*, .../search/*, .../side-menu/*, .../dialog/*, projects/nae-example-app/*
Removes UserFiltersService and its tests, deletes save/load filter components/modules/dialogs and exports, removes additionalFilterData usage and related menu items, adjusting constructors and templates.
FilterStringQuery field & registration
.../data-fields/filter-field/*, .../data-fields/public-api.ts, .../data-fields/data-fields.module.ts
Adds AbstractFilterStringQueryFieldComponent, FilterStringQueryFieldComponent, template/scss/tests, FilterFieldValidation enum, and registers filter-string_query in data fields registry.
Data-group handling & resources
.../resources/engine-endpoint/utils/resource-utils.ts, .../task-resource.service.ts, .../menu-resource.service.ts, .../resources/public-api.ts, .../resources/interface/menu-item-data.ts
Introduces handleDataGroups utility, refactors task resource to use it, implements MenuResourceService.getItemData, and exports MenuResourceService and MenuItemData.
Localized empty-state & panels
.../panel/*, `.../view/*/components/list
paginator*, .../panel/task-panel-list/, .../navigation/default-/**`
Header/case meta & i18n
projects/netgrif-components-core/src/assets/i18n/*.json, .../header/case-header/*, .../panel/case-panel/*
Adds processIdentifier and petriNetId i18n labels and CaseMetaField enum members; exposes these meta fields in case headers and panels.
Default/tabbed/simple navigation components & exports
components/.../default-*/**/*, .../model/*, .../factory-methods.ts, .../navigation.module.ts, .../navigation/public-api.ts
Adds DefaultSimpleCaseView, updates default/tabbed builders to use typed task filters, allowed-nets, empty-state configs, updates factories, injected models, module declarations/exports, and tests.

Sequence Diagram(s)

sequenceDiagram
  participant Router
  participant Breadcrumbs
  participant GroupNavResolver
  participant MenuResourceService
  participant ViewComponent

  Router->>Breadcrumbs: itemCaseId (base64) param
  Breadcrumbs->>GroupNavResolver: createResolvedViewComponentPortal(encodedCaseId, injector)
  GroupNavResolver->>MenuResourceService: getItemData(encodedCaseId)
  MenuResourceService-->>GroupNavResolver: Array<DataGroup>
  GroupNavResolver-->>ViewComponent: ComponentPortal with NAE_NAVIGATION_ITEM_TASK_DATA
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

  • netgrif/components#300 — Overlaps on abstract-case-ref-base-field-component NAE_DEFAULT_HEADERS splitting/processing.
  • netgrif/components#299 — Related changes to case-ref header trimming and default-headers handling.
  • netgrif/components#323 — Related to export flow and Excel download integration referenced by DefaultSimpleCaseView export.

@Retoocs Retoocs marked this pull request as ready for review June 2, 2026 14:31
@Retoocs
Copy link
Copy Markdown
Contributor Author

Retoocs commented Jun 3, 2026

rabbit please review

@Retoocs
Copy link
Copy Markdown
Contributor Author

Retoocs commented Jun 3, 2026

@coderabbitai review this PR

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Jun 3, 2026

@Retoocs Sure! I'll start reviewing the PR right away.

✅ Action performed

Review finished.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@Retoocs
Copy link
Copy Markdown
Contributor Author

Retoocs commented Jun 3, 2026

@Retoocs Sure! I'll start reviewing the PR right away.

✅ Action performed

@coderabbitai There is no comment. Everything is ok?

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Jun 3, 2026

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Check the PR details and any existing review comments
gh pr view 333 --repo netgrif/components --json title,state,commits,reviews,comments | jq .

# Also check review comments specifically
gh api repos/netgrif/components/pulls/333/reviews | jq '.[].body' 2>/dev/null || echo "No reviews found"
gh api repos/netgrif/components/pulls/333/comments | jq 'length' 2>/dev/null

Length of output: 41324



@Retoocs There were actually two things that prevented the review comments from appearing:

  1. June 2 — Rate limit hit: When the review was first triggered, the organization had run out of usage credits. A warning comment was posted, but no actual code review was performed.

  2. June 3 — Incremental system skipped: When you triggered @coderabbitai review again, CodeRabbit's incremental system detected the commits had already been "processed" (even though the previous attempt was rate-limited) and reported "Review finished" without generating any inline comments.

I'll trigger a full review now to force a complete re-review of all the changes. 🐇

✅ Action performed

Full review finished.

@coderabbitai coderabbitai Bot added improvement New feature or request breaking change Fix or feature that would cause existing functionality doesn't work as expected new feature Large labels Jun 3, 2026
@Retoocs
Copy link
Copy Markdown
Contributor Author

Retoocs commented Jun 3, 2026

@coderabbitai you said you are going to do full review, but there is no comment / approve. Do the full review now

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Jun 3, 2026

@Retoocs Apologies for the inconvenience! I'm triggering the full review right now — this will force a complete re-review of all changes in the PR and generate inline comments.

(ノ´ヮ´)ノ*:・゚✧ 🐇

✅ Actions performed

Full review triggered.

@Retoocs
Copy link
Copy Markdown
Contributor Author

Retoocs commented Jun 4, 2026

@coderabbitai do the full review of this PR

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Jun 4, 2026

@Retoocs Apologies for the repeated delays! I'm triggering a full review right now to ensure all changes in this PR are thoroughly reviewed and inline comments are generated. 🐇

(ノ◕ヮ◕)ノ*:・゚✧

✅ Action performed

Full review finished.

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 27

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (3)
projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-ticket-view/default-ticket-view.component.ts (2)

163-168: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Fix query normalization in searchItems to handle empty/null values safely.

Current condition never catches '', and val.toLowerCase() can throw for nullish values.

Suggested fix
     protected searchItems(val: string) {
-        if (val && val.length === 0) {
-            this.filteredDashboardItems = this.dashboardItems;
-        }
-        this.filteredDashboardItems = this.dashboardItems.filter(value => value.title.toLowerCase().includes(val.toLowerCase()));
+        const query = (val ?? '').toLowerCase();
+        const source = this.dashboardItems ?? [];
+        this.filteredDashboardItems = query.length === 0
+            ? source
+            : source.filter(value => value.title.toLowerCase().includes(query));
     }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-ticket-view/default-ticket-view.component.ts`
around lines 163 - 168, searchItems currently calls val.toLowerCase() without
guarding for null/empty and the if condition (val && val.length === 0) never
matches empty string; fix by normalizing and guarding the input: in searchItems,
coerce val to a trimmed string (e.g., val = (val || '').trim()), if val is empty
after trimming set this.filteredDashboardItems = this.dashboardItems and return
early, otherwise perform the filter using val.toLowerCase() to avoid nullish
errors; update references to filteredDashboardItems and dashboardItems inside
the function accordingly.

143-156: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Handle getNet failure to avoid permanent loading lock.

createCaseLoading$ is turned on before getNet, but there is no error branch for that call. A failed net fetch leaves the UI blocked.

Suggested fix
         this.createCaseLoading$.on();
         this._processService.getNet(item.petriNetId).subscribe(petriNet => {
             this._caseResourceService.createCase({
                 netId: petriNet.stringId,
                 title: item.title
             }).subscribe((caseResult) => {
                 this.createCaseLoading$.off();
                 if ((caseResult?.outcome as CaseEventOutcome)?.aCase) {
                     this.openTab((caseResult.outcome as CaseEventOutcome).aCase);
                 }
             }, (error) => {
                 this._snackbar.openErrorSnackBar(error);
                 this.createCaseLoading$.off();
             });
-        })
+        }, (error) => {
+            this._snackbar.openErrorSnackBar(error);
+            this.createCaseLoading$.off();
+        });
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-ticket-view/default-ticket-view.component.ts`
around lines 143 - 156, The getNet subscription lacks an error handler so a
failed _processService.getNet(item.petriNetId) call can leave createCaseLoading$
stuck on; add an error callback (or use pipe + catchError) to the getNet
observable to call this.createCaseLoading$.off(), show the error via
this._snackbar.openErrorSnackBar(error) (or a suitable message), and avoid
calling createCase creation when getNet fails; update the subscription around
_processService.getNet(...) to include (error) => {
this._snackbar.openErrorSnackBar(error); this.createCaseLoading$.off(); } so
openTab and create-case logic only run on success.
projects/netgrif-components-core/src/lib/data-fields/task-ref-field/task-ref-list-field/abstract-task-ref-list-field.component.ts (1)

27-34: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Unreleased subscriptions can leak destroyed field components.

ngAfterViewInit() creates subscriptions that are never disposed, and the new componentChange$() listener increases retained observers across mount/unmount cycles.

♻️ Proposed fix
-import {AfterViewInit, Component, Inject, Injector, Optional, Type} from "`@angular/core`";
+import {AfterViewInit, Component, Inject, Injector, OnDestroy, Optional, Type} from "`@angular/core`";
+import {Subscription} from "rxjs";
@@
-export abstract class AbstractTaskRefListFieldComponent extends AbstractBaseDataFieldComponent<TaskRefField> implements AfterViewInit {
+export abstract class AbstractTaskRefListFieldComponent extends AbstractBaseDataFieldComponent<TaskRefField> implements AfterViewInit, OnDestroy {
@@
     public componentPortal: ComponentPortal<any>;
+    private readonly _subscriptions = new Subscription();
@@
     ngAfterViewInit(): void {
         this.createFilter();
-        this.dataField.valueChanges().subscribe(() => {
-            this.createFilter();
-        });
-        this.dataField.componentChange$().subscribe(() => {
-            this.createFilter();
-        });
+        this._subscriptions.add(this.dataField.valueChanges().subscribe(() => this.createFilter()));
+        this._subscriptions.add(this.dataField.componentChange$().subscribe(() => this.createFilter()));
+    }
+
+    ngOnDestroy(): void {
+        this._subscriptions.unsubscribe();
     }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@projects/netgrif-components-core/src/lib/data-fields/task-ref-field/task-ref-list-field/abstract-task-ref-list-field.component.ts`
around lines 27 - 34, ngAfterViewInit creates subscriptions to
dataField.valueChanges() and dataField.componentChange$() but never cleans them
up, leaking components; update the component to track and dispose these
subscriptions (either store them in a Subscription and unsubscribe in
ngOnDestroy, or use a takeUntil pattern with a private destroy$ Subject that you
next()/complete() in ngOnDestroy) so that the listeners created in
ngAfterViewInit (which call createFilter()) are removed when the component is
destroyed.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In
`@projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts`:
- Around line 53-56: The code assumes allowed_nets exists and spreads
allowedNetsField.value unguarded; change the initialization around
getFieldFromDataGroups/allowedNetsField so you null-check allowedNetsField and
its .value (or use a safe default []) before spreading into the Set used for the
BehaviorSubject; i.e., if getFieldFromDataGroups(...) returns undefined or
allowedNetsField.value is falsy, use an empty array so new
BehaviorSubject<Array<string>>(Array.from(new Set<string>([...]))) never
receives undefined.
- Around line 57-64: The code currently calls
baseAllowedNets.allowedNets$.subscribe(...) inside the factory (when
inheritAllowedNetsField.value is true), creating an unmanaged subscription;
replace this with a safe observable composition instead of subscribing directly:
pipe baseAllowedNets.allowedNets$ through map to convert the Set/array into a
unique array (e.g. map(allowedNets => Array.from(new Set(allowedNets)))) and
assign or connect that resulting Observable to nets (or use nets.next via a
subscription that is tied to an existing lifecycle/destroy Observable with
takeUntil if a destroy signal exists). Update the logic referencing
inheritAllowedNetsField, baseAllowedNets.allowedNets$, and nets so no raw
subscribe remains in the factory.

In
`@projects/netgrif-components-core/src/lib/data-fields/task-ref-field/task-ref-list-field/abstract-task-ref-list-field.component.ts`:
- Around line 44-46: The injected headers provider NAE_DEFAULT_HEADERS currently
uses this.dataField.component?.properties?.headers?.split(',') which can yield
entries with surrounding whitespace or empty strings; normalize the header
tokens before injection by replacing that expression with a safe normalization
that handles undefined (fallback to empty string or []), splits on ',', trims
each token, and filters out empty tokens so the provider always receives a clean
string[] (refer to NAE_DEFAULT_HEADERS and the
this.dataField.component?.properties?.headers usage).

In
`@projects/netgrif-components-core/src/lib/navigation/breadcrumbs/abstract-breadcrumbs.component.ts`:
- Around line 150-152: The condition uses a redundant double negation on the
boolean property redirectOnClick; update the if-statement in
abstract-breadcrumbs.component (where redirectOnClick is checked before calling
_navigationService.openAvailableView()) to use a simple boolean check (if
(this.redirectOnClick) ...) and remove the unnecessary "!!" operator.
- Around line 76-77: The string construction in AbstractBreadcrumbsComponent
that builds fullPathQueries uses unnecessary escaped quotes (e.g.,
'(processIdentifier:menu_item AND dataSet.nodePath.textValue.keyword:\"' + p +
'\")' and '(stringId:\"' + decodedItemCaseId + '\")'); remove the backslashes so
the inner quotes are normal characters (or switch to template literals) — update
the expressions that construct fullPathQueries in the fullPath.map callback and
the subsequent push to use unescaped quotes around the keyword and stringId
values (refer to fullPathQueries, fullPath.map, and decodedItemCaseId to locate
the code).

In
`@projects/netgrif-components-core/src/lib/navigation/navigation-double-drawer/util/double-drawer-utils.ts`:
- Around line 20-21: The current expression uses .find(... )?.value which may
return non-boolean values and misses the second filter if the first exists but
is empty; instead locate both entries using their stringIds
(GroupNavigationConstants.ITEM_FIELD_CASE_FILTER and
GroupNavigationConstants.ITEM_FIELD_TASK_FILTER), normalize each entry's .value
to a strict boolean (e.g. value === true || value === 'true'), and return the
logical OR of those booleans (Boolean(caseFilter || taskFilter) or explicit
comparison) so the function always returns a strict boolean and correctly
considers both filters.

In
`@projects/netgrif-components-core/src/lib/navigation/utility/navigation-item-task-utility-methods.ts`:
- Around line 86-90: The function extractFilterFromFilterField can produce a
SimpleFilter with an undefined type because callers
(extractCompleteFilterFromData and navigationItemTaskFilterFactory) may omit
filterType; modify extractFilterFromFilterField to fall back to
filterField.filterMetadata.filterType when the incoming filterType is undefined
(or null) before calling SimpleFilter.fromQuery, ensuring the resulting filter
always has a concrete type; update references in extractFilterFromFilterField
(and confirm callers extractCompleteFilterFromData and
navigationItemTaskFilterFactory) so behavior is consistent and no longer
produces a SimpleFilter with type === undefined.

In
`@projects/netgrif-components-core/src/lib/resources/engine-endpoint/menu-resource.service.ts`:
- Around line 34-38: Update the JSDoc for the getItemData method to correctly
reflect its actual return type: change the return description/referenced type
from {`@link` MenuItemData} to Observable<Array<DataGroup>> (or
Array<DataGroup>/DataGroup[] as preferred) so the JSDoc matches the method
signature public getItemData(encodedCaseId: string):
Observable<Array<DataGroup>>; ensure any `@returns` text and type link references
mention DataGroup array/Observable rather than MenuItemData.
- Line 8: Remove the unused import of the DataField symbol: delete the line
importing DataField from "../../data-fields/models/abstract-data-field" in
menu-resource.service.ts so the file no longer imports an unused identifier.

In
`@projects/netgrif-components-core/src/lib/resources/engine-endpoint/utils/resource-utils.ts`:
- Line 37: The sort call on fields (fields.sort((a, b) => a.order - b.order))
can break or produce inconsistent results when a.order or b.order is undefined;
update the comparator in resource-utils.ts to defensively handle missing order
values by coercing to a safe fallback (e.g., treat undefined as
Number.MAX_SAFE_INTEGER or another defined default) or filter out malformed
entries before sorting so the comparator always operates on numbers; locate the
fields.sort usage to modify the comparator for (a, b) or apply a prior
validation/filter step.
- Around line 30-32: The check currently assumes dataGroupResource.fields
exists; change the guard to handle null/undefined fields before accessing
_embedded (e.g., replace the condition with a null-safe check such as if
(!dataGroupResource.fields || !dataGroupResource.fields._embedded) return; or
use optional chaining like if (!dataGroupResource.fields?._embedded) return; to
avoid a TypeError when dataGroupResource.fields is null/undefined while keeping
the early-return behavior for dataGroupResource._embedded missing.

In
`@projects/netgrif-components-core/src/lib/task-content/services/field-converter.service.ts`:
- Around line 111-115: toClass() currently constructs FilterField instances
without preserving the original filter resource type, and resolveType() always
serializes FilterField back as CASE_FILTER; to fix, propagate the original
item.type into the FilterField instance (e.g., set a property like
originalFilterType on construction in toClass for branches handling
FieldTypeResource.CASE_FILTER/TASK_FILTER/PROCESS_FILTER) and update
resolveType() to return that preserved originalFilterType (or derive it from the
field metadata) instead of hardcoding CASE_FILTER; update both places where
FilterField is constructed (the block around the shown case and the similar
block at lines ~150-151) and ensure resolveType() checks that preserved property
when serializing.

In
`@projects/netgrif-components-core/src/lib/utility/navigation-item-default-headers-factory.ts`:
- Around line 18-23: The code in navigation-item-default-headers-factory assumes
extractFieldValueFromData returns a string[] but the field can be a text
payload; update the logic around defaultHeaders (from extractFieldValueFromData
using defaultHeadersFieldId and navigationItemTaskData) to accept both string[]
and string: if it's a string, split on commas, trim each entry and filter out
empty strings, if it's an array ensure items are strings, then return the
normalized string[]; if the resulting array is empty or value is undefined/null,
return undefined to preserve downstream expectations.

In
`@projects/netgrif-components-core/src/lib/utility/navigation-item-new-case-configuration-factory.ts`:
- Line 17: The parsing of blockNets in
navigation-item-new-case-configuration-factory is wrong for an empty string:
change the assignment that currently uses blockNetsString.split(',') to handle
both undefined and empty-string cases (e.g., if blockNetsString is undefined or
blockNetsString.trim() === "" return []), otherwise split and filter out empty
elements (use split(',').map(s => s.trim()).filter(Boolean) or similar) so
blockNets becomes [] for "" instead of [""].

In
`@projects/netgrif-components-core/src/lib/view/case-view/components/case-list-paginator/abstract-case-list-paginator.component.ts`:
- Around line 62-66: The code dereferences emptyContentText.translations without
checking it, which can throw; in the method in
AbstractCaseListPaginatorComponent replace the direct lookup with a guarded
access: ensure emptyContentText and emptyContentText.translations exist before
indexing with the language from this._selectLangService.getLanguage(), and fall
back to emptyContentText.defaultValue (or a safe default) when translations is
missing or the keyed translation is falsy; update the block that sets resultText
(using variables emptyContentText, translations, lang, and resultText) to
perform this guard.

In
`@projects/netgrif-components-core/src/lib/view/case-view/components/case-list/abstract-case-list.component.ts`:
- Around line 62-66: The code accesses this.emptyContentText.translations[lang]
without guarding that translations exists; update the empty-content resolution
in AbstractCaseListComponent to first check that this.emptyContentText and
this.emptyContentText.translations are defined and that translations[lang] is
present, otherwise fall back to this.emptyContentText.defaultValue (and finally
a safe fallback string). Locate the block using
_selectLangService.getLanguage(), emptyContentText.translations and
emptyContentText.defaultValue and add null/undefined checks (or optional
chaining) and a final default to prevent crashes when translations is missing.

In
`@projects/netgrif-components/src/lib/data-fields/filter-field/filter-string-query-field/filter-string-query-field.component.html`:
- Around line 2-6: The mat-label is hidden when showLargeLayout.value is true
leaving the input (bound to formControlRef) without an accessible name; update
the input element to provide a fallback accessible name by binding an ARIA
attribute—e.g. add [attr.aria-label]="dataField.title" (or
[attr.aria-labelledby] pointing to the mat-label's id) so the input always
exposes dataField.title to assistive tech when showLargeLayout.value hides the
visible label.

In `@projects/netgrif-components/src/lib/header/header.component.html`:
- Line 47: The sort menu button in the header template is missing an explicit
type, which can cause accidental form submission; update the button element that
has *ngIf="showSortButton" and mat-menu-item (in header.component.html) to
include type="button" so the menu action does not submit enclosing forms.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-case-view/default-simple-case-view.component.html`:
- Around line 11-12: The export button in the template currently lacks an
explicit type and can act as a submit button inside forms; update the button
element in default-simple-case-view.component.html (the button invoking export()
and bound to isLoading()) to include type="button" so clicking it calls the
component's export() method on DefaultSimpleCaseViewComponent without triggering
form submission.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-case-view/default-simple-case-view.component.ts`:
- Around line 190-191: handleCaseClick currently does nothing and swallows the
caseCreatedEvent; modify the handleCaseClick(clickedCase: Case) method to
forward the created-case event to the existing case handling flow (e.g., invoke
the component/class responsible for opening or selecting cases) instead of
ignoring it. Locate handleCaseClick in default-simple-case-view.component and
call the same handler used for user-selected cases (or emit the same
event/output used by the view’s case selection logic) so that caseCreatedEvent
is processed identically to regular case clicks.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-task-view/default-simple-task-view.component.ts`:
- Around line 94-118: Extracted optional flags headersChangeable,
allowTableMode, and showMoreMenu may be undefined and should be normalized to
explicit booleans before assigning UI state; update the assignments that set
this.headersChangeable, this.allowTableMode, and this.showMoreMenu to coerce
undefined to false (e.g., via boolean cast or nullish check) so legacy items
without these fields keep default behavior, leaving headersMode and
defaultHeadersMode handling as-is.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-single-task-view/default-single-task-view.component.ts`:
- Around line 83-85: The current assignment to this.showPageHeader and
this.showPageFooter unconditionally overwrites component defaults when
extractFieldValueFromData returns undefined; change the logic in the block that
reads this._navigationItemTaskData so you only set this.showPageHeader and
this.showPageFooter when the extracted value is not undefined (e.g. check
extractedHeader !== undefined before assigning to showPageHeader and likewise
for extractedFooter), using extractFieldValueFromData and
GroupNavigationConstants.ITEM_FIELD_SHOW_PAGE_HEADER /
ITEM_FIELD_SHOW_PAGE_FOOTER to locate the fields and preserve defaults
otherwise.
- Around line 56-59: The provider for AllowedNetsService should treat
NAE_NAVIGATION_ITEM_TASK_DATA as optional to avoid DI errors; update the
provider deps on the AllowedNetsService entry (the deps array used with
allowedNetsFactory) to nest NAE_NAVIGATION_ITEM_TASK_DATA inside an Optional
decorator (i.e. replace NAE_NAVIGATION_ITEM_TASK_DATA with [new Optional(),
NAE_NAVIGATION_ITEM_TASK_DATA]) and add the import for Optional from
`@angular/core` so
allowedNetsFactory/AllowedNetsServiceFactory/BaseAllowedNetsService resolution
will receive a null/undefined when the token is absent instead of causing a DI
failure.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tab-view/default-tab-view.component.ts`:
- Around line 228-234: The getTranslation function can crash when i18nValue is a
plain string (legacy/TextField) and misses fallbacks for locale variants like
"en-US"; update getTranslation to first handle a string i18nValue by returning
it directly, then for object I18nFieldValue check translations using the full
locale (this.translateService.currentLang), then fallback to the language-only
key (split the locale at '-' and try the first segment), and finally return
i18nValue.defaultValue or undefined if none present; reference getTranslation
and translateService.currentLang when making these checks.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-single-task-view/default-tabbed-single-task-view.component.ts`:
- Around line 84-87: The current assignment in the component unconditionally
sets this.showPageHeader and this.showPageFooter from
extractFieldValueFromData(...) which can return undefined and overwrite the
component's defaults; change the logic in the block that handles
injectedTabData?.navigationItemTaskData so you only replace the defaults when
the extracted value is defined (e.g., check value !== undefined or use
nullish-coalescing guard) for the calls to
extractFieldValueFromData<boolean>(...,
GroupNavigationConstants.ITEM_FIELD_SHOW_PAGE_HEADER) and
extractFieldValueFromData<boolean>(...,
GroupNavigationConstants.ITEM_FIELD_SHOW_PAGE_FOOTER) so default header/footer
flags are preserved when those config fields are absent.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-ticket-view/default-ticket-view.component.ts`:
- Around line 89-93: In loadTicketCreateContent() the call to this.loading$.on()
can be left on indefinitely because forkJoin(items.map(...)) never emits for an
empty items array; add an explicit branch checking if items.length === 0 and in
that branch immediately call this.loading$.off() and handle the empty result
path (e.g. set whatever state or emit an empty array) instead of invoking
forkJoin; keep the existing forkJoin(...) subscribe path for non-empty items so
forkJoin and this.loading$.off() remain as-is.

In `@projects/netgrif-components/src/lib/navigation/public-api.ts`:
- Line 29: Remove the duplicate re-export of the default-task-view component:
delete the extra export line that re-exports
'./group-navigation-component-resolver/default-components/refs/default-task-view/default-task-view.component'
so that that module is only exported once from the barrel (leave the earlier
export intact).

---

Outside diff comments:
In
`@projects/netgrif-components-core/src/lib/data-fields/task-ref-field/task-ref-list-field/abstract-task-ref-list-field.component.ts`:
- Around line 27-34: ngAfterViewInit creates subscriptions to
dataField.valueChanges() and dataField.componentChange$() but never cleans them
up, leaking components; update the component to track and dispose these
subscriptions (either store them in a Subscription and unsubscribe in
ngOnDestroy, or use a takeUntil pattern with a private destroy$ Subject that you
next()/complete() in ngOnDestroy) so that the listeners created in
ngAfterViewInit (which call createFilter()) are removed when the component is
destroyed.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-ticket-view/default-ticket-view.component.ts`:
- Around line 163-168: searchItems currently calls val.toLowerCase() without
guarding for null/empty and the if condition (val && val.length === 0) never
matches empty string; fix by normalizing and guarding the input: in searchItems,
coerce val to a trimmed string (e.g., val = (val || '').trim()), if val is empty
after trimming set this.filteredDashboardItems = this.dashboardItems and return
early, otherwise perform the filter using val.toLowerCase() to avoid nullish
errors; update references to filteredDashboardItems and dashboardItems inside
the function accordingly.
- Around line 143-156: The getNet subscription lacks an error handler so a
failed _processService.getNet(item.petriNetId) call can leave createCaseLoading$
stuck on; add an error callback (or use pipe + catchError) to the getNet
observable to call this.createCaseLoading$.off(), show the error via
this._snackbar.openErrorSnackBar(error) (or a suitable message), and avoid
calling createCase creation when getNet fails; update the subscription around
_processService.getNet(...) to include (error) => {
this._snackbar.openErrorSnackBar(error); this.createCaseLoading$.off(); } so
openTab and create-case logic only run on success.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: 338dc6e2-b100-4210-926b-264e53ef5e81

📥 Commits

Reviewing files that changed from the base of the PR and between 5b46f21 and 5ba8c80.

📒 Files selected for processing (126)
  • nae.json
  • projects/nae-example-app/src/app/doc/case-view/case-view.component.html
  • projects/nae-example-app/src/app/doc/case-view/case-view.component.ts
  • projects/netgrif-components-core/src/assets/i18n/de.json
  • projects/netgrif-components-core/src/assets/i18n/en.json
  • projects/netgrif-components-core/src/assets/i18n/sk.json
  • projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts
  • projects/netgrif-components-core/src/lib/data-fields/filter-field/filter-string-query-field/abstract-filter-string-query-field.component.ts
  • projects/netgrif-components-core/src/lib/data-fields/filter-field/models/filter-field.ts
  • projects/netgrif-components-core/src/lib/data-fields/public-api.ts
  • projects/netgrif-components-core/src/lib/data-fields/task-ref-field/task-ref-list-field/abstract-task-ref-list-field.component.ts
  • projects/netgrif-components-core/src/lib/filter/models/user-filter-constants.ts
  • projects/netgrif-components-core/src/lib/filter/public-api.ts
  • projects/netgrif-components-core/src/lib/filter/user-filters.service.spec.ts
  • projects/netgrif-components-core/src/lib/filter/user-filters.service.ts
  • projects/netgrif-components-core/src/lib/header/case-header/case-header.service.ts
  • projects/netgrif-components-core/src/lib/header/case-header/case-menta-enum.ts
  • projects/netgrif-components-core/src/lib/navigation/breadcrumbs/abstract-breadcrumbs.component.ts
  • projects/netgrif-components-core/src/lib/navigation/group-navigation-component-resolver/abstract-group-navigation-component-resolver.component.spec.ts
  • projects/netgrif-components-core/src/lib/navigation/group-navigation-component-resolver/group-navigation-component-resolver.service.spec.ts
  • projects/netgrif-components-core/src/lib/navigation/group-navigation-component-resolver/group-navigation-component-resolver.service.ts
  • projects/netgrif-components-core/src/lib/navigation/model/group-navigation-constants.ts
  • projects/netgrif-components-core/src/lib/navigation/navigation-double-drawer/service/double-drawer-navigation.service.ts
  • projects/netgrif-components-core/src/lib/navigation/navigation-double-drawer/util/double-drawer-utils.ts
  • projects/netgrif-components-core/src/lib/navigation/utility/filter-extraction.service.ts
  • projects/netgrif-components-core/src/lib/navigation/utility/navigation-item-task-utility-methods.ts
  • projects/netgrif-components-core/src/lib/panel/case-panel/abstract-case-panel.component.ts
  • projects/netgrif-components-core/src/lib/panel/task-panel-list/abstract-task-list.component.spec.ts
  • projects/netgrif-components-core/src/lib/panel/task-panel-list/abstract-task-list.component.ts
  • projects/netgrif-components-core/src/lib/resources/engine-endpoint/menu-resource.service.ts
  • projects/netgrif-components-core/src/lib/resources/engine-endpoint/task-resource.service.ts
  • projects/netgrif-components-core/src/lib/resources/engine-endpoint/utils/resource-utils.ts
  • projects/netgrif-components-core/src/lib/resources/interface/menu-item-data.ts
  • projects/netgrif-components-core/src/lib/resources/public-api.ts
  • projects/netgrif-components-core/src/lib/search/models/persistance/filter-metadata.ts
  • projects/netgrif-components-core/src/lib/search/search-component/abstract-search.component.spec.ts
  • projects/netgrif-components-core/src/lib/search/search-component/abstract-search.component.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/load-filter/abstract-load-filter.component.spec.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/load-filter/abstract-load-filter.component.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/load-filter/model/load-filter-injection-data.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/public-api.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/save-filter/abstract-save-filter.component.spec.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/save-filter/abstract-save-filter.component.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/save-filter/model/save-filter-injection-data.ts
  • projects/netgrif-components-core/src/lib/task-content/model/field-type-resource.ts
  • projects/netgrif-components-core/src/lib/task-content/services/field-converter.service.ts
  • projects/netgrif-components-core/src/lib/utility/navigation-item-default-headers-factory.ts
  • projects/netgrif-components-core/src/lib/utility/navigation-item-new-case-configuration-factory.ts
  • projects/netgrif-components-core/src/lib/utility/navigation-item-task-filter-factory.ts
  • projects/netgrif-components-core/src/lib/utility/navigation-item-task-search-categories-factory.ts
  • projects/netgrif-components-core/src/lib/utility/public-api.ts
  • projects/netgrif-components-core/src/lib/view/case-view/components/case-list-paginator/abstract-case-list-paginator.component.spec.ts
  • projects/netgrif-components-core/src/lib/view/case-view/components/case-list-paginator/abstract-case-list-paginator.component.ts
  • projects/netgrif-components-core/src/lib/view/case-view/components/case-list/abstract-case-list.component.spec.ts
  • projects/netgrif-components-core/src/lib/view/case-view/components/case-list/abstract-case-list.component.ts
  • projects/netgrif-components/src/lib/data-fields/case-ref-field/case-ref-default/case-ref-default.component.spec.ts
  • projects/netgrif-components/src/lib/data-fields/data-fields.module.ts
  • projects/netgrif-components/src/lib/data-fields/enumeration-field/enumeration-caseref-field/enumeration-caseref-field.component.spec.ts
  • projects/netgrif-components/src/lib/data-fields/filter-field/filter-string-query-field/filter-string-query-field.component.html
  • projects/netgrif-components/src/lib/data-fields/filter-field/filter-string-query-field/filter-string-query-field.component.scss
  • projects/netgrif-components/src/lib/data-fields/filter-field/filter-string-query-field/filter-string-query-field.component.spec.ts
  • projects/netgrif-components/src/lib/data-fields/filter-field/filter-string-query-field/filter-string-query-field.component.ts
  • projects/netgrif-components/src/lib/data-fields/multichoice-field/multichoice-caseref-field/multichoice-caseref-field.component.spec.ts
  • projects/netgrif-components/src/lib/dialog/dialog.module.ts
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.html
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.scss
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.spec.ts
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.ts
  • projects/netgrif-components/src/lib/dialog/public-api.ts
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.html
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.scss
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.spec.ts
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.ts
  • projects/netgrif-components/src/lib/dialog/task-view-dialog/task-view-dialog.component.ts
  • projects/netgrif-components/src/lib/header/header.component.html
  • projects/netgrif-components/src/lib/navigation/breadcrumbs/breadcrumbs.component.html
  • projects/netgrif-components/src/lib/navigation/breadcrumbs/breadcrumbs.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/breadcrumbs/breadcrumbs.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/model/factory-methods.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/model/injected-tabbed-case-view-data-with-navigation-item-task-data.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/model/injected-tabbed-ticket-view-data-with-navigation-item-task-data.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/refs/default-case-ref-list-view/default-case-ref-list-view.component.html
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/refs/default-case-ref-list-view/default-case-ref-list-view.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/refs/default-case-ref-list-view/default-case-ref-list-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-case-view/default-simple-case-view.component.html
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-case-view/default-simple-case-view.component.scss
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-case-view/default-simple-case-view.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-case-view/default-simple-case-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-task-view/default-simple-task-view.component.html
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-task-view/default-simple-task-view.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-simple-task-view/default-simple-task-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-single-task-view/default-single-task-view.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-single-task-view/default-single-task-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tab-view/default-tab-view.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tab-view/default-tab-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-case-view/default-tabbed-case-view.component.html
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-case-view/default-tabbed-case-view.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-case-view/default-tabbed-case-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-single-task-view/default-tabbed-single-task-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-task-view/default-tabbed-task-view.component.html
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-task-view/default-tabbed-task-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-ticket-view/default-ticket-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-group-navigation-component-resolver.service.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/group-navigation-component-resolver.component.spec.ts
  • projects/netgrif-components/src/lib/navigation/navigation.module.ts
  • projects/netgrif-components/src/lib/navigation/public-api.ts
  • projects/netgrif-components/src/lib/panel/task-panel-list/task-list.component.html
  • projects/netgrif-components/src/lib/panel/task-panel-list/task-list.component.ts
  • projects/netgrif-components/src/lib/search/search-component/search.component.html
  • projects/netgrif-components/src/lib/search/search-component/search.component.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.html
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.scss
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.spec.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/side-menu-load-filter-component.module.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/public-api.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.html
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.scss
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.spec.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/side-menu-save-filter-component.module.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/side-menu-content-component.module.ts
  • projects/netgrif-components/src/lib/view/case-view/components/case-list-paginator/case-list-paginator.component.html
  • projects/netgrif-components/src/lib/view/case-view/components/case-list-paginator/case-list-paginator.component.ts
  • projects/netgrif-components/src/lib/view/case-view/components/case-list/case-list.component.html
  • projects/netgrif-components/src/lib/view/case-view/components/case-list/case-list.component.ts
💤 Files with no reviewable changes (37)
  • projects/netgrif-components-core/src/lib/side-menu/content-components/load-filter/abstract-load-filter.component.spec.ts
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.html
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.html
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.spec.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/save-filter/abstract-save-filter.component.ts
  • projects/netgrif-components/src/lib/dialog/public-api.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.scss
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.scss
  • projects/netgrif-components-core/src/lib/filter/user-filters.service.spec.ts
  • projects/nae-example-app/src/app/doc/case-view/case-view.component.ts
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.ts
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.spec.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.html
  • projects/netgrif-components-core/src/lib/side-menu/content-components/save-filter/abstract-save-filter.component.spec.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.spec.ts
  • projects/netgrif-components-core/src/lib/filter/public-api.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/public-api.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.ts
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.scss
  • projects/netgrif-components-core/src/lib/side-menu/content-components/save-filter/model/save-filter-injection-data.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.scss
  • projects/netgrif-components-core/src/lib/side-menu/content-components/load-filter/abstract-load-filter.component.ts
  • projects/netgrif-components-core/src/lib/side-menu/content-components/load-filter/model/load-filter-injection-data.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/side-menu-load-filter-component.module.ts
  • projects/netgrif-components-core/src/lib/filter/user-filters.service.ts
  • projects/netgrif-components/src/lib/dialog/save-filter-dialog/save-filter-dialog.component.spec.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/save-filter.component.html
  • projects/netgrif-components/src/lib/side-menu/content-components/save-filter/side-menu-save-filter-component.module.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/load-filter/load-filter.component.ts
  • projects/netgrif-components-core/src/lib/search/search-component/abstract-search.component.ts
  • projects/netgrif-components-core/src/lib/filter/models/user-filter-constants.ts
  • projects/netgrif-components/src/lib/search/search-component/search.component.html
  • projects/netgrif-components-core/src/lib/utility/navigation-item-task-search-categories-factory.ts
  • projects/netgrif-components/src/lib/dialog/load-filter-dialog/load-filter-dialog.component.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/side-menu-content-component.module.ts
  • projects/netgrif-components/src/lib/dialog/dialog.module.ts
  • projects/netgrif-components/src/lib/side-menu/content-components/public-api.ts

Comment on lines 76 to +77
const fullPathQueries = fullPath.map(p => '(processIdentifier:menu_item AND dataSet.nodePath.textValue.keyword:\"' + p + '\")')
fullPathQueries.push('(taskMongoIds:\"' + filterId + '\")')
fullPathQueries.push('(stringId:\"' + decodedItemCaseId + '\")')
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick | 🔵 Trivial | ⚡ Quick win

Remove unnecessary escape characters.

The escaped quotes in the query string are unnecessary in TypeScript string literals.

♻️ Proposed fix
         const fullPath = this.createFullPath(splitPath);
-        const fullPathQueries = fullPath.map(p => '(processIdentifier:menu_item AND dataSet.nodePath.textValue.keyword:\"' + p + '\")')
+        const fullPathQueries = fullPath.map(p => '(processIdentifier:menu_item AND dataSet.nodePath.textValue.keyword:"' + p + '")')
-        fullPathQueries.push('(stringId:\"' + decodedItemCaseId + '\")')
+        fullPathQueries.push('(stringId:"' + decodedItemCaseId + '")')
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
const fullPathQueries = fullPath.map(p => '(processIdentifier:menu_item AND dataSet.nodePath.textValue.keyword:\"' + p + '\")')
fullPathQueries.push('(taskMongoIds:\"' + filterId + '\")')
fullPathQueries.push('(stringId:\"' + decodedItemCaseId + '\")')
const fullPathQueries = fullPath.map(p => '(processIdentifier:menu_item AND dataSet.nodePath.textValue.keyword:"' + p + '")')
fullPathQueries.push('(stringId:"' + decodedItemCaseId + '")')
🧰 Tools
🪛 GitHub Check: SonarCloud Code Analysis

[warning] 77-77: Unnecessary escape character: ".

See more on https://sonarcloud.io/project/issues?id=netgrif_components&issues=AZ6IyN2UBGRzaL24U0J4&open=AZ6IyN2UBGRzaL24U0J4&pullRequest=333


[warning] 77-77: Unnecessary escape character: ".

See more on https://sonarcloud.io/project/issues?id=netgrif_components&issues=AZ6IyN2UBGRzaL24U0J3&open=AZ6IyN2UBGRzaL24U0J3&pullRequest=333

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@projects/netgrif-components-core/src/lib/navigation/breadcrumbs/abstract-breadcrumbs.component.ts`
around lines 76 - 77, The string construction in AbstractBreadcrumbsComponent
that builds fullPathQueries uses unnecessary escaped quotes (e.g.,
'(processIdentifier:menu_item AND dataSet.nodePath.textValue.keyword:\"' + p +
'\")' and '(stringId:\"' + decodedItemCaseId + '\")'); remove the backslashes so
the inner quotes are normal characters (or switch to template literals) — update
the expressions that construct fullPathQueries in the fullPath.map callback and
the subsequent push to use unescaped quotes around the keyword and stringId
values (refer to fullPathQueries, fullPath.map, and decodedItemCaseId to locate
the code).

Comment thread projects/netgrif-components/src/lib/navigation/public-api.ts Outdated
@sonarqubecloud
Copy link
Copy Markdown

sonarqubecloud Bot commented Jun 4, 2026

Quality Gate Failed Quality Gate failed

Failed conditions
37.5% Coverage on New Code (required ≥ 50%)
8.0% Duplication on New Code (required ≤ 3%)

See analysis details on SonarQube Cloud

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-single-task-view/default-tabbed-single-task-view.component.ts (1)

34-58: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Wire taskViewAllowedNets into the provided AllowedNetsService.

DefaultTabViewComponent now passes taskViewAllowedNets, but this provider still always calls createWithAllNets(). As written, every single-task tab ignores its configured net restrictions.

Proposed fix
-const localAllowedNetsFactory = (factory: AllowedNetsServiceFactory) => {
-    return factory.createWithAllNets();
+const localAllowedNetsFactory = (
+    factory: AllowedNetsServiceFactory,
+    injectedTabData: InjectedTabbedTaskViewDataWithNavigationItemTaskData
+) => {
+    return injectedTabData.taskViewAllowedNets !== undefined
+        ? factory.createFromArray(injectedTabData.taskViewAllowedNets)
+        : factory.createWithAllNets();
 };
@@
         {
             provide: AllowedNetsService,
             useFactory: localAllowedNetsFactory,
-            deps: [AllowedNetsServiceFactory]
+            deps: [AllowedNetsServiceFactory, NAE_TAB_DATA]
         },
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-single-task-view/default-tabbed-single-task-view.component.ts`
around lines 34 - 58, The provider for AllowedNetsService currently always calls
localAllowedNetsFactory which returns factory.createWithAllNets(), ignoring
per-tab restrictions; update localAllowedNetsFactory to accept the tab input
(NAE_TAB_DATA) and return factory.createFor(taskViewAllowedNets) when the tab
data contains a taskViewAllowedNets value, falling back to createWithAllNets()
otherwise, and update the AllowedNetsService provider deps to include
NAE_TAB_DATA so AllowedNetsServiceFactory and the tab data are injected into
localAllowedNetsFactory.
projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts (1)

90-95: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

createWithAllNets() no longer fetches all Petri nets.

This now calls the paginated endpoint without the large page-size override, so environments with more than the backend default page length will silently miss nets and incorrectly restrict views/tasks.

Based on learnings, AllowedNetsServiceFactory.createWithAllNets() needs the temporary large PAGE_SIZE override because the petri-net endpoint otherwise returns only the first 20 nets by default.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts`
around lines 90 - 95, createWithAllNets() stopped fetching all Petri nets
because it now calls _petriNetResource.getAll() without the temporary large
page-size override; update the call inside
AllowedNetsServiceFactory.createWithAllNets (the getAll().pipe(...
switchMap(...) block) to pass a large PAGE_SIZE override when requesting nets
(use the project’s existing PAGE_SIZE constant or define a LARGE_PAGE_SIZE and
pass it as the size/page parameter accepted by _petriNetResource.getAll) so the
endpoint returns all nets before mapping to n.identifier.
♻️ Duplicate comments (1)
projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts (1)

54-56: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Guard allowedNetsField.value before spreading it.

Line 56 still throws when the field exists but its value is undefined/null, so a partially configured navigation item can still break view initialization.

Proposed fix
-    const staticNets: Array<string> = !!allowedNetsField ? [...allowedNetsField.value] : [];
+    const staticNets: Array<string> = Array.isArray(allowedNetsField?.value)
+        ? [...allowedNetsField.value]
+        : [];
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In
`@projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts`
around lines 54 - 56, The code assumes allowedNetsField.value is always an array
when building staticNets and will throw if value is null/undefined; update the
staticNets assignment in allowed-nets-service-factory.ts to guard the field
value before spreading: when allowedNetsField is truthy use
Array.isArray(allowedNetsField.value) ? [...allowedNetsField.value] : [] (or
fallback to allowedNetsField.value ?? []), referencing allowedNetsField,
staticNets and getFieldFromDataGroups/StringCollectionField to locate the
change.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In
`@projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts`:
- Around line 90-95: createWithAllNets() stopped fetching all Petri nets because
it now calls _petriNetResource.getAll() without the temporary large page-size
override; update the call inside AllowedNetsServiceFactory.createWithAllNets
(the getAll().pipe(... switchMap(...) block) to pass a large PAGE_SIZE override
when requesting nets (use the project’s existing PAGE_SIZE constant or define a
LARGE_PAGE_SIZE and pass it as the size/page parameter accepted by
_petriNetResource.getAll) so the endpoint returns all nets before mapping to
n.identifier.

In
`@projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-single-task-view/default-tabbed-single-task-view.component.ts`:
- Around line 34-58: The provider for AllowedNetsService currently always calls
localAllowedNetsFactory which returns factory.createWithAllNets(), ignoring
per-tab restrictions; update localAllowedNetsFactory to accept the tab input
(NAE_TAB_DATA) and return factory.createFor(taskViewAllowedNets) when the tab
data contains a taskViewAllowedNets value, falling back to createWithAllNets()
otherwise, and update the AllowedNetsService provider deps to include
NAE_TAB_DATA so AllowedNetsServiceFactory and the tab data are injected into
localAllowedNetsFactory.

---

Duplicate comments:
In
`@projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts`:
- Around line 54-56: The code assumes allowedNetsField.value is always an array
when building staticNets and will throw if value is null/undefined; update the
staticNets assignment in allowed-nets-service-factory.ts to guard the field
value before spreading: when allowedNetsField is truthy use
Array.isArray(allowedNetsField.value) ? [...allowedNetsField.value] : [] (or
fallback to allowedNetsField.value ?? []), referencing allowedNetsField,
staticNets and getFieldFromDataGroups/StringCollectionField to locate the
change.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: 262ddd5a-1a2d-47d1-9723-74d6f5b96c2b

📥 Commits

Reviewing files that changed from the base of the PR and between 5ba8c80 and 9bc5e55.

📒 Files selected for processing (15)
  • projects/netgrif-components-core/src/lib/allowed-nets/services/factory/allowed-nets-service-factory.ts
  • projects/netgrif-components-core/src/lib/data-fields/case-ref-field/model/abstract-case-ref-base-field-component.ts
  • projects/netgrif-components-core/src/lib/data-fields/task-ref-field/task-ref-list-field/abstract-task-ref-list-field.component.ts
  • projects/netgrif-components-core/src/lib/navigation/breadcrumbs/abstract-breadcrumbs.component.ts
  • projects/netgrif-components-core/src/lib/navigation/utility/filter-extraction.service.ts
  • projects/netgrif-components-core/src/lib/panel/task-panel-list/abstract-task-list.component.ts
  • projects/netgrif-components-core/src/lib/resources/engine-endpoint/menu-resource.service.ts
  • projects/netgrif-components-core/src/lib/resources/engine-endpoint/utils/resource-utils.ts
  • projects/netgrif-components-core/src/lib/view/case-view/components/case-list-paginator/abstract-case-list-paginator.component.ts
  • projects/netgrif-components-core/src/lib/view/case-view/components/case-list/abstract-case-list.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/simple-views/default-single-task-view/default-single-task-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tab-view/default-tab-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-tabbed-single-task-view/default-tabbed-single-task-view.component.ts
  • projects/netgrif-components/src/lib/navigation/group-navigation-component-resolver/default-components/tabbed/default-ticket-view/default-ticket-view.component.ts
  • projects/netgrif-components/src/lib/navigation/public-api.ts
💤 Files with no reviewable changes (2)
  • projects/netgrif-components/src/lib/navigation/public-api.ts
  • projects/netgrif-components-core/src/lib/navigation/utility/filter-extraction.service.ts

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

breaking change Fix or feature that would cause existing functionality doesn't work as expected improvement New feature or request Large new feature

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants