1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.mycore.pi.urn;
20
21 import java.io.IOException;
22 import java.nio.file.Files;
23 import java.nio.file.Path;
24 import java.util.ArrayList;
25 import java.util.Arrays;
26 import java.util.Date;
27 import java.util.List;
28 import java.util.function.Predicate;
29 import java.util.regex.Pattern;
30 import java.util.stream.Collectors;
31
32 import org.apache.logging.log4j.LogManager;
33 import org.apache.logging.log4j.Logger;
34 import org.mycore.access.MCRAccessException;
35 import org.mycore.backend.jpa.MCREntityManagerProvider;
36 import org.mycore.datamodel.common.MCRActiveLinkException;
37 import org.mycore.datamodel.metadata.MCRBase;
38 import org.mycore.datamodel.metadata.MCRDerivate;
39 import org.mycore.datamodel.metadata.MCRMetadataManager;
40 import org.mycore.datamodel.metadata.MCRObjectDerivate;
41 import org.mycore.datamodel.niofs.MCRPath;
42 import org.mycore.datamodel.niofs.utils.MCRFileCollectingFileVisitor;
43 import org.mycore.pi.MCRPIManager;
44 import org.mycore.pi.MCRPIService;
45 import org.mycore.pi.backend.MCRPI;
46 import org.mycore.pi.exceptions.MCRPersistentIdentifierException;
47
48 import jakarta.persistence.EntityManager;
49
50
51
52
53
54
55
56
57
58 public class MCRURNGranularOAIService extends MCRPIService<MCRDNBURN> {
59
60 private static final Logger LOGGER = LogManager.getLogger();
61
62 public MCRURNGranularOAIService() {
63 super(MCRDNBURN.TYPE);
64 }
65
66 @Override
67 public MCRDNBURN register(MCRBase obj, String additional, boolean updateObject)
68 throws MCRAccessException, MCRActiveLinkException, MCRPersistentIdentifierException {
69 this.validateRegistration(obj, additional);
70
71 MCRObjectDerivate derivate = ((MCRDerivate) obj).getDerivate();
72 MCRDNBURN newURN;
73
74 if (additional.equals("")) {
75
76 newURN = registerURNsDerivate(obj, additional, derivate);
77 } else {
78
79 newURN = registerSingleURN(obj, additional, derivate);
80 }
81
82 try {
83 MCRMetadataManager.update(obj);
84 } catch (Exception e) {
85 throw new MCRPersistentIdentifierException("Error while updating derivate " + obj.getId(), e);
86 }
87
88 return newURN;
89
90 }
91
92 private MCRDNBURN registerSingleURN(MCRBase obj, String additional, MCRObjectDerivate derivate)
93 throws MCRPersistentIdentifierException {
94 LOGGER.info("Add single urn to {} / {}", obj.getId(), additional);
95
96 EntityManager em = MCREntityManagerProvider.getCurrentEntityManager();
97 MCRPath filePath = MCRPath.getPath(obj.getId().toString(), additional);
98 if (!Files.exists(filePath)) {
99 throw new MCRPersistentIdentifierException("Invalid path : " + additional);
100 }
101
102 int count = Math.toIntExact(derivate.getFileMetadata().stream().filter(file -> file.getUrn() != null).count());
103 MCRDNBURN newURN = (MCRDNBURN) MCRPIManager.getInstance().get(derivate.getURN())
104 .findFirst().get();
105
106 String setID = obj.getId().getNumberAsString();
107 MCRDNBURN urntoAssign = newURN.toGranular(setID, count + 1, count + 1);
108 derivate.getOrCreateFileMetadata(filePath, urntoAssign.asString()).setUrn(urntoAssign.asString());
109 MCRPI databaseEntry = new MCRPI(urntoAssign.asString(), getType(), obj.getId().toString(), additional,
110 this.getServiceID(), new Date());
111 em.persist(databaseEntry);
112 return newURN;
113 }
114
115 private MCRDNBURN registerURNsDerivate(MCRBase obj, String additional, MCRObjectDerivate derivate)
116 throws MCRPersistentIdentifierException {
117 LOGGER.info("Add URNs to all files of {}", obj.getId());
118
119 EntityManager em = MCREntityManagerProvider.getCurrentEntityManager();
120
121 Path path = MCRPath.getPath(obj.getId().toString(), "/");
122 MCRFileCollectingFileVisitor<Path> collectingFileVisitor = new MCRFileCollectingFileVisitor<>();
123
124 try {
125 Files.walkFileTree(path, collectingFileVisitor);
126 } catch (IOException e) {
127 throw new MCRPersistentIdentifierException("Could not walk derivate file tree!", e);
128 }
129
130 List<String> ignoreFileNamesList = getIgnoreFileList();
131
132 List<Predicate<String>> predicateList = ignoreFileNamesList
133 .stream()
134 .map(Pattern::compile)
135 .map(Pattern::asPredicate)
136 .collect(Collectors.toList());
137
138 List<MCRPath> pathList = collectingFileVisitor
139 .getPaths()
140 .stream()
141 .filter(file -> predicateList.stream()
142 .noneMatch(p -> p.test(file.toString().split(":")[1])))
143 .map(p -> (MCRPath) p)
144 .sorted()
145 .collect(Collectors.toList());
146
147 MCRDNBURN newURN = getNewIdentifier(obj, additional);
148 String setID = obj.getId().getNumberAsString();
149
150 for (int pathListIndex = 0; pathListIndex < pathList.size(); pathListIndex++) {
151 MCRDNBURN subURN = newURN.toGranular(setID, pathListIndex + 1, pathList.size());
152 derivate.getOrCreateFileMetadata(pathList.get(pathListIndex), subURN.asString()).setUrn(subURN.asString());
153 MCRPI databaseEntry = new MCRPI(subURN.asString(), getType(), obj.getId().toString(),
154 pathList.get(pathListIndex).getOwnerRelativePath(),
155 this.getServiceID(), null);
156 em.persist(databaseEntry);
157 }
158
159 derivate.setURN(newURN.asString());
160 MCRPI databaseEntry = new MCRPI(newURN.asString(), getType(), obj.getId().toString(), "",
161 this.getServiceID(), new Date());
162 em.persist(databaseEntry);
163 return newURN;
164 }
165
166 private List<String> getIgnoreFileList() {
167 List<String> ignoreFileNamesList = new ArrayList<>();
168 String ignoreFileNames = getProperties().get("IgnoreFileNames");
169 if (ignoreFileNames != null) {
170 ignoreFileNamesList.addAll(Arrays.asList(ignoreFileNames.split(",")));
171 } else {
172 ignoreFileNamesList.add("mets\\.xml");
173 }
174 return ignoreFileNamesList;
175 }
176
177 @Override
178 protected void registerIdentifier(MCRBase obj, String additional, MCRDNBURN urn)
179 throws MCRPersistentIdentifierException {
180
181 }
182
183 @Override
184 protected void delete(MCRDNBURN identifier, MCRBase obj, String additional)
185 throws MCRPersistentIdentifierException {
186 throw new MCRPersistentIdentifierException("Delete is not supported for " + getType());
187 }
188
189 @Override
190 protected void update(MCRDNBURN identifier, MCRBase obj, String additional)
191 throws MCRPersistentIdentifierException {
192
193 LOGGER.info("No update in this implementation");
194 }
195 }