Skip to content

Commit

Permalink
Merge pull request #1051 from geonetwork/ME-warn-user-newer-version
Browse files Browse the repository at this point in the history
[Editor]: Warn user if draft has been updated
  • Loading branch information
LHBruneton-C2C authored Dec 30, 2024
2 parents 8c98ae0 + b12f2c0 commit 16f1367
Show file tree
Hide file tree
Showing 32 changed files with 645 additions and 21 deletions.
63 changes: 63 additions & 0 deletions apps/metadata-editor-e2e/src/e2e/record-actions.cy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -317,4 +317,67 @@ describe('record-actions', () => {
})
})
})
describe('drafting', () => {
let recordUuid: any
describe('if a user edits the record in the meantime', () => {
beforeEach(() => {
cy.visit('/edit/9e1ea778-d0ce-4b49-90b7-37bc0e448300')
cy.url().should('include', '/edit/')
cy.editor_readFormUniqueIdentifier().then((uuid) => {
recordUuid = uuid
cy.wrap(uuid).as('recordUuid')
})
cy.get('gn-ui-form-field[ng-reflect-model=abstract] textarea').as(
'abstractField'
)
cy.get('@abstractField').clear()
cy.get('@abstractField').type('modified abstract')
cy.editor_findDraftInLocalStorage().then((value) => {
expect(value).to.contain('modified abstract')
})
cy.editor_wrapFirstDraft()
cy.clearRecordDrafts()
cy.visit('/edit/9e1ea778-d0ce-4b49-90b7-37bc0e448300')
cy.editor_wrapPreviousDraft()
cy.get('gn-ui-form-field[ng-reflect-model=abstract] textarea').as(
'abstractField'
)
cy.get('@abstractField').clear()
cy.get('@abstractField').type('modified by someone else')
cy.editor_publishAndReload()
cy.window().then((win) => {
cy.get('@firstDraft').then((firstDraft) => {
return win.localStorage.setItem(
`geonetwork-ui-draft-${recordUuid}`,
firstDraft.toString()
)
})
})
cy.visit('/edit/9e1ea778-d0ce-4b49-90b7-37bc0e448300')
})
it('should show the warning banner and the warning menu when publishing', () => {
cy.get('[data-test="draft-alert"]').should('be.visible')
cy.get('md-editor-publish-button').click()
cy.get('[data-test="publish-warning"]').should('be.visible')
})
})
describe('if nobody edits the record in the meantime', () => {
beforeEach(() => {
cy.clearRecordDrafts()
cy.visit('/edit/9e1ea778-d0ce-4b49-90b7-37bc0e448300')
cy.get('gn-ui-form-field[ng-reflect-model=abstract] textarea').as(
'abstractField'
)
cy.get('@abstractField').clear()
cy.get('@abstractField').type('modified abstract')
cy.visit('/catalog/search')
})
it('should not show any warning', () => {
cy.visit('/edit/9e1ea778-d0ce-4b49-90b7-37bc0e448300')
cy.get('[data-test="draft-alert"]').should('not.exist')
cy.get('md-editor-publish-button').click()
cy.get('[data-test="publish-warning"]').should('not.exist')
})
})
})
})
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
<ng-container [ngSwitch]="status$ | async">
<gn-ui-button
cdkOverlayOrigin
#actionMenuButton
*ngSwitchCase="'hasChanges'"
type="primary"
(buttonClick)="saveRecord()"
(buttonClick)="verifyPublishConditions()"
[matTooltip]="'editor.record.publish' | translate"
>
<ng-icon name="iconoirCloudUpload"></ng-icon>
Expand All @@ -11,12 +13,49 @@
<mat-spinner [diameter]="16"></mat-spinner>
</gn-ui-button>
<gn-ui-button
cdkOverlayOrigin
#actionMenuButton
*ngSwitchCase="'upToDate'"
type="secondary"
[disabled]="true"
(buttonClick)="saveRecord()"
(buttonClick)="verifyPublishConditions()"
[matTooltip]="'editor.record.upToDate' | translate"
>
<ng-icon name="matCheckCircleOutline"></ng-icon>
</gn-ui-button>
<ng-template #template>
<div
data-test="publish-warning"
class="w-96 p-5 flex flex-col gap-3 mt-2 border border-gray-100 bg-white shadow-2xl rounded-2xl mr-2"
>
<span
class="text-center"
translate
[translateParams]="{
date: formatDate(publishWarning.date),
user: publishWarning.user
}"
>editor.record.publish.confirmation.message</span
>
<div class="flex flex-row gap-8 justify-center">
<gn-ui-button
[style.--gn-ui-button-width]="'100px'"
(buttonClick)="cancelPublish()"
>{{
'editor.record.publish.confirmation.cancelText' | translate
}}</gn-ui-button
>
<gn-ui-button
(buttonClick)="confirmPublish()"
cdkFocusInitial
type="primary"
data-cy="publish-confirm-button"
[style.--gn-ui-button-width]="'100px'"
>{{
'editor.record.publish.confirmation.confirmText' | translate
}}</gn-ui-button
>
</div>
</div>
</ng-template>
</ng-container>
Original file line number Diff line number Diff line change
@@ -1,7 +1,12 @@
import { ComponentFixture, TestBed } from '@angular/core/testing'
import {
ComponentFixture,
TestBed,
fakeAsync,
tick,
} from '@angular/core/testing'
import { PublishButtonComponent } from './publish-button.component'
import { EditorFacade } from '@geonetwork-ui/feature/editor'
import { BehaviorSubject, firstValueFrom, of } from 'rxjs'
import { BehaviorSubject, Subject, firstValueFrom, of } from 'rxjs'
import { TranslateModule } from '@ngx-translate/core'
import { HttpClientModule } from '@angular/common/http'
import { PlatformServiceInterface } from '@geonetwork-ui/common/domain/platform.service.interface'
Expand All @@ -10,6 +15,7 @@ import {
RecordsApiService,
} from '@geonetwork-ui/data-access/gn4'
import { barbieUserFixture } from '@geonetwork-ui/common/fixtures'
import { OverlayRef } from '@angular/cdk/overlay'

class EditorFacadeMock {
changedSinceSave$ = new BehaviorSubject(false)
Expand All @@ -18,9 +24,26 @@ class EditorFacadeMock {
record$ = new BehaviorSubject({
ownerOrganization: { name: 'Group 1', id: 1 },
uniqueIdentifier: 304,
recordUpdated: new Date('2023-01-01'),
extras: { ownerInfo: '1|John|Doe' },
})
saveRecord = jest.fn()
saveSuccess$ = new BehaviorSubject(true)
checkHasRecordChanged = jest.fn()
hasRecordChanged$ = new Subject()
isRecordNotYetSaved = jest.fn().mockReturnValue(false)
recordHasDraft = jest.fn().mockReturnValue(true)
getAllDrafts = jest
.fn()
.mockReturnValue(
of([{ uniqueIdentifier: 304, recordUpdated: new Date('2023-01-01') }])
)
getRecord = jest.fn().mockReturnValue(
of({
recordUpdated: new Date('2023-02-01'),
extras: { ownerInfo: '1|John|Doe' },
})
)
}

const user = barbieUserFixture()
Expand All @@ -47,6 +70,7 @@ describe('PublishButtonComponent', () => {
let fixture: ComponentFixture<PublishButtonComponent>
let facade: EditorFacadeMock
let recordsApiService: RecordsApiService
let overlaySpy: any

beforeEach(async () => {
await TestBed.configureTestingModule({
Expand Down Expand Up @@ -79,6 +103,12 @@ describe('PublishButtonComponent', () => {
facade = TestBed.inject(EditorFacade) as any
fixture = TestBed.createComponent(PublishButtonComponent)
component = fixture.componentInstance
overlaySpy = {
dispose: jest.fn(),
attach: jest.fn(),
backdropClick: jest.fn().mockReturnValue(of()),
}
component['overlayRef'] = overlaySpy
fixture.detectChanges()
})

Expand Down Expand Up @@ -127,4 +157,51 @@ describe('PublishButtonComponent', () => {
)
})
})
describe('#confirmPublish', () => {
it('should call saveRecord', () => {
const saveRecordSpy = jest.spyOn(component, 'saveRecord')
component.confirmPublish()
expect(saveRecordSpy).toHaveBeenCalled()
})
})

describe('#cancelPublish', () => {
it('should set isActionMenuOpen to false', () => {
component.isActionMenuOpen = true
component.cancelPublish()
expect(component.isActionMenuOpen).toBe(false)
})
})

describe('#verifyPublishConditions', () => {
it('should call openConfirmationMenu if hasRecordChanged emits with a date', () => {
const openConfirmationMenuSpy = jest.spyOn(
component,
'openConfirmationMenu'
)
const saveRecordSpy = jest.spyOn(component, 'saveRecord')

component.verifyPublishConditions()
facade.hasRecordChanged$.next(null)
facade.hasRecordChanged$.next({ date: new Date(), user: 'John Doe' })

expect(openConfirmationMenuSpy).toHaveBeenCalled()
expect(saveRecordSpy).not.toHaveBeenCalled()
})

it('should call saveRecord if hasRecordChanged emits without a date', () => {
const openConfirmationMenuSpy = jest.spyOn(
component,
'openConfirmationMenu'
)
const saveRecordSpy = jest.spyOn(component, 'saveRecord')

component.verifyPublishConditions()
facade.hasRecordChanged$.next(null)
facade.hasRecordChanged$.next({ date: undefined, user: undefined })

expect(saveRecordSpy).toHaveBeenCalled()
expect(openConfirmationMenuSpy).not.toHaveBeenCalled()
})
})
})
Loading

0 comments on commit 16f1367

Please sign in to comment.