2 * Copyright (C) 2010 Mathieu Baudier <mbaudier@argeo.org>
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
17 package org
.argeo
.slc
.jcr
.dao
;
19 import java
.util
.ArrayList
;
20 import java
.util
.Calendar
;
21 import java
.util
.Date
;
22 import java
.util
.GregorianCalendar
;
23 import java
.util
.List
;
26 import javax
.jcr
.Node
;
27 import javax
.jcr
.NodeIterator
;
28 import javax
.jcr
.RepositoryException
;
29 import javax
.jcr
.Session
;
30 import javax
.jcr
.query
.Query
;
31 import javax
.jcr
.query
.QueryManager
;
32 import javax
.jcr
.query
.QueryResult
;
34 import org
.apache
.commons
.logging
.Log
;
35 import org
.apache
.commons
.logging
.LogFactory
;
36 import org
.argeo
.jcr
.JcrUtils
;
37 import org
.argeo
.slc
.SlcException
;
38 import org
.argeo
.slc
.core
.attachment
.SimpleAttachment
;
39 import org
.argeo
.slc
.core
.structure
.tree
.TreeSPath
;
40 import org
.argeo
.slc
.core
.test
.SimpleResultPart
;
41 import org
.argeo
.slc
.core
.test
.tree
.TreeTestResult
;
42 import org
.argeo
.slc
.dao
.test
.tree
.TreeTestResultDao
;
43 import org
.argeo
.slc
.structure
.StructureElement
;
44 import org
.argeo
.slc
.test
.TestResult
;
47 * The JCR implementation for tree-based result of the test result dao.
52 public class TreeTestResultDaoJcr
extends AbstractSlcJcrDao
implements
55 private final static Log log
= LogFactory
56 .getLog(TreeTestResultDaoJcr
.class);
58 public synchronized void create(TestResult testResult
) {
60 nodeMapper
.save(getSession(), basePath(testResult
), testResult
);
62 } catch (Exception e
) {
63 throw new SlcException("Cannot create testResult " + testResult
, e
);
67 public synchronized void update(TestResult testResult
) {
69 nodeMapper
.save(getSession(), basePath(testResult
), testResult
);
71 } catch (Exception e
) {
72 throw new SlcException("Cannot update testResult" + testResult
, e
);
76 public TreeTestResult
getTestResult(String uuid
) {
77 String queryString
= "//testresult[@uuid='" + uuid
+ "']";
78 Query query
= createQuery(queryString
, Query
.XPATH
);
79 Node node
= JcrUtils
.querySingleNode(query
);
82 return (TreeTestResult
) nodeMapper
.load(node
);
86 public List
<TreeTestResult
> listTestResults() {
88 // TODO: optimize query
89 String queryString
= "//testresult";
90 Query query
= createQuery(queryString
, Query
.XPATH
);
91 QueryResult queryResult
= query
.execute();
92 NodeIterator nodeIterator
= queryResult
.getNodes();
93 if (nodeIterator
.hasNext()) {
94 List
<TreeTestResult
> list
= new ArrayList
<TreeTestResult
>();
95 nodes
: while (nodeIterator
.hasNext()) {
96 Node curNode
= (Node
) nodeIterator
.next();
98 // TODO improve architecture and get rid of this hack
99 if ("slc".equals(curNode
.getParent().getName()))
102 list
.add((TreeTestResult
) nodeMapper
.load(curNode
));
108 } catch (RepositoryException e
) {
109 throw new SlcException("Cannot load list of TestResult ", e
);
113 public List
<TreeTestResult
> listResults(TreeSPath path
) {
115 // TODO: optimize query
116 String queryString
= "//testresult" + path
.getAsUniqueString();
117 Query query
= createQuery(queryString
, Query
.XPATH
);
118 QueryResult queryResult
= query
.execute();
119 NodeIterator nodeIterator
= queryResult
.getNodes();
120 if (nodeIterator
.hasNext()) {
121 List
<TreeTestResult
> list
= new ArrayList
<TreeTestResult
>();
122 while (nodeIterator
.hasNext()) {
123 list
.add((TreeTestResult
) nodeMapper
124 .load((Node
) nodeIterator
.next()));
130 } catch (RepositoryException e
) {
131 throw new SlcException("Cannot load list of TestResult ", e
);
135 public synchronized void close(final String testResultId
,
136 final Date closeDate
) {
138 // TODO: optimize query
139 String queryString
= "//testresult[@uuid='" + testResultId
+ "']";
140 Query query
= createQuery(queryString
, Query
.XPATH
);
141 Node resNode
= JcrUtils
.querySingleNode(query
);
142 Calendar cal
= new GregorianCalendar();
143 cal
.setTime(closeDate
);
145 resNode
.setProperty("closeDate", cal
);
146 else if (log
.isDebugEnabled())
147 log
.debug("Cannot close because a node for test result # "
148 + testResultId
+ " was not found");
150 } catch (RepositoryException e
) {
151 throw new SlcException("Cannot close TestResult " + testResultId
, e
);
157 * Add a SimpleResultPart to the TreeTestResult of ID testResultId at
160 * May also add some relatedElements
163 // TODO do we load objects, do treatment and persist them or do we work
165 public synchronized void addResultPart(final String testResultId
,
166 final TreeSPath path
, final SimpleResultPart resultPart
,
167 final Map
<TreeSPath
, StructureElement
> relatedElements
) {
170 // TODO: optimize query
171 String queryString
= "//testresult[@uuid='" + testResultId
+ "']";
172 Query query
= createQuery(queryString
, Query
.XPATH
);
173 Node resNode
= JcrUtils
.querySingleNode(query
);
176 String usedPath
= path
.getAsUniqueString().substring(1)
179 if (resNode
.hasNode(usedPath
))
180 curNode
= resNode
.getNode(usedPath
);
183 // TODO Factorize that
184 Node tmpNode
= resNode
;
185 String
[] pathes
= usedPath
.split("/");
186 for (int i
= 0; i
< pathes
.length
; i
++) {
187 if (tmpNode
.hasNode(pathes
[i
]))
188 tmpNode
= tmpNode
.getNode(pathes
[i
]);
190 tmpNode
= tmpNode
.addNode(pathes
[i
]);
195 nodeMapper
.update(curNode
.addNode("resultPart"), resultPart
);
197 if (relatedElements
!= null) {
198 for (TreeSPath key
: relatedElements
.keySet()) {
199 String relPath
= key
.getAsUniqueString().substring(1);
201 // check if already exists.
202 if (!resNode
.hasNode(relPath
)) {
204 // TODO Factorize that
205 Node tmpNode
= resNode
;
206 String
[] pathes
= usedPath
.split("/");
207 for (int i
= 0; i
< pathes
.length
; i
++) {
208 if (tmpNode
.hasNode(pathes
[i
]))
209 tmpNode
= tmpNode
.getNode(pathes
[i
]);
211 tmpNode
= tmpNode
.addNode(pathes
[i
]);
215 curNode
= resNode
.getNode(relPath
);
217 curNode
.setProperty("label", relatedElements
.get(key
)
220 Map
<String
, String
> tags
= relatedElements
.get(key
)
223 for (String tag
: tags
.keySet()) {
224 NodeIterator tagIt
= curNode
.getNodes("tag");
226 while (tagIt
.hasNext()) {
227 Node n
= tagIt
.nextNode();
228 if (n
.getProperty("name").getString().equals(tag
)) {
233 if (tagNode
== null) {
234 tagNode
= curNode
.addNode("tag");
235 tagNode
.setProperty("name", tag
);
238 tagNode
.setProperty("value", tags
.get(tag
));
240 // remove forbidden characters
242 // JcrUtils.removeForbiddenCharacters(tag);
243 // if (!cleanTag.equals(tag))
244 // log.warn("Tag '" + tag + "' persisted as '" +
247 // childNode.setProperty(cleanTag, tags.get(tag));
249 // for (String tag : tags.keySet()) {
250 // String cleanTag = JcrUtils
251 // .removeForbiddenCharacters(tag);
252 // if (!cleanTag.equals(tag))
253 // log.warn("Tag '" + tag + "' persisted as '"
254 // + cleanTag + "'");
255 // curNode.setProperty(cleanTag, tags.get(tag));
258 // We set the class in order to be able to retrieve
259 curNode
.setProperty("class", StructureElement
.class
265 } catch (RepositoryException e
) {
266 throw new SlcException("Cannot add resultPart", e
);
270 public synchronized void addAttachment(final String testResultId
,
271 final SimpleAttachment attachment
) {
274 // TODO: optimize query
276 // Do we have a notion of "currentNode" when we call JCRUtils one
279 // Check if attachment already exists
280 String queryString
= "//testresult[@uuid='" + testResultId
+ "']";
281 Query query
= createQuery(queryString
, Query
.XPATH
);
282 Node resNode
= JcrUtils
.querySingleNode(query
);
284 queryString
= ".//*[@uuid='" + attachment
.getUuid() + "']";
285 query
= createQuery(queryString
, Query
.XPATH
);
286 Node atNode
= JcrUtils
.querySingleNode(query
);
288 if (atNode
!= null) {
289 if (log
.isDebugEnabled())
290 log
.debug("Attachement already There ");
292 if (resNode
.hasNode("attachments"))
293 atNode
= resNode
.getNode("attachments");
295 atNode
= resNode
.addNode("attachments");
298 attachNode
= atNode
.addNode(attachment
.getName());
299 attachNode
.setProperty("uuid", attachment
.getUuid());
300 attachNode
.setProperty("contentType", attachment
305 } catch (RepositoryException e
) {
306 throw new SlcException("Cannot Add Attachment to " + testResultId
,
311 protected TreeTestResult
getTreeTestResult(Session session
,
312 String testResultId
) {
314 String queryString
= "//testresult[@uuid='" + testResultId
+ "']";
315 QueryManager qm
= session
.getWorkspace().getQueryManager();
316 Query query
= qm
.createQuery(queryString
, Query
.XPATH
);
317 Node node
= JcrUtils
.querySingleNode(query
);
320 return (TreeTestResult
) nodeMapper
.load(node
);
322 } catch (RepositoryException e
) {
323 throw new SlcException("Cannot load TestResult with ID "
324 + testResultId
+ " For Session " + session
, e
);
328 public synchronized void updateAttributes(final String testResultId
,
329 final Map
<String
, String
> attributes
) {
331 String queryString
= "//testresult[@uuid='" + testResultId
+ "']";
332 Query query
= createQuery(queryString
, Query
.XPATH
);
333 Node node
= JcrUtils
.querySingleNode(query
);
335 for (String key
: attributes
.keySet()) {
336 node
.setProperty(key
, attributes
.get(key
));
339 } catch (RepositoryException e
) {
340 throw new SlcException(
341 "Cannot update Attributes on TestResult with ID "