diff --git a/ccm-cms/package-lock.json b/ccm-cms/package-lock.json index da6c2a3a4..d21cc6d98 100644 --- a/ccm-cms/package-lock.json +++ b/ccm-cms/package-lock.json @@ -1,12 +1,12 @@ { "name": "@librecms/ccm-cms", - "version": "7.0.0-SNAPSHOT.2022-10-25T172000", + "version": "7.0.0-SNAPSHOT.2022-10-25T175437", "lockfileVersion": 2, "requires": true, "packages": { "": { "name": "@librecms/ccm-cms", - "version": "7.0.0-SNAPSHOT.2022-10-25T172000", + "version": "7.0.0-SNAPSHOT.2022-10-25T175437", "license": "LGPL-3.0-or-later", "dependencies": { "@tiptap/core": "^2.0.0-beta.127", diff --git a/ccm-cms/package.json b/ccm-cms/package.json index 93e899316..1371c7452 100644 --- a/ccm-cms/package.json +++ b/ccm-cms/package.json @@ -1,6 +1,6 @@ { "name": "@librecms/ccm-cms", - "version": "7.0.0-SNAPSHOT.2022-10-25T172000", + "version": "7.0.0-SNAPSHOT.2022-10-25T175437", "description": "JavaScript stuff for ccm-cms", "main": "target/generated-resources/assets/@content-sections/cms-admin.js", "types": "target/generated-resources/assets/@content-sections/cms-admin.d.ts", diff --git a/ccm-cms/src/main/java/org/librecms/contentsection/ContentSection.java b/ccm-cms/src/main/java/org/librecms/contentsection/ContentSection.java index 733546c46..6b94e0d51 100644 --- a/ccm-cms/src/main/java/org/librecms/contentsection/ContentSection.java +++ b/ccm-cms/src/main/java/org/librecms/contentsection/ContentSection.java @@ -198,6 +198,7 @@ public class ContentSection @JoinColumn(name = "LIFECYCLE_DEFINITION_ID") } ) + @JsonIdentityReference(alwaysAsId = true) private List lifecycleDefinitions = new ArrayList<>(); @OneToMany @@ -211,6 +212,7 @@ public class ContentSection @JoinColumn(name = "WORKFLOW_TEMPLATE_ID") } ) + @JsonIdentityReference(alwaysAsId = true) private List workflowTemplates = new ArrayList<>(); public ContentSection() { diff --git a/ccm-cms/src/main/java/org/librecms/lifecycle/Lifecycle.java b/ccm-cms/src/main/java/org/librecms/lifecycle/Lifecycle.java index 5fd3b426e..752b5c143 100644 --- a/ccm-cms/src/main/java/org/librecms/lifecycle/Lifecycle.java +++ b/ccm-cms/src/main/java/org/librecms/lifecycle/Lifecycle.java @@ -18,8 +18,12 @@ */ package org.librecms.lifecycle; +import com.fasterxml.jackson.annotation.JsonIdentityInfo; +import com.fasterxml.jackson.annotation.JsonIdentityReference; +import com.fasterxml.jackson.annotation.ObjectIdGenerators; import org.hibernate.search.annotations.Field; import org.libreccm.core.Identifiable; +import org.libreccm.imexport.Exportable; import java.io.Serializable; import java.util.ArrayList; @@ -35,6 +39,8 @@ import javax.persistence.GeneratedValue; import javax.persistence.GenerationType; import javax.persistence.Id; import javax.persistence.JoinColumn; +import javax.persistence.NamedQueries; +import javax.persistence.NamedQuery; import javax.persistence.OneToMany; import javax.persistence.OneToOne; import javax.persistence.Table; @@ -51,7 +57,18 @@ import static org.librecms.CmsConstants.*; */ @Entity @Table(name = "LIFECYCLES", schema = DB_SCHEMA) -public class Lifecycle implements Identifiable, Serializable { +@NamedQueries({ + @NamedQuery( + name = "Lifecycle.findByUuid", + query = "SELECT l FROM Lifecycle l WHERE l.uuid = :uuid" + ) +}) +@JsonIdentityInfo( + generator = ObjectIdGenerators.PropertyGenerator.class, + resolver = LifecycleIdResolver.class, + property = "uuid" +) +public class Lifecycle implements Exportable, Identifiable, Serializable { private static final long serialVersionUID = 184357562249530038L; @@ -88,6 +105,7 @@ public class Lifecycle implements Identifiable, Serializable { @OneToOne @JoinColumn(name = "DEFINITION_ID") + @JsonIdentityReference(alwaysAsId = true) private LifecycleDefinition definition; @OneToMany(mappedBy = "lifecycle") diff --git a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinition.java b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinition.java index 74161cc43..98027b179 100644 --- a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinition.java +++ b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinition.java @@ -18,8 +18,11 @@ */ package org.librecms.lifecycle; +import com.fasterxml.jackson.annotation.JsonIdentityInfo; +import com.fasterxml.jackson.annotation.ObjectIdGenerators; import org.hibernate.search.annotations.Field; import org.libreccm.core.Identifiable; +import org.libreccm.imexport.Exportable; import org.libreccm.l10n.LocalizedString; import java.io.Serializable; @@ -58,7 +61,13 @@ import static org.librecms.CmsConstants.*; query = "SELECT d FROM LifecycleDefinition d WHERE d.uuid = :uuid" ) ) -public class LifecycleDefinition implements Identifiable, Serializable { +@JsonIdentityInfo( + generator = ObjectIdGenerators.PropertyGenerator.class, + resolver = LifecycleDefinitionIdResolver.class, + property = "uuid" +) +public class LifecycleDefinition + implements Identifiable, Exportable, Serializable { private static final long serialVersionUID = 1291162870555527717L; diff --git a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinitionIdResolver.java b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinitionIdResolver.java new file mode 100644 index 000000000..a913ac960 --- /dev/null +++ b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinitionIdResolver.java @@ -0,0 +1,73 @@ +/* + * Copyright (C) 2022 LibreCCM Foundation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301 USA + */ +package org.librecms.lifecycle; + +import com.fasterxml.jackson.annotation.ObjectIdGenerator; +import com.fasterxml.jackson.annotation.ObjectIdResolver; +import org.libreccm.cdi.utils.CdiUtil; + +import java.io.Serializable; + +import javax.enterprise.context.RequestScoped; + +/** + * + * @author Jens Pelzetter + */ +@RequestScoped +public class LifecycleDefinitionIdResolver + implements Serializable, ObjectIdResolver { + + @Override + public void bindItem( + final ObjectIdGenerator.IdKey id, + final Object object + ) { + // According to the Jackson JavaDoc, this method can be used to keep + // track of objects directly in a resolver implementation. We don't need + // this here therefore this method is empty. + } + + @Override + public Object resolveId(final ObjectIdGenerator.IdKey id) { + return CdiUtil + .createCdiUtil() + .findBean(LifecycleDefinitionRepository.class) + .findByUuid(id.key.toString()) + .orElseThrow( + () -> new IllegalArgumentException( + String.format( + "No LifecycleDefinition with UUID %s in the database.", + id.key.toString() + ) + ) + ); + } + + @Override + public ObjectIdResolver newForDeserialization(final Object context) { + return new LifecycleDefinitionIdResolver(); + } + + @Override + public boolean canUseFor(final ObjectIdResolver resolverType) { + return resolverType instanceof LifecycleDefinitionIdResolver; + } + +} diff --git a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinitionImExporter.java b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinitionImExporter.java new file mode 100644 index 000000000..53a7b0be1 --- /dev/null +++ b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleDefinitionImExporter.java @@ -0,0 +1,76 @@ +/* + * Copyright (C) 2022 LibreCCM Foundation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301 USA + */ +package org.librecms.lifecycle; + +import org.libreccm.imexport.AbstractEntityImExporter; +import org.libreccm.imexport.Exportable; +import org.libreccm.imexport.Processes; + +import java.util.Objects; +import java.util.Set; + +import javax.enterprise.context.RequestScoped; +import javax.inject.Inject; + +/** + * + * @author Jens Pelzetter + */ +@RequestScoped +@Processes(LifecycleDefinition.class) +public class LifecycleDefinitionImExporter + extends AbstractEntityImExporter { + + @Inject + private LifecycleDefinitionRepository lifecycleDefRepo; + + @Override + public Class getEntityClass() { + return LifecycleDefinition.class; + } + + @Override + protected Set> getRequiredEntities() { + return Set.of( + Lifecycle.class + ); + } + + @Override + protected void saveImportedEntity(final LifecycleDefinition entity) { + lifecycleDefRepo.save(entity); + } + + @Override + protected LifecycleDefinition reloadEntity( + final LifecycleDefinition entity + ) { + return lifecycleDefRepo + .findById(Objects.requireNonNull(entity).getDefinitionId()) + .orElseThrow( + () -> new IllegalArgumentException( + String.format( + "LifecycleDefinition entity %s not found in database.", + Objects.toString(entity) + ) + ) + ); + } + +} diff --git a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleIdResolver.java b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleIdResolver.java new file mode 100644 index 000000000..58713a473 --- /dev/null +++ b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleIdResolver.java @@ -0,0 +1,74 @@ +/* + * Copyright (C) 2022 LibreCCM Foundation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301 USA + */ +package org.librecms.lifecycle; + +import com.fasterxml.jackson.annotation.ObjectIdGenerator; +import com.fasterxml.jackson.annotation.ObjectIdResolver; +import org.libreccm.cdi.utils.CdiUtil; + +import java.io.Serializable; + +import javax.enterprise.context.RequestScoped; + +/** + * + * @author Jens Pelzetter + */ +@RequestScoped +public class LifecycleIdResolver implements Serializable, ObjectIdResolver { + + private static final long serialVersionUID = 1L; + + @Override + public void bindItem( + final ObjectIdGenerator.IdKey idKey, + final Object object + ) { + // According to the Jackson JavaDoc, this method can be used to keep + // track of objects directly in a resolver implementation. We don't need + // this here therefore this method is empty. + } + + @Override + public Object resolveId(final ObjectIdGenerator.IdKey id) { + return CdiUtil + .createCdiUtil() + .findBean(LifecycleRepository.class) + .findByUuid(id.key.toString()) + .orElseThrow( + () -> new IllegalArgumentException( + String.format( + "No Lifecycle with UUID %s in the database.", + id.key.toString() + ) + ) + ); + } + + @Override + public ObjectIdResolver newForDeserialization(final Object context) { + return new LifecycleIdResolver(); + } + + @Override + public boolean canUseFor(final ObjectIdResolver resolverType) { + return resolverType instanceof LifecycleIdResolver; + } + +} diff --git a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleImExporter.java b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleImExporter.java new file mode 100644 index 000000000..d88296de4 --- /dev/null +++ b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleImExporter.java @@ -0,0 +1,75 @@ +/* + * Copyright (C) 2022 LibreCCM Foundation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301 USA + */ +package org.librecms.lifecycle; + +import org.libreccm.imexport.AbstractEntityImExporter; +import org.libreccm.imexport.Exportable; +import org.libreccm.imexport.Processes; + +import java.util.Objects; +import java.util.Set; + +import javax.enterprise.context.RequestScoped; +import javax.inject.Inject; +import javax.transaction.Transactional; + +/** + * + * @author Jens Pelzetter + */ +@RequestScoped +@Processes(Lifecycle.class) +public class LifecycleImExporter extends AbstractEntityImExporter { + + @Inject + private LifecycleRepository lifecycleRepo; + + @Override + public Class getEntityClass() { + return Lifecycle.class; + } + + @Override + protected Set> getRequiredEntities() { + return Set.of( + LifecycleDefinition.class + ); + } + + @Override + @Transactional(Transactional.TxType.REQUIRED) + protected void saveImportedEntity(final Lifecycle entity) { + lifecycleRepo.save(entity); + } + + @Override + protected Lifecycle reloadEntity(final Lifecycle entity) { + return lifecycleRepo + .findById(Objects.requireNonNull(entity).getLifecycleId()) + .orElseThrow( + () -> new IllegalArgumentException( + String.format( + "Lifecycle entity %s not found in database.", + Objects.toString(entity) + ) + ) + ); + } + +} diff --git a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleRepository.java b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleRepository.java index 55691e182..f6bd509ca 100644 --- a/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleRepository.java +++ b/ccm-cms/src/main/java/org/librecms/lifecycle/LifecycleRepository.java @@ -20,9 +20,11 @@ package org.librecms.lifecycle; import org.libreccm.core.AbstractEntityRepository; +import java.util.Optional; import java.util.UUID; import javax.enterprise.context.RequestScoped; +import javax.persistence.NoResultException; /** * @@ -60,4 +62,17 @@ public class LifecycleRepository entity.setUuid(UUID.randomUUID().toString()); } + public Optional findByUuid(final String uuid) { + try { + return Optional.of( + getEntityManager() + .createNamedQuery("Lifecycle.findByUuid", Lifecycle.class) + .setParameter("uuid", uuid) + .getSingleResult() + ); + } catch (NoResultException ex) { + return Optional.empty(); + } + } + }