Skip to content

V16 Added acceptance tests for document property value permission #19385

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 16 commits into from
Jun 2, 2025
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 9 additions & 10 deletions tests/Umbraco.Tests.AcceptanceTest/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions tests/Umbraco.Tests.AcceptanceTest/package.json
Original file line number Diff line number Diff line change
@@ -20,8 +20,8 @@
"typescript": "^4.8.3"
},
"dependencies": {
"@umbraco/json-models-builders": "^2.0.33",
"@umbraco/playwright-testhelpers": "^16.0.15",
"@umbraco/json-models-builders": "^2.0.35",
"@umbraco/playwright-testhelpers": "^16.0.20",
"camelize": "^1.0.0",
"dotenv": "^16.3.1",
"node-fetch": "^2.6.7"
Original file line number Diff line number Diff line change
@@ -51,7 +51,7 @@ test.afterEach(async ({umbracoApi}) => {

test('can browse content node with permission enabled', async ({umbracoApi, umbracoUi}) => {
// Arrange
userGroupId = await umbracoApi.userGroup.createUserGroupWithBrowseNodePermission(userGroupName);
userGroupId = await umbracoApi.userGroup.createUserGroupWithReadPermission(userGroupName);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();
@@ -66,7 +66,7 @@ test('can browse content node with permission enabled', async ({umbracoApi, umbr

test('can not browse content node with permission disabled', async ({umbracoApi, umbracoUi}) => {
// Arrange
userGroupId = await umbracoApi.userGroup.createUserGroupWithBrowseNodePermission(userGroupName, false);
userGroupId = await umbracoApi.userGroup.createUserGroupWithReadPermission(userGroupName, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
import { expect } from '@playwright/test';
import {AliasHelper, ConstantHelper, NotificationConstantHelper, test} from '@umbraco/playwright-testhelpers';

const testUser = ConstantHelper.testUserCredentials;
let testUserCookieAndToken = {cookie: "", accessToken: "", refreshToken: ""};

const userGroupName = 'TestPropertyValuePermission';
let userGroupId = null;

const documentName = 'TestDocument';
const documentTypeName = 'TestDocumentType';
const dataTypeName = 'Textstring';
const textString = 'This is test textstring';

test.beforeEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoApi.document.ensureNameNotExists(documentName);
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const documentTypeId = await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id);
await umbracoApi.document.createDocumentWithTextContent(documentName, documentTypeId, textString, dataTypeName);
});

test.afterEach(async ({umbracoApi}) => {
// Ensure we are logged in to admin
await umbracoApi.loginToAdminUser(testUserCookieAndToken.cookie, testUserCookieAndToken.accessToken, testUserCookieAndToken.refreshToken);
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoApi.document.ensureNameNotExists(documentName);
await umbracoApi.userGroup.ensureNameNotExists(userGroupName);
});

test('cannot see property values without UI read permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
userGroupId = await umbracoApi.userGroup.createUserGroupWithReadPermissionAndReadPropertyValuePermission(userGroupName, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);

// Assert
await umbracoUi.content.isPropertyEditorUiWithNameVisible('text-box', false);
});

test('can see property values with UI read but not UI write permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
userGroupId = await umbracoApi.userGroup.createUserGroupWithReadPermissionAndReadPropertyValuePermission(userGroupName, true, true);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);

// Assert
await umbracoUi.content.isPropertyEditorUiWithNameReadOnly('text-box');
});

test('cannot open content without document read permission even with UI read permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
userGroupId = await umbracoApi.userGroup.createUserGroupWithReadPermissionAndReadPropertyValuePermission(userGroupName, false, true);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);

// Assert
await umbracoUi.content.doesErrorNotificationHaveText(NotificationConstantHelper.error.permissionDenied);
});

test('cannot edit property values without UI write permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
userGroupId = await umbracoApi.userGroup.createUserGroupWithUpdatePermissionAndWritePropertyValuePermission(userGroupName, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);

// Assert
await umbracoUi.content.isDocumentReadOnly(false);
await umbracoUi.content.isPropertyEditorUiWithNameReadOnly('text-box');
});

// Remove .skip when the front-end is ready.
// Issue link: https://github.com/umbraco/Umbraco-CMS/issues/19395
test.skip('can edit property values with UI write permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
const updatedText = 'Updated test text';
userGroupId = await umbracoApi.userGroup.createUserGroupWithUpdatePermissionAndWritePropertyValuePermission(userGroupName, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);
await umbracoUi.content.enterTextstring(updatedText);
await umbracoUi.content.clickSaveButton();

// Assert
const documentData = await umbracoApi.document.getByName(documentName);
expect(documentData.values[0].alias).toEqual(AliasHelper.toAlias(dataTypeName));
expect(documentData.values[0].value).toEqual(updatedText);
});

test('cannot see property values with only UI write but no UI read permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
userGroupId = await umbracoApi.userGroup.createUserGroupWithUpdatePermissionAndWritePropertyValuePermission(userGroupName, true, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);

// Assert
await umbracoUi.content.isPropertyEditorUiWithNameVisible('text-box', false);
});

Check warning on line 127 in tests/Umbraco.Tests.AcceptanceTest/tests/DefaultConfig/Users/Permissions/UserGroup/DocumentPropertyValuePermission.spec.ts

CodeScene Delta Analysis / CodeScene Cloud Delta Analysis (main)

❌ New issue: Code Duplication

The module contains 5 functions with similar structure: 'can see property values with UI read but not UI write permission','cannot edit property values without UI write permission','cannot open content without document read permission even with UI read permission','cannot see property values with only UI write but no UI read permission' and 1 more functions. Avoid duplicated, aka copy-pasted, code inside the module. More duplication lowers the code health.
Original file line number Diff line number Diff line change
@@ -0,0 +1,150 @@
import { expect } from '@playwright/test';
import {ConstantHelper, test} from '@umbraco/playwright-testhelpers';

const testUser = ConstantHelper.testUserCredentials;
let testUserCookieAndToken = {cookie: "", accessToken: "", refreshToken: ""};

const userGroupName = 'TestPropertyValuePermission';
let userGroupId = null;

const documentName = 'TestContent';
const documentTypeName = 'TestDocumentTypeForContent';
const customDataTypeName = 'Custom Block List';
const elementTypeName = 'BlockListElement';
const propertyInBlock = 'Textstring';
const groupName = 'testGroup';
let elementTypeId = '';

test.beforeEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoApi.document.ensureNameNotExists(documentName);
const textStringData = await umbracoApi.dataType.getByName(propertyInBlock);
elementTypeId = await umbracoApi.documentType.createDefaultElementType(elementTypeName, groupName, propertyInBlock, textStringData.id);
});

test.afterEach(async ({umbracoApi}) => {
// Ensure we are logged in to admin
await umbracoApi.loginToAdminUser(testUserCookieAndToken.cookie, testUserCookieAndToken.accessToken, testUserCookieAndToken.refreshToken);
await umbracoApi.document.ensureNameNotExists(documentName);
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoApi.documentType.ensureNameNotExists(elementTypeName);
await umbracoApi.dataType.ensureNameNotExists(customDataTypeName);
});

test('can see property values in block list with UI read but not UI write permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.document.createDefaultDocumentWithABlockListEditor(documentName, elementTypeId, documentTypeName, customDataTypeName);
userGroupId = await umbracoApi.userGroup.createUserGroupWithReadPermissionAndReadPropertyValuePermission(userGroupName, true, true);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);
await umbracoUi.content.isPropertyEditorUiWithNameVisible('block-list', true);
await umbracoUi.content.clickEditBlockListBlockButton();

// Assert
await umbracoUi.content.isPropertyEditorUiWithNameReadOnly('text-box');
});

// Remove .skip when the front-end is ready.
// Issue link: https://github.com/umbraco/Umbraco-CMS/issues/19395
test.skip('can edit property values in block list with UI write permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
const updatedText = 'Updated test text';
await umbracoApi.document.createDefaultDocumentWithABlockListEditor(documentName, elementTypeId, documentTypeName, customDataTypeName);
userGroupId = await umbracoApi.userGroup.createUserGroupWithUpdatePermissionAndWritePropertyValuePermission(userGroupName, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);
await umbracoUi.content.isPropertyEditorUiWithNameVisible('block-list', true);
await umbracoUi.content.clickEditBlockListBlockButton();
await umbracoUi.content.enterTextstring(updatedText);
await umbracoUi.content.clickUpdateButton();
await umbracoUi.content.clickSaveButton();

// Assert
const documentData = await umbracoApi.document.getByName(documentName);
expect(documentData.values[0].value.contentData[0].values[0].value).toEqual(updatedText);
});

test('cannot see property values in block list with only UI write but no UI read permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.document.createDefaultDocumentWithABlockListEditor(documentName, elementTypeId, documentTypeName, customDataTypeName);
userGroupId = await umbracoApi.userGroup.createUserGroupWithUpdatePermissionAndWritePropertyValuePermission(userGroupName, true, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);

// Assert
await umbracoUi.content.isPropertyEditorUiWithNameVisible('block-list', false);
});

test('can see property values in block grid with UI read but not UI write permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.document.createDefaultDocumentWithABlockGridEditor(documentName, elementTypeId, documentTypeName, customDataTypeName);
userGroupId = await umbracoApi.userGroup.createUserGroupWithReadPermissionAndReadPropertyValuePermission(userGroupName, true, true);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);
await umbracoUi.content.isPropertyEditorUiWithNameVisible('block-grid', true);
await umbracoUi.content.clickEditBlockGridBlockButton();

// Assert
await umbracoUi.content.isPropertyEditorUiWithNameReadOnly('text-box');
});

// Remove .skip when the front-end is ready.
// Issue link: https://github.com/umbraco/Umbraco-CMS/issues/19395
test.skip('can edit property values in block grid with UI write permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
const updatedText = 'Updated test text';
await umbracoApi.document.createDefaultDocumentWithABlockGridEditor(documentName, elementTypeId, documentTypeName, customDataTypeName);
userGroupId = await umbracoApi.userGroup.createUserGroupWithUpdatePermissionAndWritePropertyValuePermission(userGroupName, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);
await umbracoUi.content.isPropertyEditorUiWithNameVisible('block-grid', true);
await umbracoUi.content.clickEditBlockGridBlockButton();
await umbracoUi.content.enterTextstring(updatedText);
await umbracoUi.content.clickUpdateButton();
await umbracoUi.content.clickSaveButton();

// Assert
const documentData = await umbracoApi.document.getByName(documentName);
expect(documentData.values[0].value.contentData[0].values[0].value).toEqual(updatedText);
});

test('cannot see property values in block grid with only UI write but no UI read permission', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.document.createDefaultDocumentWithABlockGridEditor(documentName, elementTypeId, documentTypeName, customDataTypeName);
userGroupId = await umbracoApi.userGroup.createUserGroupWithUpdatePermissionAndWritePropertyValuePermission(userGroupName, true, true, false);
await umbracoApi.user.setUserPermissions(testUser.name, testUser.email, testUser.password, userGroupId);
testUserCookieAndToken = await umbracoApi.user.loginToUser(testUser.name, testUser.email, testUser.password);
await umbracoUi.goToBackOffice();

// Act
await umbracoUi.content.goToSection(ConstantHelper.sections.content, false);
await umbracoUi.content.goToContentWithName(documentName);

// Assert
await umbracoUi.content.isPropertyEditorUiWithNameVisible('block-grid', false);
});

Check warning on line 150 in tests/Umbraco.Tests.AcceptanceTest/tests/DefaultConfig/Users/Permissions/UserGroup/DocumentPropertyValuePermissionInBlock.spec.ts

CodeScene Delta Analysis / CodeScene Cloud Delta Analysis (main)

❌ New issue: Code Duplication

The module contains 6 functions with similar structure: 'can edit property values in block grid with UI write permission','can edit property values in block list with UI write permission','can see property values in block grid with UI read but not UI write permission','can see property values in block list with UI read but not UI write permission' and 2 more functions. Avoid duplicated, aka copy-pasted, code inside the module. More duplication lowers the code health.
Original file line number Diff line number Diff line change
@@ -477,7 +477,7 @@ test('can remove granular permission to a specific document for a user group', a
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
const documentTypeId = await umbracoApi.documentType.createDefaultDocumentTypeWithAllowAsRoot(documentTypeName);
const documentId = await umbracoApi.document.createDefaultDocument(documentName, documentTypeId);
await umbracoApi.userGroup.createUserGroupWithPermissionsForSpecificDocumentWithBrowseNode(userGroupName, documentId);
await umbracoApi.userGroup.createUserGroupWithPermissionsForSpecificDocumentWithRead(userGroupName, documentId);
expect(await umbracoApi.userGroup.doesUserGroupContainGranularPermissionsForDocument(userGroupName, documentId, [allPermissions.verbPermission[0]])).toBeTruthy();
await umbracoUi.userGroup.clickUserGroupsButton();
await umbracoUi.userGroup.clickUserGroupWithName(userGroupName);
Original file line number Diff line number Diff line change
@@ -35,6 +35,8 @@ test('the default configuration of Administrators is correct', async ({umbracoAp
"Umb.Document.Read",
"Umb.Document.CreateBlueprint",
"Umb.Document.Notifications",
"Umb.Document.PropertyValue.Read",
"Umb.Document.PropertyValue.Write"
];
const granularPermissions = [];
const hasAccessToAllLanguages = true;
@@ -86,6 +88,8 @@ test('the default configuration of Editors is correct', async ({umbracoApi, umbr
"Umb.Document.Read",
"Umb.Document.CreateBlueprint",
"Umb.Document.Notifications",
"Umb.Document.PropertyValue.Read",
"Umb.Document.PropertyValue.Write"
];
const granularPermissions = [];
const hasAccessToAllLanguages = true;
@@ -156,7 +160,9 @@ test('the default configuration of Translators data is correct', async ({umbraco
const sections = ["Umb.Section.Translation"];
const fallbackPermissions = [
"Umb.Document.Update",
"Umb.Document.Read"
"Umb.Document.Read",
"Umb.Document.PropertyValue.Read",
"Umb.Document.PropertyValue.Write"
];
const granularPermissions = [];
const hasAccessToAllLanguages = true;
@@ -193,7 +199,9 @@ test('the default configuration of Writers data is correct', async ({umbracoApi,
"Umb.Document.Create",
"Umb.Document.Update",
"Umb.Document.Read",
"Umb.Document.Notifications"
"Umb.Document.Notifications",
"Umb.Document.PropertyValue.Read",
"Umb.Document.PropertyValue.Write"
];
const granularPermissions = [];
const hasAccessToAllLanguages = true;