Skip to content
This repository was archived by the owner on Nov 6, 2025. It is now read-only.

Commit 79323dd

Browse files
authored
Merge pull request #2153 from umbraco/v14/feature/media-member-compositions
Feature: media & member compositions
2 parents bc55443 + 054c263 commit 79323dd

File tree

21 files changed

+324
-23
lines changed

21 files changed

+324
-23
lines changed

src/packages/core/content-type/modals/composition-picker/composition-picker-modal.element.ts

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -90,17 +90,18 @@ export class UmbCompositionPickerModalElement extends UmbModalBaseElement<
9090
await this.#init;
9191
if (!this.#compositionRepository) return;
9292

93-
const isElement = this.data?.isElement;
94-
const currentPropertyAliases = this.data?.currentPropertyAliases;
93+
// Notice isElement is not available on all types that can be composed.
94+
const isElement = this.data?.isElement ?? undefined;
95+
const currentPropertyAliases = this.data?.currentPropertyAliases ?? [];
9596

9697
const { data } = await this.#compositionRepository.availableCompositions({
9798
unique: this.#unique,
9899
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
99100
// @ts-ignore
100101
// TODO: isElement is not available on all types that can be composed.
101-
isElement: isElement ?? false,
102+
isElement: isElement,
102103
currentCompositeUniques: this._selection,
103-
currentPropertyAliases: currentPropertyAliases ?? [],
104+
currentPropertyAliases: currentPropertyAliases,
104105
});
105106

106107
if (!data) return;
Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,2 +1 @@
1-
export { UmbDocumentTypeCompositionRepository } from './document-type-composition.repository.js';
21
export { UMB_DOCUMENT_TYPE_COMPOSITION_REPOSITORY_ALIAS } from './manifests.js';

src/packages/documents/document-types/repository/composition/manifests.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,11 +2,11 @@ import type { ManifestRepository, ManifestTypes } from '@umbraco-cms/backoffice/
22

33
export const UMB_DOCUMENT_TYPE_COMPOSITION_REPOSITORY_ALIAS = 'Umb.Repository.DocumentType.Composition';
44

5-
const queryRepository: ManifestRepository = {
5+
const compositionRepository: ManifestRepository = {
66
type: 'repository',
77
alias: UMB_DOCUMENT_TYPE_COMPOSITION_REPOSITORY_ALIAS,
88
name: 'Document Type Composition Repository',
99
api: () => import('./document-type-composition.repository.js'),
1010
};
1111

12-
export const manifests: Array<ManifestTypes> = [queryRepository];
12+
export const manifests: Array<ManifestTypes> = [compositionRepository];
Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,11 @@
11
import './components/index.js';
22

33
export * from './components/index.js';
4-
export * from './workspace/index.js';
5-
4+
export * from './entity.js';
65
export * from './repository/index.js';
76
export * from './tree/types.js';
8-
export * from './utils.ts/index.js';
97
export * from './types.js';
10-
export * from './entity.js';
8+
export * from './utils.ts/index.js';
9+
export * from './workspace/index.js';
1110

1211
export { UMB_MEDIA_TYPE_PICKER_MODAL } from './tree/index.js';
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export { UMB_MEDIA_TYPE_COMPOSITION_REPOSITORY_ALIAS } from './manifests.js';
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
import type { ManifestRepository, ManifestTypes } from '@umbraco-cms/backoffice/extension-registry';
2+
3+
export const UMB_MEDIA_TYPE_COMPOSITION_REPOSITORY_ALIAS = 'Umb.Repository.MediaType.Composition';
4+
5+
const compositionRepository: ManifestRepository = {
6+
type: 'repository',
7+
alias: UMB_MEDIA_TYPE_COMPOSITION_REPOSITORY_ALIAS,
8+
name: 'Media Type Composition Repository',
9+
api: () => import('./media-type-composition.repository.js'),
10+
};
11+
12+
export const manifests: Array<ManifestTypes> = [compositionRepository];
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
import { UmbMediaTypeCompositionServerDataSource } from './media-type-composition.server.data-source.js';
2+
import type { UmbContentTypeCompositionRepository } from '@umbraco-cms/backoffice/content-type';
3+
import type { UmbControllerHost } from '@umbraco-cms/backoffice/controller-api';
4+
import type {
5+
UmbMediaTypeAvailableCompositionRequestModel,
6+
UmbMediaTypeCompositionCompatibleModel,
7+
UmbMediaTypeCompositionReferenceModel,
8+
} from '@umbraco-cms/backoffice/media-type';
9+
import { UmbRepositoryBase } from '@umbraco-cms/backoffice/repository';
10+
11+
export class UmbMediaTypeCompositionRepository
12+
extends UmbRepositoryBase
13+
implements
14+
UmbContentTypeCompositionRepository<
15+
UmbMediaTypeCompositionReferenceModel,
16+
UmbMediaTypeCompositionCompatibleModel,
17+
UmbMediaTypeAvailableCompositionRequestModel
18+
>
19+
{
20+
#compositionSource: UmbMediaTypeCompositionServerDataSource;
21+
22+
constructor(host: UmbControllerHost) {
23+
super(host);
24+
this.#compositionSource = new UmbMediaTypeCompositionServerDataSource(this);
25+
}
26+
27+
async getReferences(unique: string) {
28+
return this.#compositionSource.getReferences(unique);
29+
}
30+
31+
async availableCompositions(args: UmbMediaTypeAvailableCompositionRequestModel) {
32+
return this.#compositionSource.availableCompositions(args);
33+
}
34+
}
35+
36+
export { UmbMediaTypeCompositionRepository as api };
Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
import type {
2+
UmbMediaTypeCompositionCompatibleModel,
3+
UmbMediaTypeCompositionReferenceModel,
4+
UmbMediaTypeAvailableCompositionRequestModel,
5+
} from '../../types.js';
6+
import { type MediaTypeCompositionRequestModel, MediaTypeService } from '@umbraco-cms/backoffice/external/backend-api';
7+
import type { UmbControllerHost } from '@umbraco-cms/backoffice/controller-api';
8+
import { tryExecuteAndNotify } from '@umbraco-cms/backoffice/resources';
9+
import type { UmbContentTypeCompositionDataSource } from '@umbraco-cms/backoffice/content-type';
10+
11+
/**
12+
* A data source for the Media Type Composition that fetches data from the server
13+
* @export
14+
* @class UmbMediaTypeCompositionServerDataSource
15+
*/
16+
export class UmbMediaTypeCompositionServerDataSource
17+
implements
18+
UmbContentTypeCompositionDataSource<
19+
UmbMediaTypeCompositionReferenceModel,
20+
UmbMediaTypeCompositionCompatibleModel,
21+
UmbMediaTypeAvailableCompositionRequestModel
22+
>
23+
{
24+
#host: UmbControllerHost;
25+
26+
/**
27+
* Creates an instance of UmbMediaTypeCompositionServerDataSource.
28+
* @param {UmbControllerHost} host
29+
* @memberof UmbMediaTypeCompositionServerDataSource
30+
*/
31+
constructor(host: UmbControllerHost) {
32+
this.#host = host;
33+
}
34+
/**
35+
* Fetches the compatible compositions for a Media type from the server
36+
* @param {string} unique
37+
* @return {*}
38+
* @memberof UmbMediaTypeCompositionServerDataSource
39+
*/
40+
async getReferences(unique: string) {
41+
const response = await tryExecuteAndNotify(
42+
this.#host,
43+
MediaTypeService.getMediaTypeByIdCompositionReferences({ id: unique }),
44+
);
45+
const error = response.error;
46+
const data: Array<UmbMediaTypeCompositionReferenceModel> | undefined = response.data?.map((reference) => {
47+
return {
48+
unique: reference.id,
49+
icon: reference.icon,
50+
name: reference.name,
51+
};
52+
});
53+
54+
return { data, error };
55+
}
56+
/**
57+
* Updates the compositions for a media type on the server
58+
* @param {MediaTypeCompositionRequestModel} requestBody
59+
* @return {*}
60+
* @memberof UmbMediaTypeCompositionServerDataSource
61+
*/
62+
async availableCompositions(args: UmbMediaTypeAvailableCompositionRequestModel) {
63+
const requestBody: MediaTypeCompositionRequestModel = {
64+
id: args.unique,
65+
currentCompositeIds: args.currentCompositeUniques,
66+
currentPropertyAliases: args.currentPropertyAliases,
67+
};
68+
69+
const response = await tryExecuteAndNotify(
70+
this.#host,
71+
MediaTypeService.postMediaTypeAvailableCompositions({ requestBody }),
72+
);
73+
const error = response.error;
74+
const data: Array<UmbMediaTypeCompositionCompatibleModel> | undefined = response.data?.map((composition) => {
75+
return {
76+
unique: composition.id,
77+
name: composition.name,
78+
icon: composition.icon,
79+
folderPath: composition.folderPath,
80+
isCompatible: composition.isCompatible,
81+
};
82+
});
83+
84+
return { data, error };
85+
}
86+
}
Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1-
export * from './item/index.js';
1+
export * from './composition/index.js';
22
export * from './detail/index.js';
3+
export * from './item/index.js';
34
export * from './structure/index.js';
Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import { manifests as detailManifests } from './detail/manifests.js';
22
import { manifests as itemManifests } from './item/manifests.js';
3+
import { manifests as compositionManifests } from './composition/manifests.js';
34
import type { ManifestTypes } from '@umbraco-cms/backoffice/extension-registry';
45

5-
export const manifests: Array<ManifestTypes> = [...detailManifests, ...itemManifests];
6+
export const manifests: Array<ManifestTypes> = [...detailManifests, ...itemManifests, ...compositionManifests];

0 commit comments

Comments
 (0)