Back to index

nordugrid-arc-nox  1.1.0~rc6
Public Member Functions | Static Public Member Functions | Private Member Functions | Private Attributes
Arc::LutsDestination Class Reference

Reporting destination adapter for SGAS LUTS. More...

#include <LutsDestination.h>

Inheritance diagram for Arc::LutsDestination:
Inheritance graph
[legend]
Collaboration diagram for Arc::LutsDestination:
Collaboration graph
[legend]

List of all members.

Public Member Functions

 LutsDestination (JobLogFile &joblog)
 Constructor.
void report (JobLogFile &joblog)
 Generates record from job log file content, collects it into the UR batch, and if batch is full, submits it to the service.
void finish ()
 Finishes pending submission of records.
 ~LutsDestination ()

Static Public Member Functions

static DestinationcreateDestination (Arc::JobLogFile &joblog)
 Creates an instance of the inherited class corresponding to the destination for the given job log file.

Private Member Functions

int submit_batch ()
Arc::MCC_Status send_request (const std::string &urset)
void clear ()

Private Attributes

Arc::Logger logger
Arc::MCCLoadermccloader
Arc::MCCsoapmcc
Arc::Config clientchain
int max_ur_set_size
 Max number of URs to put in a set before submitting it.
int urn
 Actual number of usage records in set.
std::list< JobLogFilejoblogs
 List of copies of job logs.
Arc::XMLNode usagerecordset
 Usage Record set XML.

Detailed Description

Reporting destination adapter for SGAS LUTS.

Definition at line 20 of file LutsDestination.h.


Constructor & Destructor Documentation

Constructor.

Service URL and LUTS-related parameters (e.g. UR batch size) are extracted from the given job log file.

Definition at line 13 of file LutsDestination.cpp.

                                                    :
    logger(Arc::Logger::rootLogger, "JURA.LutsDestination"),
    urn(0),
    usagerecordset(Arc::NS("","http://schema.ogf.org/urf/2003/09/urf"),
                   "UsageRecords")
  {
    std::string dump;

    //Set up the Client Message Chain:
    Arc::NS ns;
    ns[""]="http://www.nordugrid.org/schemas/ArcConfig/2007";
    ns["tcp"]="http://www.nordugrid.org/schemas/ArcMCCTCP/2007";
    clientchain.Namespaces(ns);

    //Get service URL, cert, key, CA path from job log file
    std::string serviceurl=joblog["loggerurl"];
    std::string certfile=joblog["certificate_path"];
    std::string keyfile=joblog["key_path"];
    std::string cadir=joblog["ca_certificates_dir"];
    // ...or get them from environment
    if (certfile.empty())
      certfile=Arc::GetEnv("X509_USER_CERT");
    if (keyfile.empty())
      keyfile=Arc::GetEnv("X509_USER_KEY");
    if (cadir.empty())
      cadir=Arc::GetEnv("X509_CERT_DIR");
    // ...or by default, use host cert, key, CA path
    if (certfile.empty())
      certfile=JURA_DEFAULT_CERT_FILE;
    if (keyfile.empty())
      keyfile=JURA_DEFAULT_KEY_FILE;
    if (cadir.empty())
      cadir=JURA_DEFAULT_CA_DIR;

    //  Tokenize service URL
    std::string host, port, endpoint;
    if (serviceurl.empty())
      {
        logger.msg(Arc::ERROR, "ServiceURL missing");
      }
    else
      {
        Arc::URL url(serviceurl);
        if (url.Protocol()!="https")
          {
            logger.msg(Arc::ERROR, "Protocol is %s, should be https",
                       url.Protocol());
          }
        host=url.Host();
        std::ostringstream os;
        os<<url.Port();
        port=os.str();
        endpoint=url.Path();
      }

#ifdef HAVE_CONFIG_H
    //MCC module path(s):
    clientchain.NewChild("ModuleManager").NewChild("Path")=
      INSTPREFIX "/" LIBSUBDIR;
    clientchain["ModuleManager"].NewChild("Path")=
      INSTPREFIX "/" PKGLIBSUBDIR;
#endif

    //The protocol stack: SOAP over HTTP over SSL over TCP
    clientchain.NewChild("Plugins").NewChild("Name")="mcctcp";
    clientchain.NewChild("Plugins").NewChild("Name")="mcctls";
    clientchain.NewChild("Plugins").NewChild("Name")="mcchttp";
    clientchain.NewChild("Plugins").NewChild("Name")="mccsoap";


    //The chain
    Arc::XMLNode chain=clientchain.NewChild("Chain");
    Arc::XMLNode component;
  
    //  TCP
    component=chain.NewChild("Component");
    component.NewAttribute("name")="tcp.client";
    component.NewAttribute("id")="tcp";
    Arc::XMLNode connect=component.NewChild("tcp:Connect");
    connect.NewChild("tcp:Host")=host;
    connect.NewChild("tcp:Port")=port;

    //  TLS (SSL)
    component=chain.NewChild("Component");
    component.NewAttribute("name")="tls.client";
    component.NewAttribute("id")="tls";
    component.NewChild("next").NewAttribute("id")="tcp";
    if (!certfile.empty())
      component.NewChild("CertificatePath")=certfile;
    if (!keyfile.empty())
      component.NewChild("KeyPath")=keyfile;
    if (!cadir.empty())
      component.NewChild("CACertificatesDir")=cadir;
  
    //  HTTP
    component=chain.NewChild("Component");
    component.NewAttribute("name")="http.client";
    component.NewAttribute("id")="http";
    component.NewChild("next").NewAttribute("id")="tls";
    component.NewChild("Method")="POST";
    component.NewChild("Endpoint")=endpoint;
  
    //  SOAP
    component=chain.NewChild("Component");
    component.NewAttribute("name")="soap.client";
    component.NewAttribute("id")="soap";
    component.NewAttribute("entry")="soap";
    component.NewChild("next").NewAttribute("id")="http";

    clientchain.GetDoc(dump,true);
    logger.msg(Arc::VERBOSE, "Client chain configuration: %s",
               dump.c_str() );

    //Get Batch Size:
    //Default value:
    max_ur_set_size=JURA_DEFAULT_MAX_UR_SET_SIZE;
    //From jobreport_options:
    std::string urbatch=joblog["jobreport_option_urbatch"];
    if (!urbatch.empty())
      {
       std::istringstream is(urbatch);
       is>>max_ur_set_size;
      }

  }

Here is the call graph for this function:

Definition at line 300 of file LutsDestination.cpp.

  {
    finish();
  }

Here is the call graph for this function:


Member Function Documentation

void Arc::LutsDestination::clear ( ) [private]

Definition at line 288 of file LutsDestination.cpp.

  {
    urn=0;
    joblogs.clear();
    usagerecordset.Replace(
        Arc::XMLNode(Arc::NS("",
                             "http://schema.ogf.org/urf/2003/09/urf"
                            ),
                     "UsageRecords")
                    );
  }

Here is the call graph for this function:

Here is the caller graph for this function:

Creates an instance of the inherited class corresponding to the destination for the given job log file.

Definition at line 9 of file Destination.cpp.

  {
    //std::string url=joblog["loggerurl"];
    //TODO distinguish
    return new LutsDestination(joblog);
  }

Here is the caller graph for this function:

void Arc::LutsDestination::finish ( ) [virtual]

Finishes pending submission of records.

Reimplemented from Arc::Destination.

Definition at line 166 of file LutsDestination.cpp.

  {
    if (urn>0)
      // Send the remaining URs and delete job log files.
      submit_batch();
  }

Here is the call graph for this function:

Here is the caller graph for this function:

void Arc::LutsDestination::report ( Arc::JobLogFile joblog) [virtual]

Generates record from job log file content, collects it into the UR batch, and if batch is full, submits it to the service.

Implements Arc::Destination.

Definition at line 139 of file LutsDestination.cpp.

  {
    //if (joblog.exists())
      {
        //Store copy of job log
        joblogs.push_back(joblog);
        //Create UR if can
        Arc::XMLNode usagerecord(Arc::NS(), "");
       joblog.createUsageRecord(usagerecord);
       if (usagerecord)
         {
           usagerecordset.NewChild(usagerecord);
           ++urn;
         }
       else
         {
           logger.msg(Arc::INFO,"Ignoring incomplete log file \"%s\"",
                     joblog.getFilename().c_str());
           joblog.remove();
         }
      }
    
    if (urn==max_ur_set_size)
      // Batch is full. Submit and delete job log files.
      submit_batch();
  }

Here is the call graph for this function:

Arc::MCC_Status Arc::LutsDestination::send_request ( const std::string &  urset) [private]

Definition at line 213 of file LutsDestination.cpp.

  {
    Arc::NS _empty_ns;
    Arc::PayloadSOAP req(_empty_ns);
    Arc::PayloadSOAP *resp=NULL;
    Arc::Message inmsg,outmsg;

    //Create MCC loader. This also sets up TCP connection!
    mccloader=new Arc::MCCLoader(clientchain);
    //(and we also get a load of log entries)

    soapmcc=(*mccloader)["soap"];
    if (!soapmcc)
    {
      delete mccloader;
      return Arc::MCC_Status(Arc::GENERIC_ERROR,
                             "lutsclient",
                             "No SOAP entry point in chain");
    }

    //TODO ws-addressing!

    //Build request structure:
    Arc::NS ns_wsrp("",
     "http://docs.oasis-open.org/wsrf/2004/06/wsrf-WS-ResourceProperties-1.2-draft-01.xsd"
                    );
    Arc::XMLNode query=req.NewChild("QueryResourceProperties",ns_wsrp).
                           NewChild("QueryExpression");
    query.NewAttribute("Dialect")=
      "http://www.sgas.se/namespaces/2005/06/publish/query";
    query=urset;
    //put into message:
    inmsg.Payload(&req);

    //Send
    Arc::MCC_Status status;

    status=soapmcc->process(inmsg, outmsg);

    //extract response:
    try
    {
      resp=dynamic_cast<Arc::PayloadSOAP*>(outmsg.Payload());
    }
    catch (std::exception&) {}

    if (resp==NULL)
      {
        //Unintelligible non-SOAP response
        delete mccloader;
        return Arc::MCC_Status(Arc::PROTOCOL_RECOGNIZED_ERROR,
                               "lutsclient",
                               "Response not SOAP");
      }

    if (status && ! ((*resp)["QueryResourcePropertiesResponse"]))
      {
        // Status OK, but wrong response
        std::string soapfault;
        resp->GetDoc(soapfault,false);

        delete mccloader;
        return Arc::MCC_Status(Arc::PARSING_ERROR,
               "lutsclient",
               std::string(
                 "No QueryResourcePropertiesResponse element in response: "
                           )+ 
               soapfault
               );
      }
    
    delete mccloader;
    return status;
  }

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 173 of file LutsDestination.cpp.

  {
    std::string urstr;
    usagerecordset.GetDoc(urstr,false);

    logger.msg(Arc::INFO, 
               "Logging UR set of %d URs.",
               urn);
    logger.msg(Arc::DEBUG, 
               "UR set dump: %s",
               urstr.c_str());
  
    // Communication with LUTS server
    Arc::MCC_Status status=send_request(urstr);

    if (status.isOk())
      {
        // Delete log files
        for (std::list<JobLogFile>::iterator jp=joblogs.begin();
             jp!=joblogs.end();
             jp++
             )
          {
            (*jp).remove();
          }
        clear();
        return 0;
      }
    else // status.isnotOk
      {
        logger.msg(Arc::ERROR, 
                   "%s: %s",
                   status.getOrigin().c_str(),
                   status.getExplanation().c_str()
                   );
        clear();
        return -1;
      }
  }

Here is the call graph for this function:

Here is the caller graph for this function:


Member Data Documentation

Definition at line 26 of file LutsDestination.h.

List of copies of job logs.

Definition at line 32 of file LutsDestination.h.

Definition at line 23 of file LutsDestination.h.

Max number of URs to put in a set before submitting it.

Definition at line 28 of file LutsDestination.h.

Definition at line 24 of file LutsDestination.h.

Definition at line 25 of file LutsDestination.h.

Actual number of usage records in set.

Definition at line 30 of file LutsDestination.h.

Usage Record set XML.

Definition at line 34 of file LutsDestination.h.


The documentation for this class was generated from the following files: