001/*
002 * (C) Copyright 2006-2008 Nuxeo SA (http://nuxeo.com/) and others.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 *
016 * Contributors:
017 *     Alexandre Russel
018 *
019 * $Id$
020 */
021
022package org.nuxeo.ecm.platform.annotations.gwt.client.annotea;
023
024import java.util.ArrayList;
025import java.util.HashMap;
026import java.util.List;
027import java.util.Map;
028
029import org.nuxeo.ecm.platform.annotations.gwt.client.model.Annotation;
030import org.nuxeo.ecm.platform.annotations.gwt.client.model.Container;
031import org.nuxeo.ecm.platform.annotations.gwt.client.util.XPointer;
032import org.nuxeo.ecm.platform.annotations.gwt.client.util.XPointerFactory;
033
034import com.google.gwt.xml.client.Document;
035import com.google.gwt.xml.client.Node;
036import com.google.gwt.xml.client.NodeList;
037import com.google.gwt.xml.client.XMLParser;
038
039/**
040 * @author Alexandre Russel
041 */
042public class RDFParser {
043
044    private static final String r = "http://www.w3.org/1999/02/22-rdf-syntax-ns#";
045
046    private static final String nx = "http://www.nuxeo.org/document/uid/";
047
048    public List<Annotation> getAnnotationList(String response) {
049        List<Annotation> result = new ArrayList<Annotation>();
050        Document document = XMLParser.parse(response);
051        NodeList rdfNodes = document.getElementsByTagName("RDF");
052        if (rdfNodes.getLength() == 0) {
053            rdfNodes = document.getElementsByTagName("rdf:RDF");
054        }
055        Node root = rdfNodes.item(0);
056        NodeList nodeList = root.getChildNodes();
057        for (int x = 0; x < nodeList.getLength(); x++) {
058            Annotation annotation = processAnnotation(nodeList.item(x));
059            if (annotation != null) {
060                result.add(annotation);
061            }
062        }
063        return result;
064    }
065
066    public Annotation processAnnotation(Node item) {
067        if (item == null || item.getNamespaceURI() == null || item.getNodeName() == null) {
068            return null;
069        }
070        if (item.getNamespaceURI().equals(r) && item.getNodeName().endsWith(":Description")) {
071            String about = item.getAttributes().item(0).getNodeValue();
072            String annotationUUID = about.substring(about.lastIndexOf(":") + 1);
073            return getAnnotation(annotationUUID, item.getChildNodes());
074        }
075        return null;
076    }
077
078    public Annotation getAnnotation(String annotationUUID, NodeList list) {
079        Annotation annotation = new Annotation(annotationUUID);
080        Map<String, Statement> map = new HashMap<String, Statement>();
081        Map<String, String> fields = new HashMap<String, String>();
082        for (int x = 0; x < list.getLength(); x++) {
083            Node node = list.item(x);
084            if (node.getNodeName().equals("#text") || node.getNodeType() != Node.ELEMENT_NODE) {
085                continue;
086            }
087            if (node.getNamespaceURI().equals(nx)) {
088                String nodeName = node.getNodeName();
089                String name = nodeName.substring(nodeName.indexOf(":") + 1);
090                if ("startContainer".equals(name)) {
091                    annotation.setStartContainer(Container.fromString(node.getFirstChild().getNodeValue()));
092                    continue;
093                }
094                if ("endContainer".equals(name)) {
095                    annotation.setEndContainer(Container.fromString(node.getFirstChild().getNodeValue()));
096                    continue;
097                }
098                fields.put(name, node.getFirstChild().getNodeValue());
099                continue;
100            }
101            Statement statement = new Statement(node);
102            if (statement.getObject().equals("http://www.w3.org/2000/10/annotation-ns#Annotation")) {
103                continue;
104            }
105            map.put(statement.getPredicate(), statement);
106        }
107        annotation.setType(map.get(RDFConstant.R_TYPE).getObject());
108        XPointer xpointer = XPointerFactory.getXPointer(map.get(RDFConstant.A_CONTEXT).getObject());
109
110        annotation.setXpointer(xpointer);
111        if (map.containsKey(RDFConstant.H_BODY)) {
112            Statement s = map.get(RDFConstant.H_BODY);
113            annotation.setBody(parseXMLLiteralForBody(s.getObject()));
114        } else {
115            Statement bodyStatement = map.get(RDFConstant.A_BODY);
116            annotation.setBody(bodyStatement.getObject());
117            if (bodyStatement.isResource()) {
118                annotation.setBodyUrl(true);
119            }
120        }
121
122        if (map.get(RDFConstant.D_CREATOR) != null && map.get(RDFConstant.D_CREATOR).getObject() != null) {
123            annotation.setAuthor(map.get(RDFConstant.D_CREATOR).getObject());
124        }
125        if (map.get(RDFConstant.D_DATE) != null && map.get(RDFConstant.D_DATE).getObject() != null) {
126            annotation.setStringDate(map.get(RDFConstant.D_DATE).getObject());
127        }
128
129        for (Map.Entry<String, Statement> entry : map.entrySet()) {
130            fields.put(entry.getKey(), entry.getValue().getObject());
131        }
132        annotation.setFields(fields);
133
134        return annotation;
135    }
136
137    private String parseXMLLiteralForBody(String html) {
138        if (html.contains("<body>")) {
139            String body = "<body>";
140            int beginIndex = html.indexOf(body) + body.length();
141            int endIndex = html.indexOf("</body>");
142            return html.substring(beginIndex, endIndex);
143        } else if (html.contains("&lt;body&gt;")) {
144            String body = "&lt;body&gt;";
145            int beginIndex = html.indexOf(body) + body.length();
146            int endIndex = html.indexOf("&lt;/body&gt;");
147            return html.substring(beginIndex, endIndex);
148        }
149        return "";
150    }
151
152}