@@ -41,30 +41,44 @@ public function getMetaDataIntegratorBackendConfiguration(mixed $correspondingEl
4141 return $ configuration ;
4242 }
4343
44- public function getElementData (string $ elementType , int $ elementId ): array
44+ public function getElementData (string $ elementType , int $ elementId, bool $ allowDraftReleaseType = false ): array
4545 {
46- $ elementValues = $ this ->elementMetaDataRepository ->findAll ($ elementType , $ elementId );
46+ $ fetchingReleaseType = ElementMetaDataInterface::RELEASE_TYPE_PUBLIC ;
47+ if ($ allowDraftReleaseType === true && $ this ->elementMetaDataExistsWithReleaseType ($ elementType , $ elementId , ElementMetaDataInterface::RELEASE_TYPE_DRAFT )) {
48+ $ fetchingReleaseType = ElementMetaDataInterface::RELEASE_TYPE_DRAFT ;
49+ }
50+
51+ $ elementValues = $ this ->elementMetaDataRepository ->findAll ($ elementType , $ elementId , $ fetchingReleaseType );
4752
4853 // BC Reason: If old document metadata is available, use it!
4954 // @todo: make this decision configurable? We don't need this within fresh installations!
5055
51- return $ this ->checkForLegacyData ($ elementValues , $ elementType , $ elementId );
56+ return $ this ->checkForLegacyData ($ elementValues , $ elementType , $ elementId, $ fetchingReleaseType );
5257 }
5358
5459 public function getElementDataForBackend (string $ elementType , int $ elementId ): array
5560 {
61+ $ isDraft = false ;
5662 $ parsedData = [];
57- $ data = $ this ->getElementData ($ elementType , $ elementId );
63+ $ data = $ this ->getElementData ($ elementType , $ elementId, true );
5864
5965 foreach ($ data as $ element ) {
66+
67+ if ($ element ->getReleaseType () === ElementMetaDataInterface::RELEASE_TYPE_DRAFT ) {
68+ $ isDraft = true ;
69+ }
70+
6071 $ metaDataIntegrator = $ this ->metaDataIntegratorRegistry ->get ($ element ->getIntegrator ());
6172 $ parsedData [$ element ->getIntegrator ()] = $ metaDataIntegrator ->validateBeforeBackend ($ elementType , $ elementId , $ element ->getData ());
6273 }
6374
6475 // BC Reason: If old document metadata is available, use it!
6576 // @todo: make this decision configurable? We don't need this within fresh installations!
6677
67- return $ this ->checkForLegacyBackendData ($ parsedData , $ elementType , $ elementId );
78+ return [
79+ 'isDraft ' => $ isDraft ,
80+ 'data ' => $ this ->checkForLegacyBackendData ($ parsedData , $ elementType , $ elementId )
81+ ];
6882 }
6983
7084 public function getElementDataForXliffExport (string $ elementType , int $ elementId , string $ locale ): array
@@ -114,22 +128,46 @@ public function saveElementDataFromXliffImport(string $elementType, int $element
114128 }
115129 }
116130
117- public function saveElementData (string $ elementType , int $ elementId , string $ integratorName , array $ data , bool $ merge = false ): void
118- {
119- $ elementMetaData = $ this ->elementMetaDataRepository ->findByIntegrator ($ elementType , $ elementId , $ integratorName );
131+ public function saveElementData (
132+ string $ elementType ,
133+ int $ elementId ,
134+ string $ integratorName ,
135+ array $ data ,
136+ bool $ merge = false ,
137+ string $ releaseType = ElementMetaDataInterface::RELEASE_TYPE_PUBLIC
138+ ): void {
139+
140+ $ elementMetaData = $ this ->determinateElementMetaEntity ($ elementType , $ elementId , $ integratorName , $ releaseType );
120141
121142 if (!$ elementMetaData instanceof ElementMetaDataInterface) {
122143 $ elementMetaData = new ElementMetaData ();
123144 $ elementMetaData ->setElementType ($ elementType );
124145 $ elementMetaData ->setElementId ($ elementId );
125146 $ elementMetaData ->setIntegrator ($ integratorName );
147+ $ elementMetaData ->setReleaseType ($ releaseType );
126148 }
127149
128150 $ metaDataIntegrator = $ this ->metaDataIntegratorRegistry ->get ($ integratorName );
129151 $ sanitizedData = $ metaDataIntegrator ->validateBeforePersist ($ elementType , $ elementId , $ data , $ elementMetaData ->getData (), $ merge );
130152
131153 // remove empty meta data
132154 if ($ sanitizedData === null ) {
155+
156+ if ($ releaseType === ElementMetaDataInterface::RELEASE_TYPE_DRAFT ) {
157+
158+ // if draft, we still persist an empty element
159+ // to determinate reset when publish state is incoming
160+
161+ if (
162+ $ elementMetaData ->getId () > 0 ||
163+ $ this ->elementMetaDataExistsWithReleaseType ($ elementType , $ elementId , ElementMetaDataInterface::RELEASE_TYPE_PUBLIC , $ integratorName )
164+ ) {
165+ $ this ->persistElementMetaData ($ elementMetaData , []);
166+ }
167+
168+ return ;
169+ }
170+
133171 if ($ elementMetaData ->getId () > 0 ) {
134172 $ this ->entityManager ->remove ($ elementMetaData );
135173 $ this ->entityManager ->flush ();
@@ -138,8 +176,12 @@ public function saveElementData(string $elementType, int $elementId, string $int
138176 return ;
139177 }
140178
141- $ elementMetaData ->setData ($ sanitizedData );
179+ $ this ->persistElementMetaData ($ elementMetaData , $ sanitizedData );
180+ }
142181
182+ private function persistElementMetaData (ElementMetaDataInterface $ elementMetaData , array $ data ): void
183+ {
184+ $ elementMetaData ->setData ($ data );
143185 $ this ->entityManager ->persist ($ elementMetaData );
144186 $ this ->entityManager ->flush ();
145187 }
@@ -157,9 +199,9 @@ public function generatePreviewDataForElement(string $elementType, int $elementI
157199 return $ metaDataIntegrator ->getPreviewParameter ($ element , $ template , $ data );
158200 }
159201
160- public function deleteElementData (string $ elementType , int $ elementId ): void
202+ public function deleteElementData (string $ elementType , int $ elementId, ? string $ releaseType = ElementMetaDataInterface:: RELEASE_TYPE_PUBLIC ): void
161203 {
162- $ elementData = $ this ->elementMetaDataRepository ->findAll ($ elementType , $ elementId );
204+ $ elementData = $ this ->elementMetaDataRepository ->findAll ($ elementType , $ elementId, $ releaseType );
163205
164206 if (count ($ elementData ) === 0 ) {
165207 return ;
@@ -175,7 +217,7 @@ public function deleteElementData(string $elementType, int $elementId): void
175217 /**
176218 * @return array<int, ElementMetaDataInterface>
177219 */
178- protected function checkForLegacyData (array $ elements , string $ elementType , int $ elementId ): array
220+ protected function checkForLegacyData (array $ elements , string $ elementType , int $ elementId, string $ releaseType = ElementMetaDataInterface:: RELEASE_TYPE_PUBLIC ): array
179221 {
180222 // as soon we have configured seo elements,
181223 // we'll never check the document again. It's all about performance.
@@ -197,6 +239,7 @@ protected function checkForLegacyData(array $elements, string $elementType, int
197239 $ legacyTitleDescription ->setElementType ($ elementType );
198240 $ legacyTitleDescription ->setElementId ($ elementId );
199241 $ legacyTitleDescription ->setIntegrator ('title_description ' );
242+ $ legacyTitleDescription ->setReleaseType ($ releaseType );
200243 $ legacyTitleDescription ->setData (['title ' => $ legacyData ['title ' ], 'description ' => $ legacyData ['description ' ]]);
201244 $ elements [] = $ legacyTitleDescription ;
202245 }
@@ -264,4 +307,49 @@ protected function getDocumentLegacyData(int $documentId): ?array
264307 'hasTitleDescriptionIntegrator ' => $ hasTitleDescriptionIntegrator !== false
265308 ];
266309 }
310+
311+ private function determinateElementMetaEntity (
312+ string $ elementType ,
313+ int $ elementId ,
314+ string $ integratorName ,
315+ string $ releaseType = ElementMetaDataInterface::RELEASE_TYPE_PUBLIC
316+ ): ?ElementMetaDataInterface {
317+
318+ $ hasDraft = $ this ->elementMetaDataExistsWithReleaseType ($ elementType , $ elementId , ElementMetaDataInterface::RELEASE_TYPE_DRAFT );
319+
320+ if ($ releaseType === ElementMetaDataInterface::RELEASE_TYPE_PUBLIC && $ hasDraft === true ) {
321+
322+ // delete draft
323+ $ this ->deleteElementData ($ elementType , $ elementId , ElementMetaDataInterface::RELEASE_TYPE_DRAFT );
324+
325+ return $ this ->elementMetaDataRepository ->findByIntegrator ($ elementType , $ elementId , $ integratorName , $ releaseType );
326+ }
327+
328+ return $ this ->elementMetaDataRepository ->findByIntegrator ($ elementType , $ elementId , $ integratorName , $ releaseType );
329+ }
330+
331+ private function elementMetaDataExistsWithReleaseType (string $ elementType , int $ elementId , string $ releaseType , ?string $ integratorName = null ): bool
332+ {
333+ $ qb = $ this ->elementMetaDataRepository ->getQueryBuilder ();
334+
335+ $ qb
336+ ->select ('COUNT(e.id) ' )
337+ ->andWhere ('e.elementType = :elementType ' )
338+ ->andWhere ('e.elementId = :elementId ' )
339+ ->andWhere ('e.releaseType = :releaseType ' )
340+ ->setParameter ('elementType ' , $ elementType )
341+ ->setParameter ('elementId ' , $ elementId )
342+ ->setParameter ('releaseType ' , $ releaseType );
343+
344+ if ($ integratorName !== null ) {
345+ $ qb
346+ ->andWhere ('e.integrator = :integratorName ' )
347+ ->setParameter ('integratorName ' , $ integratorName );
348+ }
349+
350+ return $ qb
351+ ->getQuery ()
352+ ->getSingleScalarResult () > 0 ;
353+ }
354+
267355}
0 commit comments