Cleaned up partials support a little
diff --git a/lib/mustache_context.dart b/lib/mustache_context.dart
index 9a722d3..36379a7 100644
--- a/lib/mustache_context.dart
+++ b/lib/mustache_context.dart
@@ -13,15 +13,19 @@
   final bool _htmlEscapeValues;
   
   String renderString(String templateName, values) {
-    var template = _partialResolver(templateName);
+    _Template template = _partialResolver(templateName);
     return template.renderString(values, 
-        lenient: _lenient, htmlEscapeValues: _htmlEscapeValues);
+        lenient: _lenient,
+        htmlEscapeValues: _htmlEscapeValues,
+        partialResolver: _partialResolver);
   }
   
   void render(String templateName, values, StringSink sink) {
-    var template = _partialResolver(templateName);
+    _Template template = _partialResolver(templateName);
     template.render(values, sink, 
-        lenient: _lenient, htmlEscapeValues: _htmlEscapeValues);    
+        lenient: _lenient,
+        htmlEscapeValues: _htmlEscapeValues,
+        partialResolver: _partialResolver);    
   }
   
 }
diff --git a/lib/template.dart b/lib/template.dart
index 29a71ff..6691c8b 100644
--- a/lib/template.dart
+++ b/lib/template.dart
@@ -5,7 +5,7 @@
 final RegExp _validTag = new RegExp(r'^[0-9a-zA-Z\_\-\.]+$');

 final RegExp _integerTag = new RegExp(r'^[0-9]+$');

 

-Template _parse(String source, {bool lenient : false}) {

+Template _parse(String source, {bool lenient : false, PartialResolver partialResolver}) {

 	var tokens = _scan(source, lenient);

 	var ast = _parseTokens(tokens, lenient);

 	return new _Template(ast, lenient);

@@ -57,60 +57,65 @@
 		}

 }

 

+

 class _Template implements Template {

   

-	_Template(this._root, this._lenient)

-	{

-		_htmlEscapeMap[_AMP] = '&';

-		_htmlEscapeMap[_LT] = '<';

-		_htmlEscapeMap[_GT] = '>';

-		_htmlEscapeMap[_QUOTE] = '"';

-		_htmlEscapeMap[_APOS] = ''';

-		_htmlEscapeMap[_FORWARD_SLASH] = '/';

-	}

+  _Template(this._root, this._lenient);

+  

+  final _Node _root;

+  final bool _lenient;

+  

+  String renderString(values,

+                      {bool lenient : false,

+                       bool htmlEscapeValues : true,

+                       PartialResolver partialResolver}) {

+    var buf = new StringBuffer();

+    render(values, buf, lenient: lenient, htmlEscapeValues: htmlEscapeValues,

+        partialResolver: partialResolver);

+    return buf.toString();

+  }

+

+  void render(values, StringSink sink, 

+              {bool lenient : false,

+               bool htmlEscapeValues : true,

+               PartialResolver partialResolver}) {

+    var renderer = new _TemplateRenderer(_root, sink, values, [values],

+        lenient, htmlEscapeValues, partialResolver);

+    renderer.render();

+  }

+}

+

+

+class _TemplateRenderer {

+  

+	_TemplateRenderer(this._root,

+	    this._sink,

+	    this._values,

+	    this._stack,

+	    this._lenient,

+	    this._htmlEscapeValues,

+	    this._partialResolver);

+	

+	_TemplateRenderer.partial(_TemplateRenderer renderer, _Template partial)

+      : this(partial._root,

+          renderer._sink,

+          renderer._values,

+          renderer._stack,

+          renderer._lenient,

+          renderer._htmlEscapeValues,

+          renderer._partialResolver);

 

 	final _Node _root;

-	

-	//FIXME careful there is a potential concurrency bug as _stack is mutated 

-	// during rendering, and if async lazy loading of partials is added this

-	// could be mutated by multiple async calls to render running concurrently.

-	// Perhaps pass this around as an argument, or create a render context object.

-	// Same is true with sink.

-	final List _stack = new List();

-	final Map _htmlEscapeMap = new Map<int, String>();

+  final StringSink _sink;

+  final _values;

+	final List _stack;

 	final bool _lenient;

-	

-	//FIXME quick ugly hack.

-	PartialResolver partialResolver;

+	final bool _htmlEscapeValues;

+	final PartialResolver _partialResolver;

 

-	bool _htmlEscapeValues;

-	StringSink _sink;

-

-	String renderString(values, {bool lenient : false, bool htmlEscapeValues : true}) {

-		var buf = new StringBuffer();

-		render(values, buf, lenient: lenient, htmlEscapeValues: htmlEscapeValues);

-		return buf.toString();

-	}

-

-	void render(values, StringSink sink, {bool lenient : false, bool htmlEscapeValues : true}) {

-		_sink = sink;

-		_htmlEscapeValues = htmlEscapeValues;

-		_stack.clear();

-		_stack.add(values);

+	void render() {

 		_root.children.forEach(_renderNode);

-		_sink = null;

 	}

-

-	//TODO Share code with render.

-  void _renderWithStack(List stack, StringSink sink,

-                        {bool lenient : false, bool htmlEscapeValues : true}) {

-    _sink = sink;

-    _htmlEscapeValues = htmlEscapeValues;

-    _stack.clear();

-    _stack.addAll(stack);

-    _root.children.forEach(_renderNode);

-    _sink = null;

-  }

 	

 	_write(String output) => _sink.write(output);

 

@@ -278,11 +283,22 @@
 

   _renderPartial(_Node node) {

     var partialName = node.value;

-    _Template template = partialResolver(partialName);

-    template._renderWithStack(_stack, _sink);

+    _Template template = _partialResolver(partialName);

+    var renderer = new _TemplateRenderer.partial(this, template);

+    renderer.render();

   }

 

+  static const Map<String,String> _htmlEscapeMap = const {

+    _AMP: '&amp;',

+    _LT: '&lt;',

+    _GT: '&gt;',

+    _QUOTE: '&quot;',

+    _APOS: '&#x27;',

+    _FORWARD_SLASH: '&#x2F;' 

+  };

+  

 	String _htmlEscape(String s) {

+	  

 		var buffer = new StringBuffer();

 		int startIndex = 0;

 		int i = 0;

diff --git a/test/mustache_test.dart b/test/mustache_test.dart
index 30fd6b7..e865466 100644
--- a/test/mustache_test.dart
+++ b/test/mustache_test.dart
@@ -234,18 +234,13 @@
 		});
 	});
 
-	solo_group('Partial tag', () {
+	group('Partial tag', () {
 		
 		test('MustacheContext', () {
 		  var template = parse('{{>partial}}'); 
 		  var includedTemplate = parse('{{foo}}');
 		  var resolver = (name) => 
-		      {'root': template, 'partial': includedTemplate}[name];
-		      
-		  //FIXME Need a sensible way to initialise the resolver.
-		  template.partialResolver = resolver;
-		  includedTemplate.partialResolver = resolver; 
-		  
+		      {'root': template, 'partial': includedTemplate}[name];		  
 		  var ctx = new MustacheContext(resolver);
 		  var output = ctx.renderString('root', {'foo': 'bar'});
 		  expect(output, 'bar');