API in Dynamics AX 2012

468 views Asked by At

I have a problem in AX 2012 when I call API by Https URL give me this error

(The request was aborted: Could not create SSL/TLS secure channel)

but when I test code in Dynamic 365 It Work

This My code:

str destinationUrl,requestJson, responseJson;

System.Net.HttpWebRequest  request;

System.Net.HttpWebResponse  response = new System.Net.HttpWebResponse();

    CLRObject      clrObj;

System.Byte[]         bytes;

System.Text.Encoding     utf8;

System.IO.Stream       requestStream, responseStream;

System.IO.StreamReader    streamReader;

System.Exception        ex;

System.Net.WebHeaderCollection httpHeader;

System.Net.ServicePoint    servicePt;
System.Net.ServicePointManager ServicePointManager;

str           byteStr;

System.Byte[]      byteArray;

System.IO.Stream     stream;

System.IO.Stream     dataStream;
int secProtocol;
boolean ssl3,tls,tls11,tls12,tls13;

destinationUrl = 'https://...';

requestJson  = @'MyJsonData';
try

{

  new InteropPermission(InteropKind::ClrInterop).assert();

  httpHeader = new System.Net.WebHeaderCollection();

  clrObj = System.Net.WebRequest::Create(destinationUrl);
   
  request = clrObj;

  utf8 = System.Text.Encoding::get_UTF8();

  bytes = utf8.GetBytes(requestJson);

   request.set_Method("POST");

  httpHeader.Add("Client-Id","5...");
  httpHeader.Add("Secret-Key","...");
  httpHeader.Add("Cookie", "...");

  request.set_Headers(httpHeader);

  request.set_ContentType('application/json');

  request.set_ContentLength(bytes.get_Length());
 
  //ServicePointManager.Expect100Continue = true;
    System.Net.ServicePointManager::set_Expect100Continue(true);
  //ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
    System.Net.ServicePointManager::set_SecurityProtocol(System.Net.SecurityProtocolType::Tls12);
  secProtocol = System.Net.ServicePointManager::get_SecurityProtocol();

  ssl3 = secProtocol == enum2int(System.Net.SecurityProtocolType::Ssl3);
  tls = secProtocol == enum2int(System.Net.SecurityProtocolType::Tls);
  tls11 = secProtocol == enum2int(System.Net.SecurityProtocolType::Tls11);
  tls12 = secProtocol == enum2int(System.Net.SecurityProtocolType::Tls12);
  tls13 = secProtocol == 12288;
   
  info(strFmt("SSL3 enabled: '%1' | TLS enabled: '%2' | TLS1.1 enabled: '%3' | TLS1.2 enabled: '%4' | TLS1.3 enabled: '%5'", ssl3, tls, tls11, tls12, tls13));
   
  requestStream = request.GetRequestStream();

  requestStream.Write(bytes, 0, bytes.get_Length());

  response = request.GetResponse();

  responseStream = response.GetResponseStream();

  streamReader = new System.IO.StreamReader(responseStream);

  responseJson = streamReader.ReadToEnd();

  info(responseJson);

}

catch (Exception::CLRError)

{

  ex = CLRInterop::getLastException().GetBaseException();

  error(ex.get_Message());

}

I used this: System.Net.ServicePointManager::set_Expect100Continue(true); System.Net.ServicePointManager::set_SecurityProtocol(System.Net.SecurityProtocolType::Tls12);

1

There are 1 answers

2
Alex Kwitny On

AX 2012 is an old application and it looks like it's having TLS issues.

The best thing to do is probably just move your code to a C# wrapper and then call your wrapper from AX. That'll ensure your TLS settings are used.

Otherwise, try forcing TLS via modifying the AX config files. If your code is running

  • server-side - [On the AOS] C:\Program Files\Microsoft Dynamics AX\60\Server\[YourAOSFolder]\bin\Ax32Serv.exe.config

  • client-side - C:\Program Files (x86)\Microsoft Dynamics AX\60\Client\Bin\Ax32.exe.config

I'm not a TLS expert, but just some Googling about .Net applications and you'd need to add something like one of the following below. Personally, I'd just experiment with them and you may need to restart the AOS or your AX client depending on where you put the code. TLS issues can be a pain, so maybe even the server, but I wouldn't think so.

Sample 1 -

<runtime>
    <AppContextSwitchOverrides value="Switch.System.ServiceModel.DisableUsingServicePointManagerSecurityProtocols=false;Switch.System.Net.DontEnableSchUseStrongCrypto=false"/>
</runtime>

Sample 2 -

<runtime>
    <AppContextSwitchOverrides value="Switch.System.Net.DontEnableSystemDefaultTlsVersions=false"/>
</runtime>

Sample 3 -

<runtime>
    <AppContextSwitchOverrides value="Switch.System.Net.DontEnableSchUseStrongCrypto=false"/>
</runtime>