Skip to content

Commit

Permalink
HPCC-31936 Fix WsEcl sample XML, WSDL and XSD features
Browse files Browse the repository at this point in the history
Move the implementation of EspHttpBinding::getWsdlOrXsd prior to HPCC-28978
into CWsEclBinding. Change the onXSD/onWsdl handlers in CWsEclBinding to call
getWsdlOrXsd directly.

Noted that the non-overridden CWsEclBinding member function getSchema was
substantially similar to the overridden version, so renamed it getSimpleSchema
and made it protected. Created ticket HPCC-32016 to refactor.

Signed-off-by: Terrence Asselin <[email protected]>
  • Loading branch information
asselitx committed Jun 6, 2024
1 parent f3bf57f commit f5bf94d
Show file tree
Hide file tree
Showing 3 changed files with 95 additions and 24 deletions.
19 changes: 6 additions & 13 deletions esp/bindings/http/platform/httpbinding.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1764,7 +1764,9 @@ void EspHttpBinding::getServiceSchema(IEspContext& context, CHttpRequest* reque
StringBuffer xmlFilename;
if (!getServiceXmlFilename(xmlFilename))
{
throw MakeStringException(-1, "Unable to get service XML filename");
// Allow subclassed specialized implementation that doesn't use ESDL
getSchema(schema, context, request, serviceQName, methodQName, true);
return;
}

StringBuffer nstr;
Expand Down Expand Up @@ -1841,12 +1843,7 @@ int EspHttpBinding::getServiceWsdlOrXsd(IEspContext &context, CHttpRequest* requ
}

StringBuffer schema;
// Allow derived classes such as WsEcl to use custom getSchema() logic when there is no serviceXmlFilename
StringBuffer serviceXmlFilename;
if (getServiceXmlFilename(serviceXmlFilename))
getServiceSchema(context, request, serviceQName, methodQName, version, isWsdl, false, schema);
else
getSchema(schema, context, request, service, method, true);
getServiceSchema(context, request, serviceQName, methodQName, version, isWsdl, false, schema);

response->setContent(schema.length(), schema.str());
response->setContentType(HTTP_TYPE_APPLICATION_XML_UTF8);
Expand Down Expand Up @@ -1941,12 +1938,8 @@ void EspHttpBinding::generateSampleXml(bool isRequest, IEspContext &context, CHt
content.appendf("<Error>generateSampleXml schema error: %s::%s</Error>", serv, method);
return;
}
// Allow derived classes such as WsEcl to use custom getSchema() logic when there is no serviceXmlFilename
StringBuffer serviceXmlFilename;
if (getServiceXmlFilename(serviceXmlFilename))
getServiceSchema(context, request, serviceQName, methodQName, getVersion(context), false, false, schemaXml);
else
getSchema(schemaXml, context, request, serv, method, true);

getServiceSchema(context, request, serviceQName, methodQName, getVersion(context), false, false, schemaXml);

Owned<IXmlSchema> schema;
IXmlType* type = nullptr;
Expand Down
94 changes: 85 additions & 9 deletions esp/services/ws_ecl/ws_ecl_service.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1403,7 +1403,7 @@ int CWsEclBinding::getXsdDefinition(IEspContext &context, CHttpRequest *request,
}


bool CWsEclBinding::getSchema(StringBuffer& schema, IEspContext &ctx, CHttpRequest* req, WsEclWuInfo &wsinfo)
bool CWsEclBinding::getSimpleSchema(StringBuffer& schema, IEspContext &ctx, CHttpRequest* req, WsEclWuInfo &wsinfo)
{
Owned<IPropertyTree> namespaces = createPTree();
appendSchemaNamespaces(namespaces, ctx, req, wsinfo);
Expand Down Expand Up @@ -1453,9 +1453,9 @@ bool CWsEclBinding::getSchema(StringBuffer& schema, IEspContext &ctx, CHttpReque
return true;
}

// Moved from the prior implementation in EspHttpBinding which relies on ESDL to generate the schema
// Moved from the prior implementation in EspHttpBinding which now relies on ESDL to generate the schema.
// However, since WsEcl is acting a front-end for roxie queries, it needs this custom implementation
// that uses the information from the roxie instead.
// that uses the information from the roxie instead of ESDL.
bool CWsEclBinding::getSchema(StringBuffer& schema, IEspContext &ctx, CHttpRequest* req, const char *service, const char *method,bool standalone)
{
StringBuffer serviceQName;
Expand Down Expand Up @@ -1601,7 +1601,7 @@ int CWsEclBinding::getGenForm(IEspContext &context, CHttpRequest* request, CHttp
}
}
else
getSchema(formxml, context, request, wuinfo);
getSimpleSchema(formxml, context, request, wuinfo);

formxml.append("<CustomViews>");
if (web)
Expand Down Expand Up @@ -1709,7 +1709,7 @@ void CWsEclBinding::getWsEcl2XmlRequest(StringBuffer& soapmsg, IEspContext &cont
element.append(wsinfo.queryname.str()).append("Request");

StringBuffer schemaXml;
getSchema(schemaXml, context, request, wsinfo);
getSimpleSchema(schemaXml, context, request, wsinfo);
ESPLOG(LogMax,"request schema: %s", schemaXml.str());
Owned<IXmlSchema> schema = createXmlSchemaFromString(schemaXml);
if (schema.get())
Expand Down Expand Up @@ -1745,7 +1745,7 @@ void CWsEclBinding::getWsEclJsonRequest(StringBuffer& jsonmsg, IEspContext &cont
element.append("Request");

StringBuffer schemaXml;
getSchema(schemaXml, context, request, wsinfo);
getSimpleSchema(schemaXml, context, request, wsinfo);
ESPLOG(LogMax,"request schema: %s", schemaXml.str());
Owned<IXmlSchema> schema = createXmlSchemaFromString(schemaXml);
if (schema.get())
Expand Down Expand Up @@ -2378,20 +2378,96 @@ int CWsEclBinding::getWsdlBindings(IEspContext &context, CHttpRequest *request,
int CWsEclBinding::onGetWsdl(IEspContext &context, CHttpRequest* request, CHttpResponse* response, WsEclWuInfo &wsinfo)
{
context.setBindingValue(&wsinfo);
EspHttpBinding::onGetWsdl(context, request, response, wsinfo.qsetname.str(), wsinfo.queryname.str());
getWsdlOrXsd(context, request, response, wsinfo.qsetname.str(), wsinfo.queryname.str(), true);
context.setBindingValue(NULL);
return 0;
}

int CWsEclBinding::onGetXsd(IEspContext &context, CHttpRequest* request, CHttpResponse* response, WsEclWuInfo &wsinfo)
{
context.setBindingValue(&wsinfo);
EspHttpBinding::onGetXsd(context, request, response, wsinfo.qsetname.str(), wsinfo.queryname.str());
getWsdlOrXsd(context, request, response, wsinfo.qsetname.str(), wsinfo.queryname.str(), false);
context.setBindingValue(NULL);

return 0;
}

int CWsEclBinding::getWsdlOrXsd(IEspContext &context, CHttpRequest* request, CHttpResponse* response, const char *service, const char *method, bool isWsdl)
{
bool mda=(request->queryParameters()->getPropInt("mda")!=0);
try
{
StringBuffer serviceQName;
StringBuffer methodQName;

if (!qualifyServiceName(context, service, method, serviceQName, &methodQName))
{
return onGetNotFound(context, request, response, service);
}
else
{
const char *sqName = serviceQName.str();
const char *mqName = methodQName.str();
StringBuffer ns;
generateNamespace(context, request, serviceQName.str(), methodQName.str(), ns);

StringBuffer content("<?xml version=\"1.0\" encoding=\"UTF-8\"?>");
if (context.queryRequestParameters()->hasProp("display"))
content.append("<?xml-stylesheet type=\"text/xsl\" href=\"/esp/xslt/xmlformatter.xsl\"?>");
else if (isWsdl && context.queryRequestParameters()->hasProp("wsdlviewer"))
content.append("<?xml-stylesheet type=\"text/xsl\" href=\"/esp/xslt/wsdl-viewer.xsl\"?>");
if (isWsdl)
{
content.appendf("<definitions xmlns=\"http://schemas.xmlsoap.org/wsdl/\" xmlns:soap=\"http://schemas.xmlsoap.org/wsdl/soap/\" xmlns:http=\"http://schemas.xmlsoap.org/wsdl/http/\" xmlns:xsd=\"http://www.w3.org/2001/XMLSchema\""
" xmlns:mime=\"http://schemas.xmlsoap.org/wsdl/mime/\" xmlns:tns=\"%s\""
" targetNamespace=\"%s\">", ns.str(), ns.str());
content.append("<types>");
}

getSchema(content,context,request,service,method,!isWsdl);

if (isWsdl)
{
content.append("</types>");

getWsdlMessages(context, request, content, sqName, mqName, mda);
getWsdlPorts(context, request, content, sqName, mqName, mda);
getWsdlBindings(context, request, content, sqName, mqName, mda);

StringBuffer location(getWsdlAddress());
if (request->queryParameters()->hasProp("wsdl_destination_path"))
location.append(request->queryParameters()->queryProp("wsdl_destination_path"));
else
location.append('/').append(sqName).appendf("?ver_=%g", context.getClientVersion());

if (request->queryParameters()->hasProp("encode_results"))
{
const char *encval = request->queryParameters()->queryProp("encode_results");
location.append("&amp;").appendf("encode_=%s", (encval && *encval) ? encval : "1");
}

content.appendf("<service name=\"%s\">", sqName);
content.appendf("<port name=\"%sServiceSoap\" binding=\"tns:%sServiceSoap\">", sqName, sqName);
content.appendf("<soap:address location=\"%s\"/>", location.str());
content.append("</port>");
content.append("</service>");
content.append("</definitions>");
}

response->setContent(content.length(), content.str());
response->setContentType(HTTP_TYPE_APPLICATION_XML_UTF8);
response->setStatus(HTTP_STATUS_OK);
}
}
catch (IException *e)
{
return onGetException(context, request, response, *e);
}

response->send();
return 0;
}


int CWsEclBinding::getWsEclDefinition(CHttpRequest* request, CHttpResponse* response, const char *thepath)
{
Expand Down Expand Up @@ -2511,7 +2587,7 @@ int CWsEclBinding::getRestURL(IEspContext *ctx, CHttpRequest *request, CHttpResp

StringBuffer schemaXml;

getSchema(schemaXml, *ctx, request, wsinfo);
getSimpleSchema(schemaXml, *ctx, request, wsinfo);
Owned<IXmlSchema> schema = createXmlSchemaFromString(schemaXml);
if (schema.get())
{
Expand Down
6 changes: 4 additions & 2 deletions esp/services/ws_ecl/ws_ecl_service.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,9 @@ class CWsEclBinding : public CHttpSoapBinding

protected:
bool getSchema(StringBuffer& schema, IEspContext &ctx, CHttpRequest* req, const char *service, const char *method,bool standalone) override;
int getWsdlOrXsd(IEspContext &context, CHttpRequest* request, CHttpResponse* response, const char *service, const char *method, bool isWsdl);
// Does not provide all the flexibility of the getSchema override. Consider refactoring out to use getSchema in its place.
bool getSimpleSchema(StringBuffer& schema, IEspContext &ctx, CHttpRequest* req, WsEclWuInfo &wsinfo) ;

public:
CWsEclBinding(IPropertyTree *cfg, const char *bindname, const char *procname) :
Expand Down Expand Up @@ -202,8 +205,7 @@ class CWsEclBinding : public CHttpSoapBinding
bool qualifyServiceName(IEspContext &context, const char *servname, const char *methname, StringBuffer &servQName, StringBuffer *methQName){servQName.clear().append(servname); if (methQName) methQName->clear().append(methname); return true;}

int getXsdDefinition(IEspContext &context, CHttpRequest *request, StringBuffer &content, WsEclWuInfo &wsinfo);
bool getSchema(StringBuffer& schema, IEspContext &ctx, CHttpRequest* req, WsEclWuInfo &wsinfo) ;


void appendSchemaNamespaces(IPropertyTree *namespaces, IEspContext &ctx, CHttpRequest* req, WsEclWuInfo &wsinfo);
void appendSchemaNamespaces(IPropertyTree *namespaces, IEspContext &ctx, CHttpRequest* req, const char *service, const char *method);

Expand Down

0 comments on commit f5bf94d

Please sign in to comment.