kreta/Kreta.EESZTInterface/eFT/DoRequest.cs
2024-03-13 00:33:46 +01:00

187 lines
6.7 KiB
C#

using System;
using System.IO;
using System.Net;
using System.Net.Security;
using System.Security.Cryptography.X509Certificates;
using System.Text;
using System.Xml;
using Kreta.EESZTInterface.STS;
using Kreta.Resources;
namespace Kreta.EESZTInterface.eFT
{
public class DoRequest
{
public static (XmlDocument soapResponse, byte[] mTOMAttachment) GetSoapSamlResponse(string eftUri, X509Certificate2 sslAuthCert, string soapRequest, SamlAssertion samlAssertion)
{
try
{
HttpWebRequest request = GetHttpWebRequest(eftUri, sslAuthCert, samlAssertion);
var (data, hasAttachment) = WriteToHttpStream(request, soapRequest);
var msResp = new MemoryStream(data);
StreamReader sr = new StreamReader(msResp);
var responseString = sr.ReadToEnd();
if (!hasAttachment)
{
var soapResponse = ThrowIfSoapFault(responseString);
return (soapResponse, null);
}
else
{
var xmlEleje = responseString.IndexOf("<?xml");
var xmlVege = responseString.IndexOf("\r\n--MIME_Boundary");
responseString = responseString.Substring(xmlEleje, xmlVege - xmlEleje);
var soapResponse = ThrowIfSoapFault(responseString);
byte[] boundary1 = Encoding.UTF8.GetBytes("org>" + "\r\n\r\n");
byte[] boundary2 = Encoding.UTF8.GetBytes("\r\n--" + "MIME_Boundary" + "--\r\n");
var attachment = GetAttachmentData(data, boundary1, boundary2);
return (soapResponse, attachment);
}
}
catch (WebException wex)
{
string exMessage = wex.Message;
if (wex.Response != null)
{
using (var responseReader = new StreamReader(wex.Response.GetResponseStream()))
{
exMessage = responseReader.ReadToEnd();
ThrowIfSoapFault(exMessage);
}
}
throw new Exception(exMessage, wex);
}
catch
{
throw;
}
}
private static HttpWebRequest GetHttpWebRequest(string stsUri, X509Certificate2 sslAuthCert, SamlAssertion samlAssertion = null)
{
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(stsUri);
request.Headers.Add("SOAPAction", "");
request.ContentType = "application/soap+xml;charset=\"utf-8\"";
request.Accept = "application/soap+xml";
request.Method = "POST";
request.ClientCertificates.Add(sslAuthCert);
return request;
}
private static (byte[] data, bool hasAttachment) WriteToHttpStream(HttpWebRequest request, string soapRequest)
{
using (Stream stream = request.GetRequestStream())
{
MemoryStream ms = new MemoryStream(Encoding.UTF8.GetBytes(soapRequest));
ms.WriteTo(stream);
}
WebResponse response = request.GetResponse();
MemoryStream msResp = new MemoryStream();
int read;
byte[] buffer = new byte[1024];
while ((read = response.GetResponseStream().Read(buffer, 0, buffer.Length)) > 0)
{
msResp.Write(buffer, 0, read);
}
return (data: msResp.ToArray(), hasAttachment: response.ContentType.Contains("multipart"));
}
private static byte[] GetAttachmentData(byte[] data, byte[] boundary1, byte[] boundary2)
{
if (data == null || boundary1 == null || boundary2 == null)
return null;
if (boundary1.LongLength > data.LongLength)
return null;
long i, j, startIndex;
bool match;
int boundary1Pos = 0;
for (i = 0; i < data.LongLength; i++)
{
startIndex = i;
match = true;
for (j = 0; j < boundary1.LongLength; j++)
{
if (data[startIndex] != boundary1[j])
{
match = false;
break;
}
if (startIndex < data.LongLength)
{
startIndex++;
}
}
if (match)
boundary1Pos = Convert.ToInt32(startIndex - boundary1.LongLength);
}
int pos1 = boundary1Pos + boundary1.Length;
int pos2 = data.Length - boundary2.Length;
int length = pos2 - pos1;
try
{
byte[] output = new byte[length];
Array.Copy(data, pos1, output, 0, length);
return output;
}
catch { }
return null;
}
private static XmlDocument ThrowIfSoapFault(string response)
{
XmlDocument soapMessage;
try
{
soapMessage = ExtractDocumentFromResponse(response);
if (soapMessage == null)
{
throw new Exception();
}
}
catch (Exception ex)
{
throw new Exception(EESZTInterfaceResource.NemMegfeleloSOAPValaszFormatum, ex);
}
XmlElement fault = XmlHelper.GetElement("Fault", Namespaces.soap11Ns, soapMessage.DocumentElement);
if (fault == null)
{
return soapMessage;
}
var faultCodeNodes = XmlHelper.GetElement("faultcode", "", fault);
var faultReasonNodes = XmlHelper.GetElement("faultstring", "", fault);
var exceptionDetailNodes = XmlHelper.GetElement("detail", "", fault);
throw new Exception("Hiba! Kód:" + faultCodeNodes.InnerText + " Részletek:" + faultReasonNodes.InnerText,
new Exception((exceptionDetailNodes == null) ? "" : exceptionDetailNodes.InnerText));
}
private static XmlDocument ExtractDocumentFromResponse(string response)
{
var soapResponse = new XmlDocument();
soapResponse.PreserveWhitespace = true;
soapResponse.LoadXml(response);
return soapResponse;
}
private bool ValidateServerCertificate(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors sslPolicyErrors)
{
return true;
}
}
}