2
* Copyright 2005-2012 Restlet S.A.S.
4
* The contents of this file are subject to the terms of one of the following
5
* open source licenses: Apache 2.0 or LGPL 3.0 or LGPL 2.1 or CDDL 1.0 or EPL
6
* 1.0 (the "Licenses"). You can select the license that you prefer but you may
7
* not use this file except in compliance with one of these Licenses.
9
* You can obtain a copy of the Apache 2.0 license at
10
* http://www.opensource.org/licenses/apache-2.0
12
* You can obtain a copy of the LGPL 3.0 license at
13
* http://www.opensource.org/licenses/lgpl-3.0
15
* You can obtain a copy of the LGPL 2.1 license at
16
* http://www.opensource.org/licenses/lgpl-2.1
18
* You can obtain a copy of the CDDL 1.0 license at
19
* http://www.opensource.org/licenses/cddl1
21
* You can obtain a copy of the EPL 1.0 license at
22
* http://www.opensource.org/licenses/eclipse-1.0
24
* See the Licenses for the specific language governing permissions and
25
* limitations under the Licenses.
27
* Alternatively, you can obtain a royalty free commercial license with less
28
* limitations, transferable or non-transferable, directly at
29
* http://www.restlet.com/products/restlet-framework
31
* Restlet is a registered trademark of Restlet S.A.S.
34
package org.restlet.ext.rdf;
36
import java.io.IOException;
37
import java.io.Writer;
38
import java.util.logging.Level;
40
import org.restlet.Context;
41
import org.restlet.data.MediaType;
42
import org.restlet.data.Reference;
43
import org.restlet.ext.rdf.internal.n3.RdfN3Reader;
44
import org.restlet.ext.rdf.internal.n3.RdfN3Writer;
45
import org.restlet.ext.rdf.internal.ntriples.RdfNTriplesReader;
46
import org.restlet.ext.rdf.internal.ntriples.RdfNTriplesWriter;
47
import org.restlet.ext.rdf.internal.turtle.RdfTurtleReader;
48
import org.restlet.ext.rdf.internal.turtle.RdfTurtleWriter;
49
import org.restlet.ext.rdf.internal.xml.RdfXmlReader;
50
import org.restlet.ext.rdf.internal.xml.RdfXmlWriter;
51
import org.restlet.representation.Representation;
52
import org.restlet.representation.WriterRepresentation;
55
* Generic RDF representation. Provides support for the Resource Description
56
* Framework (RDF) Semantic Web standard. It supports major RDF serialization
57
* formats (n3, Turtle, N-Triples and RDF/XML) and is able to both serialize and
58
* deserialize a {@link Graph}.
60
* @author Jerome Louvel
62
public class RdfRepresentation extends WriterRepresentation {
64
/** The inner graph of links. */
67
/** The inner RDF representation. */
68
private Representation rdfRepresentation;
73
public RdfRepresentation() {
74
super(MediaType.TEXT_XML);
78
* Constructor with argument.
83
* The representation's mediaType.
85
public RdfRepresentation(Graph linkSet, MediaType mediaType) {
91
* Constructor with argument.
94
* The representation's mediaType.
96
public RdfRepresentation(MediaType mediaType) {
101
* Constructor that parsed a given RDF representation into a link set.
103
* @param rdfRepresentation
104
* The RDF representation to parse.
105
* @throws IOException
107
public RdfRepresentation(Representation rdfRepresentation)
109
super(rdfRepresentation.getMediaType());
110
this.rdfRepresentation = rdfRepresentation;
114
* Returns an instance of a graph handler used when parsing the inner RDF
118
* The graph to build.
119
* @return An instance of a graph handler used when parsing the inner RDF
122
public GraphHandler createBuilder(Graph graph) {
123
return new GraphBuilder(this.graph);
127
* Returns an instance of a graph handler used when writing the inner set of
131
* The given media type of the parsed RDF representation.
133
* The character writer to write to.
134
* @return An instance of a graph handler used when writing the inner set of
136
* @throws IOException
138
public GraphHandler createWriter(MediaType mediaType, Writer writer)
140
if (MediaType.TEXT_RDF_N3.equals(getMediaType())) {
141
return new RdfN3Writer(writer);
142
} else if (MediaType.TEXT_XML.equals(getMediaType())) {
143
return new RdfXmlWriter(writer);
144
} else if (MediaType.APPLICATION_ALL_XML.includes(getMediaType())) {
145
return new RdfXmlWriter(writer);
146
} else if (MediaType.TEXT_PLAIN.equals(getMediaType())) {
147
return new RdfNTriplesWriter(writer);
148
} else if (MediaType.TEXT_RDF_NTRIPLES.equals(getMediaType())) {
149
return new RdfNTriplesWriter(writer);
150
} else if (MediaType.APPLICATION_RDF_TURTLE.equals(getMediaType())) {
151
return new RdfTurtleWriter(writer);
154
// Writing for other media types goes here.
159
* Updates the list of known namespaces for the given graph of links.
162
* The given graph of links.
163
* @param GraphHandler
166
private void discoverNamespaces(Graph linkset, GraphHandler graphHandler) {
167
for (Link link : linkset) {
168
discoverNamespaces(link, graphHandler);
173
* Updates the list of known namespaces of the XML writer for the given
178
* @param GraphHandler
181
private void discoverNamespaces(Link link, GraphHandler graphHandler) {
182
// The subject of the link is not discovered, it is generated as the
183
// value of an "about" attribute.
184
if (link.hasLinkSource()) {
185
discoverNamespaces(link.getSourceAsLink(), graphHandler);
186
} else if (link.hasGraphSource()) {
187
discoverNamespaces(link.getSourceAsGraph(), graphHandler);
190
discoverNamespaces(link.getTypeRef(), graphHandler);
192
if (link.hasLinkTarget()) {
193
discoverNamespaces(link.getTargetAsLink(), graphHandler);
194
} else if (link.hasGraphSource()) {
195
discoverNamespaces(link.getSourceAsGraph(), graphHandler);
200
* Updates the list of known namespaces of the XML writer for the given
204
* The given reference.
208
private void discoverNamespaces(Reference reference,
209
GraphHandler graphHandler) {
210
if (!Link.isBlankRef(reference)) {
211
graphHandler.startPrefixMapping(null, reference);
216
* Returns the graph of links.
218
* @return The graph of links.
221
public Graph getGraph() throws Exception {
222
if (this.graph == null) {
223
this.graph = new Graph();
224
parse(createBuilder(this.graph));
230
* Parses the inner RDF representation. The given graph handler is invoked
231
* each time a link is detected.
233
* @param graphHandler
237
public void parse(GraphHandler graphHandler) throws Exception {
238
if (rdfRepresentation != null) {
239
if (MediaType.TEXT_RDF_N3.equals(rdfRepresentation.getMediaType())) {
240
new RdfN3Reader(rdfRepresentation, graphHandler).parse();
241
} else if (MediaType.TEXT_XML.equals(rdfRepresentation
243
new RdfXmlReader(rdfRepresentation, graphHandler).parse();
244
} else if (MediaType.APPLICATION_ALL_XML.includes(rdfRepresentation
246
new RdfXmlReader(rdfRepresentation, graphHandler).parse();
247
} else if (MediaType.TEXT_PLAIN.equals(rdfRepresentation
249
new RdfNTriplesReader(rdfRepresentation, graphHandler).parse();
250
} else if (MediaType.TEXT_RDF_NTRIPLES.equals(rdfRepresentation
252
new RdfNTriplesReader(rdfRepresentation, graphHandler).parse();
253
} else if (MediaType.APPLICATION_RDF_TURTLE
254
.equals(rdfRepresentation.getMediaType())) {
255
new RdfTurtleReader(rdfRepresentation, graphHandler).parse();
256
} else if (MediaType.valueOf("text/rdf+n3").equals(
257
rdfRepresentation.getMediaType())) {
258
// Deprecated media type still in usage
259
new RdfN3Reader(rdfRepresentation, graphHandler).parse();
261
// Parsing for other media types goes here.
266
* Sets the graph of links.
269
* The graph of links.
271
public void setGraph(Graph linkSet) {
272
this.graph = linkSet;
278
* @param graphHandler
279
* @throws IOException
281
public void write(GraphHandler graphHandler) throws IOException {
284
discoverNamespaces(graph, graphHandler);
285
graphHandler.startGraph();
287
for (Link link : graph) {
288
if (link.hasReferenceSource()) {
289
if (link.hasReferenceTarget()) {
290
graphHandler.link(link.getSourceAsReference(),
292
link.getTargetAsReference());
293
} else if (link.hasLiteralTarget()) {
294
graphHandler.link(link.getSourceAsReference(),
296
link.getTargetAsLiteral());
297
} else if (link.hasLinkTarget()) {
298
Context.getCurrentLogger()
300
"Cannot write the representation of a statement due to the fact that the object is neither a Reference nor a literal.");
302
Context.getCurrentLogger()
304
"Cannot write the representation of a statement due to the fact that the object is neither a Reference nor a literal.");
306
} else if (link.hasGraphSource()) {
307
if (link.hasReferenceTarget()) {
308
graphHandler.link(link.getSourceAsGraph(),
310
link.getTargetAsReference());
311
} else if (link.hasLiteralTarget()) {
312
graphHandler.link(link.getSourceAsGraph(),
314
link.getTargetAsLiteral());
315
} else if (link.hasLinkTarget()) {
316
Context.getCurrentLogger()
318
"Cannot write the representation of a statement due to the fact that the object is neither a Reference nor a literal.");
320
Context.getCurrentLogger()
322
"Cannot write the representation of a statement due to the fact that the object is neither a Reference nor a literal.");
326
graphHandler.endGraph();
328
} catch (Exception e) {
329
Context.getCurrentLogger()
331
"Cannot write the RDF graph due to an unexpected exception",
337
public void write(Writer writer) throws IOException {
338
write(createWriter(getMediaType(), writer));