Merge remote-tracking branch 'origin/v14/dev' into contrib

This commit is contained in:
Jacob Overgaard
2024-05-23 14:32:53 +02:00
19 changed files with 1685 additions and 29 deletions

View File

@@ -12,23 +12,23 @@
</ItemGroup>
<!-- Microsoft packages -->
<ItemGroup>
<PackageVersion Include="Microsoft.AspNetCore.Mvc.Razor.RuntimeCompilation" Version="8.0.4" />
<PackageVersion Include="Microsoft.AspNetCore.Mvc.Razor.RuntimeCompilation" Version="8.0.5" />
<PackageVersion Include="Microsoft.CodeAnalysis.CSharp" Version="4.8.0" />
<PackageVersion Include="Microsoft.Data.Sqlite" Version="8.0.4" />
<PackageVersion Include="Microsoft.EntityFrameworkCore.Sqlite" Version="8.0.4" />
<PackageVersion Include="Microsoft.EntityFrameworkCore.SqlServer" Version="8.0.4" />
<PackageVersion Include="Microsoft.EntityFrameworkCore.Design" Version="8.0.4" />
<PackageVersion Include="Microsoft.Data.Sqlite" Version="8.0.5" />
<PackageVersion Include="Microsoft.EntityFrameworkCore.Sqlite" Version="8.0.5" />
<PackageVersion Include="Microsoft.EntityFrameworkCore.SqlServer" Version="8.0.5" />
<PackageVersion Include="Microsoft.EntityFrameworkCore.Design" Version="8.0.5" />
<PackageVersion Include="Microsoft.Extensions.Caching.Abstractions" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.Caching.Memory" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.Configuration.Abstractions" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.Configuration.Json" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.DependencyInjection" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.FileProviders.Embedded" Version="8.0.4" />
<PackageVersion Include="Microsoft.Extensions.FileProviders.Embedded" Version="8.0.5" />
<PackageVersion Include="Microsoft.Extensions.FileProviders.Physical" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.Hosting.Abstractions" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.Http" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.Identity.Core" Version="8.0.4" />
<PackageVersion Include="Microsoft.Extensions.Identity.Stores" Version="8.0.4" />
<PackageVersion Include="Microsoft.Extensions.Identity.Core" Version="8.0.5" />
<PackageVersion Include="Microsoft.Extensions.Identity.Stores" Version="8.0.5" />
<PackageVersion Include="Microsoft.Extensions.Logging" Version="8.0.0" />
<PackageVersion Include="Microsoft.Extensions.Options" Version="8.0.2" />
<PackageVersion Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="8.0.0" />
@@ -46,10 +46,10 @@
<PackageVersion Include="Dazinator.Extensions.FileProviders" Version="2.0.0" />
<PackageVersion Include="Examine" Version="3.2.0" />
<PackageVersion Include="Examine.Core" Version="3.2.0" />
<PackageVersion Include="HtmlAgilityPack" Version="1.11.60" />
<PackageVersion Include="JsonPatch.Net" Version="3.0.0" />
<PackageVersion Include="HtmlAgilityPack" Version="1.11.61" />
<PackageVersion Include="JsonPatch.Net" Version="3.1.0" />
<PackageVersion Include="K4os.Compression.LZ4" Version="1.3.8" />
<PackageVersion Include="MailKit" Version="4.5.0" />
<PackageVersion Include="MailKit" Version="4.6.0" />
<PackageVersion Include="Markdown" Version="2.2.1" />
<PackageVersion Include="MessagePack" Version="2.5.140" />
<PackageVersion Include="MiniProfiler.AspNetCore.Mvc" Version="4.3.8" />
@@ -57,9 +57,9 @@
<PackageVersion Include="ncrontab" Version="3.3.3" />
<PackageVersion Include="NPoco" Version="5.7.1" />
<PackageVersion Include="NPoco.SqlServer" Version="5.7.1" />
<PackageVersion Include="OpenIddict.Abstractions" Version="5.4.0" />
<PackageVersion Include="OpenIddict.AspNetCore" Version="5.4.0" />
<PackageVersion Include="OpenIddict.EntityFrameworkCore" Version="5.4.0" />
<PackageVersion Include="OpenIddict.Abstractions" Version="5.6.0" />
<PackageVersion Include="OpenIddict.AspNetCore" Version="5.6.0" />
<PackageVersion Include="OpenIddict.EntityFrameworkCore" Version="5.6.0" />
<PackageVersion Include="Serilog" Version="3.1.1" />
<PackageVersion Include="Serilog.AspNetCore" Version="8.0.1" />
<PackageVersion Include="Serilog.Enrichers.Process" Version="2.0.2" />
@@ -74,16 +74,16 @@
<PackageVersion Include="Serilog.Sinks.Map" Version="1.0.2" />
<PackageVersion Include="SixLabors.ImageSharp" Version="3.1.4" />
<PackageVersion Include="SixLabors.ImageSharp.Web" Version="3.1.2" />
<PackageVersion Include="Swashbuckle.AspNetCore" Version="6.5.0" />
<PackageVersion Include="Swashbuckle.AspNetCore" Version="6.6.2" />
</ItemGroup>
<!-- Transitive pinned versions (only required because our direct dependencies have vulnerable versions of transitive dependencies) -->
<ItemGroup>
<!-- Both Microsoft.EntityFrameworkCore.SqlServer and NPoco.SqlServer bring in a vulnerable version of Azure.Identity -->
<PackageVersion Include="Azure.Identity" Version="1.11.0" />
<PackageVersion Include="Azure.Identity" Version="1.11.3" />
<!-- Dazinator.Extensions.FileProviders brings in a vulnerable version of System.Net.Http -->
<PackageVersion Include="System.Net.Http" Version="4.3.4" />
<!-- Examine brings in a vulnerable version of System.Security.Cryptography.Xml -->
<PackageVersion Include="System.Security.Cryptography.Xml" Version="8.0.0" />
<PackageVersion Include="System.Security.Cryptography.Xml" Version="8.0.1" />
<!-- Both Dazinator.Extensions.FileProviders and MiniProfiler.AspNetCore.Mvc bring in a vulnerable version of System.Text.RegularExpressions -->
<PackageVersion Include="System.Text.RegularExpressions" Version="4.3.1" />
</ItemGroup>

View File

@@ -19,6 +19,7 @@ const createInput = (opts: {
autocomplete: AutoFill;
label: string;
inputmode: string;
autofocus?: boolean;
}) => {
const input = document.createElement('input');
input.type = opts.type;
@@ -28,6 +29,7 @@ const createInput = (opts: {
input.required = true;
input.inputMode = opts.inputmode;
input.ariaLabel = opts.label;
input.autofocus = opts.autofocus || false;
return input;
};
@@ -171,6 +173,7 @@ export default class UmbAuthElement extends UmbLitElement {
autocomplete: 'username',
label: labelUsername,
inputmode: this.usernameIsEmail ? 'email' : '',
autofocus: true,
});
this._passwordInput = createInput({
id: 'password-input',

View File

@@ -5,9 +5,9 @@
<ItemGroup>
<!-- Microsoft packages -->
<PackageVersion Include="BenchmarkDotNet" Version="0.13.12" />
<PackageVersion Include="Microsoft.AspNetCore.Mvc.Testing" Version="8.0.4" />
<PackageVersion Include="Microsoft.AspNetCore.Mvc.Testing" Version="8.0.5" />
<PackageVersion Include="Microsoft.Extensions.Logging.Debug" Version="8.0.0" />
<PackageVersion Include="Microsoft.NET.Test.Sdk" Version="17.9.0" />
<PackageVersion Include="Microsoft.NET.Test.Sdk" Version="17.10.0" />
<PackageVersion Include="System.Data.DataSetExtensions" Version="4.5.0" />
<PackageVersion Include="System.Data.Odbc" Version="8.0.0" />
<PackageVersion Include="System.Data.OleDb" Version="8.0.0" />
@@ -17,7 +17,7 @@
<!-- Third-party packages -->
<PackageVersion Include="AutoFixture.AutoMoq" Version="4.18.1" />
<PackageVersion Include="AutoFixture.NUnit3" Version="4.18.1" />
<PackageVersion Include="Bogus" Version="35.5.0" />
<PackageVersion Include="Bogus" Version="35.5.1" />
<PackageVersion Include="Moq" Version="4.18.4" />
<PackageVersion Include="NUnit" Version="3.14.0" />
<PackageVersion Include="NUnit3TestAdapter" Version="4.5.0" PrivateAssets="all" />

View File

@@ -8,7 +8,7 @@
"hasInstallScript": true,
"dependencies": {
"@umbraco/json-models-builders": "^2.0.5",
"@umbraco/playwright-testhelpers": "^2.0.0-beta.46",
"@umbraco/playwright-testhelpers": "^2.0.0-beta.49",
"camelize": "^1.0.0",
"dotenv": "^16.3.1",
"faker": "^4.1.0",
@@ -146,9 +146,9 @@
"integrity": "sha512-9tCqYEDHI5RYFQigXFwF1hnCwcWCOJl/hmll0lr5D2Ljjb0o4wphb69wikeJDz5qCEzXCoPvG6ss5SDP6IfOdg=="
},
"node_modules/@umbraco/playwright-testhelpers": {
"version": "2.0.0-beta.46",
"resolved": "https://registry.npmjs.org/@umbraco/playwright-testhelpers/-/playwright-testhelpers-2.0.0-beta.46.tgz",
"integrity": "sha512-SJKmKO/84QFnCy0j7fGEYbRtbLZKC/k1xlyUKrkZpzVekVIS6gSki5ECWu4LiJnfmo+yhxGBsA2l3iLZfL1gow==",
"version": "2.0.0-beta.49",
"resolved": "https://registry.npmjs.org/@umbraco/playwright-testhelpers/-/playwright-testhelpers-2.0.0-beta.49.tgz",
"integrity": "sha512-fmEJjuawY8QEHLQ9xozp83GozkVFFwEAHMYnNENYt98XSyu55OA7sRxIXUabKPOUGzgcGkiSceicKG7JXBoofw==",
"dependencies": {
"@umbraco/json-models-builders": "2.0.6",
"camelize": "^1.0.0",

View File

@@ -22,7 +22,7 @@
},
"dependencies": {
"@umbraco/json-models-builders": "^2.0.5",
"@umbraco/playwright-testhelpers": "^2.0.0-beta.46",
"@umbraco/playwright-testhelpers": "^2.0.0-beta.49",
"camelize": "^1.0.0",
"dotenv": "^16.3.1",
"faker": "^4.1.0",

View File

@@ -0,0 +1,150 @@
import {AliasHelper, ConstantHelper, test} from '@umbraco/playwright-testhelpers';
import {expect} from '@playwright/test';
const documentTypeName = 'TestDocumentType';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoUi.goToBackOffice();
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
});
test('can create a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.clickActionsMenuAtRoot();
await umbracoUi.documentType.clickCreateButton();
await umbracoUi.documentType.clickCreateDocumentTypeButton();
await umbracoUi.documentType.enterDocumentTypeName(documentTypeName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
await umbracoUi.documentType.reloadTree('Document Types');
await umbracoUi.documentType.isDocumentTreeItemVisible(documentTypeName);
});
test('can create a document type with a template', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoApi.template.ensureNameNotExists(documentTypeName);
// Act
await umbracoUi.documentType.clickActionsMenuAtRoot();
await umbracoUi.documentType.clickCreateButton();
await umbracoUi.documentType.clickCreateDocumentTypeWithTemplateButton();
await umbracoUi.documentType.enterDocumentTypeName(documentTypeName);
await umbracoUi.documentType.clickSaveButton();
// Assert
// Checks if both the success notification for document Types and teh template are visible
await umbracoUi.documentType.doesSuccessNotificationsHaveCount(2);
// Checks if the documentType contains the template
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
const templateData = await umbracoApi.template.getByName(documentTypeName);
expect(documentTypeData.allowedTemplates[0].id).toEqual(templateData.id);
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
// Clean
await umbracoApi.template.ensureNameNotExists(documentTypeName);
});
test('can create a element type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.clickActionsMenuAtRoot();
await umbracoUi.documentType.clickCreateButton();
await umbracoUi.documentType.clickCreateElementTypeButton();
await umbracoUi.documentType.enterDocumentTypeName(documentTypeName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
// Checks if the isElement is true
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.isElement).toBeTruthy();
});
test('can rename a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const wrongName = 'NotADocumentTypeName';
await umbracoApi.documentType.ensureNameNotExists(wrongName);
await umbracoApi.documentType.createDefaultDocumentType(wrongName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(wrongName);
await umbracoUi.documentType.enterDocumentTypeName(documentTypeName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
await umbracoUi.documentType.isDocumentTreeItemVisible(wrongName, false);
await umbracoUi.documentType.isDocumentTreeItemVisible(documentTypeName);
});
test('can update the alias for a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const oldAlias = AliasHelper.toAlias(documentTypeName);
const newAlias = 'newDocumentTypeAlias';
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
const documentTypeDataOld = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeDataOld.alias).toBe(oldAlias);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.enterAliasName(newAlias);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
await umbracoUi.documentType.isDocumentTreeItemVisible(documentTypeName, true);
const documentTypeDataNew = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeDataNew.alias).toBe(newAlias);
});
test('can add an icon for a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const bugIcon = 'icon-bug';
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.updateIcon(bugIcon);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.icon).toBe(bugIcon);
await umbracoUi.documentType.isDocumentTreeItemVisible(documentTypeName, true);
});
test('can delete a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
// Act
await umbracoUi.documentType.clickRootFolderCaretButton();
await umbracoUi.documentType.clickActionsMenuForDocumentType(documentTypeName);
await umbracoUi.documentType.clickDeleteExactButton();
await umbracoUi.documentType.clickConfirmToDeleteButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeFalsy();
});

View File

@@ -0,0 +1,431 @@
import {ConstantHelper, test} from "@umbraco/playwright-testhelpers";
import {expect} from "@playwright/test";
const documentTypeName = 'TestDocumentType';
const dataTypeName = 'Approved Color';
const groupName = 'TestGroup';
const tabName = 'TestTab';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoUi.goToBackOffice();
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
});
test('can add a property to a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickAddGroupButton();
await umbracoUi.documentType.addPropertyEditor(dataTypeName);
await umbracoUi.documentType.enterGroupName(groupName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
const dataType = await umbracoApi.dataType.getByName(dataTypeName);
// Checks if the correct property was added to the document type
expect(documentTypeData.properties[0].dataType.id).toBe(dataType.id);
});
test('can update a property in a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const newDataTypeName = 'Image Media Picker';
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.updatePropertyEditor(newDataTypeName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
const dataType = await umbracoApi.dataType.getByName(newDataTypeName);
// Checks if the correct property was added to the document type
expect(documentTypeData.properties[0].dataType.id).toBe(dataType.id);
});
test('can update group name in a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const newGroupName = 'UpdatedGroupName';
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.enterGroupName(newGroupName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.containers[0].name).toBe(newGroupName);
});
test('can delete a group in a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id, groupName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.deleteGroup(groupName, true);
await umbracoUi.documentType.clickConfirmToDeleteButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.containers.length).toBe(0);
expect(documentTypeData.properties.length).toBe(0);
});
// TODO: Currently I am getting an error If I delete a tab that contains children. The children are not cleaned up when deleting the tab.
test.skip('can delete a tab in a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.documentType.createDocumentTypeWithPropertyEditorInTab(documentTypeName, dataTypeName, dataTypeData.id, tabName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickRemoveTabWithName(tabName);
await umbracoUi.documentType.clickConfirmToDeleteButton();
await umbracoUi.documentType.clickSaveButton();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
});
test('can delete a property editor in a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id, groupName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.deletePropertyEditorWithName(dataTypeName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.properties.length).toBe(0);
});
test('can create a document type with a property in a tab', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickAddTabButton();
await umbracoUi.documentType.enterTabName(tabName);
await umbracoUi.documentType.clickAddGroupButton();
await umbracoUi.documentType.addPropertyEditor(dataTypeName, 1);
await umbracoUi.documentType.enterGroupName(groupName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(await umbracoApi.documentType.doesTabContainCorrectPropertyEditorInGroup(documentTypeName, dataTypeName, documentTypeData.properties[0].dataType.id, tabName, groupName)).toBeTruthy();
});
test('can create a document type with multiple groups', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondDataTypeName = 'Image Media Picker';
const secondGroupName = 'TesterGroup';
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id, groupName);
const secondDataType = await umbracoApi.dataType.getByName(secondDataTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickAddGroupButton();
await umbracoUi.documentType.enterGroupName(secondGroupName, 1);
await umbracoUi.documentType.addPropertyEditor(secondDataTypeName, 1);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
expect(await umbracoApi.documentType.doesGroupContainCorrectPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id, groupName)).toBeTruthy();
expect(await umbracoApi.documentType.doesGroupContainCorrectPropertyEditor(documentTypeName, secondDataTypeName, secondDataType.id, secondGroupName)).toBeTruthy();
});
test('can create a document type with multiple tabs', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondDataTypeName = 'Image Media Picker';
const secondGroupName = 'TesterGroup';
const secondTabName = 'SecondTab';
await umbracoApi.documentType.createDocumentTypeWithPropertyEditorInTab(documentTypeName, dataTypeName, dataTypeData.id, tabName, groupName);
const secondDataType = await umbracoApi.dataType.getByName(secondDataTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickAddTabButton();
await umbracoUi.documentType.enterTabName(secondTabName);
await umbracoUi.documentType.clickAddGroupButton();
await umbracoUi.documentType.enterGroupName(secondGroupName);
await umbracoUi.documentType.addPropertyEditor(secondDataTypeName, 1);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesNameExist(documentTypeName)).toBeTruthy();
expect(await umbracoApi.documentType.doesTabContainCorrectPropertyEditorInGroup(documentTypeName, dataTypeName, dataTypeData.id, tabName, groupName)).toBeTruthy();
expect(await umbracoApi.documentType.doesTabContainCorrectPropertyEditorInGroup(documentTypeName, secondDataTypeName, secondDataType.id, secondTabName, secondGroupName)).toBeTruthy();
});
test('can create a document type with a composition', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const compositionDocumentTypeName = 'CompositionDocumentType';
await umbracoApi.documentType.ensureNameNotExists(compositionDocumentTypeName);
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const compositionDocumentTypeId = await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(compositionDocumentTypeName, dataTypeName, dataTypeData.id, groupName);
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickCompositionsButton();
await umbracoUi.documentType.clickButtonWithName(compositionDocumentTypeName);
await umbracoUi.documentType.clickSubmitButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(umbracoUi.documentType.doesGroupHaveValue(groupName)).toBeTruthy();
// Checks if the composition in the document type is correct
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.compositions[0].documentType.id).toBe(compositionDocumentTypeId);
// Clean
await umbracoApi.documentType.ensureNameNotExists(compositionDocumentTypeName);
});
test('can remove a composition form a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const compositionDocumentTypeName = 'CompositionDocumentType';
await umbracoApi.documentType.ensureNameNotExists(compositionDocumentTypeName);
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const compositionDocumentTypeId = await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(compositionDocumentTypeName, dataTypeName, dataTypeData.id, groupName);
await umbracoApi.documentType.createDocumentTypeWithAComposition(documentTypeName, compositionDocumentTypeId);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickCompositionsButton();
await umbracoUi.documentType.clickButtonWithName(compositionDocumentTypeName);
await umbracoUi.documentType.clickSubmitButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoUi.documentType.doesGroupHaveValue(groupName)).toBeFalsy();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.compositions).toEqual([]);
// Clean
await umbracoApi.documentType.ensureNameNotExists(compositionDocumentTypeName);
});
test('can reorder groups in a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondGroupName = 'SecondGroup';
await umbracoApi.documentType.createDocumentTypeWithTwoGroups(documentTypeName, dataTypeName, dataTypeData.id, groupName, secondGroupName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoUi.documentType.goToDocumentType(documentTypeName);
// Act
await umbracoUi.documentType.clickReorderButton();
const groupValues = await umbracoUi.documentType.reorderTwoGroups();
const firstGroupValue = groupValues.firstGroupValue;
const secondGroupValue = groupValues.secondGroupValue;
await umbracoUi.documentType.clickIAmDoneReorderingButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
// Since we swapped sorting order, the firstGroupValue should have sortOrder 1 and the secondGroupValue should have sortOrder 0
expect(await umbracoApi.documentType.doesDocumentTypeGroupNameContainCorrectSortOrder(documentTypeName, secondGroupValue, 0)).toBeTruthy();
expect(await umbracoApi.documentType.doesDocumentTypeGroupNameContainCorrectSortOrder(documentTypeName, firstGroupValue, 1)).toBeTruthy();
});
// TODO: Unskip when it works. Sometimes the properties are not dragged correctly.
test.skip('can reorder properties in a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const dataTypeNameTwo = "Second Color Picker";
await umbracoApi.documentType.createDocumentTypeWithTwoPropertyEditors(documentTypeName, dataTypeName, dataTypeData.id, dataTypeNameTwo, dataTypeData.id);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickReorderButton();
// Drag and Drop
await umbracoUi.waitForTimeout(5000);
const dragFromLocator = umbracoUi.documentType.getTextLocatorWithName(dataTypeNameTwo);
const dragToLocator = umbracoUi.documentType.getTextLocatorWithName(dataTypeName);
await umbracoUi.documentType.dragAndDrop(dragFromLocator, dragToLocator, 0, 0, 5);
await umbracoUi.documentType.clickIAmDoneReorderingButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.properties[0].name).toBe(dataTypeNameTwo);
expect(documentTypeData.properties[1].name).toBe(dataTypeName);
});
// TODO: Unskip when the frontend does not give the secondTab -1 as the sortOrder
test.skip('can reorder tabs in a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondTabName = 'SecondTab';
await umbracoApi.documentType.createDocumentTypeWithTwoTabs(documentTypeName, dataTypeName, dataTypeData.id, tabName, secondTabName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoUi.documentType.goToDocumentType(documentTypeName);
// Act
const dragToLocator = umbracoUi.documentType.getTabLocatorWithName(tabName);
const dragFromLocator = umbracoUi.documentType.getTabLocatorWithName(secondTabName);
await umbracoUi.documentType.clickReorderButton();
await umbracoUi.documentType.dragAndDrop(dragFromLocator, dragToLocator, 0, 0, 10);
await umbracoUi.documentType.clickIAmDoneReorderingButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
expect(await umbracoApi.documentType.doesDocumentTypeTabNameContainCorrectSortOrder(documentTypeName, secondTabName, 0)).toBeTruthy();
expect(await umbracoApi.documentType.doesDocumentTypeTabNameContainCorrectSortOrder(documentTypeName, tabName, 1)).toBeTruthy();
});
test('can add a description to a property in a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const descriptionText = 'This is a property';
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickEditorSettingsButton();
await umbracoUi.documentType.enterPropertyEditorDescription(descriptionText);
await umbracoUi.documentType.clickUpdateButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
await expect(umbracoUi.documentType.enterDescriptionTxt).toBeVisible();
expect(umbracoUi.documentType.doesDescriptionHaveValue(descriptionText)).toBeTruthy();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.properties[0].description).toBe(descriptionText);
});
test('can set is mandatory for a property in a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickEditorSettingsButton();
await umbracoUi.documentType.clickMandatorySlider();
await umbracoUi.documentType.clickUpdateButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.properties[0].validation.mandatory).toBeTruthy();
});
test('can enable validation for a property in a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const regex = '^[a-zA-Z0-9]*$';
const regexMessage = 'Only letters and numbers are allowed';
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickEditorSettingsButton();
await umbracoUi.documentType.selectValidationOption('');
await umbracoUi.documentType.enterRegEx(regex);
await umbracoUi.documentType.enterRegExMessage(regexMessage);
await umbracoUi.documentType.clickUpdateButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.properties[0].validation.regEx).toBe(regex);
expect(documentTypeData.properties[0].validation.regExMessage).toBe(regexMessage);
});
test('can allow vary by culture for a property in a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id, groupName, true);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickEditorSettingsButton();
await umbracoUi.documentType.clickVaryByCultureSlider();
await umbracoUi.documentType.clickUpdateButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.properties[0].variesByCulture).toBeTruthy();
});
test('can set appearance to label on top for a property in a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.documentType.createDocumentTypeWithPropertyEditor(documentTypeName, dataTypeName, dataTypeData.id);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickEditorSettingsButton();
await umbracoUi.documentType.clickLabelOnTopButton();
await umbracoUi.documentType.clickUpdateButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.properties[0].appearance.labelOnTop).toBeTruthy();
});

View File

@@ -0,0 +1,128 @@
import {ConstantHelper, test} from '@umbraco/playwright-testhelpers';
import {expect} from '@playwright/test';
const documentFolderName = 'TestFolder';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentFolderName);
await umbracoUi.goToBackOffice();
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentFolderName);
});
test('can create a empty document type folder', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Act
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoUi.documentType.clickActionsMenuForName('Document Types');
await umbracoUi.documentType.clickCreateButton();
await umbracoUi.documentType.clickCreateDocumentFolderButton();
await umbracoUi.documentType.enterFolderName(documentFolderName);
await umbracoUi.documentType.clickCreateFolderButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const folder = await umbracoApi.documentType.getByName(documentFolderName);
expect(folder.name).toBe(documentFolderName);
// Checks if the folder is in the root
await umbracoUi.documentType.reloadTree('Document Types');
await umbracoUi.documentType.isDocumentTreeItemVisible(documentFolderName);
});
test('can delete a document type folder', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createFolder(documentFolderName);
// Act
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoUi.documentType.clickRootFolderCaretButton();
await umbracoUi.documentType.clickActionsMenuForName(documentFolderName);
await umbracoUi.documentType.deleteFolder();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
await umbracoApi.documentType.doesNameExist(documentFolderName);
await umbracoUi.documentType.isDocumentTreeItemVisible(documentFolderName, false);
});
test('can rename a document type folder', async ({umbracoApi, umbracoUi}) => {
// Arrange
const oldFolderName = 'OldName';
await umbracoApi.documentType.createFolder(oldFolderName);
// Act
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoUi.documentType.clickRootFolderCaretButton();
await umbracoUi.documentType.clickActionsMenuForName(oldFolderName);
await umbracoUi.documentType.clickRenameFolderButton();
await umbracoUi.documentType.enterFolderName(documentFolderName);
await umbracoUi.documentType.clickUpdateFolderButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const folder = await umbracoApi.documentType.getByName(documentFolderName);
expect(folder.name).toBe(documentFolderName);
await umbracoUi.documentType.isDocumentTreeItemVisible(oldFolderName, false);
await umbracoUi.documentType.isDocumentTreeItemVisible(documentFolderName);
});
test('can create a document type folder in a folder', async ({umbracoApi, umbracoUi}) => {
// Arrange
const childFolderName = 'ChildFolder';
await umbracoApi.documentType.ensureNameNotExists(childFolderName);
const parentFolderId = await umbracoApi.documentType.createFolder(documentFolderName);
// Act
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoUi.documentType.clickRootFolderCaretButton();
await umbracoUi.documentType.clickActionsMenuForName(documentFolderName);
await umbracoUi.documentType.clickCreateButton();
await umbracoUi.documentType.clickCreateDocumentFolderButton();
await umbracoUi.documentType.enterFolderName(childFolderName);
await umbracoUi.documentType.clickCreateFolderButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const folder = await umbracoApi.documentType.getByName(childFolderName);
expect(folder.name).toBe(childFolderName);
// Checks if the parentFolder contains the ChildFolder as a child
const parentFolder = await umbracoApi.documentType.getChildren(parentFolderId);
expect(parentFolder[0].name).toBe(childFolderName);
// Clean
await umbracoApi.documentType.ensureNameNotExists(childFolderName);
});
test('can create a folder in a folder in a folder', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const grandParentFolderName = 'TheGrandFolder';
const parentFolderName = 'TheParentFolder';
await umbracoApi.documentType.ensureNameNotExists(grandParentFolderName);
await umbracoApi.documentType.ensureNameNotExists(parentFolderName);
const grandParentFolderId = await umbracoApi.documentType.createFolder(grandParentFolderName);
const parentFolderId = await umbracoApi.documentType.createFolder(parentFolderName, grandParentFolderId);
// Act
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
await umbracoUi.documentType.clickRootFolderCaretButton();
await umbracoUi.documentType.clickCaretButtonForName(grandParentFolderName);
await umbracoUi.documentType.clickActionsMenuForName(parentFolderName);
await umbracoUi.documentType.clickCreateButton();
await umbracoUi.documentType.clickCreateDocumentFolderButton();
await umbracoUi.documentType.enterFolderName(documentFolderName);
await umbracoUi.documentType.clickCreateFolderButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
await umbracoUi.documentType.reloadTree(parentFolderName);
await umbracoUi.documentType.isDocumentTreeItemVisible(documentFolderName);
const grandParentChildren = await umbracoApi.documentType.getChildren(grandParentFolderId);
expect(grandParentChildren[0].name).toBe(parentFolderName);
const parentChildren = await umbracoApi.documentType.getChildren(parentFolderId);
expect(parentChildren[0].name).toBe(documentFolderName);
// Clean
await umbracoApi.documentType.ensureNameNotExists(grandParentFolderName);
await umbracoApi.documentType.ensureNameNotExists(parentFolderName);
});

View File

@@ -0,0 +1,84 @@
import {ConstantHelper, test} from "@umbraco/playwright-testhelpers";
import {expect} from "@playwright/test";
const documentTypeName = 'TestDocumentType';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoUi.goToBackOffice();
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
});
test('can add allow vary by culture for a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickDocumentTypeSettingsTab();
await umbracoUi.documentType.clickVaryByCultureButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.variesByCulture).toBeTruthy();
});
test('can add allow segmentation for a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickDocumentTypeSettingsTab();
await umbracoUi.documentType.clickVaryBySegmentsButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.variesBySegment).toBeTruthy();
});
test('can set is an element type for a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickDocumentTypeSettingsTab();
await umbracoUi.documentType.clickTextButtonWithName('Element type');
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.isElement).toBeTruthy();
});
// TODO: Unskip. Currently The cleanup is not updated upon save
test.skip('can disable history cleanup for a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
// Is needed
await umbracoUi.waitForTimeout(200);
await umbracoUi.documentType.clickDocumentTypeSettingsTab();
await umbracoUi.documentType.clickAutoCleanupButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.cleanup.preventCleanup).toBeTruthy();
});

View File

@@ -0,0 +1,97 @@
import {ConstantHelper, test} from "@umbraco/playwright-testhelpers";
import {expect} from "@playwright/test";
const documentTypeName = 'TestDocumentType';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoUi.goToBackOffice();
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
});
test('can add allow as root to a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickStructureTab();
await umbracoUi.documentType.clickAllowAtRootButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.allowedAsRoot).toBeTruthy();
});
test('can add an allowed child node to a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickStructureTab();
await umbracoUi.documentType.clickChooseButton();
await umbracoUi.documentType.clickButtonWithName(documentTypeName);
await umbracoUi.documentType.clickAllowedChildNodesButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.allowedDocumentTypes[0].documentType.id).toBe(documentTypeData.id);
});
test('can remove an allowed child node from a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const childDocumentTypeName = 'ChildDocumentType';
await umbracoApi.documentType.ensureNameNotExists(childDocumentTypeName);
const childDocumentTypeId = await umbracoApi.documentType.createDefaultDocumentType(childDocumentTypeName);
await umbracoApi.documentType.createDocumentTypeWithAllowedChildNode(documentTypeName, childDocumentTypeId);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickStructureTab();
await umbracoUi.documentType.clickRemoveButtonForName(childDocumentTypeName);
await umbracoUi.documentType.clickConfirmRemoveButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.allowedDocumentTypes.length).toBe(0);
// Clean
await umbracoApi.documentType.ensureNameNotExists(childDocumentTypeName);
});
test('can configure a collection for a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const collectionDataTypeName = 'TestCollection';
await umbracoApi.dataType.ensureNameNotExists(collectionDataTypeName);
const collectionDataTypeId = await umbracoApi.dataType.create(collectionDataTypeName, 'Umbraco.ListView', [], null, 'Umb.PropertyEditorUi.CollectionView');
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickStructureTab();
await umbracoUi.documentType.clickConfigureAsACollectionButton();
await umbracoUi.documentType.clickTextButtonWithName(collectionDataTypeName);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.collection.id).toEqual(collectionDataTypeId);
// Clean
await umbracoApi.dataType.ensureNameNotExists(collectionDataTypeName);
});

View File

@@ -0,0 +1,78 @@
import {ConstantHelper, test} from "@umbraco/playwright-testhelpers";
import {expect} from "@playwright/test";
const documentTypeName = 'TestDocumentType';
const templateName = 'TestTemplate';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
await umbracoUi.goToBackOffice();
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.documentType.ensureNameNotExists(documentTypeName);
});
test('can add an allowed template to a document type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.documentType.createDefaultDocumentType(documentTypeName);
await umbracoApi.template.ensureNameNotExists(templateName);
const templateId = await umbracoApi.template.createDefaultTemplate(templateName);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickDocumentTypeTemplatesTab();
await umbracoUi.documentType.clickAddButton();
await umbracoUi.documentType.clickLabelWithName(templateName);
await umbracoUi.documentType.clickChooseButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.allowedTemplates[0].id).toBe(templateId);
// Clean
await umbracoApi.template.ensureNameNotExists(templateName);
});
test('can set an allowed template as default for document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.template.ensureNameNotExists(templateName);
const templateId = await umbracoApi.template.createDefaultTemplate(templateName);
await umbracoApi.documentType.createDocumentTypeWithAllowedTemplate(documentTypeName, templateId);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickDocumentTypeTemplatesTab();
await umbracoUi.documentType.clickDefaultTemplateButton();
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.allowedTemplates[0].id).toBe(templateId);
expect(documentTypeData.defaultTemplate.id).toBe(templateId);
});
// When removing a template, the defaultTemplateId is set to "" which is not correct
test.skip('can remove an allowed template from a document type', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.template.ensureNameNotExists(templateName);
const templateId = await umbracoApi.template.createDefaultTemplate(templateName);
await umbracoApi.documentType.createDocumentTypeWithAllowedTemplate(documentTypeName, templateId);
await umbracoUi.documentType.goToSection(ConstantHelper.sections.settings);
// Act
await umbracoUi.documentType.goToDocumentType(documentTypeName);
await umbracoUi.documentType.clickDocumentTypeTemplatesTab();
await umbracoUi.documentType.clickRemoveWithName(templateName, true);
await umbracoUi.documentType.clickSaveButton();
// Assert
await umbracoUi.documentType.isSuccessNotificationVisible();
const documentTypeData = await umbracoApi.documentType.getByName(documentTypeName);
expect(documentTypeData.allowedTemplates).toHaveLength(0);
});

View File

@@ -1,4 +1,4 @@
import {test} from '@umbraco/playwright-testhelpers';
import {test} from '@umbraco/playwright-testhelpers';
import {expect} from "@playwright/test";
const languageName = 'Arabic';
@@ -15,7 +15,7 @@ test.afterEach(async ({umbracoApi}) => {
await umbracoApi.language.ensureNameNotExists(languageName);
});
test('can add language', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
test.skip('can add language', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoUi.language.goToSettingsTreeItem('Language');

View File

@@ -0,0 +1,94 @@
import {expect} from "@playwright/test";
import {AliasHelper, ConstantHelper, test} from '@umbraco/playwright-testhelpers';
const mediaTypeName = 'TestMediaType';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeName);
await umbracoUi.goToBackOffice();
await umbracoUi.mediaType.goToSection(ConstantHelper.sections.settings);
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeName);
});
test('can create a media type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Act
await umbracoUi.mediaType.clickActionsMenuForName('Media Types');
await umbracoUi.mediaType.clickCreateButton();
await umbracoUi.mediaType.clickNewMediaTypeButton();
await umbracoUi.mediaType.enterMediaTypeName(mediaTypeName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeName)).toBeTruthy();
});
test('can rename a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const wrongName = 'NotAMediaTypeName';
await umbracoApi.mediaType.ensureNameNotExists(wrongName);
await umbracoApi.mediaType.createDefaultMediaType(wrongName);
// Act
await umbracoUi.mediaType.goToMediaType(wrongName);
await umbracoUi.mediaType.enterMediaTypeName(mediaTypeName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeName)).toBeTruthy();
});
test('can update the alias for a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const oldAlias = AliasHelper.toAlias(mediaTypeName);
const updatedAlias = 'TestMediaAlias';
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
const mediaTypeDataOld = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeDataOld.alias).toBe(oldAlias);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.enterAliasName(updatedAlias);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.alias).toBe(updatedAlias);
});
test('can add an icon for a media type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const bugIcon = 'icon-bug';
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.updateIcon(bugIcon);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.icon).toBe(bugIcon);
await umbracoUi.mediaType.isTreeItemVisible(mediaTypeName, true);
});
test('can delete a media type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.clickRootFolderCaretButton();
await umbracoUi.mediaType.clickActionsMenuForName(mediaTypeName);
await umbracoUi.mediaType.clickDeleteButton();
await umbracoUi.mediaType.clickConfirmToDeleteButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeName)).toBeFalsy();
});

View File

@@ -0,0 +1,363 @@
import {ConstantHelper, test} from "@umbraco/playwright-testhelpers";
import {expect} from "@playwright/test";
const mediaTypeName = 'TestMediaType';
const dataTypeName = 'Upload File';
const groupName = 'TestGroup';
const tabName = 'TestTab';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeName);
await umbracoUi.goToBackOffice();
await umbracoUi.mediaType.goToSection(ConstantHelper.sections.settings);
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeName);
});
test('can create a media type with a property', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickAddGroupButton();
await umbracoUi.mediaType.addPropertyEditor(dataTypeName);
await umbracoUi.mediaType.enterGroupName(groupName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeName)).toBeTruthy();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
const dataType = await umbracoApi.dataType.getByName(dataTypeName);
// Checks if the correct property was added to the media type
expect(mediaTypeData.properties[0].dataType.id).toBe(dataType.id);
});
test('can update a property in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const newDataTypeName = 'Image Media Picker';
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.updatePropertyEditor(newDataTypeName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
const dataType = await umbracoApi.dataType.getByName(newDataTypeName);
// Checks if the correct property was added to the media type
expect(mediaTypeData.properties[0].dataType.id).toBe(dataType.id);
});
test('can update group name in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const updatedGroupName = 'UpdatedGroupName';
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id, groupName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.enterGroupName(updatedGroupName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.containers[0].name).toBe(updatedGroupName);
});
test('can delete a property in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id, groupName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.deletePropertyEditorWithName(dataTypeName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.properties.length).toBe(0);
});
test('can add a description to property in a media type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const descriptionText = 'Test Description';
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id, groupName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickEditorSettingsButton();
await umbracoUi.mediaType.enterPropertyEditorDescription(descriptionText);
await umbracoUi.mediaType.clickUpdateButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
await expect(umbracoUi.mediaType.enterDescriptionTxt).toBeVisible();
expect(umbracoUi.mediaType.doesDescriptionHaveValue(descriptionText)).toBeTruthy();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.properties[0].description).toBe(descriptionText);
});
test('can set a property as mandatory in a media type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickEditorSettingsButton();
await umbracoUi.mediaType.clickMandatorySlider();
await umbracoUi.mediaType.clickUpdateButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.properties[0].validation.mandatory).toBeTruthy();
});
test('can set up validation for a property in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const regex = '^[a-zA-Z0-9]*$';
const regexMessage = 'Only letters and numbers are allowed';
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickEditorSettingsButton();
await umbracoUi.mediaType.selectValidationOption('');
await umbracoUi.mediaType.enterRegEx(regex);
await umbracoUi.mediaType.enterRegExMessage(regexMessage);
await umbracoUi.mediaType.clickUpdateButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.properties[0].validation.regEx).toBe(regex);
expect(mediaTypeData.properties[0].validation.regExMessage).toBe(regexMessage);
});
test('can set appearance as label on top for property in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickEditorSettingsButton();
await umbracoUi.mediaType.clickLabelOnTopButton();
await umbracoUi.mediaType.clickUpdateButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.properties[0].appearance.labelOnTop).toBeTruthy();
});
test('can delete a group in a media type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id, groupName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.deleteGroup(groupName, true);
await umbracoUi.mediaType.clickConfirmToDeleteButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.containers.length).toBe(0);
expect(mediaTypeData.properties.length).toBe(0);
});
test('can create a media type with a property in a tab', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickAddTabButton();
await umbracoUi.mediaType.enterTabName(tabName);
await umbracoUi.mediaType.addPropertyEditor(dataTypeName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
// Checks if the media type has the correct tab and property
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(await umbracoApi.mediaType.doesTabContainerCorrectPropertyEditor(mediaTypeName, tabName, mediaTypeData.properties[0].dataType.id)).toBeTruthy();
});
test('can create a media type with multiple groups', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondDataTypeName = 'Image Media Picker';
await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id, groupName);
const secondDataType = await umbracoApi.dataType.getByName(secondDataTypeName);
const secondGroupName = 'TesterGroup';
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickAddGroupButton();
await umbracoUi.mediaType.addPropertyEditor(secondDataTypeName, 1);
await umbracoUi.mediaType.enterGroupName(secondGroupName, 1);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeName)).toBeTruthy();
expect(await umbracoApi.mediaType.doesGroupContainCorrectPropertyEditor(mediaTypeName, dataTypeName, dataTypeData.id, groupName)).toBeTruthy();
expect(await umbracoApi.mediaType.doesGroupContainCorrectPropertyEditor(mediaTypeName, secondDataTypeName, secondDataType.id, secondGroupName)).toBeTruthy();
});
test('can create a media type with multiple tabs', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondDataTypeName = 'Image Media Picker';
const secondGroupName = 'TesterGroup';
const secondTabName = 'SecondTab';
await umbracoApi.mediaType.createMediaTypeWithPropertyEditorInTab(mediaTypeName, dataTypeName, dataTypeData.id, tabName, groupName);
const secondDataType = await umbracoApi.dataType.getByName(secondDataTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickAddTabButton();
await umbracoUi.mediaType.enterTabName(secondTabName);
await umbracoUi.mediaType.clickAddGroupButton();
await umbracoUi.mediaType.enterGroupName(secondGroupName);
await umbracoUi.mediaType.addPropertyEditor(secondDataTypeName, 1);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeName)).toBeTruthy();
expect(await umbracoApi.mediaType.doesTabContainCorrectPropertyEditorInGroup(mediaTypeName, dataTypeName, dataTypeData.id, tabName, groupName)).toBeTruthy();
expect(await umbracoApi.mediaType.doesTabContainCorrectPropertyEditorInGroup(mediaTypeName, secondDataTypeName, secondDataType.id, secondTabName, secondGroupName)).toBeTruthy();
});
test('can delete a tab from a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
await umbracoApi.mediaType.createMediaTypeWithPropertyEditorInTab(mediaTypeName, dataTypeName, dataTypeData.id, tabName, groupName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickRemoveTabWithName(tabName);
await umbracoUi.mediaType.clickConfirmToDeleteButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeName)).toBeTruthy();
});
// TODO: Currently there is no composition button, which makes it impossible to test
test.skip('can create a media type with a composition', async ({umbracoApi, umbracoUi}) => {
// Arrange
const compositionMediaTypeName = 'CompositionMediaType';
await umbracoApi.mediaType.ensureNameNotExists(compositionMediaTypeName);
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const compositionMediaTypeId = await umbracoApi.mediaType.createMediaTypeWithPropertyEditor(compositionMediaTypeName, dataTypeName, dataTypeData.id, groupName);
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickCompositionsButton();
await umbracoUi.mediaType.clickButtonWithName(compositionMediaTypeName);
await umbracoUi.mediaType.clickSubmitButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(umbracoUi.mediaType.doesGroupHaveValue(groupName)).toBeTruthy();
// Checks if the composition in the media type is correct
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.compositions[0].mediaType.id).toBe(compositionMediaTypeId);
// Clean
await umbracoApi.mediaType.ensureNameNotExists(compositionMediaTypeName);
});
test('can reorder groups in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondGroupName = 'SecondGroup';
await umbracoApi.mediaType.createMediaTypeWithTwoGroups(mediaTypeName, dataTypeName, dataTypeData.id, groupName, secondGroupName);
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.clickReorderButton();
const groupValues = await umbracoUi.mediaType.reorderTwoGroups();
const firstGroupValue = groupValues.firstGroupValue;
const secondGroupValue = groupValues.secondGroupValue;
await umbracoUi.mediaType.clickIAmDoneReorderingButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
// Since we swapped sorting order, the firstGroupValue should have sortOrder 1 and the secondGroupValue should have sortOrder 0
expect(await umbracoApi.mediaType.doesMediaTypeGroupNameContainCorrectSortOrder(mediaTypeName, secondGroupValue, 0)).toBeTruthy();
expect(await umbracoApi.mediaType.doesMediaTypeGroupNameContainCorrectSortOrder(mediaTypeName, firstGroupValue, 1)).toBeTruthy();
});
// TODO: Unskip when it works. Sometimes the properties are not dragged correctly.
test.skip('can reorder properties in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const dataTypeNameTwo = "Upload Second File";
await umbracoApi.mediaType.createMediaTypeWithTwoPropertyEditors(mediaTypeName, dataTypeName, dataTypeData.id, dataTypeNameTwo, dataTypeData.id);
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.clickReorderButton();
// Drag and Drop
const dragFromLocator = umbracoUi.mediaType.getTextLocatorWithName(dataTypeNameTwo);
const dragToLocator = umbracoUi.mediaType.getTextLocatorWithName(dataTypeName);
await umbracoUi.mediaType.dragAndDrop(dragFromLocator, dragToLocator, -10, 0, 5);
await umbracoUi.waitForTimeout(200);
await umbracoUi.mediaType.clickIAmDoneReorderingButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.properties[0].name).toBe(dataTypeNameTwo);
});
// TODO: Unskip when the frontend does not give the secondTab -1 as the sortOrder
test.skip('can reorder tabs in a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const dataTypeData = await umbracoApi.dataType.getByName(dataTypeName);
const secondTabName = 'SecondTab';
await umbracoApi.mediaType.createMediaTypeWithTwoTabs(mediaTypeName, dataTypeName, dataTypeData.id, tabName, secondTabName);
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
// Act
const dragToLocator = umbracoUi.mediaType.getTabLocatorWithName(tabName);
const dragFromLocator = umbracoUi.mediaType.getTabLocatorWithName(secondTabName);
await umbracoUi.mediaType.clickReorderButton();
await umbracoUi.mediaType.dragAndDrop(dragFromLocator, dragToLocator, 0, 0, 10);
await umbracoUi.mediaType.clickIAmDoneReorderingButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesMediaTypeTabNameContainCorrectSortOrder(mediaTypeName, secondTabName, 0)).toBeTruthy();
expect(await umbracoApi.mediaType.doesMediaTypeTabNameContainCorrectSortOrder(mediaTypeName, tabName, 1)).toBeTruthy();
});

View File

@@ -0,0 +1,109 @@
import {ConstantHelper, test} from '@umbraco/playwright-testhelpers';
import {expect} from "@playwright/test";
const mediaTypeFolderName = 'TestMediaTypeFolder';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeFolderName);
await umbracoUi.goToBackOffice();
await umbracoUi.mediaType.goToSection(ConstantHelper.sections.settings);
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeFolderName);
});
test('can create a empty media type folder', async ({umbracoApi, umbracoUi}) => {
// Act
await umbracoUi.mediaType.clickActionsMenuForName('Media Types');
await umbracoUi.mediaType.createFolder(mediaTypeFolderName);
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const folder = await umbracoApi.mediaType.getByName(mediaTypeFolderName);
expect(folder.name).toBe(mediaTypeFolderName);
// Checks if the folder is in the root
await umbracoUi.mediaType.clickRootFolderCaretButton();
await umbracoUi.mediaType.isTreeItemVisible(mediaTypeFolderName, true);
});
test('can delete a media type folder', async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.mediaType.createFolder(mediaTypeFolderName);
// Act
await umbracoUi.mediaType.clickRootFolderCaretButton();
await umbracoUi.mediaType.clickActionsMenuForName(mediaTypeFolderName);
await umbracoUi.mediaType.deleteFolder();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesNameExist(mediaTypeFolderName)).toBeFalsy();
});
test('can rename a media type folder', async ({umbracoApi, umbracoUi}) => {
// Arrange
const oldFolderName = 'OldName';
await umbracoApi.mediaType.createFolder(oldFolderName);
// Act
await umbracoUi.mediaType.clickRootFolderCaretButton();
await umbracoUi.mediaType.clickActionsMenuForName(oldFolderName);
await umbracoUi.mediaType.clickRenameFolderButton();
await umbracoUi.mediaType.enterFolderName(mediaTypeFolderName);
await umbracoUi.mediaType.clickUpdateFolderButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const folder = await umbracoApi.mediaType.getByName(mediaTypeFolderName);
expect(folder.name).toBe(mediaTypeFolderName);
});
test('can create a media type folder in a folder', async ({umbracoApi, umbracoUi}) => {
// Arrange
const childFolderName = 'ChildFolder';
await umbracoApi.mediaType.ensureNameNotExists(childFolderName);
const parentFolderId = await umbracoApi.mediaType.createFolder(mediaTypeFolderName);
// Act
await umbracoUi.mediaType.clickRootFolderCaretButton();
await umbracoUi.mediaType.clickActionsMenuForName(mediaTypeFolderName);
await umbracoUi.mediaType.createFolder(childFolderName);
// Assert
await umbracoUi.mediaType.clickCaretButtonForName(mediaTypeFolderName);
await umbracoUi.mediaType.isTreeItemVisible(childFolderName, true);
const parentFolderChildren = await umbracoApi.mediaType.getChildren(parentFolderId);
expect(parentFolderChildren[0].name).toBe(childFolderName);
// Clean
await umbracoApi.mediaType.ensureNameNotExists(childFolderName);
});
test('can create a media type folder in a folder in a folder', async ({umbracoApi, umbracoUi}) => {
// Arrange
const grandparentFolderName = 'GrandparentFolder';
const childFolderName = 'ChildFolder';
await umbracoApi.mediaType.ensureNameNotExists(childFolderName);
await umbracoApi.mediaType.ensureNameNotExists(grandparentFolderName);
const grandParentFolderId = await umbracoApi.mediaType.createFolder(grandparentFolderName);
const parentFolderId = await umbracoApi.mediaType.createFolder(mediaTypeFolderName, grandParentFolderId);
// Act
await umbracoUi.mediaType.clickRootFolderCaretButton();
await umbracoUi.mediaType.clickCaretButtonForName(grandparentFolderName);
await umbracoUi.mediaType.clickActionsMenuForName(mediaTypeFolderName);
await umbracoUi.mediaType.createFolder(childFolderName);
// Assert
await umbracoUi.mediaType.clickCaretButtonForName(mediaTypeFolderName);
await umbracoUi.mediaType.isTreeItemVisible(childFolderName, true);
const grandParentFolderChildren = await umbracoApi.mediaType.getChildren(grandParentFolderId);
expect(grandParentFolderChildren[0].name).toBe(mediaTypeFolderName);
const parentFolderChildren = await umbracoApi.mediaType.getChildren(parentFolderId);
expect(parentFolderChildren[0].name).toBe(childFolderName);
// Clean
await umbracoApi.mediaType.ensureNameNotExists(childFolderName);
await umbracoApi.mediaType.ensureNameNotExists(grandparentFolderName);
});

View File

@@ -0,0 +1,118 @@
import {ConstantHelper, test} from "@umbraco/playwright-testhelpers";
import {expect} from "@playwright/test";
const mediaTypeName = 'TestMediaType';
test.beforeEach(async ({umbracoUi, umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeName);
await umbracoUi.goToBackOffice();
await umbracoUi.mediaType.goToSection(ConstantHelper.sections.settings);
});
test.afterEach(async ({umbracoApi}) => {
await umbracoApi.mediaType.ensureNameNotExists(mediaTypeName);
});
test('can create a media type with allow at root enabled', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickStructureTab();
await umbracoUi.mediaType.clickAllowAtRootButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.allowedAsRoot).toBeTruthy();
});
test('can create a media type with an allowed child node type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickStructureTab();
await umbracoUi.mediaType.clickChooseButton();
await umbracoUi.mediaType.clickButtonWithName(mediaTypeName);
await umbracoUi.mediaType.clickAllowedChildNodesButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.allowedMediaTypes[0].mediaType.id).toBe(mediaTypeData.id);
});
test('can create a media type with multiple allowed child nodes types', async ({umbracoApi, umbracoUi}) => {
// Arrange
const mediaTypeId = await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
const secondMediaTypeName = 'SecondMediaType';
await umbracoApi.mediaType.ensureNameNotExists(secondMediaTypeName);
const secondMediaTypeId = await umbracoApi.mediaType.createDefaultMediaType(secondMediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickStructureTab();
await umbracoUi.mediaType.clickChooseButton();
await umbracoUi.mediaType.clickButtonWithName(mediaTypeName);
await umbracoUi.mediaType.clickButtonWithName(secondMediaTypeName);
await umbracoUi.mediaType.clickAllowedChildNodesButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
expect(await umbracoApi.mediaType.doesMediaTypeContainAllowedChildNodeIds(mediaTypeName, [mediaTypeId, secondMediaTypeId])).toBeTruthy();
// Clean
await umbracoApi.mediaType.ensureNameNotExists(secondMediaTypeName);
});
test('can delete an allowed child note from a media type', {tag: '@smoke'}, async ({umbracoApi, umbracoUi}) => {
// Arrange
const childNodeName = 'MediaChildNode';
await umbracoApi.mediaType.ensureNameNotExists(childNodeName);
const childNodeId = await umbracoApi.mediaType.createDefaultMediaType(childNodeName);
await umbracoApi.mediaType.createMediaTypeWithAllowedChildNode(mediaTypeName, childNodeId);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickStructureTab();
await umbracoUi.mediaType.clickRemoveButtonForName(childNodeName);
await umbracoUi.mediaType.clickConfirmRemoveButton();
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(childNodeName);
expect(mediaTypeData.allowedMediaTypes.length).toBe(0);
// Clean
await umbracoApi.mediaType.ensureNameNotExists(childNodeName);
});
test('can configure a collection for a media type', async ({umbracoApi, umbracoUi}) => {
// Arrange
const collectionDataTypeName = 'TestCollection';
await umbracoApi.dataType.ensureNameNotExists(collectionDataTypeName);
const collectionDataTypeId = await umbracoApi.dataType.create(collectionDataTypeName, 'Umbraco.ListView', [], null, 'Umb.PropertyEditorUi.CollectionView');
await umbracoApi.mediaType.createDefaultMediaType(mediaTypeName);
// Act
await umbracoUi.mediaType.goToMediaType(mediaTypeName);
await umbracoUi.mediaType.clickStructureTab();
await umbracoUi.mediaType.clickConfigureAsACollectionButton();
await umbracoUi.mediaType.clickTextButtonWithName(collectionDataTypeName);
await umbracoUi.mediaType.clickSaveButton();
// Assert
await umbracoUi.mediaType.isSuccessNotificationVisible();
const mediaTypeData = await umbracoApi.mediaType.getByName(mediaTypeName);
expect(mediaTypeData.collection.id).toEqual(collectionDataTypeId);
// Clean
await umbracoApi.dataType.ensureNameNotExists(collectionDataTypeName);
});

View File

@@ -10,6 +10,7 @@ setup('authenticate', async ({page}) => {
await umbracoUi.login.enterEmail(process.env.UMBRACO_USER_LOGIN);
await umbracoUi.login.enterPassword(process.env.UMBRACO_USER_PASSWORD);
await umbracoUi.login.clickLoginButton();
await page.waitForTimeout(5000);
await umbracoUi.login.goToSection(ConstantHelper.sections.settings);
await umbracoUi.page.context().storageState({path: STORAGE_STATE});
});