00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #include <libxml/encoding.h>
00034
00035 #include <iostream>
00036 #include <map>
00037
00038 using std::cout ;
00039 using std::endl ;
00040 using std::map ;
00041
00042 #include "CmdPretty.h"
00043 #include "BESXMLUtils.h"
00044
00045 string CmdPretty::_indent ;
00046
00047 void
00048 CmdPretty::make_pretty( const string &response, ostream &strm )
00049 {
00050 if( response[0] == '<' && response[1] == '?' )
00051 {
00052 LIBXML_TEST_VERSION
00053
00054 xmlDoc *doc = NULL ;
00055 xmlNode *root_element = NULL ;
00056
00057 doc = xmlParseDoc( (unsigned char *)response.c_str() ) ;
00058 if( doc == NULL )
00059 {
00060 cout << "bescmdln tried to pretty print xml document: "
00061 << "failed to parse document" << endl ;
00062 strm << response ;
00063 xmlCleanupParser() ;
00064 return ;
00065 }
00066
00067
00068 root_element = xmlDocGetRootElement( doc ) ;
00069 if( !root_element )
00070 {
00071 cout << "bescmdln tried to pretty print xml document: "
00072 << "failed to get document root" << endl ;
00073 strm << response ;
00074 if( doc ) xmlFreeDoc( doc ) ;
00075 xmlCleanupParser() ;
00076 return ;
00077 }
00078
00079 CmdPretty::pretty_element( root_element, strm ) ;
00080
00081 if( doc ) xmlFreeDoc( doc ) ;
00082 xmlCleanupParser() ;
00083 }
00084 else
00085 {
00086 strm << response ;
00087 }
00088 }
00089
00090 void
00091 CmdPretty::pretty_element( xmlNode *node, ostream &strm )
00092 {
00093 if( !node )
00094 {
00095 return ;
00096 }
00097
00098 string node_name ;
00099 string node_val ;
00100 map< string, string> node_props ;
00101 BESXMLUtils::GetNodeInfo( node, node_name, node_val, node_props ) ;
00102 pretty_name( node, node_name, strm ) ;
00103 map<string,string>::const_iterator i = node_props.begin() ;
00104 map<string,string>::const_iterator e = node_props.end() ;
00105 for( ; i != e; i++ )
00106 {
00107 strm << " " << (*i).first ;
00108 if( !(*i).second.empty() )
00109 {
00110 strm << "=\"" << (*i).second << "\"" ;
00111 }
00112 }
00113
00114 string cname ;
00115 string cval ;
00116 map<string, string> cprops ;
00117
00118
00119
00120 bool has_stuff = false ;
00121 xmlNode *cnode = BESXMLUtils::GetFirstChild( node, cname, cval, cprops ) ;
00122
00123 if( !cnode && !node_val.empty() && node_val.length() < 80-_indent.length() )
00124 {
00125 strm << ">" << node_val << "</" << node_name << ">" << endl ;
00126 }
00127 else
00128 {
00129 if( cnode || !node_val.empty() )
00130 {
00131 has_stuff = true ;
00132 strm << ">" << endl ;
00133 CmdPretty::indent( 4 ) ;
00134 }
00135 if( !node_val.empty() )
00136 {
00137 CmdPretty::pretty_value( node_val, strm ) ;
00138 }
00139 while( cnode )
00140 {
00141 CmdPretty::pretty_element( cnode, strm ) ;
00142 cnode = BESXMLUtils::GetNextChild( cnode, cname, cval, cprops ) ;
00143 }
00144 if( has_stuff )
00145 {
00146 CmdPretty::unindent( 4 ) ;
00147 strm << _indent << "</" << node_name << ">" << endl ;
00148 }
00149 else
00150 {
00151 strm << " />" << endl ;
00152 }
00153 }
00154 }
00155
00156 void
00157 CmdPretty::pretty_value( string &value, ostream &strm )
00158 {
00159 strm << _indent << value << endl ;
00160 }
00161
00162 void
00163 CmdPretty::pretty_name( xmlNode *node, const string &name, ostream &strm )
00164 {
00165 if( node )
00166 {
00167
00168 xmlNs *ns = node->nsDef ;
00169 string newname ;
00170 bool firstns = true ;
00171 while( ns )
00172 {
00173 if( ns->prefix )
00174 {
00175 if( !firstns )
00176 {
00177 newname += ":" ;
00178 }
00179 newname += (const char *)ns->prefix ;
00180 }
00181 ns = ns->next ;
00182 firstns = false ;
00183 }
00184 if( !newname.empty() )
00185 {
00186 newname += ":" ;
00187 }
00188 newname += name ;
00189
00190 strm << CmdPretty::_indent << "<" << newname ;
00191
00192
00193 ns = node->nsDef ;
00194 while( ns )
00195 {
00196 strm << " xmlns" ;
00197 if( ns->prefix )
00198 {
00199 strm << ":" << ns->prefix ;
00200 }
00201 if( ns->href )
00202 {
00203 strm << "=\"" << ns->href << "\"" ;
00204 }
00205 ns = ns->next ;
00206 }
00207 }
00208 }
00209
00210 void
00211 CmdPretty::indent( unsigned int spaces )
00212 {
00213 unsigned int index = 0 ;
00214 for( index = 0; index < spaces; index++ )
00215 {
00216 CmdPretty::_indent += " " ;
00217 }
00218 }
00219
00220 void
00221 CmdPretty::unindent( unsigned int spaces )
00222 {
00223 if( spaces >= _indent.length() )
00224 {
00225 _indent = "" ;
00226 }
00227 else
00228 {
00229 _indent = _indent.substr( 0, _indent.length() - spaces ) ;
00230 }
00231 }
00232