Call an asmx web service from NAV

I am a complete beginner in web services. Can anyone please help me in call an external asmx web from NAV 2016 and pass a parameter during the call?
I understand this is not a step by step training forum, but a step by step process in calling the web service and then passing a parameter will rescue me.
My apologies ahead :s

Best Answers

  • navbeginnernavbeginner Posts: 23
    Accepted Answer
    ftornero wrote: »
    This is an example of a call to a Webservice who is expecting 2 parameters, countryCode and year
    OBJECT Codeunit 50051 Web Service SOAP example
    {
      OBJECT-PROPERTIES
      {
        Date=04/09/18;
        Time=17:13:56;
        Modified=Yes;
        Version List=SOAP;
      }
      PROPERTIES
      {
        OnRun=BEGIN
    
                xml := '<?xml version="1.0" encoding="utf-8"?><soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><soap:Body>'+
                         '<GetHolidaysForYear xmlns="http://www.holidaywebservice.com/HolidayService_v2/">'+
                           '<countryCode>UnitedStates</countryCode>'+
                           '<year>2019</year>'+
                         '</GetHolidaysForYear>'+
                       '</soap:Body></soap:Envelope>';
    
                url := 'http://www.holidaywebservice.com/HolidayService_v2/HolidayService2.asmx';
                uriObj := uriObj.Uri(url);
                Request := Request.CreateDefault(uriObj);
                Request.Method := 'POST';
                Request.ContentType := 'text/xml';
                soapAction := '"http://www.holidaywebservice.com/HolidayService_v2/GetHolidaysForYear"';
                Request.Headers.Add('SOAPAction', soapAction);
                Request.Timeout := 120000;
    
                // Send the request to the webservice
                stream := stream.StreamWriter(Request.GetRequestStream(), ascii.UTF8);
                stream.Write(xml);
                stream.Close();
    
                // Get the response
                Response := Request.GetResponse();
                reader := reader.XmlTextReader(Response.GetResponseStream());
    
                // Save the response to a XML
                document := document.XmlDocument();
                document.Load(reader);
                FileSrv := FileMgt.ServerTempFileName('xml');
                document.Save(FileSrv);
    
                // Get from the server
                ToFile := FileMgt.ClientTempFileName('xml');
                FileMgt.DownloadToFile(FileSrv, ToFile);
    
                // Show the response XML
                HYPERLINK(ToFile);
              END;
    
      }
      CODE
      {
        VAR
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Uri";
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Net.HttpWebRequest";
          [email protected] : DotNet "'mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.IO.StreamWriter";
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Net.HttpWebResponse";
          [email protected]00000006 : DotNet "'System.Xml, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Xml.XmlTextReader";
          [email protected] : DotNet "'System.Xml, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Xml.XmlDocument";
          [email protected] : DotNet "'mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Text.Encoding";
          [email protected] : Codeunit 419;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
    
        BEGIN
        END.
      }
    }
    

    Is possible that to call your web service you only need to change the parts in red, but you must see the webservice documentation.

    ycytac29ibdw.jpg

    Regards

    Thanks ftornero,

    I would try the above solution and inform.

Answers

  • navbeginnernavbeginner Posts: 23Member
    ErictP wrote: »
    ErictP wrote: »

    Hi ErictP,

    Thanks a lot for your reply.

    I tried to put the code provided in your first link in a report and try running it, so that I may have a start.
    But I received the following error.
    hn23qpgh5rnn.png

    I tried to google on the error, but couldn't find any solution. Can you help?
  • navbeginnernavbeginner Posts: 23Member
    Experts please help me...
  • navbeginnernavbeginner Posts: 23Member
    Accepted Answer
    ftornero wrote: »
    This is an example of a call to a Webservice who is expecting 2 parameters, countryCode and year
    OBJECT Codeunit 50051 Web Service SOAP example
    {
      OBJECT-PROPERTIES
      {
        Date=04/09/18;
        Time=17:13:56;
        Modified=Yes;
        Version List=SOAP;
      }
      PROPERTIES
      {
        OnRun=BEGIN
    
                xml := '<?xml version="1.0" encoding="utf-8"?><soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><soap:Body>'+
                         '<GetHolidaysForYear xmlns="http://www.holidaywebservice.com/HolidayService_v2/">'+
                           '<countryCode>UnitedStates</countryCode>'+
                           '<year>2019</year>'+
                         '</GetHolidaysForYear>'+
                       '</soap:Body></soap:Envelope>';
    
                url := 'http://www.holidaywebservice.com/HolidayService_v2/HolidayService2.asmx';
                uriObj := uriObj.Uri(url);
                Request := Request.CreateDefault(uriObj);
                Request.Method := 'POST';
                Request.ContentType := 'text/xml';
                soapAction := '"http://www.holidaywebservice.com/HolidayService_v2/GetHolidaysForYear"';
                Request.Headers.Add('SOAPAction', soapAction);
                Request.Timeout := 120000;
    
                // Send the request to the webservice
                stream := stream.StreamWriter(Request.GetRequestStream(), ascii.UTF8);
                stream.Write(xml);
                stream.Close();
    
                // Get the response
                Response := Request.GetResponse();
                reader := reader.XmlTextReader(Response.GetResponseStream());
    
                // Save the response to a XML
                document := document.XmlDocument();
                document.Load(reader);
                FileSrv := FileMgt.ServerTempFileName('xml');
                document.Save(FileSrv);
    
                // Get from the server
                ToFile := FileMgt.ClientTempFileName('xml');
                FileMgt.DownloadToFile(FileSrv, ToFile);
    
                // Show the response XML
                HYPERLINK(ToFile);
              END;
    
      }
      CODE
      {
        VAR
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Uri";
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Net.HttpWebRequest";
          [email protected] : DotNet "'mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.IO.StreamWriter";
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Net.HttpWebResponse";
          [email protected] : DotNet "'System.Xml, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Xml.XmlTextReader";
          [email protected] : DotNet "'System.Xml, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Xml.XmlDocument";
          [email protected] : DotNet "'mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Text.Encoding";
          [email protected] : Codeunit 419;
          [email protected]000000015 : Text;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
    
        BEGIN
        END.
      }
    }
    

    Is possible that to call your web service you only need to change the parts in red, but you must see the webservice documentation.

    ycytac29ibdw.jpg

    Regards

    Thanks ftornero,

    I would try the above solution and inform.
  • navbeginnernavbeginner Posts: 23Member
    ftornero wrote: »
    This is an example of a call to a Webservice who is expecting 2 parameters, countryCode and year
    OBJECT Codeunit 50051 Web Service SOAP example
    {
      OBJECT-PROPERTIES
      {
        Date=04/09/18;
        Time=17:13:56;
        Modified=Yes;
        Version List=SOAP;
      }
      PROPERTIES
      {
        OnRun=BEGIN
    
                xml := '<?xml version="1.0" encoding="utf-8"?><soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><soap:Body>'+
                         '<GetHolidaysForYear xmlns="http://www.holidaywebservice.com/HolidayService_v2/">'+
                           '<countryCode>UnitedStates</countryCode>'+
                           '<year>2019</year>'+
                         '</GetHolidaysForYear>'+
                       '</soap:Body></soap:Envelope>';
    
                url := 'http://www.holidaywebservice.com/HolidayService_v2/HolidayService2.asmx';
                uriObj := uriObj.Uri(url);
                Request := Request.CreateDefault(uriObj);
                Request.Method := 'POST';
                Request.ContentType := 'text/xml';
                soapAction := '"http://www.holidaywebservice.com/HolidayService_v2/GetHolidaysForYear"';
                Request.Headers.Add('SOAPAction', soapAction);
                Request.Timeout := 120000;
    
                // Send the request to the webservice
                stream := stream.StreamWriter(Request.GetRequestStream(), ascii.UTF8);
                stream.Write(xml);
                stream.Close();
    
                // Get the response
                Response := Request.GetResponse();
                reader := reader.XmlTextReader(Response.GetResponseStream());
    
                // Save the response to a XML
                document := document.XmlDocument();
                document.Load(reader);
                FileSrv := FileMgt.ServerTempFileName('xml');
                document.Save(FileSrv);
    
                // Get from the server
                ToFile := FileMgt.ClientTempFileName('xml');
                FileMgt.DownloadToFile(FileSrv, ToFile);
    
                // Show the response XML
                HYPERLINK(ToFile);
              END;
    
      }
      CODE
      {
        VAR
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Uri";
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Net.HttpWebRequest";
          [email protected] : DotNet "'mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.IO.StreamWriter";
          [email protected] : DotNet "'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Net.HttpWebResponse";
          [email protected] : DotNet "'System.Xml, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Xml.XmlTextReader";
          [email protected] : DotNet "'System.Xml, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Xml.XmlDocument";
          [email protected] : DotNet "'mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.System.Text.Encoding";
          [email protected] : Codeunit 419;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
          [email protected] : Text;
    
        BEGIN
        END.
      }
    }
    

    Is possible that to call your web service you only need to change the parts in red, but you must see the webservice documentation.

    ycytac29ibdw.jpg

    Regards

    Thanks a lot ftornero,
    your solution really helped me. :)
  • vnprocvnproc VietNamPosts: 28Member
    I am interested in this solution. I want to ask the question, after saving XML file, how to use object XMLPort to import data to NAV 2013 table. Please help me with the solution.

    Thanks so much.
  • ftorneroftornero Posts: 241Member
    Hello @vnproc,

    After you get the response XML file you can save it to a OutStream and later on use as a Instream for the SETSOURCE method in the XMLPort.

    Regards.
  • vnprocvnproc VietNamPosts: 28Member
    Hi Ftornero.

    Thank you for your reply

    I have a question about the format of the XML file after getting from the web service. I will set up XMLPort file how to get data into NAV 2013 table.
    <?xml version="1.0" encoding="utf-8"?>
    <soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
      <soap:Header>
        <Authentication xmlns="http://tempuri.org/">
          <UserName>string</UserName>
          <Password>string</Password>
        </Authentication>
      </soap:Header>
      <soap:Body>
        <GetLatestOrders xmlns="http://tempuri.org/" />
      </soap:Body>
    </soap:Envelope>
    HTTP/1.1 200 OK
    Content-Type: text/xml; charset=utf-8
    Content-Length: length
    
    <?xml version="1.0" encoding="utf-8"?>
    <soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
      <soap:Body>
        <GetLatestOrdersResponse xmlns="http://tempuri.org/">
          <GetLatestOrdersResult>
            <Data>
              <Order>
                <OrderCode>string</OrderCode>
                <OrderDate>string</OrderDate>
              </Order>
              <Order>
                <OrderCode>string</OrderCode>
                <OrderDate>string</OrderDate>
              </Order>
            </Data>
            <MsgError>
              <Code>int</Code>
              <Message>string</Message>
            </MsgError>
          </GetLatestOrdersResult>
        </GetLatestOrdersResponse>
      </soap:Body>
    </soap:Envelope>
    
    
    <?xml version="1.0" encoding="utf-16"?>
    <Envelope>
      <Body>
        <GetLatestOrdersResponse>
          <GetLatestOrdersResult>
            <Data>
              <Order>
                <OrderCode>OU1234321</OrderCode>
                <OrderDate>04/08/2019 11:59:42 SA</OrderDate>
              </Order>
              <Order>
                <OrderCode>OU1234325</OrderCode>
                <OrderDate>04/08/2019 11:59:42 SA</OrderDate>
              </Order>
            </Data>
            <MsgError>
              <Code>0</Code>
            </MsgError>
          </GetLatestOrdersResult>
        </GetLatestOrdersResponse>
      </Body>
    </Envelope>
    

    Thanks so much.
  • ftorneroftornero Posts: 241Member
    Hello @vnproc ,

    If your XML looks like the last one this XMLPort will import the data into a NAV table.

    You maybe need to test the MsgError->Code before do anything else.
    OBJECT XMLport 50002 XMLPort Prueba2
    {
      OBJECT-PROPERTIES
      {
        Date=04/08/19;
        Time=18:14:42;
        Modified=Yes;
        Version List=;
      }
      PROPERTIES
      {
        Encoding=UTF-16;
        OnPreXMLport=BEGIN
                       IF Tabla.FINDLAST THEN
                         qMov := Tabla.NMov
                       ELSE
                         qMov := 0;
                     END;
    
      }
      ELEMENTS
      {
        { [{354D2F6D-5C97-4F03-9E13-CC58412B5AE5}];  ;Envelope            ;Element ;Text    ;
                                                      MaxOccurs=Once }
    
        { [{BA7A2157-70E2-44FD-8BAD-7382AB86021A}];1 ;Body                ;Element ;Text    ;
                                                      MaxOccurs=Once }
    
        { [{8314AEA7-93E7-46B2-90C4-8162798DA59E}];2 ;GetLatestOrdersResponse;Element;Text  ;
                                                      MaxOccurs=Once }
    
        { [{FC021764-9FD2-4D59-9EB6-3871B67A0BB1}];3 ;GetLatestOrdersResult;Element;Text    ;
                                                      MaxOccurs=Once }
    
        { [{ED4D332F-91A8-4CFA-B01C-C46AF0E3FB02}];4 ;Data                ;Element ;Text    ;
                                                      MaxOccurs=Once }
    
        { [{DFA2921E-21E5-4BEC-AA0D-67FA5E3CE3DD}];5 ;Order               ;Element ;Text    ;
                                                      Import::OnAfterAssignVariable=BEGIN
                                                                                      Tabla.INIT;
                                                                                      qMov := qMov + 1;
                                                                                      Tabla.NMov := qMov;
                                                                                      Tabla.Order := OrderCode;
                                                                                      Tabla.OrderDate := Txt2DateTime(OrderDate);
                                                                                      Tabla.INSERT;
                                                                                    END;
                                                                                     }
    
        { [{67447662-DDFC-44CC-B4C0-5D6B112BCC3E}];6 ;OrderCode           ;Element ;Text    ;
                                                      MaxOccurs=Once }
    
        { [{CE599035-9895-47FB-BA92-A8197CE9875F}];6 ;OrderDate           ;Element ;Text    ;
                                                      MaxOccurs=Once }
    
        { [{4B65E647-A90A-4854-8B8E-EC694D30E9A7}];4 ;MsgError            ;Element ;Text    ;
                                                      MaxOccurs=Once }
    
        { [{EBD48FA8-7985-4155-995A-ACC2CBB8C6FE}];5 ;Code                ;Element ;Text    ;
                                                      MaxOccurs=Once }
    
      }
      EVENTS
      {
      }
      REQUESTPAGE
      {
        PROPERTIES
        {
        }
        CONTROLS
        {
        }
      }
      CODE
      {
        VAR
          [email protected] : Record 90002;
          [email protected] : Integer;
    
        PROCEDURE [email protected]([email protected] : Text[250]) : DateTime;
        VAR
          [email protected] : DateTime;
          [email protected] : Date;
          [email protected] : Time;
        BEGIN
          qDT := 0DT;
          IF DELCHR(Texto,'=') = '' THEN
            EXIT(qDT);
          IF EVALUATE(qDate, COPYSTR(Texto, 1, 10)) THEN
            IF EVALUATE(qTime, COPYSTR(Texto, 12, 8)) THEN
              qDT := CREATEDATETIME(qDate, qTime);
          EXIT(qDT);
        END;
    
        BEGIN
        END.
      }
    }
    

    Regards.
  • vnprocvnproc VietNamPosts: 28Member
    Thanks ftornero & RockWithNAV

    I would like to ask more questions about variable transmission.
    Example: I want to call the Webservice from day to day, so what would it look like. And I can retrieve data from the current date back before 30 days.

    How do I call the parameter?

    Thanks so much
    
    Xml :='<?xml version="1.0" encoding="utf-8"?><soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><soap:Header>'+
          '<ServiceAuthentication xmlns="http://tempuri.org/">'+
          '</ServiceAuthentication></soap:Header><soap:Body>'+
          '<GetLatestOrders xmlns="http://tempuri.org/" /></soap:Body></soap:Envelope>';
    
    //MESSAGE(url);
    uriObj := uriObj.Uri(url);
    Request := Request.CreateDefault(uriObj);
    Request.Method := 'POST';
    Request.ContentType := 'text/xml; charset=utf-8';
    SoapAction :='http://tempuri.org/GetLatestOrders';
    
    Request.Headers.Add('SOAPAction', SoapAction);
    Request.Timeout := 120000;
    
    // Send the request to the webservice
    Stream := Stream.StreamWriter(Request.GetRequestStream(), ascii.UTF8);
    Stream.Write(Xml);
    Stream.Close();
    
    // Get the response
    Response:=Response.HttpWebResponse;
    Response := Request.GetResponse();
    Reader := Reader.XmlTextReader(Response.GetResponseStream());
    
    ClientFilePath:=StatementFolderFullPath +'\'+'XMLConvert.txt';
    ClientFilePathTo:='C:\Temp\XMLConvert.txt';
    
    
    // Save the response to a XML
    document := document.XmlDocument();
    document.Load(Reader);
    FileSrv := FileMgt.ServerTempFileName('txt');
    document.Save(FileSrv);
    
    document.Save(ClientFilePath);
    document.Load(ClientFilePath);
    
    RemoveNamespace(document,document);
    document.Save(ClientFilePathTo);
    
    // Get from the server
    ToFile := FileMgt.ClientTempFileName('txt');
    RemoveNamespace(document,document);
    
    FileMgt.DownloadToFile(FileSrv,ToFile);
    // Show the response XML
    
    END;
    
  • RockWithNAVRockWithNAV Posts: 872Member
    The question is still not clear to me, can you make it a level more clear please?
  • vnprocvnproc VietNamPosts: 28Member
    Hi RockWithNAV,
    '<countryCode>UnitedStates</countryCode>'+
                           '<year>2019</year>'+
                         '</GetHolidaysForYear>'+
    
    I meant to call parameters from the Service. In the example above.

    But here I want to call the order date parameter (from day to day)

    Thanks.
  • RockWithNAVRockWithNAV Posts: 872Member
    @vnproc - See calling any API , first we need to understand like what are the defined parameters that are supposed to be send , the one where I gave the example I am sending Customer No to check either that Customer no exist and the API on which I am targeting is also expecting the same from me, so as a parameter whatever you want you can send it all depends how the target API is built and suppose to respond.
  • ftorneroftornero Posts: 241Member
    Hello @vnproc,

    You need to check the web service WSDL to get the functions that you can use and how use them.

    With a program like SoapUI and this WSDL you can get an example of how to call to those functions.

    Regards.
  • vnprocvnproc VietNamPosts: 28Member
    Thanks ftornero & RockWithNAV

    Is there any problem when I call the service with the port?
    Ex : http://www.holidaywebservice.com:9000

    Then function change?
    url := 'http://www.holidaywebservice.com:9000/HolidayService_v2/HolidayService2.asmx';
    uriObj := uriObj.Uri(url);
    

    If yes, do I need to make any changes to the code.

    Thanks so much
  • ftorneroftornero Posts: 241Member
    Hello @vnproc,

    If the call to the web service is defined with a port number, there is no problem using it.

    Regards.
  • vnprocvnproc VietNamPosts: 28Member
    Thanks ftornero.

    Hi Everybody.

    When I run the manual from CodeUnit, then it's work.
    But when using the job queue, the following error:

    Microsoft Dynamics NAV Application Server attempted to issue a client callback to create a DotNet object: C:\ProgramData\Microsoft\Microsoft Dynamics NAV\70\Server\MicrosoftDynamicsNavServer$NAV70\users\JOMY\***\TEMP\__TEMP__8c48ec2d48b04f9da1719be1f781f61a.tmp.txt (CodeUnit 419 File Management). Client callbacks are not supported on Microsoft Dynamics NAV Application Server.

    Please fix help.

    Thanks so much
  • ftorneroftornero Posts: 241Member
    Hello @vnproc,

    In the job queue your code is running in the server, so any DotNet var must run on the server.

    The error that you get is because you are using a function inside the codeunit 419 that is trying to manage same file in the client side, you need to change that function to the eqivalent one running in the sever side.

    Regards
  • vnprocvnproc VietNamPosts: 28Member
    Thanks Ftornero,

    Problem soved. I'm have fix on line
    //FileMgt.DownloadToFile(FileSrv,ToFile);
    
Sign In or Register to comment.