//
//  ========================================================================
//  Copyright (c) 1995-2017 Mort Bay Consulting Pty. Ltd.
//  ------------------------------------------------------------------------
//  All rights reserved. This program and the accompanying materials
//  are made available under the terms of the Eclipse Public License v1.0
//  and Apache License v2.0 which accompanies this distribution.
//
//      The Eclipse Public License is available at
//      http://www.eclipse.org/legal/epl-v10.html
//
//      The Apache License v2.0 is available at
//      http://www.opensource.org/licenses/apache2.0.php
//
//  You may elect to redistribute this code under either of these licenses.
//  ========================================================================
//

package org.eclipse.jetty.xml;

import java.io.Closeable;
import java.io.IOException;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.util.Map;
import java.util.Stack;

import org.eclipse.jetty.util.StringUtil;

public class XmlAppendable
{
    private final String SPACES="                                                                 ";
    private final Appendable _out;
    private final int _indent;
    private final Stack<String> _tags = new Stack<>();
    private String _space="";

    public XmlAppendable(OutputStream out,String encoding) throws IOException
    {
        this(new OutputStreamWriter(out,encoding),encoding);
    }
    
    public XmlAppendable(Appendable out) throws IOException
    {
        this(out,2);
    }
    
    public XmlAppendable(Appendable out,String encoding) throws IOException
    {
        this(out,2,encoding);
    }
    
    public XmlAppendable(Appendable out, int indent) throws IOException
    {
        this(out,indent,"utf-8");
    }
    
    public XmlAppendable(Appendable out, int indent, String encoding) throws IOException
    {
        _out=out;
        _indent=indent;
        _out.append("<?xml version=\"1.0\" encoding=\""+encoding+"\"?>\n");
    }

    public XmlAppendable openTag(String tag, Map<String,String> attributes) throws IOException
    {
        _out.append(_space).append('<').append(tag);
        attributes(attributes);
        
        _out.append(">\n");
        _space=_space+SPACES.substring(0,_indent);
        _tags.push(tag);
        return this;
    }
    
    public XmlAppendable openTag(String tag) throws IOException
    {
        _out.append(_space).append('<').append(tag).append(">\n");
        _space=_space+SPACES.substring(0,_indent);
        _tags.push(tag);
        return this;
    }
    
    public XmlAppendable content(String s) throws IOException
    {
        if (s!=null)
            _out.append(StringUtil.sanitizeXmlString(s));
        
        return this;
    }

    public XmlAppendable cdata(String s) throws IOException
    {
        _out.append("<![CDATA[").append(s).append("]]>");
        return this;
    }
    
    public XmlAppendable tag(String tag) throws IOException
    {
        _out.append(_space).append('<').append(tag).append("/>\n");
        return this;
    }
    
    public XmlAppendable tag(String tag, Map<String,String> attributes) throws IOException
    {
        _out.append(_space).append('<').append(tag);
        attributes(attributes);
        _out.append("/>\n");
        return this;
    }
    
    public XmlAppendable tag(String tag,String content) throws IOException
    {
        _out.append(_space).append('<').append(tag).append('>');
        content(content);
        _out.append("</").append(tag).append(">\n");
        return this;
    }
    
    public XmlAppendable tagCDATA(String tag,String data) throws IOException
    {
        _out.append(_space).append('<').append(tag).append('>');
        cdata(data);
        _out.append("</").append(tag).append(">\n");
        return this;
    }
    
    public XmlAppendable tag(String tag, Map<String,String> attributes,String content) throws IOException
    {
        _out.append(_space).append('<').append(tag);
        attributes(attributes);
        _out.append('>');
        content(content);
        _out.append("</").append(tag).append(">\n");
        return this;
    }
    
    public XmlAppendable closeTag() throws IOException
    {
        if (_tags.isEmpty())
            throw new IllegalStateException("Tags closed");
        String tag=_tags.pop();
        _space=_space.substring(0,_space.length()-_indent);
        _out.append(_space).append("</").append(tag).append(">\n");
        if (_tags.isEmpty() && _out instanceof Closeable)
            ((Closeable)_out).close();
        return this;
    }
    
    private void attributes(Map<String,String> attributes) throws IOException
    {
        for (String k:attributes.keySet())
        {
            String v = attributes.get(k);
            _out.append(' ').append(k).append("=\"");
            content(v);
            _out.append('"');
        }
    }
    
    public void literal(String xml) throws IOException
    {
        _out.append(xml);
    }

}
