XML_Loader.cpp

Go to the documentation of this file.
00001 // $Id: XML_Loader.cpp 78900 2007-07-15 13:05:48Z sowayaa $
00002 
00003 #include "orbsvcs/Notify/XML_Loader.h"
00004 #include "orbsvcs/Notify/Topology_Object.h"
00005 
00006 #include "ACEXML/common/DefaultHandler.h"
00007 #include "ACEXML/parser/parser/Parser.h"
00008 #include "ACEXML/common/FileCharStream.h"
00009 
00010 #include "ace/Containers_T.h"
00011 #include "tao/debug.h"
00012 #include "ace/OS_NS_unistd.h"
00013 
00014 //#define DEBUG_LEVEL 9
00015 #ifndef DEBUG_LEVEL
00016 # define DEBUG_LEVEL TAO_debug_level
00017 #endif //DEBUG_LEVEL
00018 
00019 using namespace TAO_Notify;
00020 
00021 TAO_BEGIN_VERSIONED_NAMESPACE_DECL
00022 
00023 namespace TAO_Notify {
00024   extern const char TOPOLOGY_ID_NAME[];
00025 }
00026 
00027 TAO_END_VERSIONED_NAMESPACE_DECL
00028 
00029 namespace {
00030   CORBA::Long makeNVPList (NVPList& nvp, ACEXML_Attributes* attrs)
00031   {
00032     CORBA::Long id = 0;
00033     for (size_t i = 0; i < attrs->getLength (); ++i)
00034     {
00035       const char * name = attrs->getQName (i);
00036       const char * value = attrs->getValue (i);
00037       if (ACE_OS::strcmp (name,
00038                          TAO_VERSIONED_NAMESPACE_NAME::TAO_Notify::TOPOLOGY_ID_NAME) == 0)
00039       {
00040         id = ACE_OS::atoi (value);
00041       }
00042       nvp.push_back (NVP (name, value));
00043     }
00044     return id;
00045   }
00046 }
00047 
00048 TAO_BEGIN_VERSIONED_NAMESPACE_DECL
00049 
00050 namespace TAO_Notify
00051 {
00052   XML_Loader::XML_Loader ()
00053     : input_ (0)
00054     , live_ (false)
00055   {
00056   }
00057 
00058   XML_Loader::~XML_Loader ()
00059   {
00060   }
00061 
00062   bool
00063   XML_Loader::open (const ACE_CString & base_name)
00064   {
00065     bool result = false;
00066 
00067     // if *.xml exists, use it
00068     // if it does not exist then
00069     // use the previous one was renamed to *.000
00070     // If neither *.xml nor *.000 exist then something
00071     // "impossible" happened (or its a new system with no saved state).
00072 
00073     this->file_name_ = base_name;
00074     this->file_name_ += ".xml";
00075 
00076     // 4 is "read permission"
00077     result =  (0 == ACE_OS::access (this->file_name_.c_str (), 4));
00078     if (result)
00079     {
00080       this->live_ = false;
00081       auto_ptr<ACEXML_FileCharStream> fstm (new ACEXML_FileCharStream);
00082       // xml input source will take ownership
00083 
00084       if (fstm->open (this->file_name_.c_str ()) == 0)
00085       {
00086         // InputSource takes ownership
00087         ACEXML_InputSource input (fstm.get ());
00088         (void) fstm.release ();
00089 
00090         ACEXML_Parser parser;
00091         parser.setContentHandler (this);
00092         parser.setDTDHandler (this);
00093         parser.setErrorHandler (this);
00094         parser.setEntityResolver (this);
00095 
00096         try
00097         {
00098           parser.parse (&input);
00099         }
00100         catch (const ACEXML_Exception& ex)
00101         {
00102           // The only way to find out what it is, it to let it print itself, so...
00103           ACE_ERROR ((LM_ERROR, "Unable to load \"%s\".\n Will try backup file.\n", this->file_name_.c_str ()));
00104           ex.print ();
00105           result = false;
00106         }
00107       }
00108       else
00109       {
00110         ACE_DEBUG((LM_DEBUG, ACE_TEXT("Unable to open the XML input file: %s.\n Will try backup file.\n"), file_name_.c_str()));
00111         result = false;
00112       }
00113     }
00114 
00115     if (! result)
00116     {
00117       this->file_name_ = base_name;
00118       this->file_name_ += ".000";
00119       result = (0 == ACE_OS::access (this->file_name_.c_str (), 4));
00120     }
00121     return result;
00122   }
00123 
00124   //virtual
00125   void
00126   XML_Loader::load (Topology_Object *root)
00127   {
00128     ACE_ASSERT (root != 0);
00129     this->live_ = true;
00130 
00131     auto_ptr<ACEXML_FileCharStream> fstm (new ACEXML_FileCharStream);
00132     // xml input source will take ownership
00133 
00134     if (fstm->open (this->file_name_.c_str ()) == 0)
00135     {
00136       // InputSource takes ownership
00137       ACEXML_InputSource input (fstm.get ());
00138       (void) fstm.release ();
00139 
00140       ACEXML_Parser parser;
00141       parser.setContentHandler (this);
00142       parser.setDTDHandler (this);
00143       parser.setErrorHandler (this);
00144       parser.setEntityResolver (this);
00145 
00146       try
00147       {
00148         object_stack_.push (root);
00149         parser.parse (&input ACEXML_ENV_ARG_PARAMETER);
00150         ACEXML_TRY_CHECK;
00151         ACE_ASSERT (object_stack_.size () == 1);
00152         Topology_Object* cur;
00153         object_stack_.pop (cur);
00154       }
00155       catch (const ACEXML_Exception& ex)
00156       {
00157         // The only way to find out what it is, it to let it print itself, so...
00158         ACE_ERROR ((LM_ERROR, "Unable to load \"%s\".\n", this->file_name_.c_str ()));
00159         ex.print ();
00160         throw CORBA::INTERNAL();
00161       }
00162     }
00163     else
00164     {
00165       ACE_DEBUG((LM_DEBUG, ACE_TEXT("Unable to open the XML input file: %s.\n"), file_name_.c_str()));
00166       throw CORBA::INTERNAL();
00167     }
00168   }
00169 
00170   void
00171   XML_Loader::startElement (const ACEXML_Char*,
00172     const ACEXML_Char*,
00173     const ACEXML_Char* name,
00174     ACEXML_Attributes* xml_attrs)
00175   {
00176     ACE_ASSERT (name != 0);
00177     ACE_ASSERT (xml_attrs != 0);
00178     if (this->live_)
00179     {
00180       ACE_ASSERT (object_stack_.size () > 0);
00181       Topology_Object* cur = 0;
00182       if (object_stack_.top (cur) == 0)
00183       {
00184         try
00185         {
00186           NVPList attrs;
00187           CORBA::Long id = makeNVPList (attrs, xml_attrs);
00188 
00189           if (DEBUG_LEVEL > 5) ACE_DEBUG ((LM_INFO,
00190             ACE_TEXT("(%P|%t) XML_Loader: Element %s\n"),
00191             name
00192             ));
00193 
00194           ACE_CString cname (name);
00195           Topology_Object* next = cur->load_child (cname, id, attrs);
00196           ACE_ASSERT(next != 0);
00197           object_stack_.push (next);
00198         }
00199         catch (const CORBA::Exception& ex)
00200         {
00201           throw ACEXML_SAXException (ex._info ().c_str ());
00202         }
00203       }
00204     }
00205   }
00206 
00207   void
00208   XML_Loader::endElement (const ACEXML_Char*,
00209     const ACEXML_Char*,
00210     const ACEXML_Char* name)
00211   {
00212     ACE_UNUSED_ARG (name);
00213     if (this->live_)
00214     {
00215       ACE_ASSERT (object_stack_.size () > 0);
00216       if (DEBUG_LEVEL > 5)
00217         {
00218           ACE_DEBUG ((LM_INFO,
00219                       ACE_TEXT("(%P|%t) XML_Loader: End Element %s\n"),
00220                       name));
00221         }
00222       Topology_Object* cur = 0;
00223       object_stack_.pop (cur);
00224     }
00225   }
00226 
00227 } /* namespace TAO_Notify */
00228 
00229 TAO_END_VERSIONED_NAMESPACE_DECL

Generated on Sun Jan 27 15:40:02 2008 for TAO_CosNotification by doxygen 1.3.6