Skip to content

[DSpace-CRIS] Administrative Edit of archived items via submission form and security configuration for metadata visibility (Frontend)#5145

Merged
tdonohue merged 29 commits into
DSpace:mainfrom
4Science:task/main/DURACOM-453
Apr 2, 2026
Merged

[DSpace-CRIS] Administrative Edit of archived items via submission form and security configuration for metadata visibility (Frontend)#5145
tdonohue merged 29 commits into
DSpace:mainfrom
4Science:task/main/DURACOM-453

Conversation

@FrancescoMolinaro

@FrancescoMolinaro FrancescoMolinaro commented Feb 20, 2026

Copy link
Copy Markdown
Contributor

References

Relates to:

Description

With this PR we introduce a new menu voice in the item page menu to access the editing in submission form, even if archived.

image

the old menu voice for editing has been renamed to "Administer" to differentiate the different set of functionalities behind the menu.

The new menu will allow to open a submission form populated with the existing metadata for further enrichment of the item.

Along this feature, the possibility to pick wich form to use for each collection submission has been introduced:

image

This PR brings also a new configuration for the MyDspace page, called otherworkspace , which allow to have a shared workspace accessible to administrators of collection where they will be placed, to other Eperson according to a configurable set of metadata, other than to their submitter.

image

Along the editing changes, this PR brings also the possibility to define security levels for the metadata, this require a rest config as follows, inside metadata-security.cfg:

metadatavalue.visibility.settings = [0 1 2]
metadatavalue.visibility.Person.settings = [0 1]
metadatavalue.visibility.Person.dc.date.available.settings = [0 1]

as you can see is possible to have three different level values and is possible to define them globally, based on entity type or based on the couple entity type/metadata.
Configuration lookup follows a fallback logic, if for a given metadata, no value is defined, default metadata security settings for the entity (metadatavalue.visibility..settings) applies. If neither at entity level metadata security is defined, default metadatavalue.visibility.settings field value is used.
A null value means that for a metadata, or its fallback, no security rules must be proposed to the submitter or to the editor.

Out of the box, CRIS has 3 different security levels:

level 0 (Public): metadata value is available to all users, even Anonymous in case entity is available to them
level 1 (Trusted): metadata value is available only to logged in users members of a defined group, named “Trusted”, as a prerequisite, this group must be available in DSpace-CRIS 7 installation
level 2 (Admin and Owner): metadata value is available only to users belonging to the “Administrators” group or to the owner of the DSpace-CRIS 7 entity.

On the UI a toggle representing each value will be diplayed in submission or in administrative view:

image image

The effectivness of the security level is although not yet visible in this PR, as it will require the CRIS custom layout feature that will be made available with DSpace/DSpace#11779.

Once the layout feature is ported the metadata will be visible based on the security level and the user permission.

List of changes in this PR:

Adapted collection form for submission definition and entity type selection.
Added new way to edit archived item in submission style.
Implemented possibility to define security levels on metadata.
Added possibility to define a shared workspace.

There are currently some failure on the e2e tests, due to missing rest changes on the test instance; the tests expected to fail are my-dspace.cy.ts and submission.cy.ts.

To review the e2e test locally the linked rest PR is needed.

Checklist

This checklist provides a reminder of what we are going to look for when reviewing your PR. You do not need to complete this checklist prior creating your PR (draft PRs are always welcome).
However, reviewers may request that you complete any actions in this list if you have not done so. If you are unsure about an item in the checklist, don't hesitate to ask. We're here to help!

  • My PR is created against the main branch of code (unless it is a backport or is fixing an issue specific to an older branch).
  • My PR is small in size (e.g. less than 1,000 lines of code, not including comments & specs/tests), or I have provided reasons as to why that's not possible.
  • My PR passes ESLint validation using npm run lint
  • My PR doesn't introduce circular dependencies (verified via npm run check-circ-deps)
  • My PR includes TypeDoc comments for all new (or modified) public methods and classes. It also includes TypeDoc for large or complex private methods.
  • My PR passes all specs/tests and includes new/updated specs or tests based on the Code Testing Guide.
  • My PR aligns with Accessibility guidelines if it makes changes to the user interface.
  • My PR uses i18n (internationalization) keys instead of hardcoded English text, to allow for translations.
  • My PR includes details on how to test it. I've provided clear instructions to reviewers on how to successfully test this fix or feature.
  • If my PR includes new libraries/dependencies (in package.json), I've made sure their licenses align with the DSpace BSD License based on the Licensing of Contributions documentation.
  • If my PR includes new features or configurations, I've provided basic technical documentation in the PR itself.
  • If my PR fixes an issue ticket, I've linked them together.

@tdonohue tdonohue added new feature DSpace-CRIS merger This ticket/PR relates to the merger of DSpace-CRIS into DSpace. labels Feb 20, 2026
@tdonohue tdonohue moved this to 🙋 Needs Reviewers Assigned in DSpace 10.0 Release Feb 20, 2026
@tdonohue

Copy link
Copy Markdown
Member

@FrancescoMolinaro : Same with this PR, please add in the description which DSpace-CRIS differences this PR implements/includes.

@pnbecker

pnbecker commented Mar 4, 2026

Copy link
Copy Markdown
Member

Is there also a backend PR for the security configuration for metadata visibility?

@FrancescoMolinaro

Copy link
Copy Markdown
Contributor Author

Hi @pnbecker yes there is a Rest PR but is not ready yet, I will link it as soon as possible.

@github-actions

Copy link
Copy Markdown

Hi @FrancescoMolinaro,
Conflicts have been detected against the base branch.
Please resolve these conflicts as soon as you can. Thanks!

@tdonohue

Copy link
Copy Markdown
Member

@pnbecker and @FrancescoMolinaro : It looks like the backend PR for this PR is DSpace/DSpace#11964. I'll update the description of this PR to make that clear

@tdonohue tdonohue changed the title [DSpace-CRIS] porting of administrative edit via submission form and security configuration for metadata visibility [DSpace-CRIS] Administrative Edit of archived items via submission form and security configuration for metadata visibility (Frontend) Mar 13, 2026
@AdamF42

AdamF42 commented Apr 1, 2026

Copy link
Copy Markdown
Contributor
  • double upload on item with upload section not mandatory -> On CRIS the upload is always mandatory in the form so I believe we might have overlooked this scenario, I see anyway a double bitstream being added with a single binary being sent to the rest.

  • Wrong search results for shared workspace -> I think there is a wrong query being executed with the new discovery config, we should fix the search logic for this use case.

For the remaning open points :

  • The double upload problem should be fixed.

  • Wrong search results for shared workspace -> We can create a follow up task to handle this.

@tdonohue

tdonohue commented Apr 1, 2026

Copy link
Copy Markdown
Member

NOTE: I've done final testing today and verified the "double upload" problem is fixed. The backend PR was just merged. Once the fresh Docker images for the backend are created (may take 30-60mins), I'm going to restart the tests in this PR to verify all e2e tests now pass.

Assuming the e2e tests pass, this PR will also be merged as it's already at +2. Any outstanding issues (including those I reported above) should be moved to follow-up tickets so they can be addressed in 10.0 (or later if necessary)

@tdonohue

tdonohue commented Apr 1, 2026

Copy link
Copy Markdown
Member

@FrancescoMolinaro : After merging the backend PR, all e2e tests except one (item-statistics.cy.ts) are passing now in this PR. I'm trying to figure out why that one test is failing...it could just be minor updates are needed.

@tdonohue

tdonohue commented Apr 1, 2026

Copy link
Copy Markdown
Member

@FrancescoMolinaro : After more analysis of the item-statistics.cy.ts failures:

  • I can reproduce this failure locally if I run npm run e2e and run that test via Cypress.
  • It appears the "Statistics" menu (in the header) is not loading on Item pages in this Cypress test environment. The reason is unclear to me, but I've also locally modified the timeout to be 20 seconds, and the "Statistics" menu never loads (so it's not a timeout issue in the test)
  • Strangely, when I test this outside of Cypress, the "Statistics" menu does appear on Item/Entity pages. So, it seems to be only an issue within the Cypress environment.
  • I'm not sure why this PR causes this failure, but this failure doesn't exist on current main. My guess is that something in this PR is causing this failure (indirectly), but I'm not sure what it is right now.

In order to still move this PR along quickly, I'd propose we temporarily disable the failing test and create a follow-up ticket to fix this issue. The specific test to disable is the first one in that file, and we can disable it by changing the it to xit (to skip that test).

@tdonohue

tdonohue commented Apr 1, 2026

Copy link
Copy Markdown
Member

@FrancescoMolinaro : A follow-up to my last message. This PR definitely is causing the error in item-statistics.cy.ts.

I've realized that if I load any Publication Entity page while running the UI in Dev Mode then the "Statistics" menu never appears in the header. Here's how to reproduce:

  1. Run the UI in Dev Mode
  2. Visit any Publication entity page. If you browse/search to get to the page, the "Statistics" menu appears in the header.
  3. Reload the Publication page in your browser. The "Statistics" menu will disappear. In other words, a direct link to the publication page will NOT load the "Statistics" menu.

I'm still OK with temporarily disabling this e2e test unless it's obvious how to fix this bug. We can move that e2e test to a folllow-up ticket, if it's not able to be fixed in this PR.

@tdonohue tdonohue left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

@FrancescoMolinaro : In addition to the broken e2e test above, I stumbled on a few very minor issues in the i18n keys below. These would be good to fix quickly

Comment thread src/assets/i18n/en.json5 Outdated

"mydspace.show.workspace": "Your submissions",

"mydspace.show.otherworkspace": "Shared Submissions",

@tdonohue tdonohue Apr 1, 2026

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

In re-testing today, it appears this key should be updated to be mydspace.show.otherWorkspace, as the key mydspace.show.otherworkspace is no longer working. (The difference is that "Workspace" needs to be capitalized for this key to work)

Comment thread src/assets/i18n/en.json5 Outdated

"workflow.search.results.head": "Workflow tasks",

"otherworkspace.search.results.head": "Workspace submissions",

@tdonohue tdonohue Apr 1, 2026

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Similarly here, this key should be updated to be otherWorkspace.search.results.head.

Can we also update the value to say "Shared submissions" to match the value of mydspace.show.otherWorkspace above?

@tdonohue

tdonohue commented Apr 1, 2026

Copy link
Copy Markdown
Member

@FrancescoMolinaro : Final note from me for today...

For this issue:

(NEW) While the new "Edit" feature now works for traditional Item objects, it's not correctly handling traditional Authority Control values. For instance, if I edit a traditional Item that has an Author of "Tim Donohue" which has an ID in the authority column, then the Edit form will display the Authority ID and NOT the value. Here's a screenshot of what I mean. This particular Item has an Author named "Donohue, Tim" which has an Authority ID. You see the Authority ID and not the value in the Author field when editing the Item. (This behavior ONLY occurs for traditional Items and not for Publications)

I've found that I cannot reproduce this with a new Item. I.e. I cannot seem to create an Item from the UI which will cause this behavior. I suspect I have some old, corrupt data in my system which is resulting in this behavior (possibly the bug occurs when the Authority ID of a metadata field is invalid or points at a deleted object's UUID??). Regardless, in the User Interface, I cannot create an invalid Authority ID because it's validity is checked & saving the invalid value fails.

So, it's possible this is only reproducible with corrupted data. For now, I'll hold off on creating a ticket until I can find a way to reproduce it reliably.

@FrancescoMolinaro

Copy link
Copy Markdown
Contributor Author

Hi @tdonohue , thanks for the feedback and sorry for the delay, the e2e should be fixed now, the error was caused by an uncaught error in the new edit menu, I have also updated the labels as you noted, hopefully this is now ready for merge.

@tdonohue tdonohue left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

👍 Thanks @FrancescoMolinaro for the final cleanup (getting test fixed & i18n fixes). It looks correct to me and I verified the i18n keys are working properly now. Merging this with +2 approvals.

@tdonohue
tdonohue merged commit 781bef5 into DSpace:main Apr 2, 2026
16 checks passed
@github-project-automation github-project-automation Bot moved this from 👍 Reviewer Approved to ✅ Done in DSpace 10.0 Release Apr 2, 2026
@tdonohue

tdonohue commented Apr 2, 2026

Copy link
Copy Markdown
Member

@FrancescoMolinaro : Forgot to mention, I'm adding the "needs documentation" flag to this PR because the new features added here all need to be documented in our 10.x docs: https://wiki.lyrasis.org/display/DSDOC10x

@tdonohue tdonohue added the needs documentation PR is missing documentation. All new features and config changes require documentation. label Apr 2, 2026
@tdonohue tdonohue added this to the 10.0 milestone Apr 2, 2026
@tdonohue

tdonohue commented May 4, 2026

Copy link
Copy Markdown
Member

@FrancescoMolinaro and @AdamF42 : It looks like we have some basic docs on Editing in Submission mode, but we're still missing documentation of Metadata security (e.g. metadatavalue.security.* settings) and selecting a submission form for Collections.

Once those docs can be added to the 10.x docs, we can remove the needs documentation label from this PR.

@tdonohue

Copy link
Copy Markdown
Member

@tdonohue tdonohue removed the needs documentation PR is missing documentation. All new features and config changes require documentation. label May 12, 2026
milanmajchrak added a commit to dataquest-dev/uoe-dspace-datashare-angular that referenced this pull request Jul 9, 2026
…port DSpace#5145)

Fix submission stuck on "Saving..." (serialize save effects, backport DSpace#5145)
dspeed2 pushed a commit to UoEMainLibrary/dspace-datashare-angular that referenced this pull request Jul 9, 2026
* feat: show file checksum instead of format in full item view

Replace the per-file "Format" line in the full item view file listing
with a "File checksum" line (algorithm + value). Add the checkSum field
to the Bitstream model so the REST value deserializes, and add the
item.page.filesection.checksum i18n key.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

* refactor: guard checksum display and show value only

Wrap the full item view checksum dt/dd in *ngIf="file?.checkSum" and render
only the checksum value (drop the algorithm prefix), so no stray colon shows
when a bitstream has no checksum. Propagate item.page.filesection.checksum to
all locale files with an English placeholder.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

* refactor: align Bitstream checkSum with upstream ChecksumInfo

Match DSpace/dspace-angular@main (commit 4f72074): use the exported
ChecksumInfo interface and `checkSum: ChecksumInfo` positioned after
`description`, replacing the inline anonymous type, to minimize conflicts on a
future DSpace 9 migration. Display and i18n key are unchanged (upstream renders
no checksum row in the full item view).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

* revert: drop non-en filesection.checksum i18n key

UoE instance only ships English; other locale .json5 files aren't
maintained here. Revert the checksum key addition to all 27 non-en
locales, keep it in en.json5 only.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

* refactor: drop redundant optional chaining on checkSum

file is guaranteed by *ngFor and checkSum is truthy inside the *ngIf
guard, so use plain file.checkSum / file.checkSum.value to match the
surrounding template style.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>

* fix: changed - File checksum: - to - Checksum: -

* fix: added checksum algorithm (same style as upstream)

* Fix submission stuck on "Saving..." by serializing save effects (switchMap -> concatMap)

Backport of the save-effect change from upstream PR DSpace#5145
(commit a3c14c5, first released in DSpace 10.0; not present in 8.x/9.x).

The four submission save effects used switchMap. When two save actions of the
same type overlap (common during editing: unguarded section/upload/save-for-later
saves, save-on-change on validation errors, or an enabled autosave timer),
switchMap cancels the in-flight save's inner observable AFTER it dispatched
StartTransactionPatchOperationsAction (commitPending=true) but BEFORE its response
handler runs. Commit/Rollback are dispatched only inside that cancelled observable,
so commitPending stays true forever; the next save is then dropped by the
take(1)+filter(!commitPending) guard in submitJsonPatchOperations, no
SAVE_*_SUCCESS/ERROR is emitted, savePending stays true, and the form is stuck on
"Saving..." until the user reloads (losing unsaved metadata).

concatMap serializes the save effects so each inner observable completes
(dispatching Commit/Rollback and clearing commitPending) before the next save runs,
eliminating the race.

Only the four save effects are changed (saveSubmission$, saveForLaterSubmission$,
saveSection$, saveAndDeposit$), matching upstream. deposit/discard/updateSection
intentionally keep switchMap. The improved catchError from DSpace#5145 is not backported
(it depends on parseErrorResponse and action signatures not present in 8.3).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* Harden submission form/vocabulary loading against permanent stuck spinners

Fixes a class of "spinner spins forever, user must reload and loses typed
metadata" bugs in the submission form. A component sets a loading/searching flag,
loads data via a RemoteData pipe, and resets the flag ONLY on the success path
using getFirstSucceededRemoteData()/...Payload()/...ListPayload(). DSpace turns
HTTP errors into a NON-throwing failed RemoteData (state=Error), and the
store-backed RemoteData observable never completes, so on a failed OR slow/
never-responding request the success-only operator never emits, the component's
catchError (which only catches thrown errors) never fires, and the spinner stays
forever. There is also no HTTP request timeout anywhere in the app.

Inherited from vanilla DSpace 8.3 and NOT fixed upstream (the same pattern is
still present on main/10.x), so there is no backport available -- this is a new
hardening fix, following the same getFirstCompletedRemoteData approach upstream
used for the whole-form loading fix (DSpace#4060).

For each affected load: switch getFirstSucceededRemoteData* to
getFirstCompletedRemoteData() (emits on success AND failure, then completes),
extract the payload failure-safely, add timeout({ each: 30000 }) for
never-responding requests, and reset the spinner flag in finalize() so it always
clears. On failure/timeout the control shows an empty result instead of hanging.

Sites fixed (all inherited from 8.3):
- sections/form/section-form.component.ts (Describe section) -- bounded 30s
  timeout so it never spins forever; kept getFirstSucceededRemoteData for the
  item follow-link to avoid dereferencing an undefined submission object.
- ds-dynamic-form-ui/models/list/dynamic-list.component.ts (radio/checkbox vocab, e.g. dc.type)
- ds-dynamic-form-ui/models/scrollable-dropdown/dynamic-scrollable-dropdown.component.ts (vocabulary dropdowns)
- ds-dynamic-form-ui/models/onebox/dynamic-onebox.component.ts (authority typeahead)
- ds-dynamic-form-ui/models/tag/dynamic-tag.component.ts (keyword/tag authority)
- ds-dynamic-form-ui/models/lookup/dynamic-lookup.component.ts (lookup authority)
- vocabulary-treeview/vocabulary-treeview.service.ts (hierarchical vocabulary tree)
- collection-dropdown/collection-dropdown.component.ts (collection picker; parentCommunity was hanging reduce())
- submission/form/collection/submission-form-collection.component.ts (change-collection selector)
- sections/cc-license/submission-section-cc-licenses.component.ts (CC-license section)
- ds-dynamic-form-ui/models/relation-group/dynamic-relation-group.components.ts (relation chips on edit)

Verified locally: `tsc --noEmit -p tsconfig.app.json` and `eslint` both pass with
0 errors on the changed files.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* docs(repro): add before/after reproduction of the dropdown loading hang

Deterministic reproduction on a local DSpace 8.3 stack (published dspace-8_x-test
backend images + this frontend). A Playwright script simulates a failing/slow
controlled-vocabulary endpoint by returning HTTP 500 for
/api/submission/vocabularies/{name}/entries, then opens the "Type" dropdown on a
new submission's Describe form.

- before: getFirstSucceededRemoteData ignores the failed RemoteData, so the "Loading..."
  indicator stays visible forever (measured stuck for the full 14s observation window).
- after: getFirstCompletedRemoteData + finalize handles the failed RemoteData, the
  spinner clears immediately and the dropdown shows "No results found".

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* docs(repro): add before/after reproduction of the stuck "Saving..." hang

Deterministic reproduction on a local DSpace 8.3 stack. A Playwright script
delays every submission PATCH by ~3s (models a slow save) and fires two
overlapping autosaves (two edits of the autosave-on-change dc.title field).

- before (base, switchMap): the second save cancels the in-flight first save
  mid-transaction; commitPending is orphaned true; the second save is dropped by
  the take(1)+filter(!commitPending) guard (only 1 PATCH ever leaves the client);
  savePending never resets -> footer stuck on "Saving..." for the full 18s window.
- after (this PR, concatMap): the saves are serialized; the first completes and
  clears commitPending before the second runs; "Saving..." clears within ~4s.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* docs(repro): add never-responding-backend (timeout backstop) before/after

Second reproduction covering the slow/never-responding path (not just HTTP 500).
The vocabulary /entries request is held open forever (models a hung socket).

- before (no timeout): "Loading..." stays stuck past 45s (never recovers).
- after (timeout({each:30000})): the spinner clears ~30s after the request stalls
  and the dropdown shows "No results found".

Clips are sped up ~3x. Confirms the timeout() backstop half of the fix, which the
HTTP-500 reproduction did not exercise.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* fix(item-page): show DOI field on simple item view while DOI registration is pending

The DataShare simple item view renders the DOI ("Persistent Identifier") field
via ds-item-page-uri-field, which filtered dc.identifier.uri for values starting
with https://doi.org. The whole field wrapper was gated behind *ngIf="hasDoiLink",
so when a record's DOI has not been registered yet (the DOI value is only written
to dc.identifier.uri by the backend AFTER the doi-organiser scheduled task
registers it), the field was hidden entirely and users saw no indication that a
DOI exists or is coming.

Restore the previous behaviour where the DOI field is always shown (with an empty
value while registration is pending):

- MetadataUriValuesComponent / ItemPageUriFieldComponent: add an opt-in `doiField`
  input. In DOI mode the field wrapper is always rendered (hideIfNoTextContent =
  false) and only https://doi.org values are shown as links. When false (default)
  the upstream generic behaviour is kept, which also repairs non-DOI URI fields in
  the base theme that were unintentionally hidden by the previous global filter.
- datashare untyped-item: opt the DOI field into `[doiField]="true"`.

Test-driven: added specs for the pending (no DOI yet), registered, and empty cases,
plus the default (non-DOI) URI behaviour.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* Reduce vocab-load timeout to 15s + show a user-friendly error notification

Follow-up to the loading-spinner hardening:
- Lower the request timeout backstop from 30s to 15s on all the hardened loads
  (a 30s spinner is too long for an interactive dropdown).
- On a failed OR timed-out controlled-vocabulary / authority lookup, show a
  dismissible error toast ("Something went wrong while loading the options.
  Please try again.") instead of silently showing an empty "No results found",
  so the user knows to retry. Added a shared notifyVocabularyLoadError() helper on
  the DsDynamicVocabularyComponent base (via inject()) and wired it into the
  scrollable-dropdown and lookup loads. A genuinely empty (succeeded) result is
  unchanged -> still "No results found", no error toast.
- Harden dynamic-onebox vocabulary$ (findVocabularyById): getFirstSucceededRemoteDataPayload
  -> getFirstCompletedRemoteData, so a failed vocabulary-metadata lookup resolves
  to "not hierarchical" (no tree button) instead of leaving isHierarchicalVocabulary$
  pending forever. Null-safe guards on result?.hierarchical and vocabulary?.preloadLevel.

tsc --noEmit and eslint pass with 0 errors. Verified in the local repro: on a 500,
the Type dropdown now clears immediately, shows "No results found", AND a red
"Something went wrong ... Please try again." toast appears.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* docs(repro): refresh dropdown "after" clip to show the 15s + error-toast behaviour

The after clip now shows the updated recovery: on a failed vocabulary load the
Type dropdown clears immediately, shows "No results found", and a dismissible
"Something went wrong ... Please try again." error toast appears.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* docs(repro): refresh never-responding after clip for the 15s timeout (was 30s)

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* refactor(item-page): collapse DOI/default URI rendering into a single wrapper

Address review nits on the pending-DOI fix without changing behaviour:

- Merge the doiField and default template branches into one ds-metadata-field-wrapper
  ([hideIfNoTextContent]="!doiField"), removing the duplicated link markup.
- Add a `doiValues` getter that filters mdValues to https://doi.org values (restoring the
  `typeof value === 'string'` guard). In DOI mode the *ngFor and the `!last` separator are
  computed against this visible-DOI subset, so a trailing non-DOI value can no longer emit a
  stray separator after the last DOI.
- Tighten the registered-case spec to assert the label header, and add a regression spec for
  multiple DOIs followed by a non-DOI value (only one separator between the DOIs).

Verified locally: metadata-uri-values + item-page-uri-field specs 23/23 green, lint clean,
build:prod (SSR production build) exits 0.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* test: provide NotificationsService stub in vocabulary component specs

The DsDynamicVocabularyComponent base now injects NotificationsService (for the
"something went wrong" error notification on a failed vocabulary load). Its
subclasses' unit tests (scrollable-dropdown, onebox, tag, lookup) did not provide
it, so component construction failed with
"NullInjectorError: NotificationsService -> Store -> No provider for Store"
(NotificationsService is providedIn root and depends on the ngrx Store, which the
isolated TestBeds don't set up).

Provide the existing NotificationsServiceStub in each of the four specs.
Verified locally: those 4 spec files now run 54/54 SUCCESS (were 54 FAILED).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* chore: remove reproduction media from the code branch

The before/after clips are now hosted on the separate 'pr-repro-media' branch and
referenced from this PR's description, so they are no longer part of the code diff.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* chore: remove reproduction media from the code branch

The before/after clips are now hosted on the separate 'pr-repro-media' branch and
referenced from this PR's description, so they are no longer part of the code diff.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* feat(item-page): load DOI resolver from backend config instead of hard-coding it

The DOI field decides which dc.identifier.uri values are DOIs by matching the DOI
resolver base URL. That URL is a backend setting (identifier.doi.resolver), so read
it from the REST config endpoint instead of hard-coding "https://doi.org" in the UI.

- MetadataUriValuesComponent now fetches identifier.doi.resolver via
  ConfigurationDataService on init (only in doiField mode) and uses it in doiValues.
  Falls back to the DSpace default https://doi.org (DOIServiceImpl#RESOLVER_DEFAULT)
  when the property is not exposed/defined, so it stays correct without any backend
  change.
- Added a spec proving a value matching a custom configured resolver is treated as a
  DOI, and provided ConfigurationDataService stubs to the dependent specs
  (item-page-uri-field, publication, untyped-item).

Requires the backend to expose identifier.doi.resolver in rest.properties.exposed
(separate backend PR); until then the frontend uses the default resolver.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* feat(item-page): show "DOI registration in progress" while a DOI is pending

Instead of showing an empty DOI ("Persistent Identifier") field while the DOI is still
queued for registration by the scheduled task, show a "DOI registration in progress"
message. Once registration completes and the resolver value appears in dc.identifier.uri,
the DOI link is shown instead.

- metadata-uri-values: in doiField mode, render the item.page.doi.pending message when
  there is no DOI value yet (doiValues is empty).
- add the item.page.doi.pending i18n key to the datashare theme and core en.json5.
- specs: assert the message is shown when pending / no identifier, and NOT shown once a
  DOI is present.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Juraj Roka <95219754+jr-rk@users.noreply.github.com>
Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
Co-authored-by: milanmajchrak <minptai7@gmail.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

authorization related to authorization, permissions or groups component: Item (Archived) Item display or editing component: submission DSpace-CRIS merger This ticket/PR relates to the merger of DSpace-CRIS into DSpace. new feature

Projects

No open projects
Status: ✅ Done

Development

Successfully merging this pull request may close these issues.

[DSpace-CRIS] Administrative Edit of archived items via submission form and security configuration for metadata visibility

6 participants