You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@jena.apache.org by an...@apache.org on 2013/02/06 23:50:38 UTC

svn commit: r1443260 - in /jena/Experimental/riot-output/src: main/java/dev/ main/java/riot/ main/java/riot/writer/ test/java/riot/writer/

Author: andy
Date: Wed Feb  6 22:50:37 2013
New Revision: 1443260

URL: http://svn.apache.org/viewvc?rev=1443260&view=rev
Log:
Snapshot - structure reasonable.

Added:
    jena/Experimental/riot-output/src/main/java/dev/ExRIOT_out1.java
    jena/Experimental/riot-output/src/main/java/riot/WriterVariant.java
    jena/Experimental/riot-output/src/main/java/riot/writer/RDFXMLWriter.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TurtleShell.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriter.java
Modified:
    jena/Experimental/riot-output/src/main/java/dev/MainWriter.java
    jena/Experimental/riot-output/src/main/java/dev/PROJECT_RiotWriter.java
    jena/Experimental/riot-output/src/main/java/riot/RDFSerialization.java
    jena/Experimental/riot-output/src/main/java/riot/RDFWriterRegistry.java
    jena/Experimental/riot-output/src/main/java/riot/RiotWriter.java
    jena/Experimental/riot-output/src/main/java/riot/WriterRIOTFactory.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TW2.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriter.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterBlocks.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterFlat.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterBlocks.java
    jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterFlat.java
    jena/Experimental/riot-output/src/main/java/riot/writer/WriterContext.java
    jena/Experimental/riot-output/src/test/java/riot/writer/TestRIOTWriter.java

Added: jena/Experimental/riot-output/src/main/java/dev/ExRIOT_out1.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/dev/ExRIOT_out1.java?rev=1443260&view=auto
==============================================================================
--- jena/Experimental/riot-output/src/main/java/dev/ExRIOT_out1.java (added)
+++ jena/Experimental/riot-output/src/main/java/dev/ExRIOT_out1.java Wed Feb  6 22:50:37 2013
@@ -0,0 +1,30 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package dev;
+
+/** Example writing a model with RIOT */
+public class ExRIOT_out1
+{
+    public static void main(String[] args)
+    {
+        
+    }
+
+}
+

Modified: jena/Experimental/riot-output/src/main/java/dev/MainWriter.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/dev/MainWriter.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/dev/MainWriter.java (original)
+++ jena/Experimental/riot-output/src/main/java/dev/MainWriter.java Wed Feb  6 22:50:37 2013
@@ -31,7 +31,10 @@ import org.apache.jena.riot.system.Prefi
 import org.apache.jena.riot.system.PrefixMapFactory ;
 import org.apache.jena.riot.system.StreamRDF ;
 import riot.RiotWriter ;
-import riot.writer.* ;
+import riot.writer.TriGWriter ;
+import riot.writer.TurtleWriter ;
+import riot.writer.TurtleWriterBlocks ;
+import riot.writer.TurtleWriterFlat ;
 
 import com.hp.hpl.jena.graph.Graph ;
 import com.hp.hpl.jena.graph.Node ;
@@ -47,8 +50,8 @@ public class MainWriter
 {
     public static void main(String ...args)
     {
-        writeTTL() ;
-        //writeTriG() ;
+        //writeTTL() ;
+        writeTriG() ;
     }
     
     public static void writeTriG()
@@ -61,36 +64,45 @@ public class MainWriter
     
     public static void writeTTL()
     {
-        String fn = "W.ttl" ;
+        String fn = "D.ttl" ;
         
         Model m = RDFDataMgr.loadModel(fn) ;
+        RDFDataMgr.read(m, "W.ttl") ;
         
         boolean ALL = false ; 
+        int written = 0 ;
         
-        if ( ALL || true )
+        if ( ALL || false )
         {
             System.out.println("# Write new (flat)") ;
             TurtleWriterFlat.write(System.out, m) ;
             System.out.println("----------------------------------") ;
+            written++ ;
         }
         if ( ALL || false )
         {
             System.out.println("# Write new (Pretty)") ;
-            TurtleWriter2.write(System.out, m) ;
+            TurtleWriter.write(System.out, m) ;
             System.out.println("----------------------------------") ;
+            written++ ;
         }
         if ( ALL || false )
         {
             System.out.println("# Write new (blocks)") ;
             TurtleWriterBlocks.write(System.out, m) ;
             System.out.println("----------------------------------") ;
+            written++ ;
         }
         if ( ALL || false )
         {
             System.out.println("# Write old") ;
             m.write(System.out, "TTL") ;
             System.out.println("----------------------------------") ;
+            written++ ;
         }
+        
+        if ( written > 0 ) System.exit(0) ;
+
 
         System.out.println("# Write (Pretty)") ;
         RiotWriter.write(System.out, m.getGraph(), Lang.TURTLE) ;

Modified: jena/Experimental/riot-output/src/main/java/dev/PROJECT_RiotWriter.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/dev/PROJECT_RiotWriter.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/dev/PROJECT_RiotWriter.java (original)
+++ jena/Experimental/riot-output/src/main/java/dev/PROJECT_RiotWriter.java Wed Feb  6 22:50:37 2013
@@ -20,42 +20,35 @@ package dev;
 
 public class PROJECT_RiotWriter
 {
-    // Prefix map should generate Turtle legal abbrevs.
-    //  Variations.
+    // JSON-LD
+    // check prefixes from model.
+    // Remove prefixes options on statics
     
-    // Sort ouf WriteStreamRDF
-    //  Pull down Blocks-only material to *Blocks.
-    //  Widths for flat writing?
-    //  Start graph end graph
+    // TurtleWriter - use WriterContext
     
-    // Common super class for WriterStreamRDFBlocks/triples - it's the print(..) that is abstract.
-    // Do numbers.s
+    // Base class for WriterContext and then Trutle, trig 
+    // write prefixes, write graph 
+    // TurtleWriter
     
-    // RDFSerialization - relationship to Lang.
-    // Lang+Style?
+    // RDF/XML adapter. [done]
+    // baseURI.
     
-    // NT and NQ writers? Or are RIOT current OK?
-    
-    // Interface and organisation.
+    // ExRIOT_out1 :: write  model
+    // ExRIOT_out2 :: register language and writer 
     
-    // RiotWriter
+    // NT and NQ writers? Or are RIOT current OK?
     
-    // Writing lists
-    // Clean code
-    //    TurtleWriter2
-    //    TW2
-
     // TODO - check for TODO
 
+    // Options.
+    
     // PredicateObjectLists
     //   type to front.
+    // Objects by ","
     // Property order is:
     // 1 - rdf:type (as "a")
     // 2 - other rdf: rdfs: namespace items (sorted)
     // 3 - all other properties, sorted by URI (not qname)  
     //     same properties together - with and without object lists
-    
-    // TriG:
-    // Turtle plus
 }
 

Modified: jena/Experimental/riot-output/src/main/java/riot/RDFSerialization.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/RDFSerialization.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/RDFSerialization.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/RDFSerialization.java Wed Feb  6 22:50:37 2013
@@ -18,9 +18,57 @@
 
 package riot;
 
+import org.apache.jena.atlas.lib.Lib ;
+import org.apache.jena.riot.Lang ;
+
 /** Constants for writable formats */  
 public class RDFSerialization
 {
+    private final Lang lang ;
+    private final WriterVariant variant ;
+
+    public RDFSerialization(Lang lang) { this(lang, null) ; }
+    
+    public RDFSerialization(Lang lang, WriterVariant variant)
+    {
+        this.lang = lang ;
+        this.variant = variant ;
+    }
+
+    public Lang getLang()
+    {
+        return lang ;
+    }
+
+    public WriterVariant getVariant()
+    {
+        return variant ;
+    }
+
+    @Override
+    public int hashCode()
+    {
+        final int prime = 31 ;
+        int result = 1 ;
+        result = prime * result + ((lang == null) ? 0 : lang.hashCode()) ;
+        result = prime * result + ((variant == null) ? 0 : variant.hashCode()) ;
+        return result ;
+    }
 
+    @Override
+    public boolean equals(Object obj)
+    {
+        if (this == obj) return true ;
+        if (obj == null) return false ;
+        if (getClass() != obj.getClass()) return false ;
+        RDFSerialization other = (RDFSerialization)obj ;
+        if ( ! Lib.equal(lang, other.lang) )
+            return false ;
+        if ( ! Lib.equal(variant, other.variant) )
+            return false ;
+        return true ;
+    }
+    
+    
 }
 

Modified: jena/Experimental/riot-output/src/main/java/riot/RDFWriterRegistry.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/RDFWriterRegistry.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/RDFWriterRegistry.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/RDFWriterRegistry.java Wed Feb  6 22:50:37 2013
@@ -18,77 +18,154 @@
 
 package riot;
 
-import static org.apache.jena.riot.RDFLanguages.N3 ;
-import static org.apache.jena.riot.RDFLanguages.NQUADS ;
-import static org.apache.jena.riot.RDFLanguages.NTRIPLES ;
-import static org.apache.jena.riot.RDFLanguages.RDFJSON ;
-import static org.apache.jena.riot.RDFLanguages.RDFXML ;
-import static org.apache.jena.riot.RDFLanguages.TRIG ;
 import static org.apache.jena.riot.RDFLanguages.TURTLE ;
 
 import java.io.OutputStream ;
 import java.util.HashMap ;
 import java.util.Map ;
 
+import org.apache.jena.atlas.lib.Lib ;
 import org.apache.jena.riot.Lang ;
-import riot.writer.TurtleWriter2 ;
+import org.apache.jena.riot.RDFLanguages ;
+import org.apache.jena.riot.RiotException ;
+import riot.writer.TurtleWriter ;
 
 import com.hp.hpl.jena.graph.Graph ;
 
 public class RDFWriterRegistry
 {
     // Registry with the pretty write 
-    static Map<Lang, WriterRIOTFactory> registryPretty = new HashMap<Lang, WriterRIOTFactory>() ;
+    static Map<RDFSerialization, WriterRIOTFactory> registry = new HashMap<RDFSerialization, WriterRIOTFactory>() ;
+
+    public static WriterVariant wvPretty = new WriterVariant("pretty" ) ; 
+    public static WriterVariant wvBlocks = new WriterVariant("blocks" ) ; 
+    public static WriterVariant wvFlat = new WriterVariant("flat" ) ;
+    
+    public static RDFSerialization TurtlePretty = new RDFSerialization(Lang.TURTLE, wvPretty) ;
+    public static RDFSerialization Turtle       = TurtlePretty ; 
+    public static RDFSerialization TurtleBlocks = new RDFSerialization(Lang.TURTLE, wvBlocks) ;
+    public static RDFSerialization TurtleFlat   = new RDFSerialization(Lang.TURTLE, wvFlat) ;
+
+    public static RDFSerialization NTriples     = new RDFSerialization(Lang.NTRIPLES) ;
+    public static RDFSerialization NQuads       = new RDFSerialization(Lang.NQUADS) ;
+
+    public static RDFSerialization TrigPretty   = new RDFSerialization(Lang.TRIG, wvPretty) ;
+    public static RDFSerialization Trig         = TrigPretty ; 
+    public static RDFSerialization TrigBlocks   = new RDFSerialization(Lang.TRIG, wvBlocks) ;
+    public static RDFSerialization TrigFlat     = new RDFSerialization(Lang.TRIG, wvFlat) ;
+
+    // RDF/JSON
+    // 
+    public static WriterVariant wvPlain         = new WriterVariant("plain" ) ; 
+    public static WriterVariant wvAbbrev        = new WriterVariant("flat" ) ;
+    
+    public static RDFSerialization RDFXMLPretty = new RDFSerialization(Lang.RDFXML, wvAbbrev) ;
+    public static RDFSerialization RDFXMLAbbrev = RDFXMLPretty ;
+    public static RDFSerialization RDFXML       = RDFXMLPretty ;
+    public static RDFSerialization RDFXMLPlain  = new RDFSerialization(Lang.RDFXML, wvPlain) ;
     
-    // Registry with the scalable writer 
-    static Map<Lang, WriterRIOTFactory> registryStreaming = new HashMap<Lang, WriterRIOTFactory>() ;
+    public static RDFSerialization RDFJSON      = new RDFSerialization(Lang.RDFJSON) ;
     
     static WriterRIOTFactory wfactory = new WriterRIOTFactory() {
         @Override
-        public RiotSerializer create(OutputStream out, Graph graph, Lang lang)
+        public RiotSerializer create(OutputStream out, Graph graph, RDFSerialization serialization)
         {
-            // Temporary hack.
-            RiotSerializer w = null ;
-
-            if ( TURTLE.equals(lang) )
-                w = createTurtle(out, graph) ;
-            else if ( NTRIPLES.equals(lang) )
-                w = createNTriples(out, graph) ;
-            else if ( N3.equals(lang) )
-                w = createN3(out, graph) ;
-            else if ( RDFJSON.equals(lang) )
-                w = createRDFJSON(out, graph) ;
-            else if ( RDFXML.equals(lang) )
-                w = createRDFJSON(out, graph) ;
-            else if ( TRIG.equals(lang) )
-                w = createTrig(out, graph) ;
-            else if ( NQUADS.equals(lang) )
-                w = createNQuads(out, graph) ;
-            return w ;
+            // Built-ins
+            if ( Lib.equal(TurtlePretty, serialization) )
+                return createTurtle(out, graph) ;
+            if ( Lib.equal(TurtleBlocks, serialization) )
+                return null ;
+            if ( Lib.equal(TurtleFlat, serialization) )
+                return null ;
+            if ( Lib.equal(NTriples, serialization) )
+                return createNTriples(out, graph) ;
+            if ( Lib.equal(RDFJSON, serialization) )
+                return createRDFJSON(out, graph) ;
+            if ( Lib.equal(RDFXMLPretty, serialization) )
+                return createRDFXML(out, graph) ;
+            if ( Lib.equal(RDFXMLPlain, serialization) )
+                return null ;
+            // graphs in quad format.
+            if ( Lib.equal(TrigPretty, serialization) )
+                return createTrig(out, graph) ;
+            if ( Lib.equal(TrigBlocks, serialization) )
+                return null ;
+            if ( Lib.equal(TrigFlat, serialization) )
+                return null ;
+            if ( Lib.equal(NQuads, serialization) )
+                return createNQuads(out, graph) ;
+            return null ;
         }} ;
 
     static { init() ; }
     
     static void init()
     {
-        registryPretty.put(TURTLE, wfactory) ;
-        registryPretty.put(NTRIPLES, wfactory) ;
-        registryPretty.put(N3, wfactory) ;
-        registryPretty.put(RDFJSON, wfactory) ;
-        registryPretty.put(TRIG, wfactory) ;
-        registryPretty.put(NQUADS, wfactory) ;
+        register(TurtlePretty,  wfactory) ;
+        register(TurtleBlocks,  wfactory) ;
+        register(TurtleFlat,    wfactory) ;
+        
+        register(NTriples,      wfactory) ;
+        register(RDFJSON,       wfactory) ;
+
+        register(RDFXMLPretty,  wfactory) ;
+        register(RDFXMLPlain,   wfactory) ;
+
+        register(TrigPretty,    wfactory) ;
+        register(TrigBlocks,    wfactory) ;
+        register(TrigFlat,      wfactory) ;
+        
+        register(NQuads,        wfactory) ;
+        
     }
     
+    private static void register(RDFSerialization serialization, WriterRIOTFactory wfactory)
+    {
+        registry.put(serialization, wfactory) ;
+    }
+
+    // Map Lang to default output format.
     public static WriterRIOTFactory getWriterFactory(Lang lang)
     {
-        return registryPretty.get(lang) ;
+        RDFSerialization serialization = defaultSerialization(lang) ;
+        if ( serialization == null )
+            throw new RiotException("No default serialization for language "+lang) ;
+        return getWriterFactory(serialization) ;  
     }
 
+    public static RDFSerialization defaultSerialization(Lang lang)
+    {
+        if ( RDFLanguages.TURTLE.equals(lang) )     return Turtle ;
+        if ( RDFLanguages.N3.equals(lang) )         return Turtle ;
+        if ( RDFLanguages.NTRIPLES.equals(lang) )   return NTriples ;
+        
+        if ( RDFLanguages.TRIG.equals(lang) )       return Trig ;
+        if ( RDFLanguages.NQUADS.equals(lang) )     return NQuads ;
+        
+        if ( RDFLanguages.RDFXML.equals(lang) )     return RDFXML ;
+        if ( RDFLanguages.RDFJSON.equals(lang) )    return RDFJSON ;
+        
+        return null ;
+    }
+    
+    
+    public static WriterRIOTFactory getWriterFactory(Lang lang, WriterVariant variant)
+    {
+        return getWriterFactory(new RDFSerialization(lang, variant)) ;
+    }
+    
+    public static WriterRIOTFactory getWriterFactory(RDFSerialization serialization)
+    {
+        return registry.get(serialization) ;
+    }
+    
+    // builtins.
+    
     private static RiotSerializer createTurtle(final OutputStream out, final Graph graph)
     {
         // TODO Temporary
         return new RiotSerializer() {
-            @Override public void write() { TurtleWriter2.write(out, graph, graph.getPrefixMapping().getNsPrefixMap()) ; }
+            @Override public void write() { TurtleWriter.write(out, graph, graph.getPrefixMapping().getNsPrefixMap()) ; }
             @Override public Lang getLang() { return TURTLE ; }
         } ;
     }
@@ -97,7 +174,7 @@ public class RDFWriterRegistry
     {
         // TODO Temporary
         return new RiotSerializer() {
-            @Override public void write() { TurtleWriter2.write(out, graph, graph.getPrefixMapping().getNsPrefixMap()) ; }
+            @Override public void write() { TurtleWriter.write(out, graph, graph.getPrefixMapping().getNsPrefixMap()) ; }
             @Override public Lang getLang() { return TURTLE ; }
         } ;
     }
@@ -105,6 +182,11 @@ public class RDFWriterRegistry
     private static RiotSerializer createNTriples(OutputStream out, Graph graph)
     { return null ; }
 
+    private static RiotSerializer createRDFXML(OutputStream out, Graph graph)
+    {
+        return null ;
+    }
+
     private static RiotSerializer createRDFJSON(OutputStream out, Graph graph)
     { return null ; }
 

Modified: jena/Experimental/riot-output/src/main/java/riot/RiotWriter.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/RiotWriter.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/RiotWriter.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/RiotWriter.java Wed Feb  6 22:50:37 2013
@@ -25,20 +25,144 @@ import org.apache.jena.atlas.lib.NotImpl
 import org.apache.jena.riot.Lang ;
 
 import com.hp.hpl.jena.graph.Graph ;
+import com.hp.hpl.jena.query.Dataset ;
+import com.hp.hpl.jena.rdf.model.Model ;
 import com.hp.hpl.jena.sparql.core.DatasetGraph ;
 
 public class RiotWriter
 {
+    /** Write the model to the output stream in the default serialization for the language.
+     * @param out       OutputStream
+     * @param model     Graph to write
+     * @param lang      Language for the seralization.
+     */
+    public static void write(OutputStream out, Model model, Lang lang)
+    {
+        write(out, model.getGraph(), lang) ;
+    }
+
+    /** Write the model to the output stream for the language and variant of serialization. 
+     * @param out       OutputStream
+     * @param model     Model to write
+     * @param lang      Language for the seralization.
+     * @param variant   Language seralization variant
+     */
+    public static void write(OutputStream out, Model model, Lang lang, WriterVariant variant) 
+    {
+        write(out, model.getGraph(), lang, variant) ;
+    }
+
+    /** Write the model to the output stream in the default serialization for the language.
+     * @param out           OutputStream
+     * @param model         Model to write
+     * @param serialization Serialization format
+     */
+    public static void write(OutputStream out, Model model, RDFSerialization serialization)
+    {
+        write(out, model.getGraph(), serialization) ;
+    }
+    
+    /** Write the graph to the output stream in the default serialization for the language.
+     * @param out       OutputStream
+     * @param graph     Graph to write
+     * @param lang      Language for the seralization.
+     */
     public static void write(OutputStream out, Graph graph, Lang lang)
     {
-        WriterRIOTFactory wf = RDFWriterRegistry.getWriterFactory(lang) ;
-        RiotSerializer w = wf.create(out, graph, lang) ;
+        RDFSerialization serialization = RDFWriterRegistry.defaultSerialization(lang) ;
+        write(out, graph, serialization) ;
+    }
+
+    /** Write the graph to the output stream for the language and variant of serialization. 
+     * @param out       OutputStream
+     * @param graph     Graph to write
+     * @param lang      Language for the seralization.
+     * @param variant   Language seralization variant
+     */
+    public static void write(OutputStream out, Graph graph, Lang lang, WriterVariant variant) 
+    {
+        RDFSerialization serialization = new RDFSerialization(lang, variant) ;
+        write(out, graph, serialization) ;
+    }
+
+    /** Write the graph to the output stream in the default serialization for the language.
+     * @param out           OutputStream
+     * @param graph         Graph to write
+     * @param serialization Serialization format
+     */
+    public static void write(OutputStream out, Graph graph, RDFSerialization serialization)
+    {
+        WriterRIOTFactory wf = RDFWriterRegistry.getWriterFactory(serialization) ;
+        RiotSerializer w = wf.create(out, graph, serialization) ;
         w.write() ;
     }
-    
-    public static void write(OutputStream out, DatasetGraph datasetGraph, Lang lang)
+
+    /** Write the Dataset to the output stream in the default serialization for the language.
+     * @param out       OutputStream
+     * @param dataset   Dataset to write
+     * @param lang      Language for the seralization.
+     */
+    public static void write(OutputStream out, Dataset dataset, Lang lang)
     {
+        write(out, dataset.asDatasetGraph(), lang) ;
+    }
+
+    /** Write the graph to the output stream for the language and variant of serialization. 
+     * @param out       OutputStream
+     * @param dataset   Dataset to write
+     * @param lang      Language for the seralization.
+     * @param variant   Language seralization variant
+     */
+    public static void write(OutputStream out, Dataset dataset, Lang lang, WriterVariant variant) 
+    {
+        write(out, dataset.asDatasetGraph(), lang, variant) ;
+    }
+
+    /** Write the graph to the output stream in the default serialization for the language.
+     * @param out           OutputStream
+     * @param dataset       Dataset to write
+     * @param serialization Serialization format
+     */
+    public static void write(OutputStream out, Dataset dataset, RDFSerialization serialization)
+    {
+        write(out, dataset.asDatasetGraph(), serialization) ;
+    }
+
+    /** Write the DatasetGraph to the output stream in the default serialization for the language.
+     * @param out       OutputStream
+     * @param dataset   DatasetGraph to write
+     * @param lang      Language for the seralization.
+     */
+    public static void write(OutputStream out, DatasetGraph dataset, Lang lang)
+    {
+        RDFSerialization serialization = RDFWriterRegistry.defaultSerialization(lang) ;
+        write(out, dataset, serialization) ;
+    }
+
+    /** Write the graph to the output stream for the language and variant of serialization. 
+     * @param out       OutputStream
+     * @param dataset   DatasetGraph to write
+     * @param lang      Language for the seralization.
+     * @param variant   Language seralization variant
+     */
+    public static void write(OutputStream out, DatasetGraph dataset, Lang lang, WriterVariant variant) 
+    {
+        RDFSerialization serialization = new RDFSerialization(lang, variant) ;
+        write(out, dataset, serialization) ;
+    }
+
+    /** Write the graph to the output stream in the default serialization for the language.
+     * @param out           OutputStream
+     * @param dataset       DatasetGraph to write
+     * @param serialization Serialization format
+     */
+    public static void write(OutputStream out, DatasetGraph dataset, RDFSerialization serialization)
+    {
+        WriterRIOTFactory wf = RDFWriterRegistry.getWriterFactory(serialization) ;
         throw new NotImplemented() ;
+//        RiotSerializer w = null ; //??
+//        w.write() ;
     }
+    
 }
 

Modified: jena/Experimental/riot-output/src/main/java/riot/WriterRIOTFactory.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/WriterRIOTFactory.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/WriterRIOTFactory.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/WriterRIOTFactory.java Wed Feb  6 22:50:37 2013
@@ -20,12 +20,10 @@ package riot;
 
 import java.io.OutputStream ;
 
-import org.apache.jena.riot.Lang ;
-
 import com.hp.hpl.jena.graph.Graph ;
 
 /** Factory for creating writers (usually one-time use but see a particular writer for details) */ 
 public interface WriterRIOTFactory
 {
-    public RiotSerializer create(OutputStream out, Graph graph, Lang lang) ;
+    public RiotSerializer create(OutputStream out, Graph graph, RDFSerialization syntaxForm) ;
 }

Added: jena/Experimental/riot-output/src/main/java/riot/WriterVariant.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/WriterVariant.java?rev=1443260&view=auto
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/WriterVariant.java (added)
+++ jena/Experimental/riot-output/src/main/java/riot/WriterVariant.java Wed Feb  6 22:50:37 2013
@@ -0,0 +1,53 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package riot;
+
+import org.apache.jena.atlas.lib.Lib ;
+
+import com.hp.hpl.jena.sparql.util.Symbol ;
+
+public class WriterVariant
+{
+    private final Symbol symbol ;
+    
+    public WriterVariant(String name)
+    {
+        symbol = Symbol.create(name) ;
+    }
+
+    @Override
+    public int hashCode()
+    {
+        final int prime = 31 ;
+        int result = 1 ;
+        result = prime * result + ((symbol == null) ? 0 : symbol.hashCode()) ;
+        return result ;
+    }
+
+    @Override
+    public boolean equals(Object obj)
+    {
+        if (this == obj) return true ;
+        if (obj == null) return false ;
+        if (getClass() != obj.getClass()) return false ;
+        WriterVariant other = (WriterVariant)obj ;
+        if ( ! Lib.equal(symbol, other.symbol) ) return false ;
+        return true ;
+    }
+}

Added: jena/Experimental/riot-output/src/main/java/riot/writer/RDFXMLWriter.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/RDFXMLWriter.java?rev=1443260&view=auto
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/RDFXMLWriter.java (added)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/RDFXMLWriter.java Wed Feb  6 22:50:37 2013
@@ -0,0 +1,69 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package riot.writer;
+
+import java.io.OutputStream ;
+
+import com.hp.hpl.jena.graph.Graph ;
+import com.hp.hpl.jena.rdf.model.Model ;
+import com.hp.hpl.jena.rdf.model.ModelFactory ;
+import com.hp.hpl.jena.rdf.model.RDFWriter ;
+import com.hp.hpl.jena.xmloutput.impl.Abbreviated ;
+import com.hp.hpl.jena.xmloutput.impl.Basic ;
+
+/** Wrapper to the RDF/XML writer (preRIOT).
+ */
+
+public class RDFXMLWriter
+{
+    public static void writePlain(OutputStream out, Model model)
+    {
+        RDFWriter w = new Basic() ;
+        w.write(model, out, null) ;
+    }
+    
+    public static void writeAbbrev(OutputStream out, Model model)
+    {
+        RDFWriter w = new Abbreviated() ;
+        w.write(model, out, null) ;
+    }
+    
+    // RiotWriter
+    public static void write(OutputStream out, RDFWriter writer, Graph graph)
+    {
+        write(out, writer, graph, null) ;
+    }
+    
+    public static void write(OutputStream out, RDFWriter rdfWriter, Graph graph, String baseURI)
+    {
+        rdfWriter.write(ModelFactory.createModelForGraph(graph), out, baseURI) ;
+    }
+
+    public static void write(OutputStream out, RDFWriter writer, Model model)
+    {
+        write(out, writer, model, null) ;
+    }
+    
+    public static void write(OutputStream out, RDFWriter rdfWriter, Model model, String baseURI)
+    {
+        rdfWriter.write(model, out, baseURI) ;
+    }
+
+}
+

Modified: jena/Experimental/riot-output/src/main/java/riot/writer/TW2.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TW2.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TW2.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TW2.java Wed Feb  6 22:50:37 2013
@@ -29,14 +29,17 @@ import java.util.Map.Entry ;
 import org.apache.jena.atlas.io.IndentedWriter ;
 import org.apache.jena.atlas.iterator.Iter ;
 import org.apache.jena.atlas.lib.Pair ;
+import org.apache.jena.riot.out.NodeToLabel ;
+import org.apache.jena.riot.system.PrefixMap ;
+import org.apache.jena.riot.system.PrefixMapFactory ;
 import riot.out.NodeFormatter ;
+import riot.out.NodeFormatterTTL ;
 
 import com.hp.hpl.jena.graph.Graph ;
 import com.hp.hpl.jena.graph.Node ;
 import com.hp.hpl.jena.graph.Triple ;
 import com.hp.hpl.jena.sparql.util.FmtUtils ;
 import com.hp.hpl.jena.util.iterator.ExtendedIterator ;
-//import com.hp.hpl.jena.sparql.util.FmtUtils ;
 
 /** Support code for the RIOT TurtleWriter */ 
 public class TW2
@@ -195,7 +198,9 @@ public class TW2
 
     static final boolean recordObjectMisses = true ; 
     
-    /** Find all embeddable objects */  
+    /** Find all embeddable objects */
+    
+    // TODO Remove.
     @SuppressWarnings("null")
     static void findOneConnectedBNodeObjects(WriterContext cxt)
     {
@@ -247,7 +252,7 @@ public class TW2
     }
 
     /* Get all the triples for the graph.find */
-    private static long countTriples(Graph graph, Node s, Node p, Node o)
+    static long countTriples(Graph graph, Node s, Node p, Node o)
     {
         ExtendedIterator<Triple> iter = graph.find(s, p, o) ;
         try { return Iter.count(iter) ; }
@@ -276,17 +281,31 @@ public class TW2
         } finally { iter.close() ; }
     }
 
+    static WriterContext createContext(IndentedWriter out, Graph graph, Map<String, String> prefixMap)
+    {
+        WriterContext cxt = new WriterContext() ;
+        PrefixMap pmap = PrefixMapFactory.create() ;
+        for ( Entry<String, String> e : prefixMap.entrySet() )
+            pmap.add(e.getKey(), e.getValue()) ;
+        
+        cxt.out = out ;
+        cxt.prefixMap = prefixMap ;
+        cxt.nodeFmt = new NodeFormatterTTL(null,  pmap, NodeToLabel.createScopeByDocument()) ;
+        cxt.graph = graph ;
+        return cxt ;
+    }
+    
     static void writeNode(WriterContext cxt, Node node)
     {
         writeNode(cxt.out, cxt.nodeFmt, node) ;
     }
     
-    static void writeNode(IndentedWriter out, NodeFormatter fmt,Node node)
+    static void writeNode(IndentedWriter out, NodeFormatter fmt, Node node)
     {
         fmt.format(out, node) ;
     }
         
-    static void writeNode(IndentedWriter out, Map<String, String> prefixMap, Node node)
+    static void X_writeNode(IndentedWriter out, Map<String, String> prefixMap, Node node)
     {
         //TODO Temporary.
         // See RIOT NodeFormatter

Modified: jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriter.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriter.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriter.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriter.java Wed Feb  6 22:50:37 2013
@@ -29,7 +29,8 @@ import com.hp.hpl.jena.graph.Node ;
 import com.hp.hpl.jena.query.Dataset ;
 import com.hp.hpl.jena.sparql.core.DatasetGraph ;
 
-public class TriGWriter
+/** TriG pretty writer */
+public class TriGWriter extends TurtleShell
 {
     public static final int GRAPH_INDENT = 4 ;
     
@@ -41,29 +42,46 @@ public class TriGWriter
     public static void write(OutputStream out, DatasetGraph dsg,  Map<String, String> prefixMap)
     {
         IndentedWriter iOut = new IndentedWriter(out, false) ;
+        
+        TriGWriter w = new TriGWriter(iOut, prefixMap) ;
+        w.write(dsg) ;
+        iOut.flush() ;
+    }
+
+    public TriGWriter(IndentedWriter out, Map<String, String> prefixMap)
+    {
+        super(out, prefixMap) ;
+    }
+
+    private void write(DatasetGraph dsg)
+    {
+        writePrefixes(prefixMap) ;
+
         Iterator<Node> graphNames = dsg.listGraphNodes() ;
         
-        writeGraph(iOut, null, dsg.getDefaultGraph(),  prefixMap) ;
+        writeGraph(null, dsg.getDefaultGraph()) ;
         
         for ( ; graphNames.hasNext() ; )
         {
-            iOut.println() ;
+            out.println() ;
             Node gn = graphNames.next() ;
-            writeGraph(iOut, gn, dsg.getGraph(gn),  prefixMap) ;
+            writeGraph(gn, dsg.getGraph(gn)) ;
         }
-        iOut.flush() ;
     }
 
-    private static void writeGraph(IndentedWriter out, Node name, Graph graph,  Map<String, String> prefixMap)
+    
+    
+    private void writeGraph(Node name, Graph graph)
     {
         if ( name != null )
         {
-            TW2.writeNode(out, prefixMap, name) ;
+            writeNode(name) ;
             out.print("  ") ;
         }
         out.println("{") ;
         out.incIndent(GRAPH_INDENT) ;
-        TurtleWriter2.write(out, graph, prefixMap) ;
+        // Pretty Turtle Writer. 
+        writeGraph(graph) ;
         
         out.decIndent(GRAPH_INDENT) ;
         out.ensureStartOfLine() ;

Modified: jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterBlocks.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterBlocks.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterBlocks.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterBlocks.java Wed Feb  6 22:50:37 2013
@@ -25,6 +25,9 @@ import org.apache.jena.riot.system.Strea
 
 import com.hp.hpl.jena.sparql.core.DatasetGraph ;
 
+/** TriG writer that streams - print in blocks of quads clustered
+ *  by adjacent same graph and same subject
+ */
 public class TriGWriterBlocks extends WriterStreamBase
 {
     public static void write(IndentedWriter out, DatasetGraph datasetGraph, Map<String, String> prefixes) 

Modified: jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterFlat.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterFlat.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterFlat.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TriGWriterFlat.java Wed Feb  6 22:50:37 2013
@@ -25,6 +25,10 @@ import org.apache.jena.riot.system.Strea
 
 import com.hp.hpl.jena.sparql.core.DatasetGraph ;
 
+/** TriG writer that writes quads one per line
+ *  in TriG form with prefixes and short form literals (e.g. integers) 
+ */
+
 public class TriGWriterFlat extends WriterStreamBase
 {
     public static void write(IndentedWriter out, DatasetGraph datasetGraph, Map<String, String> prefixes) 

Added: jena/Experimental/riot-output/src/main/java/riot/writer/TurtleShell.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TurtleShell.java?rev=1443260&view=auto
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TurtleShell.java (added)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TurtleShell.java Wed Feb  6 22:50:37 2013
@@ -0,0 +1,499 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for ad
+ * ditional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package riot.writer;
+
+import static riot.writer.WriterConst.INDENT_OBJECT ;
+import static riot.writer.WriterConst.INDENT_PREDICATE ;
+import static riot.writer.WriterConst.LONG_PREDICATE ;
+import static riot.writer.WriterConst.LONG_SUBJECT ;
+import static riot.writer.WriterConst.MIN_GAP ;
+import static riot.writer.WriterConst.RDF_First ;
+import static riot.writer.WriterConst.RDF_Nil ;
+import static riot.writer.WriterConst.RDF_Rest ;
+import static riot.writer.WriterConst.iriType ;
+import static riot.writer.WriterConst.rdfNS ;
+
+import java.util.* ;
+import java.util.Map.Entry ;
+
+import org.apache.jena.atlas.io.IndentedWriter ;
+import org.apache.jena.atlas.lib.Pair ;
+import org.apache.jena.riot.out.NodeToLabel ;
+import org.apache.jena.riot.system.PrefixMap ;
+import org.apache.jena.riot.system.PrefixMapFactory ;
+import riot.other.GLib ;
+import riot.out.NodeFormatter ;
+import riot.out.NodeFormatterTTL ;
+
+import com.hp.hpl.jena.graph.Graph ;
+import com.hp.hpl.jena.graph.Node ;
+import com.hp.hpl.jena.graph.Triple ;
+import com.hp.hpl.jena.util.iterator.ExtendedIterator ;
+
+/** Base class to support the pretty formsl of Turtle-related languages (Turle, TriG) */ 
+public class TurtleShell
+{
+    IndentedWriter out ; 
+    NodeFormatter nodeFmt ;
+    Map<String, String> prefixMap ;
+
+    // Per graph member variables.
+    Graph graph ; 
+    Set<Node> nestedObjects ;           // Blank nodes that have one incoming triple
+    Map<Node, List<Node>> lists;        // The head node in each well-formed lists -> list elements 
+    Map<Node, List<Node>> freeLists;    // List that do not have any incoming triples 
+    Map<Node, List<Node>> nLinkedLists; // Lists that have more than one incoming triple 
+    Collection<Node> listElts ;         // All nodes that are part of list structures.
+
+    TurtleShell(IndentedWriter out, Map<String, String> prefixMap)
+    {
+        this.out = out ;
+        this.prefixMap = prefixMap ;
+        
+        //TODO = use only 
+        PrefixMap pmap = PrefixMapFactory.create() ;
+        for ( Entry<String, String> e : prefixMap.entrySet() )
+            pmap.add(e.getKey(), e.getValue()) ;
+        
+        nodeFmt = new NodeFormatterTTL(null,  pmap, NodeToLabel.createScopeByDocument()) ;
+        
+    }
+                
+
+    // and a blank line.
+    protected void writePrefixes(Map<String, String> prefixMap)
+    {
+        // TODO
+        TW2.writePrefixes(out, prefixMap) ;
+        if ( ! prefixMap.isEmpty() )
+            out.println();
+    }
+    
+    private void initGraph(Graph graph)
+    {
+        this.graph = graph ;
+        findOneConnectedBNodeObjects() ;
+        findLists() ;
+        
+        // TODO Right check?
+        // Stop head of lists printed as triples going all the way to the good part. 
+        nestedObjects.removeAll(listElts) ;
+        
+    }
+    
+    static boolean recordObjectMisses = true ; 
+    
+    private void findOneConnectedBNodeObjects()
+    {
+        Set<Node> bNodesObj1 = new HashSet<Node>()  ;        // The subject of exactly one triple.
+        Set<Node> rejects = recordObjectMisses ? new HashSet<Node>() : null ;      // Nodes known not to meet the requirement.
+
+        ExtendedIterator<Triple> iter = graph.find(Node.ANY, Node.ANY, Node.ANY) ;
+        try {
+            for ( ; iter.hasNext() ; )
+            {
+                Triple t = iter.next() ;
+                Node obj = t.getObject() ;
+                if ( ! obj.isBlank() )
+                    continue ;
+                if ( rejects != null && rejects.contains(obj) )
+                    continue ;
+                // No point checking bNodesObj1.
+                Node n = connectedOnce(obj) ;
+                if ( n != null )
+                    bNodesObj1.add(n) ;
+            }
+        } finally { iter.close() ; }
+        nestedObjects = bNodesObj1 ;
+    }
+
+    private Node connectedOnce(Node obj)
+    {
+        ExtendedIterator<Triple> iter = graph.find(Node.ANY, Node.ANY, obj) ;
+        int count = 0 ;
+        try {
+            if ( ! iter.hasNext() ) return null ;
+            iter.next() ;
+            if ( ! iter.hasNext() ) return obj ;
+            return null ;
+        } finally { iter.close() ; }
+    }
+
+    // --- Lists setup
+    /** Find all list heads and all nodes in well-formed lists.
+     * Return a (list head -> Elements map), list elements)  
+     */
+    void findLists()
+    {
+        // HashSets for use during parsing.
+        lists = new HashMap<Node, List<Node>>() ;
+        // Lists that are printed as free standing lists. 
+        freeLists = new HashMap<Node, List<Node>>() ;
+        // Lists that are shared 
+        nLinkedLists = new HashMap<Node, List<Node>>() ;
+        // All elements of lists we will print as lists. 
+        listElts = new HashSet<Node>() ;
+        List<Triple> tails = TW2.triples(graph, Node.ANY, RDF_Rest, RDF_Nil) ;
+        for ( Triple t : tails )
+        {
+            // Returns the elements, reversed.
+            Collection<Node> listElts2 = new HashSet<Node>() ;
+            Pair<Node, List<Node>> p = followTailToHead(t.getSubject(), listElts2) ;
+            if ( p != null )
+            {
+                Node headElt = p.getLeft() ; 
+                // Free standing?private
+                List<Node> elts = p.getRight() ;
+                long numLinks = TW2.countTriples(graph, null, null, headElt) ;
+                if ( numLinks == 1 )
+                    lists.put(headElt, elts) ;
+                else if ( numLinks == 0 )
+                    // 0 connected lists
+                    freeLists.put(headElt, elts) ;
+                else 
+                {
+                    // Two triples to this list.
+                    // TODO Can't print the list in abbreviated form as we need to name the head.
+                    // Take out first element, print rest normally, new head is a one-connected node.
+                    //OR do in the printing. (N3 has "_:b :-")
+                    nLinkedLists.put(headElt, elts) ;
+                }
+                listElts.addAll(listElts2) ;
+            }
+        }
+    }
+    
+    // return head elt node, list of elements.
+    private Pair<Node, List<Node>> followTailToHead(Node lastListElt, Collection<Node> listElts)
+    {
+        List<Node> listCells = new ArrayList<Node>() ;
+        List<Node> eltsReversed = new ArrayList<Node>() ;
+        List<Triple> acc =  new ArrayList<Triple>() ;
+        Node x = lastListElt ;
+        
+        for ( ; ; )
+        {
+            if ( ! validListElement(x, acc) )
+            {
+                if ( listCells.size() == 0 )
+                    // No earlier valid list.
+                    return null ;
+                // Fix up to previous valid list cell.
+                x = listCells.remove(listCells.size()-1) ;
+                break ;
+            }
+            
+            Triple t = TW2.triple1(graph, x, RDF_First, null) ;
+            if ( t == null )
+                return null ;
+            eltsReversed.add(t.getObject()) ;
+            listCells.add(x) ;
+            
+            // Try to move up the list.
+            List<Triple> acc2 = TW2.triples(graph, null, null, x) ;
+            long numRest = TW2.countTriples(graph, null, RDF_Rest, x) ;
+            if ( numRest != 1 )
+            {
+                // Head of well-formed list.
+                // Classified by 0,1,more links later.
+                listCells.add(x) ;
+                break ;
+            }
+            // numRest == 1
+            int numLinks = acc2.size() ;
+            if ( numLinks > 1 )
+                // Non-list links to x
+                break ;
+            // Valid.
+            Triple tLink = acc2.get(0) ;
+            x = tLink.getSubject() ;
+        }
+        // Success.
+        listElts.addAll(listCells) ;
+        Collections.reverse(eltsReversed) ;
+        return Pair.create(x, eltsReversed);
+    }
+
+    /* Return the triples of the list element, or null if invalid list */
+    private boolean validListElement(Node x, List<Triple> acc)
+    {
+        Triple t1 = TW2.triple1(graph, x, RDF_Rest, null) ; // Which we came up to get here :-(
+        if ( t1 == null )
+            return false ;
+        Triple t2 = TW2.triple1(graph, x, RDF_First, null) ;
+        if ( t2 == null )
+            return false ;
+        long N = TW2.countTriples(graph, x, null, null) ;
+        if ( N != 2 )
+            return false ;
+        acc.add(t1) ;
+        acc.add(t2) ;
+        return true ;
+    }
+
+    // ----
+    
+    protected void writeGraph(Graph graph)
+    {
+        initGraph(graph) ;
+        // Prefixes
+        writePrefixes(prefixMap) ;
+        if ( ! prefixMap.isEmpty() )
+            out.println();
+
+        // Or - listSubjects and sort.
+        Iterator<Node> subjects = GLib.listSubjects(graph) ;
+        boolean b = writeBySubject(subjects) ;
+
+        // Write remainders
+        if ( ! nLinkedLists.isEmpty() )
+        {
+            // Print carefully - need a label for the first cell.
+            // So we write out the first element of the list in triples, then put
+            // the remainer as a pretty lst.
+            
+            if ( b ) out.println() ;
+            b = false ;
+            
+            for ( Node n : nLinkedLists.keySet() )
+            {
+                List<Node> x = nLinkedLists.get(n) ;
+                
+                writeNode(n) ;
+                
+                if ( out.getCol() > LONG_SUBJECT )
+                    println() ;
+                else
+                    gap() ;
+                out.incIndent(INDENT_PREDICATE) ;
+                // ----
+                // DRY writeCluster.
+                out.pad() ;
+                writeNode(RDF_First) ;
+                print(" ") ;
+                writeNode(x.get(0)) ;
+                print(" ;") ;
+                println() ;
+                writeNode(RDF_Rest) ;
+                print("  ") ;
+                x = x.subList(1, x.size()) ;
+                list(x) ;
+                print(" .") ;
+                println() ; 
+            }
+        }
+        //else out.println("# No NNNN") ;
+        
+        if ( ! freeLists.isEmpty() )
+        {
+            if ( b ) out.println() ;
+            out.println("# >> 0000") ;
+            // Write free lists.
+            for ( Node n : freeLists.keySet() )
+            {
+                list(freeLists.get(n)) ;
+                out.println(" .") ;
+            }
+            //out.println() ;
+        }
+        //else out.println("# No 0000") ;
+    }
+    
+    // return true if did write something.
+    boolean writeBySubject(Iterator<Node> subjects)
+    {
+        boolean first = true ;
+        for ( ; subjects.hasNext() ; )
+        {
+            Node subj = subjects.next() ;
+            if ( nestedObjects.contains(subj) )
+                continue ;
+            if ( listElts.contains(subj) )
+                continue ;
+            if ( ! first ) 
+                out.println() ;
+            first = false ;
+            
+            Collection<Triple> cluster = TW2.triplesOfSubject(graph, subj) ;
+            writeCluster(subj, cluster) ;
+        }
+        return !first ;
+    }
+    
+    
+    // Common subject
+    // Used by the blocks writer as well.
+    void writeCluster(Node subject, Collection<Triple> cluster)
+    {
+        if ( cluster.isEmpty() ) return ;
+        writeNode(subject) ;
+        
+        if ( out.getCol() > LONG_SUBJECT )
+            out.println() ; 
+        else
+            gap() ;
+        out.incIndent(INDENT_PREDICATE) ;
+        out.pad() ;
+        writePredicateObjectList(cluster) ;
+        out.decIndent(INDENT_PREDICATE) ;
+        print(" .") ;  // Not perfect
+        println() ; 
+    }
+    
+    // need to skip the triples nested.
+    
+    private void writePredicateObjectList(Collection<Triple> cluster)
+    {
+        boolean first = true ;
+        // Calc columns
+        
+        // Sort triples.
+        //  rdf:type
+        //  other rdf and rdfs
+        //  properties together
+        //  object lists?
+        // Find the colject pad column.
+        
+        
+        for ( Triple triple : cluster )
+        {
+            if ( first )
+                first = false ;
+            else
+            {
+                print(" ;") ;
+                println() ;
+            }
+            
+            // Write predicate.
+            int colPredicateStart = out.getCol() ;
+            
+            if ( ! prefixMap.containsValue(rdfNS) && triple.getPredicate().getURI().equals(iriType) )
+                print("a") ;
+            else
+                writeNode(triple.getPredicate()) ;
+            int colPredicateFinish = out.getCol() ;
+            int wPredicate = (colPredicateFinish-colPredicateStart) ;
+            
+            // Needs to be relative?
+            if ( wPredicate > LONG_PREDICATE )
+                println() ;
+            else
+                gap() ;
+            
+            // Secondary one should be less
+            out.incIndent(INDENT_OBJECT) ;
+            out.pad() ;
+            Node obj = triple.getObject() ;
+            writeObject(obj) ;
+            out.decIndent(INDENT_OBJECT) ;
+        }
+    }
+    
+    // --> write S or O??
+    private void writeObject(Node obj)
+    {
+        // Order matters? - one connected objects may include list elements.
+        if ( lists.containsKey(obj) )
+            list(lists.get(obj)) ; 
+        else if ( nestedObjects.contains(obj) )
+            nestedObject(obj) ;
+        else
+            writeNode(obj) ;
+    }
+
+    final void writeNode(Node node)
+    {
+        nodeFmt.format(out, node) ;
+    }
+    
+    private void nestedObject(Node obj)
+    {
+        Collection<Triple> x = TW2.triplesOfSubject(graph, obj) ;
+        
+        if ( x.isEmpty() )
+        {
+            print("[] ") ;
+            return ;
+        }
+
+        if ( x.size() == 1 )
+        {
+            print("[ ") ;
+            // Includes nested object in triple.
+            writePredicateObjectList(x) ;
+            print(" ]") ;
+            return ;
+        }
+
+        // Two or more.
+        int here = out.getCol() ; // before "["
+        print("[") ;
+        int i1 = out.getAbsoluteIndent() ;
+        out.setAbsoluteIndent(here) ;
+        // Inline: println(out) ;
+        out.incIndent(2) ;
+        writePredicateObjectList(x) ;
+        out.decIndent(2) ;
+        if ( true )
+        {
+            println() ; // Newline for "]"
+            print("]") ;
+        }
+        else
+        {   // Compact
+            print(" ]") ;
+        }
+        out.setAbsoluteIndent(i1) ;
+    }
+    
+     
+    private void list(List<Node> elts)
+    {
+        out.print("(") ;
+        for ( Node n : elts )
+        {
+            out.print(" ") ;
+            writeObject(n) ;
+        }
+
+        out.print(" )") ;
+    }
+    
+    private void print(String x)
+    {
+        out.print(x) ;
+    }
+
+    private void gap()
+    {
+        out.print(' ', MIN_GAP) ;
+    }
+    
+    // flush aggressively (debugging)
+    private void println()
+    {
+        out.println() ;
+        //out.flush() ;
+    }
+
+    
+}
+

Added: jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriter.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriter.java?rev=1443260&view=auto
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriter.java (added)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriter.java Wed Feb  6 22:50:37 2013
@@ -0,0 +1,69 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package riot.writer;
+
+import java.io.OutputStream ;
+import java.util.Map ;
+
+import org.apache.jena.atlas.io.IndentedWriter ;
+
+import com.hp.hpl.jena.graph.Graph ;
+import com.hp.hpl.jena.rdf.model.Model ;
+
+public class TurtleWriter extends TurtleShell
+{
+    public static void write(OutputStream cxt, Model model)
+    {
+        write(cxt, model.getGraph(), model.getNsPrefixMap()) ;
+    }
+    
+    public static void write(OutputStream out, Graph graph,  Map<String, String> prefixMap)
+    {
+        IndentedWriter iOut = new IndentedWriter(out, false) ;
+        write(iOut, graph, prefixMap) ;
+    }
+
+    // Call from TriG as well.
+    static void write(IndentedWriter out, Graph graph, Map<String, String> prefixMap)
+    {
+        write$(out, graph, prefixMap) ;
+        out.flush() ;
+    }
+
+    static void write$(IndentedWriter out, Graph graph, Map<String, String> prefixMap)
+    {
+        TurtleWriter w = new TurtleWriter(out, prefixMap) ;
+        w.write(graph) ;
+        out.flush() ;
+
+    }
+
+    public TurtleWriter(IndentedWriter out, Map<String, String> prefixMap)
+    {
+        super(out, prefixMap) ;
+    }
+
+
+    private void write(Graph graph)
+    {
+        writePrefixes(prefixMap) ;
+        writeGraph(graph) ;
+    }
+}
+

Modified: jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterBlocks.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterBlocks.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterBlocks.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterBlocks.java Wed Feb  6 22:50:37 2013
@@ -27,6 +27,9 @@ import org.apache.jena.riot.system.Strea
 import com.hp.hpl.jena.graph.Graph ;
 import com.hp.hpl.jena.rdf.model.Model ;
 
+/** Turtle writer that streams - print in blocks of triples formatted
+ *  by adjacent same subject.
+ */
 public class TurtleWriterBlocks extends WriterStreamBase
 {
     public static void write(OutputStream out, Model model)

Modified: jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterFlat.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterFlat.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterFlat.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/TurtleWriterFlat.java Wed Feb  6 22:50:37 2013
@@ -27,7 +27,7 @@ import org.apache.jena.riot.system.Strea
 import com.hp.hpl.jena.graph.Graph ;
 import com.hp.hpl.jena.rdf.model.Model ;
 
-/** Write Turtle as one line of prefixed names */   
+/** Write Turtle as one line of prefixed names, with short form literals (e.g. integers) */   
 public class TurtleWriterFlat extends WriterStreamBase
 {
     public static void write(OutputStream out, Model model)

Modified: jena/Experimental/riot-output/src/main/java/riot/writer/WriterContext.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/main/java/riot/writer/WriterContext.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/main/java/riot/writer/WriterContext.java (original)
+++ jena/Experimental/riot-output/src/main/java/riot/writer/WriterContext.java Wed Feb  6 22:50:37 2013
@@ -32,10 +32,13 @@ import com.hp.hpl.jena.graph.Node ;
 // Package scope - a struct for holding all the details of the writing process.
 final class WriterContext
 {
+    WriterContext() {}
+    
     IndentedWriter out ; 
-    Graph graph ; 
     NodeFormatter nodeFmt ;
     Map<String, String> prefixMap ;
+    
+    Graph graph ; 
     Set<Node> nestedObjects ;           // Blank nodes that have one incoming triple
     Map<Node, List<Node>> lists;        // The head node in each well-formed lists -> list elements 
     Map<Node, List<Node>> freeLists;    // List that do not have any incoming triples 

Modified: jena/Experimental/riot-output/src/test/java/riot/writer/TestRIOTWriter.java
URL: http://svn.apache.org/viewvc/jena/Experimental/riot-output/src/test/java/riot/writer/TestRIOTWriter.java?rev=1443260&r1=1443259&r2=1443260&view=diff
==============================================================================
--- jena/Experimental/riot-output/src/test/java/riot/writer/TestRIOTWriter.java (original)
+++ jena/Experimental/riot-output/src/test/java/riot/writer/TestRIOTWriter.java Wed Feb  6 22:50:37 2013
@@ -27,7 +27,6 @@ import org.apache.jena.atlas.junit.BaseT
 import org.apache.jena.riot.Lang ;
 import org.apache.jena.riot.RDFDataMgr ;
 import org.junit.Test ;
-import riot.writer.TurtleWriter2 ;
 
 import com.hp.hpl.jena.rdf.model.Model ;
 import com.hp.hpl.jena.rdf.model.ModelFactory ;
@@ -64,7 +63,7 @@ public class TestRIOTWriter extends Base
         
         // check.
         ByteArrayOutputStream out = new ByteArrayOutputStream() ;
-        TurtleWriter2.write(out, m) ;
+        TurtleWriter.write(out, m) ;
         ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray()) ;
         
         Model m2 = ModelFactory.createDefaultModel() ;