Merge branch 'v15/dev' into v15/feature/member-sidebar-menu
This commit is contained in:
@@ -1,7 +1,8 @@
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import { html, customElement, LitElement, property, css } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbElementMixin } from '@umbraco-cms/backoffice/element-api';
|
||||
import type { UmbBlockDataType, UmbBlockEditorCustomViewElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockDataType } from '@umbraco-cms/backoffice/block';
|
||||
import type { UmbBlockEditorCustomViewElement } from '@umbraco-cms/backoffice/block-custom-view';
|
||||
|
||||
// eslint-disable-next-line local-rules/enforce-umb-prefix-on-element-name
|
||||
@customElement('example-block-custom-view')
|
||||
|
||||
@@ -1,6 +1,4 @@
|
||||
import type { ManifestBlockEditorCustomView } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestBlockEditorCustomView> = [
|
||||
export const manifests: Array<UmbExtensionManifest> = [
|
||||
{
|
||||
type: 'blockEditorCustomView',
|
||||
alias: 'Umb.blockEditorCustomView.TestView',
|
||||
|
||||
5
src/Umbraco.Web.UI.Client/package-lock.json
generated
5
src/Umbraco.Web.UI.Client/package-lock.json
generated
@@ -7811,6 +7811,10 @@
|
||||
"resolved": "src/packages/health-check",
|
||||
"link": true
|
||||
},
|
||||
"node_modules/@umbraco-backoffice/help": {
|
||||
"resolved": "src/packages/help",
|
||||
"link": true
|
||||
},
|
||||
"node_modules/@umbraco-backoffice/language": {
|
||||
"resolved": "src/packages/language",
|
||||
"link": true
|
||||
@@ -23078,6 +23082,7 @@
|
||||
"src/packages/health-check": {
|
||||
"name": "@umbraco-backoffice/health-check"
|
||||
},
|
||||
"src/packages/help": {},
|
||||
"src/packages/language": {
|
||||
"name": "@umbraco-backoffice/language"
|
||||
},
|
||||
|
||||
@@ -17,6 +17,7 @@
|
||||
"./action": "./dist-cms/packages/core/action/index.js",
|
||||
"./audit-log": "./dist-cms/packages/core/audit-log/index.js",
|
||||
"./auth": "./dist-cms/packages/core/auth/index.js",
|
||||
"./block-custom-view": "./dist-cms/packages/block/block-custom-view/index.js",
|
||||
"./block-grid": "./dist-cms/packages/block/block-grid/index.js",
|
||||
"./block-list": "./dist-cms/packages/block/block-list/index.js",
|
||||
"./block-rte": "./dist-cms/packages/block/block-rte/index.js",
|
||||
@@ -41,6 +42,7 @@
|
||||
"./entity": "./dist-cms/packages/core/entity/index.js",
|
||||
"./event": "./dist-cms/packages/core/event/index.js",
|
||||
"./extension-registry": "./dist-cms/packages/core/extension-registry/index.js",
|
||||
"./help": "./dist-cms/packages/help/index.js",
|
||||
"./icon": "./dist-cms/packages/core/icon-registry/index.js",
|
||||
"./id": "./dist-cms/packages/core/id/index.js",
|
||||
"./imaging": "./dist-cms/packages/media/imaging/index.js",
|
||||
|
||||
@@ -18,6 +18,7 @@ const CORE_PACKAGES = [
|
||||
import('../../packages/dictionary/umbraco-package.js'),
|
||||
import('../../packages/documents/umbraco-package.js'),
|
||||
import('../../packages/health-check/umbraco-package.js'),
|
||||
import('../../packages/help/umbraco-package.js'),
|
||||
import('../../packages/language/umbraco-package.js'),
|
||||
import('../../packages/log-viewer/umbraco-package.js'),
|
||||
import('../../packages/markdown-editor/umbraco-package.js'),
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
import type { ManifestBase } from '../types/index.js';
|
||||
import type { UmbApi } from './api.interface.js';
|
||||
|
||||
/**
|
||||
* Interface for APIs of a Extension.
|
||||
*/
|
||||
export interface UmbExtensionApi<ManifestType extends ManifestBase = ManifestBase> extends UmbApi {
|
||||
manifest?: ManifestType;
|
||||
}
|
||||
@@ -1,2 +1,3 @@
|
||||
export * from './entry-point.interface.js';
|
||||
export * from './api.interface.js';
|
||||
export * from './extension-api.interface.js';
|
||||
|
||||
@@ -1,4 +1,11 @@
|
||||
import type { ManifestElementWithElementName, ManifestKind, ManifestBase } from '../types/index.js';
|
||||
import type { WorkspaceAliasConditionConfig } from '@umbraco-cms/backoffice/workspace';
|
||||
import type {
|
||||
ManifestElementWithElementName,
|
||||
ManifestKind,
|
||||
ManifestBase,
|
||||
ManifestWithDynamicConditions,
|
||||
UmbConditionConfigBase,
|
||||
} from '../types/index.js';
|
||||
import { UmbExtensionRegistry } from './extension.registry.js';
|
||||
import { expect } from '@open-wc/testing';
|
||||
|
||||
@@ -453,3 +460,224 @@ describe('UmbExtensionRegistry with exclusions', () => {
|
||||
expect(extensionRegistry.isRegistered('Umb.Test.Section.Late')).to.be.false;
|
||||
});
|
||||
});
|
||||
|
||||
describe('Add Conditions', () => {
|
||||
let extensionRegistry: UmbExtensionRegistry<any>;
|
||||
let manifests: Array<ManifestWithDynamicConditions>;
|
||||
|
||||
beforeEach(() => {
|
||||
extensionRegistry = new UmbExtensionRegistry<ManifestWithDynamicConditions>();
|
||||
manifests = [
|
||||
{
|
||||
type: 'section',
|
||||
name: 'test-section-1',
|
||||
alias: 'Umb.Test.Section.1',
|
||||
weight: 1,
|
||||
conditions: [
|
||||
{
|
||||
alias: 'Umb.Test.Condition.Invalid',
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
type: 'section',
|
||||
name: 'test-section-2',
|
||||
alias: 'Umb.Test.Section.2',
|
||||
weight: 200,
|
||||
},
|
||||
];
|
||||
|
||||
manifests.forEach((manifest) => extensionRegistry.register(manifest));
|
||||
|
||||
extensionRegistry.register({
|
||||
type: 'condition',
|
||||
name: 'test-condition-invalid',
|
||||
alias: 'Umb.Test.Condition.Invalid',
|
||||
});
|
||||
});
|
||||
|
||||
it('should have the extensions registered', () => {
|
||||
expect(extensionRegistry.isRegistered('Umb.Test.Section.1')).to.be.true;
|
||||
expect(extensionRegistry.isRegistered('Umb.Test.Section.2')).to.be.true;
|
||||
expect(extensionRegistry.isRegistered('Umb.Test.Condition.Invalid')).to.be.true;
|
||||
expect(extensionRegistry.isRegistered('Umb.Test.Condition.Valid')).to.be.false;
|
||||
});
|
||||
|
||||
it('allows an extension condition to be updated', async () => {
|
||||
const ext = extensionRegistry.getByAlias('Umb.Test.Section.1') as ManifestWithDynamicConditions;
|
||||
expect(ext.conditions?.length).to.equal(1);
|
||||
|
||||
// Register new condition as if I was in my own entrypoint
|
||||
extensionRegistry.register({
|
||||
type: 'condition',
|
||||
name: 'test-condition-valid',
|
||||
alias: 'Umb.Test.Condition.Valid',
|
||||
});
|
||||
|
||||
// Add the new condition to the extension
|
||||
const conditionToAdd: UmbConditionConfigBase = {
|
||||
alias: 'Umb.Test.Condition.Valid',
|
||||
};
|
||||
await extensionRegistry.appendCondition('Umb.Test.Section.1', conditionToAdd);
|
||||
|
||||
// Check new condition is registered
|
||||
expect(extensionRegistry.isRegistered('Umb.Test.Condition.Valid')).to.be.true;
|
||||
|
||||
// Verify the extension now has two conditions and in correct order with aliases
|
||||
const updatedExt = extensionRegistry.getByAlias('Umb.Test.Section.1') as ManifestWithDynamicConditions;
|
||||
expect(updatedExt.conditions?.length).to.equal(2);
|
||||
expect(updatedExt.conditions?.[0]?.alias).to.equal('Umb.Test.Condition.Invalid');
|
||||
expect(updatedExt.conditions?.[1]?.alias).to.equal('Umb.Test.Condition.Valid');
|
||||
|
||||
// Verify the other extension was not updated:
|
||||
const otherExt = extensionRegistry.getByAlias('Umb.Test.Section.2') as ManifestWithDynamicConditions;
|
||||
expect(otherExt.conditions).to.be.undefined;
|
||||
|
||||
// Add a condition with a specific config to Section2
|
||||
const workspaceCondition: WorkspaceAliasConditionConfig = {
|
||||
alias: 'Umb.Condition.WorkspaceAlias',
|
||||
match: 'Umb.Workspace.Document',
|
||||
};
|
||||
|
||||
await extensionRegistry.appendCondition('Umb.Test.Section.2', workspaceCondition);
|
||||
|
||||
const updatedWorkspaceExt = extensionRegistry.getByAlias('Umb.Test.Section.2') as ManifestWithDynamicConditions;
|
||||
expect(updatedWorkspaceExt.conditions?.length).to.equal(1);
|
||||
expect(updatedWorkspaceExt.conditions?.[0]?.alias).to.equal('Umb.Condition.WorkspaceAlias');
|
||||
});
|
||||
|
||||
it('allows an extension to update with multiple conditions', async () => {
|
||||
const ext = extensionRegistry.getByAlias('Umb.Test.Section.1') as ManifestWithDynamicConditions;
|
||||
expect(ext.conditions?.length).to.equal(1);
|
||||
|
||||
const conditions: Array<UmbConditionConfigBase> = [
|
||||
{
|
||||
alias: 'Umb.Test.Condition.Valid',
|
||||
},
|
||||
{
|
||||
alias: 'Umb.Condition.WorkspaceAlias',
|
||||
match: 'Umb.Workspace.Document',
|
||||
} as WorkspaceAliasConditionConfig,
|
||||
];
|
||||
|
||||
await extensionRegistry.appendConditions('Umb.Test.Section.1', conditions);
|
||||
|
||||
const extUpdated = extensionRegistry.getByAlias('Umb.Test.Section.1') as ManifestWithDynamicConditions;
|
||||
expect(extUpdated.conditions?.length).to.equal(3);
|
||||
expect(extUpdated.conditions?.[0]?.alias).to.equal('Umb.Test.Condition.Invalid');
|
||||
expect(extUpdated.conditions?.[1]?.alias).to.equal('Umb.Test.Condition.Valid');
|
||||
expect(extUpdated.conditions?.[2]?.alias).to.equal('Umb.Condition.WorkspaceAlias');
|
||||
});
|
||||
|
||||
it('allows conditions to be prepended when an extension is loaded later on', async () => {
|
||||
const conditions: Array<UmbConditionConfigBase> = [
|
||||
{
|
||||
alias: 'Umb.Test.Condition.Invalid',
|
||||
},
|
||||
{
|
||||
alias: 'Umb.Condition.WorkspaceAlias',
|
||||
match: 'Umb.Workspace.Document',
|
||||
} as WorkspaceAliasConditionConfig,
|
||||
];
|
||||
|
||||
// Prepend the conditions, but do not await this.
|
||||
extensionRegistry.appendConditions('Late.Extension.To.Be.Loaded', conditions);
|
||||
|
||||
// Make sure the extension is not registered YET
|
||||
expect(extensionRegistry.isRegistered('Late.Extension.To.Be.Loaded')).to.be.false;
|
||||
|
||||
// Register the extension LATE/after the conditions have been added
|
||||
extensionRegistry.register({
|
||||
type: 'section',
|
||||
name: 'Late Section Extension with one condition',
|
||||
alias: 'Late.Extension.To.Be.Loaded',
|
||||
weight: 200,
|
||||
conditions: [
|
||||
{
|
||||
alias: 'Umb.Test.Condition.Valid',
|
||||
},
|
||||
],
|
||||
});
|
||||
|
||||
expect(extensionRegistry.isRegistered('Late.Extension.To.Be.Loaded')).to.be.true;
|
||||
|
||||
const extUpdated = extensionRegistry.getByAlias('Late.Extension.To.Be.Loaded') as ManifestWithDynamicConditions;
|
||||
|
||||
expect(extUpdated.conditions?.length).to.equal(3);
|
||||
expect(extUpdated.conditions?.[0]?.alias).to.equal('Umb.Test.Condition.Valid');
|
||||
expect(extUpdated.conditions?.[1]?.alias).to.equal('Umb.Test.Condition.Invalid');
|
||||
expect(extUpdated.conditions?.[2]?.alias).to.equal('Umb.Condition.WorkspaceAlias');
|
||||
});
|
||||
|
||||
/**
|
||||
* As of current state, it is by design without further reasons to why, but it is made so additional conditions are only added to a current or next time registered manifest.
|
||||
* Meaning if it happens to be unregistered and re-registered it does not happen again.
|
||||
* Unless the exact same appending of conditions happens again. [NL]
|
||||
*
|
||||
* This makes sense if extensions gets offloaded and re-registered, but the extension that registered additional conditions didn't get loaded/registered second time. Therefor they need to be re-registered for such to work. [NL]
|
||||
*/
|
||||
it('only append conditions to the next time the extension is registered', async () => {
|
||||
const conditions: Array<UmbConditionConfigBase> = [
|
||||
{
|
||||
alias: 'Umb.Test.Condition.Invalid',
|
||||
},
|
||||
{
|
||||
alias: 'Umb.Condition.WorkspaceAlias',
|
||||
match: 'Umb.Workspace.Document',
|
||||
} as WorkspaceAliasConditionConfig,
|
||||
];
|
||||
|
||||
// Prepend the conditions, but do not await this.
|
||||
extensionRegistry.appendConditions('Late.Extension.To.Be.Loaded', conditions);
|
||||
|
||||
// Make sure the extension is not registered YET
|
||||
expect(extensionRegistry.isRegistered('Late.Extension.To.Be.Loaded')).to.be.false;
|
||||
|
||||
// Register the extension LATE/after the conditions have been added
|
||||
extensionRegistry.register({
|
||||
type: 'section',
|
||||
name: 'Late Section Extension with one condition',
|
||||
alias: 'Late.Extension.To.Be.Loaded',
|
||||
weight: 200,
|
||||
conditions: [
|
||||
{
|
||||
alias: 'Umb.Test.Condition.Valid',
|
||||
},
|
||||
],
|
||||
});
|
||||
|
||||
expect(extensionRegistry.isRegistered('Late.Extension.To.Be.Loaded')).to.be.true;
|
||||
|
||||
const extUpdateFirstTime = extensionRegistry.getByAlias(
|
||||
'Late.Extension.To.Be.Loaded',
|
||||
) as ManifestWithDynamicConditions;
|
||||
expect(extUpdateFirstTime.conditions?.length).to.equal(3);
|
||||
|
||||
extensionRegistry.unregister('Late.Extension.To.Be.Loaded');
|
||||
|
||||
// Make sure the extension is not registered YET
|
||||
expect(extensionRegistry.isRegistered('Late.Extension.To.Be.Loaded')).to.be.false;
|
||||
|
||||
// Register the extension LATE/after the conditions have been added
|
||||
extensionRegistry.register({
|
||||
type: 'section',
|
||||
name: 'Late Section Extension with one condition',
|
||||
alias: 'Late.Extension.To.Be.Loaded',
|
||||
weight: 200,
|
||||
conditions: [
|
||||
{
|
||||
alias: 'Umb.Test.Condition.Valid',
|
||||
},
|
||||
],
|
||||
});
|
||||
|
||||
expect(extensionRegistry.isRegistered('Late.Extension.To.Be.Loaded')).to.be.true;
|
||||
|
||||
const extUpdateSecondTime = extensionRegistry.getByAlias(
|
||||
'Late.Extension.To.Be.Loaded',
|
||||
) as ManifestWithDynamicConditions;
|
||||
|
||||
expect(extUpdateSecondTime.conditions?.length).to.equal(1);
|
||||
expect(extUpdateSecondTime.conditions?.[0]?.alias).to.equal('Umb.Test.Condition.Valid');
|
||||
});
|
||||
});
|
||||
|
||||
@@ -1,4 +1,9 @@
|
||||
import type { ManifestBase, ManifestKind } from '../types/index.js';
|
||||
import type {
|
||||
ManifestBase,
|
||||
ManifestKind,
|
||||
ManifestWithDynamicConditions,
|
||||
UmbConditionConfigBase,
|
||||
} from '../types/index.js';
|
||||
import type { SpecificManifestTypeOrManifestBase } from '../types/map.types.js';
|
||||
import { UmbBasicState } from '@umbraco-cms/backoffice/observable-api';
|
||||
import type { Observable } from '@umbraco-cms/backoffice/external/rxjs';
|
||||
@@ -6,8 +11,9 @@ import { map, distinctUntilChanged, combineLatest, of, switchMap } from '@umbrac
|
||||
|
||||
/**
|
||||
*
|
||||
* @param previousValue
|
||||
* @param currentValue
|
||||
* @param previousValue {Array<ManifestBase>} - previous value
|
||||
* @param currentValue {Array<ManifestBase>} - current value
|
||||
* @returns {boolean} - true if value is assumed to be the same as previous value.
|
||||
*/
|
||||
function extensionArrayMemoization<T extends Pick<ManifestBase, 'alias'>>(
|
||||
previousValue: Array<T>,
|
||||
@@ -26,8 +32,9 @@ function extensionArrayMemoization<T extends Pick<ManifestBase, 'alias'>>(
|
||||
|
||||
/**
|
||||
*
|
||||
* @param previousValue
|
||||
* @param currentValue
|
||||
* @param previousValue {Array<ManifestBase>} - previous value
|
||||
* @param currentValue {Array<ManifestBase>} - current value
|
||||
* @returns {boolean} - true if value is assumed to be the same as previous value.
|
||||
*/
|
||||
function extensionAndKindMatchArrayMemoization<
|
||||
T extends Pick<ManifestBase, 'alias'> & { __isMatchedWithKind?: boolean },
|
||||
@@ -57,8 +64,9 @@ function extensionAndKindMatchArrayMemoization<
|
||||
|
||||
/**
|
||||
*
|
||||
* @param previousValue
|
||||
* @param currentValue
|
||||
* @param previousValue {Array<ManifestBase>} - previous value
|
||||
* @param currentValue {Array<ManifestBase>} - current value
|
||||
* @returns {boolean} - true if value is assumed to be the same as previous value.
|
||||
*/
|
||||
function extensionSingleMemoization<T extends Pick<ManifestBase, 'alias'>>(
|
||||
previousValue: T | undefined,
|
||||
@@ -72,8 +80,9 @@ function extensionSingleMemoization<T extends Pick<ManifestBase, 'alias'>>(
|
||||
|
||||
/**
|
||||
*
|
||||
* @param previousValue
|
||||
* @param currentValue
|
||||
* @param previousValue {Array<ManifestBase>} - previous value
|
||||
* @param currentValue {Array<ManifestBase>} - current value
|
||||
* @returns {boolean} - true if value is assumed to be the same as previous value.
|
||||
*/
|
||||
function extensionAndKindMatchSingleMemoization<
|
||||
T extends Pick<ManifestBase, 'alias'> & { __isMatchedWithKind?: boolean },
|
||||
@@ -100,8 +109,26 @@ export class UmbExtensionRegistry<
|
||||
|
||||
private _kinds = new UmbBasicState<Array<ManifestKind<ManifestTypes>>>([]);
|
||||
public readonly kinds = this._kinds.asObservable();
|
||||
|
||||
#exclusions: Array<string> = [];
|
||||
|
||||
#additionalConditions: Map<string, Array<UmbConditionConfigBase>> = new Map();
|
||||
#appendAdditionalConditions(manifest: ManifestTypes) {
|
||||
const newConditions = this.#additionalConditions.get(manifest.alias);
|
||||
if (newConditions) {
|
||||
// Append the condition to the extensions conditions array
|
||||
if ((manifest as ManifestWithDynamicConditions).conditions) {
|
||||
for (const condition of newConditions) {
|
||||
(manifest as ManifestWithDynamicConditions).conditions!.push(condition);
|
||||
}
|
||||
} else {
|
||||
(manifest as ManifestWithDynamicConditions).conditions = newConditions;
|
||||
}
|
||||
this.#additionalConditions.delete(manifest.alias);
|
||||
}
|
||||
return manifest;
|
||||
}
|
||||
|
||||
defineKind(kind: ManifestKind<ManifestTypes>): void {
|
||||
const extensionsValues = this._extensions.getValue();
|
||||
const extension = extensionsValues.find(
|
||||
@@ -136,12 +163,25 @@ export class UmbExtensionRegistry<
|
||||
};
|
||||
|
||||
register(manifest: ManifestTypes | ManifestKind<ManifestTypes>): void {
|
||||
const isValid = this.#checkExtension(manifest);
|
||||
const isValid = this.#validateExtension(manifest);
|
||||
if (!isValid) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._extensions.setValue([...this._extensions.getValue(), manifest as ManifestTypes]);
|
||||
if (manifest.type === 'kind') {
|
||||
this.defineKind(manifest as ManifestKind<ManifestTypes>);
|
||||
return;
|
||||
}
|
||||
|
||||
const isApproved = this.#isExtensionApproved(manifest);
|
||||
if (!isApproved) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._extensions.setValue([
|
||||
...this._extensions.getValue(),
|
||||
this.#appendAdditionalConditions(manifest as ManifestTypes),
|
||||
]);
|
||||
}
|
||||
|
||||
getAllExtensions(): Array<ManifestTypes> {
|
||||
@@ -177,7 +217,7 @@ export class UmbExtensionRegistry<
|
||||
return false;
|
||||
}
|
||||
|
||||
#checkExtension(manifest: ManifestTypes | ManifestKind<ManifestTypes>): boolean {
|
||||
#validateExtension(manifest: ManifestTypes | ManifestKind<ManifestTypes>): boolean {
|
||||
if (!manifest.type) {
|
||||
console.error(`Extension is missing type`, manifest);
|
||||
return false;
|
||||
@@ -188,11 +228,9 @@ export class UmbExtensionRegistry<
|
||||
return false;
|
||||
}
|
||||
|
||||
if (manifest.type === 'kind') {
|
||||
this.defineKind(manifest as ManifestKind<ManifestTypes>);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
#isExtensionApproved(manifest: ManifestTypes | ManifestKind<ManifestTypes>): boolean {
|
||||
if (!this.#acceptExtension(manifest as ManifestTypes)) {
|
||||
return false;
|
||||
}
|
||||
@@ -430,4 +468,41 @@ export class UmbExtensionRegistry<
|
||||
distinctUntilChanged(extensionAndKindMatchArrayMemoization),
|
||||
) as Observable<Array<ExtensionTypes>>;
|
||||
}
|
||||
|
||||
/**
|
||||
* Append a new condition to an existing extension
|
||||
* Useful to add a condition for example the Save And Publish workspace action shipped by core.
|
||||
* @param {string} alias - The alias of the extension to append the condition to.
|
||||
* @param {UmbConditionConfigBase} newCondition - The condition to append to the extension.
|
||||
*/
|
||||
appendCondition(alias: string, newCondition: UmbConditionConfigBase) {
|
||||
this.appendConditions(alias, [newCondition]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Appends an array of conditions to an existing extension
|
||||
* @param {string} alias - The alias of the extension to append the condition to
|
||||
* @param {Array<UmbConditionConfigBase>} newConditions - An array of conditions to be appended to an extension manifest.
|
||||
*/
|
||||
appendConditions(alias: string, newConditions: Array<UmbConditionConfigBase>) {
|
||||
const existingConditionsToBeAdded = this.#additionalConditions.get(alias);
|
||||
this.#additionalConditions.set(
|
||||
alias,
|
||||
existingConditionsToBeAdded ? [...existingConditionsToBeAdded, ...newConditions] : newConditions,
|
||||
);
|
||||
|
||||
const allExtensions = this._extensions.getValue();
|
||||
for (const extension of allExtensions) {
|
||||
if (extension.alias === alias) {
|
||||
// Replace the existing extension with the updated one
|
||||
allExtensions[allExtensions.indexOf(extension)] = this.#appendAdditionalConditions(extension as ManifestTypes);
|
||||
|
||||
// Update the main extensions collection/observable
|
||||
this._extensions.setValue(allExtensions);
|
||||
|
||||
//Stop the search:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@ import type { ManifestBase } from './manifest-base.interface.js';
|
||||
/**
|
||||
* This type of extension takes a JS module and registers all exported manifests from the pointed JS file.
|
||||
*/
|
||||
export interface ManifestBundle<UmbManifestTypes extends ManifestBase = ManifestBase>
|
||||
extends ManifestPlainJs<{ [key: string]: Array<UmbManifestTypes> }> {
|
||||
export interface ManifestBundle<ManifestTypes extends ManifestBase = ManifestBase>
|
||||
extends ManifestPlainJs<{ [key: string]: Array<ManifestTypes> }> {
|
||||
type: 'bundle';
|
||||
}
|
||||
|
||||
@@ -1,20 +1,26 @@
|
||||
import type { UmbBlockEditorCustomViewElement } from '../interfaces/index.js';
|
||||
import type { UmbBlockEditorCustomViewElement } from './types.js';
|
||||
import type { ManifestElement } from '@umbraco-cms/backoffice/extension-api';
|
||||
|
||||
export interface ManifestBlockEditorCustomView extends ManifestElement<UmbBlockEditorCustomViewElement> {
|
||||
type: 'blockEditorCustomView';
|
||||
/**
|
||||
* @property {string | Array<string> } - Declare if this Custom View only must appear at specific Content Types by Alias.
|
||||
* @property {string | Array<string> } forContentTypeAlias - Declare if this Custom View only must appear at specific Content Types by Alias.
|
||||
* @description Optional condition if you like this custom view to only appear at for one or more specific Content Types.
|
||||
* @example 'my-element-type-alias'
|
||||
* @example ['my-element-type-alias-A', 'my-element-type-alias-B']
|
||||
*/
|
||||
forContentTypeAlias?: string | Array<string>;
|
||||
/**
|
||||
* @property {string | Array<string> } - Declare if this Custom View only must appear at specific Block Editors.
|
||||
* @property {string | Array<string> } forBlockEditor - Declare if this Custom View only must appear at specific Block Editors.
|
||||
* @description Optional condition if you like this custom view to only appear at a specific type of Block Editor.
|
||||
* @example 'block-list'
|
||||
* @example ['block-list', 'block-grid']
|
||||
*/
|
||||
forBlockEditor?: string | Array<string>;
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface UmbExtensionManifestMap {
|
||||
blockEditorCustomView: ManifestBlockEditorCustomView;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
export type * from './types.js';
|
||||
@@ -1,29 +1,8 @@
|
||||
import type { ManifestBlockEditorCustomView } from '../index.js';
|
||||
import type { UUIModalSidebarSize } from '@umbraco-cms/backoffice/external/uui';
|
||||
// Shared with the Property Editor
|
||||
export interface UmbBlockTypeBaseModel {
|
||||
contentElementTypeKey: string;
|
||||
settingsElementTypeKey?: string;
|
||||
label?: string;
|
||||
thumbnail?: string;
|
||||
iconColor?: string;
|
||||
backgroundColor?: string;
|
||||
editorSize?: UUIModalSidebarSize;
|
||||
forceHideContentEditorInOverlay: boolean;
|
||||
}
|
||||
import type { ManifestBlockEditorCustomView } from './block-editor-custom-view.extension.js';
|
||||
import type { UmbBlockLayoutBaseModel, UmbBlockDataType } from '@umbraco-cms/backoffice/block';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
// Shared with the Property Editor
|
||||
export interface UmbBlockLayoutBaseModel {
|
||||
contentUdi: string;
|
||||
settingsUdi?: string | null;
|
||||
}
|
||||
|
||||
// Shared with the Property Editor
|
||||
export interface UmbBlockDataType {
|
||||
udi: string;
|
||||
contentTypeKey: string;
|
||||
[key: string]: unknown;
|
||||
}
|
||||
export type * from './block-editor-custom-view.extension.js';
|
||||
|
||||
export interface UmbBlockEditorCustomViewConfiguration {
|
||||
editContentPath?: string;
|
||||
@@ -3,9 +3,9 @@ import { UmbBlockGridInlinePropertyDatasetContext } from './block-grid-inline-pr
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { css, customElement, html, property, state } from '@umbraco-cms/backoffice/external/lit';
|
||||
import type { UmbPropertyTypeModel } from '@umbraco-cms/backoffice/content-type';
|
||||
import type { UmbBlockEditorCustomViewConfiguration } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import '../block-grid-areas-container/index.js';
|
||||
import '../ref-grid-block/index.js';
|
||||
import type { UmbBlockEditorCustomViewConfiguration } from '@umbraco-cms/backoffice/block-custom-view';
|
||||
|
||||
/**
|
||||
* @element umb-block-grid-block-inline
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
import { UMB_BLOCK_GRID_ENTRY_CONTEXT } from '../../context/block-grid-entry.context-token.js';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { css, customElement, html, property, state } from '@umbraco-cms/backoffice/external/lit';
|
||||
import type { UmbBlockEditorCustomViewConfiguration } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockDataType } from '@umbraco-cms/backoffice/block';
|
||||
import type { UmbBlockEditorCustomViewConfiguration } from '@umbraco-cms/backoffice/block-custom-view';
|
||||
|
||||
import '@umbraco-cms/backoffice/ufm';
|
||||
import '../block-grid-areas-container/index.js';
|
||||
|
||||
@@ -2,11 +2,7 @@ import { UmbBlockGridEntryContext } from '../../context/block-grid-entry.context
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { html, css, customElement, property, state, nothing } from '@umbraco-cms/backoffice/external/lit';
|
||||
import type { PropertyValueMap } from '@umbraco-cms/backoffice/external/lit';
|
||||
import type {
|
||||
ManifestBlockEditorCustomView,
|
||||
UmbBlockEditorCustomViewProperties,
|
||||
UmbPropertyEditorUiElement,
|
||||
} from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { stringOrStringArrayContains } from '@umbraco-cms/backoffice/utils';
|
||||
import { UMB_BLOCK_GRID, type UmbBlockGridLayoutModel } from '@umbraco-cms/backoffice/block-grid';
|
||||
|
||||
@@ -15,6 +11,10 @@ import '../block-grid-block/index.js';
|
||||
import '../block-scale-handler/index.js';
|
||||
import { UmbObserveValidationStateController } from '@umbraco-cms/backoffice/validation';
|
||||
import { UmbDataPathBlockElementDataQuery } from '@umbraco-cms/backoffice/block';
|
||||
import type {
|
||||
ManifestBlockEditorCustomView,
|
||||
UmbBlockEditorCustomViewProperties,
|
||||
} from '@umbraco-cms/backoffice/block-custom-view';
|
||||
import { UUIBlinkAnimationValue, UUIBlinkKeyframes } from '@umbraco-cms/backoffice/external/uui';
|
||||
import type { UmbExtensionElementInitializer } from '@umbraco-cms/backoffice/extension-api';
|
||||
/**
|
||||
|
||||
@@ -2,16 +2,16 @@ import { UmbBlockListEntryContext } from '../../context/block-list-entry.context
|
||||
import { UMB_BLOCK_LIST, type UmbBlockListLayoutModel } from '../../types.js';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { html, css, customElement, property, state, nothing } from '@umbraco-cms/backoffice/external/lit';
|
||||
import type {
|
||||
ManifestBlockEditorCustomView,
|
||||
UmbBlockEditorCustomViewProperties,
|
||||
UmbPropertyEditorUiElement,
|
||||
} from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import '../ref-list-block/index.js';
|
||||
import '../inline-list-block/index.js';
|
||||
import { stringOrStringArrayContains } from '@umbraco-cms/backoffice/utils';
|
||||
import { UmbObserveValidationStateController } from '@umbraco-cms/backoffice/validation';
|
||||
import { UmbDataPathBlockElementDataQuery } from '@umbraco-cms/backoffice/block';
|
||||
import type {
|
||||
ManifestBlockEditorCustomView,
|
||||
UmbBlockEditorCustomViewProperties,
|
||||
} from '@umbraco-cms/backoffice/block-custom-view';
|
||||
|
||||
/**
|
||||
* @element umb-block-list-entry
|
||||
|
||||
@@ -6,7 +6,7 @@ import { UMB_BLOCK_LIST_PROPERTY_EDITOR_ALIAS } from './manifests.js';
|
||||
import { UmbLitElement, umbDestroyOnDisconnect } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { html, customElement, property, state, repeat, css, nothing } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import type { UmbPropertyEditorUiElement, UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import {
|
||||
UmbPropertyValueChangeEvent,
|
||||
type UmbPropertyEditorConfigCollection,
|
||||
@@ -19,6 +19,7 @@ import {
|
||||
UmbBlockElementDataValidationPathTranslator,
|
||||
type UmbBlockLayoutBaseModel,
|
||||
} from '@umbraco-cms/backoffice/block';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
import '../../components/block-list-entry/index.js';
|
||||
import { UMB_PROPERTY_CONTEXT } from '@umbraco-cms/backoffice/property';
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import '../../../block-type/components/input-block-type/index.js';
|
||||
import type { UmbInputBlockTypeElement } from '../../../block-type/index.js';
|
||||
import { UMB_BLOCK_LIST_TYPE } from '../../types.js';
|
||||
import type { UmbBlockTypeBaseModel, UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockTypeBaseModel, UmbInputBlockTypeElement } from '@umbraco-cms/backoffice/block-type';
|
||||
import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { html, customElement, property, state } from '@umbraco-cms/backoffice/external/lit';
|
||||
import {
|
||||
UmbPropertyValueChangeEvent,
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockLayoutBaseModel, UmbBlockValueType } from '@umbraco-cms/backoffice/block';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
export const UMB_BLOCK_LIST_TYPE = 'block-list-type';
|
||||
export const UMB_BLOCK_LIST = 'block-list';
|
||||
|
||||
@@ -2,11 +2,9 @@ import type { UmbBlockRteLayoutModel } from '../../types.js';
|
||||
import { UmbBlockRteEntryContext } from '../../context/block-rte-entry.context.js';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { html, css, property, state, customElement } from '@umbraco-cms/backoffice/external/lit';
|
||||
import type {
|
||||
UmbBlockEditorCustomViewProperties,
|
||||
UmbPropertyEditorUiElement,
|
||||
} from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import type { UmbBlockEditorCustomViewProperties } from '@umbraco-cms/backoffice/block-custom-view';
|
||||
|
||||
import '../ref-rte-block/index.js';
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@ import { UMB_BLOCK_RTE_MANAGER_CONTEXT } from '../context/block-rte-manager.cont
|
||||
import { UMB_BLOCK_RTE_ENTRIES_CONTEXT } from '../context/block-rte-entries.context-token.js';
|
||||
import { type TinyMcePluginArguments, UmbTinyMcePluginBase } from '@umbraco-cms/backoffice/tiny-mce';
|
||||
import { UmbLocalizationController } from '@umbraco-cms/backoffice/localization-api';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
export default class UmbTinyMceMultiUrlPickerPlugin extends UmbTinyMcePluginBase {
|
||||
#localize = new UmbLocalizationController(this._host);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
import type { UmbBlockLayoutBaseModel, UmbBlockValueType } from '@umbraco-cms/backoffice/block';
|
||||
|
||||
export const UMB_BLOCK_RTE_TYPE = 'block-rte-type';
|
||||
|
||||
@@ -2,11 +2,12 @@ import { UMB_MANIFEST_VIEWER_MODAL } from '../../../modals/manifest-viewer/index
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { html, customElement, state, property, css } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UMB_PROPERTY_DATASET_CONTEXT } from '@umbraco-cms/backoffice/property';
|
||||
import { umbExtensionsRegistry, type ManifestBlockEditorCustomView } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { umbExtensionsRegistry } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { stringOrStringArrayContains } from '@umbraco-cms/backoffice/utils';
|
||||
import { UmbExtensionsManifestInitializer } from '@umbraco-cms/backoffice/extension-api';
|
||||
import { UmbDocumentTypeDetailRepository } from '@umbraco-cms/backoffice/document-type';
|
||||
import { UMB_MODAL_MANAGER_CONTEXT } from '@umbraco-cms/backoffice/modal';
|
||||
import type { ManifestBlockEditorCustomView } from '@umbraco-cms/backoffice/block-custom-view';
|
||||
|
||||
@customElement('umb-block-type-custom-view-guide')
|
||||
export class UmbBlockTypeCustomViewGuideElement extends UmbLitElement {
|
||||
@@ -88,7 +89,7 @@ export class UmbBlockTypeCustomViewGuideElement extends UmbLitElement {
|
||||
async #generateManifest() {
|
||||
const modalManager = await this.getContext(UMB_MODAL_MANAGER_CONTEXT);
|
||||
|
||||
const manifest = {
|
||||
const manifest: UmbExtensionManifest = {
|
||||
type: 'blockEditorCustomView',
|
||||
alias: 'Local.blockEditorCustomView.' + this.#contentTypeAlias,
|
||||
name: 'Block Editor Custom View for ' + this.#contentTypeName,
|
||||
|
||||
@@ -12,7 +12,7 @@ import {
|
||||
UMB_DOCUMENT_TYPE_PICKER_MODAL,
|
||||
} from '@umbraco-cms/backoffice/document-type';
|
||||
import { UmbSorterController } from '@umbraco-cms/backoffice/sorter';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
import '../block-type-card/index.js';
|
||||
|
||||
|
||||
@@ -1,6 +1,16 @@
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
export type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UUIModalSidebarSize } from '@umbraco-cms/backoffice/external/uui';
|
||||
|
||||
// Shared with the Property Editor
|
||||
export interface UmbBlockTypeBaseModel {
|
||||
contentElementTypeKey: string;
|
||||
settingsElementTypeKey?: string;
|
||||
label?: string;
|
||||
thumbnail?: string;
|
||||
iconColor?: string;
|
||||
backgroundColor?: string;
|
||||
editorSize?: UUIModalSidebarSize;
|
||||
forceHideContentEditorInOverlay: boolean;
|
||||
}
|
||||
export interface UmbBlockTypeGroup {
|
||||
name?: string;
|
||||
key: string;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import type { UmbBlockTypeWithGroupKey } from '../types.js';
|
||||
import type { UmbBlockTypeBaseModel, UmbBlockTypeWithGroupKey } from '../types.js';
|
||||
import { UmbBlockTypeWorkspaceEditorElement } from './block-type-workspace-editor.element.js';
|
||||
import type { UmbPropertyDatasetContext } from '@umbraco-cms/backoffice/property';
|
||||
import { UMB_PROPERTY_CONTEXT } from '@umbraco-cms/backoffice/property';
|
||||
@@ -13,7 +13,7 @@ import {
|
||||
} from '@umbraco-cms/backoffice/workspace';
|
||||
import { UmbObjectState, appendToFrozenArray } from '@umbraco-cms/backoffice/observable-api';
|
||||
import type { UmbControllerHost } from '@umbraco-cms/backoffice/controller-api';
|
||||
import type { ManifestWorkspace, UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { ManifestWorkspace } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export class UmbBlockTypeWorkspaceContext<BlockTypeData extends UmbBlockTypeWithGroupKey = UmbBlockTypeWithGroupKey>
|
||||
extends UmbSubmittableWorkspaceContextBase<BlockTypeData>
|
||||
|
||||
@@ -3,7 +3,7 @@ import type { UmbBlockWorkspaceOriginData } from '../workspace/block-workspace.m
|
||||
import type { UmbBlockEntriesContext } from './block-entries.context.js';
|
||||
import type { UMB_BLOCK_MANAGER_CONTEXT } from './block-manager.context-token.js';
|
||||
import { UmbContextToken } from '@umbraco-cms/backoffice/context-api';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
export const UMB_BLOCK_ENTRIES_CONTEXT = new UmbContextToken<
|
||||
UmbBlockEntriesContext<
|
||||
|
||||
@@ -4,10 +4,10 @@ import type { UmbBlockDataObjectModel, UmbBlockManagerContext } from './block-ma
|
||||
import { UMB_BLOCK_ENTRIES_CONTEXT } from './block-entries.context-token.js';
|
||||
import { type Observable, UmbArrayState, UmbBasicState, UmbStringState } from '@umbraco-cms/backoffice/observable-api';
|
||||
import { UmbContextBase } from '@umbraco-cms/backoffice/class-api';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbContextToken } from '@umbraco-cms/backoffice/context-api';
|
||||
import type { UmbControllerHost } from '@umbraco-cms/backoffice/controller-api';
|
||||
import type { UmbModalRouteBuilder } from '@umbraco-cms/backoffice/router';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
export abstract class UmbBlockEntriesContext<
|
||||
BlockManagerContextTokenType extends UmbContextToken<BlockManagerContextType, BlockManagerContextType>,
|
||||
|
||||
@@ -4,7 +4,7 @@ import type { UMB_BLOCK_ENTRIES_CONTEXT } from './block-entries.context-token.js
|
||||
import type { UmbBlockEntriesContext } from './block-entries.context.js';
|
||||
import type { UmbBlockEntryContext } from './block-entry.context.js';
|
||||
import type { UMB_BLOCK_MANAGER_CONTEXT } from './block-manager.context-token.js';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
import { UmbContextToken } from '@umbraco-cms/backoffice/context-api';
|
||||
|
||||
export const UMB_BLOCK_ENTRY_CONTEXT = new UmbContextToken<
|
||||
|
||||
@@ -15,7 +15,7 @@ import { encodeFilePath } from '@umbraco-cms/backoffice/utils';
|
||||
import { umbConfirmModal } from '@umbraco-cms/backoffice/modal';
|
||||
import type { UmbContentTypeModel } from '@umbraco-cms/backoffice/content-type';
|
||||
import type { Observable } from '@umbraco-cms/backoffice/external/rxjs';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
export abstract class UmbBlockEntryContext<
|
||||
BlockManagerContextTokenType extends UmbContextToken<BlockManagerContextType>,
|
||||
|
||||
@@ -5,12 +5,12 @@ import { UmbContextBase } from '@umbraco-cms/backoffice/class-api';
|
||||
import type { UmbControllerHost } from '@umbraco-cms/backoffice/controller-api';
|
||||
import { UmbArrayState, UmbBooleanState, UmbClassState, UmbStringState } from '@umbraco-cms/backoffice/observable-api';
|
||||
import { UmbDocumentTypeDetailRepository } from '@umbraco-cms/backoffice/document-type';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbContentTypeModel } from '@umbraco-cms/backoffice/content-type';
|
||||
import { UmbId } from '@umbraco-cms/backoffice/id';
|
||||
import type { UmbPropertyEditorConfigCollection } from '@umbraco-cms/backoffice/property-editor';
|
||||
import { UMB_PROPERTY_CONTEXT } from '@umbraco-cms/backoffice/property';
|
||||
import type { UmbVariantId } from '@umbraco-cms/backoffice/variant';
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
/**
|
||||
*
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
export * from './context/index.js';
|
||||
export * from './modals/index.js';
|
||||
export * from './types.js';
|
||||
export type * from './types.js';
|
||||
export * from './validation/index.js';
|
||||
export * from './workspace/index.js';
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import type { UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { UmbModalToken } from '@umbraco-cms/backoffice/modal';
|
||||
import type { UmbBlockWorkspaceData } from '@umbraco-cms/backoffice/block';
|
||||
import type { UmbBlockTypeGroup } from '@umbraco-cms/backoffice/block-type';
|
||||
import type { UmbBlockTypeGroup, UmbBlockTypeBaseModel } from '@umbraco-cms/backoffice/block-type';
|
||||
|
||||
export interface UmbBlockCatalogueModalData {
|
||||
blocks: Array<UmbBlockTypeBaseModel>;
|
||||
|
||||
@@ -1,5 +1,15 @@
|
||||
import type { UmbBlockDataType, UmbBlockLayoutBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
export type { UmbBlockDataType, UmbBlockLayoutBaseModel } from '@umbraco-cms/backoffice/extension-registry';
|
||||
// Shared with the Property Editor
|
||||
export interface UmbBlockLayoutBaseModel {
|
||||
contentUdi: string;
|
||||
settingsUdi?: string | null;
|
||||
}
|
||||
|
||||
// Shared with the Property Editor
|
||||
export interface UmbBlockDataType {
|
||||
udi: string;
|
||||
contentTypeKey: string;
|
||||
[key: string]: unknown;
|
||||
}
|
||||
|
||||
export interface UmbBlockValueType<BlockLayoutType extends UmbBlockLayoutBaseModel> {
|
||||
layout: { [key: string]: Array<BlockLayoutType> | undefined };
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import type { UmbBlockDataType, UmbBlockEditorCustomViewElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbBlockDataType } from '@umbraco-cms/backoffice/block';
|
||||
import type { UmbBlockEditorCustomViewElement } from '@umbraco-cms/backoffice/block-custom-view';
|
||||
import { css, customElement, html, property } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
|
||||
|
||||
@@ -1,6 +1,4 @@
|
||||
import type { ManifestBlockEditorCustomView } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifest: ManifestBlockEditorCustomView = {
|
||||
export const manifest: UmbExtensionManifest = {
|
||||
type: 'blockEditorCustomView',
|
||||
alias: 'Umb.blockEditorCustomView.TestView',
|
||||
name: 'Block Editor Custom View Test',
|
||||
|
||||
@@ -12,6 +12,7 @@ export default defineConfig({
|
||||
dist,
|
||||
entry: {
|
||||
'block/index': 'block/index.ts',
|
||||
'block-custom-view/index': 'block-custom-view/index.ts',
|
||||
'block-grid/index': 'block-grid/index.ts',
|
||||
'block-list/index': 'block-list/index.ts',
|
||||
'block-rte/index': 'block-rte/index.ts',
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
export * from './block-editor-custom-view-element.interface.js';
|
||||
export * from './dashboard-element.interface.js';
|
||||
export * from './external-login-provider-element.interface.js';
|
||||
export * from './menu-item-element.interface.js';
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import type { ManifestAuthProvider } from './auth-provider.model.js';
|
||||
import type { ManifestBlockEditorCustomView } from './block-editor-custom-view.model.js';
|
||||
import type { ManifestCollection } from './collection.models.js';
|
||||
import type { ManifestCollectionView } from './collection-view.model.js';
|
||||
import type { ManifestCurrentUserAction, ManifestCurrentUserActionDefaultKind } from './current-user-action.model.js';
|
||||
@@ -30,7 +29,7 @@ import type { ManifestHealthCheck } from './health-check.model.js';
|
||||
import type { ManifestIcons } from './icons.model.js';
|
||||
import type { ManifestLocalization } from './localization.model.js';
|
||||
import type { ManifestMenu } from './menu.model.js';
|
||||
import type { ManifestMenuItem, ManifestMenuItemTreeKind } from './menu-item.model.js';
|
||||
import type { ManifestMenuItem, ManifestMenuItemLinkKind, ManifestMenuItemTreeKind } from './menu-item.model.js';
|
||||
import type { ManifestModal } from './modal.model.js';
|
||||
import type { ManifestPackageView } from './package-view.model.js';
|
||||
import type { ManifestPreviewAppProvider } from './preview-app.model.js';
|
||||
@@ -78,7 +77,6 @@ import type { ManifestBase, ManifestBundle, ManifestCondition } from '@umbraco-c
|
||||
export type * from './app-entry-point.model.js';
|
||||
export type * from './auth-provider.model.js';
|
||||
export type * from './backoffice-entry-point.model.js';
|
||||
export type * from './block-editor-custom-view.model.js';
|
||||
export type * from './collection-action.model.js';
|
||||
export type * from './collection-view.model.js';
|
||||
export type * from './collection.models.js';
|
||||
@@ -160,7 +158,6 @@ export type ManifestTypes =
|
||||
| ManifestAppEntryPoint
|
||||
| ManifestAuthProvider
|
||||
| ManifestBackofficeEntryPoint
|
||||
| ManifestBlockEditorCustomView
|
||||
| ManifestBundle<ManifestTypes>
|
||||
| ManifestCollection
|
||||
| ManifestCollectionAction
|
||||
@@ -188,6 +185,7 @@ export type ManifestTypes =
|
||||
| ManifestMenu
|
||||
| ManifestMenuItem
|
||||
| ManifestMenuItemTreeKind
|
||||
| ManifestMenuItemLinkKind
|
||||
| ManifestMfaLoginProvider
|
||||
| ManifestModal
|
||||
| ManifestMonacoMarkdownEditorAction
|
||||
@@ -221,3 +219,36 @@ export type ManifestTypes =
|
||||
| ManifestWorkspaces
|
||||
| ManifestWorkspaceViews
|
||||
| ManifestBase;
|
||||
|
||||
type UnionOfProperties<T> = T extends object ? T[keyof T] : never;
|
||||
|
||||
declare global {
|
||||
/**
|
||||
* This global type allows to declare manifests types from its own module.
|
||||
* @example
|
||||
```js
|
||||
declare global {
|
||||
interface UmbExtensionManifestMap {
|
||||
My_UNIQUE_MANIFEST_NAME: MyExtensionManifestType;
|
||||
}
|
||||
}
|
||||
```
|
||||
If you have multiple types, you can declare them in this way:
|
||||
```js
|
||||
declare global {
|
||||
interface UmbExtensionManifestMap {
|
||||
My_UNIQUE_MANIFEST_NAME: MyExtensionManifestTypeA | MyExtensionManifestTypeB;
|
||||
}
|
||||
}
|
||||
```
|
||||
*/
|
||||
interface UmbExtensionManifestMap {
|
||||
UMB_CORE: ManifestTypes;
|
||||
}
|
||||
|
||||
/**
|
||||
* This global type provides a union of all declared manifest types.
|
||||
* If this is a local package that declares additional Manifest Types, then these will also be included in this union.
|
||||
*/
|
||||
type UmbExtensionManifest = UnionOfProperties<UmbExtensionManifestMap>;
|
||||
}
|
||||
|
||||
@@ -26,3 +26,13 @@ export interface MetaMenuItemTreeKind extends MetaMenuItem {
|
||||
treeAlias: string;
|
||||
hideTreeRoot?: boolean;
|
||||
}
|
||||
|
||||
export interface ManifestMenuItemLinkKind extends ManifestMenuItem {
|
||||
type: 'menuItem';
|
||||
kind: 'link';
|
||||
meta: MetaMenuItemLinkKind;
|
||||
}
|
||||
|
||||
export interface MetaMenuItemLinkKind extends MetaMenuItem {
|
||||
href: string;
|
||||
}
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
import type { ManifestTypes } from './models/index.js';
|
||||
import type { ManifestKind } from '@umbraco-cms/backoffice/extension-api';
|
||||
import { UmbExtensionRegistry } from '@umbraco-cms/backoffice/extension-api';
|
||||
|
||||
export type UmbBackofficeManifestKind = ManifestKind<ManifestTypes>;
|
||||
export type UmbBackofficeExtensionRegistry = UmbExtensionRegistry<ManifestTypes>;
|
||||
export type UmbBackofficeManifestKind = ManifestKind<UmbExtensionManifest>;
|
||||
export type UmbBackofficeExtensionRegistry = UmbExtensionRegistry<UmbExtensionManifest>;
|
||||
|
||||
export const umbExtensionsRegistry = new UmbExtensionRegistry<ManifestTypes>() as UmbBackofficeExtensionRegistry;
|
||||
export const umbExtensionsRegistry = new UmbExtensionRegistry<UmbExtensionManifest>() as UmbBackofficeExtensionRegistry;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import type { ManifestTypes } from './models/index.js';
|
||||
import './models/index.js';
|
||||
|
||||
/**
|
||||
* Umbraco package manifest JSON
|
||||
@@ -37,7 +37,7 @@ export interface UmbracoPackage {
|
||||
* @title An array of Umbraco package manifest types that will be installed
|
||||
* @required
|
||||
*/
|
||||
extensions: ManifestTypes[];
|
||||
extensions: UmbExtensionManifest[];
|
||||
|
||||
/**
|
||||
* @title The importmap for the package
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
export * from '@umbraco-cms/backoffice/extension-registry';
|
||||
@@ -9,6 +9,7 @@ import { manifests as entityBulkActionManifests } from './entity-bulk-action/man
|
||||
import { manifests as extensionManifests } from './extension-registry/manifests.js';
|
||||
import { manifests as iconRegistryManifests } from './icon-registry/manifests.js';
|
||||
import { manifests as localizationManifests } from './localization/manifests.js';
|
||||
import { manifests as menuManifests } from './menu/manifests.js';
|
||||
import { manifests as modalManifests } from './modal/common/manifests.js';
|
||||
import { manifests as pickerManifests } from './picker/manifests.js';
|
||||
import { manifests as propertyActionManifests } from './property-action/manifests.js';
|
||||
@@ -35,6 +36,7 @@ export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [
|
||||
...extensionManifests,
|
||||
...iconRegistryManifests,
|
||||
...localizationManifests,
|
||||
...menuManifests,
|
||||
...modalManifests,
|
||||
...pickerManifests,
|
||||
...propertyActionManifests,
|
||||
|
||||
@@ -37,6 +37,15 @@ export class UmbMenuItemLayoutElement extends UmbLitElement {
|
||||
@property({ type: String })
|
||||
public href?: string;
|
||||
|
||||
/**
|
||||
* Set an anchor tag target, only used when using href.
|
||||
* @type {string}
|
||||
* @attr
|
||||
* @default undefined
|
||||
*/
|
||||
@property({ type: String })
|
||||
public target?: '_blank' | '_parent' | '_self' | '_top';
|
||||
|
||||
@state()
|
||||
private _isActive = false;
|
||||
|
||||
@@ -63,7 +72,8 @@ export class UmbMenuItemLayoutElement extends UmbLitElement {
|
||||
label=${this.label}
|
||||
.caretLabel=${this.localize.term('visuallyHiddenTexts_expandChildItems') + ' ' + this.label}
|
||||
?active=${this._isActive}
|
||||
?has-children=${this.hasChildren}>
|
||||
?has-children=${this.hasChildren}
|
||||
target=${ifDefined(this.href && this.target ? this.target : undefined)}>
|
||||
<umb-icon slot="icon" name=${this.iconName}></umb-icon>
|
||||
${this.entityType
|
||||
? html`<umb-entity-actions-bundle
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
import { customElement, html, property } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import type { ManifestMenuItemLinkKind, UmbMenuItemElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
const elementName = 'umb-link-menu-item';
|
||||
@customElement(elementName)
|
||||
export class UmbLinkMenuItemElement extends UmbLitElement implements UmbMenuItemElement {
|
||||
@property({ type: Object, attribute: false })
|
||||
manifest?: ManifestMenuItemLinkKind;
|
||||
|
||||
#getTarget() {
|
||||
const href = this.manifest?.meta.href;
|
||||
|
||||
if (href && href.startsWith('http')) {
|
||||
return '_blank';
|
||||
}
|
||||
|
||||
return '_self';
|
||||
}
|
||||
|
||||
override render() {
|
||||
return html`
|
||||
<umb-menu-item-layout
|
||||
.href=${this.manifest?.meta.href}
|
||||
target=${this.#getTarget()}
|
||||
.iconName=${this.manifest?.meta.icon ?? ''}
|
||||
.label=${this.localize.string(this.manifest?.meta.label ?? this.manifest?.name ?? '')}>
|
||||
</umb-menu-item-layout>
|
||||
`;
|
||||
}
|
||||
}
|
||||
|
||||
export { UmbLinkMenuItemElement as element };
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
[elementName]: UmbLinkMenuItemElement;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
import type { ManifestTypes, UmbBackofficeManifestKind } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [
|
||||
{
|
||||
type: 'kind',
|
||||
alias: 'Umb.Kind.MenuItem.Link',
|
||||
matchKind: 'link',
|
||||
matchType: 'menuItem',
|
||||
manifest: {
|
||||
type: 'menuItem',
|
||||
element: () => import('./link-menu-item.element.js'),
|
||||
},
|
||||
},
|
||||
];
|
||||
@@ -0,0 +1,4 @@
|
||||
import { manifests as linkManifests } from './link/manifests.js';
|
||||
import type { ManifestTypes, UmbBackofficeManifestKind } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [...linkManifests];
|
||||
@@ -0,0 +1,4 @@
|
||||
import { manifests as menuItemManifests } from './components/menu-item/manifests.js';
|
||||
import type { ManifestTypes, UmbBackofficeManifestKind } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [...menuItemManifests];
|
||||
@@ -0,0 +1,77 @@
|
||||
import { UMB_HELP_MENU_ALIAS } from '../menu/index.js';
|
||||
import type { CSSResultGroup } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { css, html, customElement, state, nothing } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbHeaderAppButtonElement } from '@umbraco-cms/backoffice/components';
|
||||
import { umbExtensionsRegistry, type ManifestMenu } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { UmbExtensionsManifestInitializer } from '@umbraco-cms/backoffice/extension-api';
|
||||
|
||||
const elementName = 'umb-help-header-app';
|
||||
@customElement(elementName)
|
||||
export class UmbHelpHeaderAppElement extends UmbHeaderAppButtonElement {
|
||||
@state()
|
||||
private _popoverOpen = false;
|
||||
|
||||
@state()
|
||||
private _helpMenuHasMenuItems = false;
|
||||
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
new UmbExtensionsManifestInitializer(
|
||||
this,
|
||||
umbExtensionsRegistry,
|
||||
'menuItem',
|
||||
(manifest) => manifest.meta.menus.includes(UMB_HELP_MENU_ALIAS),
|
||||
(menuItems) => {
|
||||
const manifests = menuItems.map((menuItem) => menuItem.manifest);
|
||||
this._helpMenuHasMenuItems = manifests.length > 0;
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
#onPopoverToggle(event: ToggleEvent) {
|
||||
// TODO: This ignorer is just neede for JSON SCHEMA TO WORK, As its not updated with latest TS jet.
|
||||
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
||||
// @ts-ignore
|
||||
this._popoverOpen = event.newState === 'open';
|
||||
}
|
||||
|
||||
override render() {
|
||||
return html` ${this.#renderButton()} ${this.#renderPopover()} `;
|
||||
}
|
||||
|
||||
#renderButton() {
|
||||
if (!this._helpMenuHasMenuItems) return nothing;
|
||||
|
||||
return html`
|
||||
<uui-button popovertarget="help-menu-popover" look="primary" label="help" compact>
|
||||
<uui-icon name="icon-help-alt"></uui-icon>
|
||||
</uui-button>
|
||||
`;
|
||||
}
|
||||
|
||||
#renderPopover() {
|
||||
return html`
|
||||
<uui-popover-container id="help-menu-popover" @toggle=${this.#onPopoverToggle}>
|
||||
<umb-popover-layout>
|
||||
<uui-scroll-container>
|
||||
<umb-extension-slot
|
||||
type="menu"
|
||||
.filter="${(menu: ManifestMenu) => menu.alias === UMB_HELP_MENU_ALIAS}"
|
||||
default-element="umb-menu"></umb-extension-slot>
|
||||
</uui-scroll-container>
|
||||
</umb-popover-layout>
|
||||
</uui-popover-container>
|
||||
`;
|
||||
}
|
||||
|
||||
static override styles: CSSResultGroup = [UmbHeaderAppButtonElement.styles, css``];
|
||||
}
|
||||
|
||||
export { UmbHelpHeaderAppElement as element };
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
[elementName]: UmbHelpHeaderAppElement;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
import type { ManifestTypes, UmbBackofficeManifestKind } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [
|
||||
{
|
||||
type: 'headerApp',
|
||||
alias: 'Umb.HeaderApp.Help',
|
||||
name: 'Help Header App',
|
||||
element: () => import('./help-header-app.element.js'),
|
||||
weight: 500,
|
||||
},
|
||||
];
|
||||
1
src/Umbraco.Web.UI.Client/src/packages/help/index.ts
Normal file
1
src/Umbraco.Web.UI.Client/src/packages/help/index.ts
Normal file
@@ -0,0 +1 @@
|
||||
export * from './menu/index.js';
|
||||
5
src/Umbraco.Web.UI.Client/src/packages/help/manifests.ts
Normal file
5
src/Umbraco.Web.UI.Client/src/packages/help/manifests.ts
Normal file
@@ -0,0 +1,5 @@
|
||||
import { manifests as headerAppManifests } from './header-app/manifests.js';
|
||||
import { manifests as menuManifests } from './menu/manifests.js';
|
||||
import type { ManifestTypes, UmbBackofficeManifestKind } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [...menuManifests, ...headerAppManifests];
|
||||
@@ -0,0 +1 @@
|
||||
export const UMB_HELP_MENU_ALIAS = 'Umb.Menu.Help';
|
||||
@@ -0,0 +1 @@
|
||||
export * from './constants.js';
|
||||
@@ -0,0 +1,47 @@
|
||||
import { UMB_HELP_MENU_ALIAS } from './constants.js';
|
||||
import { UMB_CURRENT_USER_IS_ADMIN_CONDITION_ALIAS } from '@umbraco-cms/backoffice/current-user';
|
||||
import type { ManifestTypes, UmbBackofficeManifestKind } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [
|
||||
{
|
||||
type: 'menu',
|
||||
alias: UMB_HELP_MENU_ALIAS,
|
||||
name: 'Help Menu',
|
||||
},
|
||||
{
|
||||
type: 'menuItem',
|
||||
kind: 'link',
|
||||
alias: 'Umb.MenuItem.Help.LearningBase',
|
||||
name: 'Learning Base Help Menu Item',
|
||||
weight: 200,
|
||||
meta: {
|
||||
menus: [UMB_HELP_MENU_ALIAS],
|
||||
label: 'Umbraco Learning Base',
|
||||
icon: 'icon-movie-alt',
|
||||
href: 'https://umbra.co/ulb',
|
||||
},
|
||||
conditions: [
|
||||
{
|
||||
alias: UMB_CURRENT_USER_IS_ADMIN_CONDITION_ALIAS,
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
type: 'menuItem',
|
||||
kind: 'link',
|
||||
alias: 'Umb.MenuItem.Help.CommunityWebsite',
|
||||
name: 'Community Website Help Menu Item',
|
||||
weight: 100,
|
||||
meta: {
|
||||
menus: [UMB_HELP_MENU_ALIAS],
|
||||
label: 'Community Website',
|
||||
icon: 'icon-hearts',
|
||||
href: 'https://our.umbraco.com?utm_source=core&utm_medium=help&utm_content=link&utm_campaign=our',
|
||||
},
|
||||
conditions: [
|
||||
{
|
||||
alias: UMB_CURRENT_USER_IS_ADMIN_CONDITION_ALIAS,
|
||||
},
|
||||
],
|
||||
},
|
||||
];
|
||||
8
src/Umbraco.Web.UI.Client/src/packages/help/package.json
Normal file
8
src/Umbraco.Web.UI.Client/src/packages/help/package.json
Normal file
@@ -0,0 +1,8 @@
|
||||
{
|
||||
"name": "@umbraco-backoffice/help",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"build": "vite build"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
export const name = 'Umbraco.Core.Help';
|
||||
export const extensions = [
|
||||
{
|
||||
name: 'Help Bundle',
|
||||
alias: 'Umb.Bundle.Help',
|
||||
type: 'bundle',
|
||||
js: () => import('./manifests.js'),
|
||||
},
|
||||
];
|
||||
12
src/Umbraco.Web.UI.Client/src/packages/help/vite.config.ts
Normal file
12
src/Umbraco.Web.UI.Client/src/packages/help/vite.config.ts
Normal file
@@ -0,0 +1,12 @@
|
||||
import { defineConfig } from 'vite';
|
||||
import { rmSync } from 'fs';
|
||||
import { getDefaultConfig } from '../../vite-config-base';
|
||||
|
||||
const dist = '../../../dist-cms/packages/help';
|
||||
|
||||
// delete the unbundled dist folder
|
||||
rmSync(dist, { recursive: true, force: true });
|
||||
|
||||
export default defineConfig({
|
||||
...getDefaultConfig({ dist }),
|
||||
});
|
||||
@@ -1,6 +1,6 @@
|
||||
import { UmbInputBlockTypeElement } from '@umbraco-cms/backoffice/block-type';
|
||||
import { type UmbBlockTypeBaseModel, UmbInputBlockTypeElement } from '@umbraco-cms/backoffice/block-type';
|
||||
import { UMB_BLOCK_RTE_TYPE } from '@umbraco-cms/backoffice/block-rte';
|
||||
import type { UmbBlockTypeBaseModel, UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { html, customElement, property, state, nothing } from '@umbraco-cms/backoffice/external/lit';
|
||||
import {
|
||||
UmbPropertyValueChangeEvent,
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
export * from './is-admin/index.js';
|
||||
@@ -0,0 +1 @@
|
||||
export const UMB_CURRENT_USER_IS_ADMIN_CONDITION_ALIAS = 'Umb.Condition.CurrentUser.IsAdmin';
|
||||
@@ -0,0 +1 @@
|
||||
export * from './constants.js';
|
||||
@@ -0,0 +1,9 @@
|
||||
import { UMB_CURRENT_USER_IS_ADMIN_CONDITION_ALIAS } from './constants.js';
|
||||
import type { ManifestCondition } from '@umbraco-cms/backoffice/extension-api';
|
||||
|
||||
export const manifest: ManifestCondition = {
|
||||
type: 'condition',
|
||||
name: 'Current user is admin Condition',
|
||||
alias: UMB_CURRENT_USER_IS_ADMIN_CONDITION_ALIAS,
|
||||
api: () => import('./is-admin.condition.js'),
|
||||
};
|
||||
@@ -0,0 +1,20 @@
|
||||
import { isCurrentUserAnAdmin } from '../../utils/is-current-user.function.js';
|
||||
import type { UmbControllerHost } from '@umbraco-cms/backoffice/controller-api';
|
||||
import type {
|
||||
UmbConditionConfigBase,
|
||||
UmbConditionControllerArguments,
|
||||
UmbExtensionCondition,
|
||||
} from '@umbraco-cms/backoffice/extension-api';
|
||||
import { UmbConditionBase } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export class UmbContentHasPropertiesWorkspaceCondition
|
||||
extends UmbConditionBase<UmbConditionConfigBase>
|
||||
implements UmbExtensionCondition
|
||||
{
|
||||
constructor(host: UmbControllerHost, args: UmbConditionControllerArguments<UmbConditionConfigBase>) {
|
||||
super(host, args);
|
||||
isCurrentUserAnAdmin(host).then((isAdmin) => (this.permitted = isAdmin));
|
||||
}
|
||||
}
|
||||
|
||||
export { UmbContentHasPropertiesWorkspaceCondition as api };
|
||||
@@ -0,0 +1,3 @@
|
||||
import { manifest as isAdminManifests } from './is-admin/is-admin.condition.manifest.js';
|
||||
|
||||
export const manifests = [isAdminManifests];
|
||||
@@ -1,9 +1,10 @@
|
||||
export * from './action/index.js';
|
||||
export * from './components/index.js';
|
||||
export * from './history/current-user-history.store.js';
|
||||
export * from './utils/index.js';
|
||||
export * from './repository/index.js';
|
||||
export * from './conditions/index.js';
|
||||
export * from './current-user.context.js';
|
||||
export * from './current-user.context.token.js';
|
||||
export * from './history/current-user-history.store.js';
|
||||
export * from './repository/index.js';
|
||||
export * from './utils/index.js';
|
||||
|
||||
export type * from './types.js';
|
||||
|
||||
@@ -1,11 +1,13 @@
|
||||
import { manifest as actionDefaultKindManifest } from './action/default.kind.js';
|
||||
import { manifests as modalManifests } from './modals/manifests.js';
|
||||
import { manifests as historyManifests } from './history/manifests.js';
|
||||
import { manifests as conditionManifests } from './conditions/manifests.js';
|
||||
import { manifests as externalLoginProviderManifests } from './external-login/manifests.js';
|
||||
import { manifests as historyManifests } from './history/manifests.js';
|
||||
import { manifests as mfaLoginProviderManifests } from './mfa-login/manifests.js';
|
||||
import { manifests as modalManifests } from './modals/manifests.js';
|
||||
import { manifests as profileManifests } from './profile/manifests.js';
|
||||
import { manifests as themeManifests } from './theme/manifests.js';
|
||||
import { manifests as repositoryManifests } from './repository/manifests.js';
|
||||
import { manifests as themeManifests } from './theme/manifests.js';
|
||||
|
||||
import type { ManifestTypes } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const headerApps: Array<ManifestTypes> = [
|
||||
@@ -21,19 +23,15 @@ export const headerApps: Array<ManifestTypes> = [
|
||||
name: 'Current User',
|
||||
element: () => import('./current-user-header-app.element.js'),
|
||||
weight: 0,
|
||||
meta: {
|
||||
label: 'TODO: how should we enable this to not be set.',
|
||||
icon: 'TODO: how should we enable this to not be set.',
|
||||
pathname: 'user',
|
||||
},
|
||||
},
|
||||
];
|
||||
|
||||
export const manifests = [
|
||||
actionDefaultKindManifest,
|
||||
...conditionManifests,
|
||||
...externalLoginProviderManifests,
|
||||
...headerApps,
|
||||
...historyManifests,
|
||||
...externalLoginProviderManifests,
|
||||
...mfaLoginProviderManifests,
|
||||
...modalManifests,
|
||||
...profileManifests,
|
||||
|
||||
@@ -7,6 +7,7 @@ import type {
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import { css, html, customElement, query } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbModalBaseElement } from '@umbraco-cms/backoffice/modal';
|
||||
import type { UUIInputElement } from '@umbraco-cms/backoffice/external/uui';
|
||||
|
||||
const elementName = 'umb-create-user-client-credential-modal';
|
||||
@customElement(elementName)
|
||||
@@ -17,10 +18,27 @@ export class UmbCreateUserModalElement extends UmbModalBaseElement<
|
||||
@query('#CreateUserClientCredentialForm')
|
||||
_form?: HTMLFormElement;
|
||||
|
||||
@query('#unique')
|
||||
_inputUniqueElement?: UUIInputElement;
|
||||
|
||||
#userClientCredentialRepository = new UmbUserClientCredentialRepository(this);
|
||||
|
||||
#uniquePrefix = 'umbraco-back-office-';
|
||||
|
||||
protected override firstUpdated(): void {
|
||||
// For some reason the pattern attribute is not working with this specific regex. It complains about the regex is invalid.
|
||||
// TODO: investigate why this is happening.
|
||||
this._inputUniqueElement?.addValidator(
|
||||
'patternMismatch',
|
||||
() => 'Only alphanumeric characters and hyphens are allowed',
|
||||
() => {
|
||||
const value = (this._inputUniqueElement?.value as string) || '';
|
||||
// eslint-disable-next-line no-useless-escape
|
||||
return !new RegExp(/^[a-zA-Z0-9\-]+$/).test(value);
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
async #onSubmit(e: SubmitEvent) {
|
||||
e.preventDefault();
|
||||
|
||||
|
||||
@@ -9,7 +9,6 @@ import { manifests as propertyEditorManifests } from './property-editor/manifest
|
||||
import { manifests as repositoryManifests } from './repository/manifests.js';
|
||||
import { manifests as workspaceManifests } from './workspace/manifests.js';
|
||||
import { manifests as menuItemManifests } from './menu-item/manifests.js';
|
||||
|
||||
import type { ManifestTypes, UmbBackofficeManifestKind } from '@umbraco-cms/backoffice/extension-registry';
|
||||
|
||||
export const manifests: Array<ManifestTypes | UmbBackofficeManifestKind> = [
|
||||
|
||||
@@ -45,6 +45,7 @@ DON'T EDIT THIS FILE DIRECTLY. It is generated by /devops/tsconfig/index.js
|
||||
"@umbraco-cms/backoffice/action": ["./src/packages/core/action/index.ts"],
|
||||
"@umbraco-cms/backoffice/audit-log": ["./src/packages/core/audit-log/index.ts"],
|
||||
"@umbraco-cms/backoffice/auth": ["./src/packages/core/auth/index.ts"],
|
||||
"@umbraco-cms/backoffice/block-custom-view": ["./src/packages/block/block-custom-view/index.ts"],
|
||||
"@umbraco-cms/backoffice/block-grid": ["./src/packages/block/block-grid/index.ts"],
|
||||
"@umbraco-cms/backoffice/block-list": ["./src/packages/block/block-list/index.ts"],
|
||||
"@umbraco-cms/backoffice/block-rte": ["./src/packages/block/block-rte/index.ts"],
|
||||
@@ -69,6 +70,7 @@ DON'T EDIT THIS FILE DIRECTLY. It is generated by /devops/tsconfig/index.js
|
||||
"@umbraco-cms/backoffice/entity": ["./src/packages/core/entity/index.ts"],
|
||||
"@umbraco-cms/backoffice/event": ["./src/packages/core/event/index.ts"],
|
||||
"@umbraco-cms/backoffice/extension-registry": ["./src/packages/core/extension-registry/index.ts"],
|
||||
"@umbraco-cms/backoffice/help": ["./src/packages/help/index.ts"],
|
||||
"@umbraco-cms/backoffice/icon": ["./src/packages/core/icon-registry/index.ts"],
|
||||
"@umbraco-cms/backoffice/id": ["./src/packages/core/id/index.ts"],
|
||||
"@umbraco-cms/backoffice/imaging": ["./src/packages/media/imaging/index.ts"],
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
"name": "My Dashboard",
|
||||
"alias": "myDashboard",
|
||||
|
||||
|
||||
"weight": -10,
|
||||
"elementName": "my-dashboard",
|
||||
"js": "js/my-dashboard.js",
|
||||
Reference in New Issue
Block a user