/// <summary> /// 요청 정보중에 응답정보로 다시 보내기 위해서 헤더 정보를 복사한다. /// </summary> /// <param name="requestDocument">요청문서</param> /// <param name="responseDocument">응답문서</param> public static void CopyRequestHeader(this XdsRequestDocument requestDocument, XdsResponseDocument responseDocument) { requestDocument.ShouldNotBeNull("requestDocument"); responseDocument.ShouldNotBeNull("responseDocument"); responseDocument.ConnectionString = requestDocument.ConnectionString; responseDocument.Transaction = requestDocument.Transaction; responseDocument.IsolationLevel = requestDocument.IsolationLevel; }
/// <summary> /// 요청정보를 실행하여 응답정보를 반환합니다. /// </summary> /// <param name="requestDocument">요청정보</param> /// <param name="commandTimeout">요청 처리 제한 시간 (단위 : seconds, 기본값 : 90)</param> /// <returns>요청 처리 응답정보</returns> public virtual XdsResponseDocument Execute(XdsRequestDocument requestDocument, int? commandTimeout) { if(IsDebugEnabled) log.Debug("요청정보에 따른 Database 작업을 시작합니다..."); requestDocument.ShouldNotBeNull("requestDocument"); if(requestDocument == null) return XmlDataTool.CreateResponseWithError(new InvalidOperationException(MsgConsts.NoRequestProvided)); var responseDocument = new XdsResponseDocument(); TransactionScope txScope = null; try { if(IsDebugEnabled) log.Debug("요청문서 분석 및 응답문서를 초기화 합니다."); requestDocument.CopyRequestHeader(responseDocument); if(requestDocument.CommandTimeout > commandTimeout.GetValueOrDefault(90)) commandTimeout = requestDocument.CommandTimeout; if(requestDocument.Transaction) { if(IsDebugEnabled) log.Debug("요청문서에 Transaction 적용 옵션이 설정되어 있습니다. TransactionScope를 이용하여, 전체 요청을 Transaction 하에서 실행합니다."); txScope = AdoTool.CreateTransactionScope(TransactionScopeOption.Required, IsolationLevel.ReadCommitted); } //! 실제 요청 처리 ExecuteRequestCore(requestDocument, responseDocument); // Transaction을 Commit 한다 // if(txScope != null) { if(IsDebugEnabled) log.Debug("Transaction Commit을 시작합니다..."); txScope.Complete(); if(IsDebugEnabled) log.Debug("Transaction Commit에 성공했습니다.!!!"); } } catch(Exception ex) { responseDocument.ReportError(ex); } finally { if(txScope != null) txScope.Dispose(); } if(IsDebugEnabled) log.Debug("모든 요청을 처리하고, ResponseDocument를 반환합니다."); return responseDocument; }
public static XdsResponseDocument CreateResponseWithError(Exception ex) { var responseDoc = new XdsResponseDocument(); if(ex != null) { responseDoc.Errors.AddError(ex); if(log.IsWarnEnabled) log.WarnException("예외가 발생하여 예외정보를 담은 응답문서를 생성했습니다.", ex); } return responseDoc; }
private static XdsResponseDocument GetResponseDocument() { var responseDoc = new XdsResponseDocument(); var index = responseDoc.AddResponseItem(new XdsResponseItem(XmlDataResponseKind.DataSet, 1, 1)); responseDoc[index].Fields.AddFieldArray("USER_ID", "USER_NAME", "USER_PWD"); responseDoc[index].Records.AddColumnArray("debop", "배성혁", "비밀번호"); responseDoc[index].Records.AddColumnArray("mskwon", "권미숙", "비밀번호"); responseDoc.Errors.AddError(new InvalidOperationException("테스트용 에러 메시지 입니다.")); Assert.AreEqual(1, responseDoc.Responses.Count); Assert.AreEqual(1, responseDoc.Errors.Count); return responseDoc; }
private static XdsResponseDocument GetResponseDocument() { var responseDoc = new XdsResponseDocument(); var index = responseDoc.AddResponseItem(new XdsResponseItem(XmlDataResponseKind.DataSet, 1, 1)); responseDoc[index].Fields.AddFieldArray("USER_ID", "USER_NAME", "USER_PWD"); responseDoc[index].Records.AddColumnArray("debop", "배성혁", "비밀번호"); responseDoc[index].Records.AddColumnArray("mskwon", "권미숙", "비밀번호"); responseDoc.Errors.AddError(new InvalidOperationException("테스트용 에러 메시지 입니다.")); Assert.AreEqual(1, responseDoc.Responses.Count); Assert.AreEqual(1, responseDoc.Errors.Count); return(responseDoc); }
/// <summary> /// 요청 정보를 병렬로 모두 수행합니다. /// </summary> protected override void ExecuteRequestCore(XdsRequestDocument requestDocument, XdsResponseDocument responseDocument) { if(requestDocument.IsParallelToolecute == false) { base.ExecuteRequestCore(requestDocument, responseDocument); return; } if(IsDebugEnabled) log.Debug(@"요청을 병렬방식으로 수행합니다..."); // 요청을 병렬로 처리합니다. requestDocument.Requests .AsParallel() .AsOrdered() .ForAll(request => DoProcessRequestItem(request, responseDocument)); if(IsDebugEnabled) log.Info(@"모든 요청을 병렬 수행으로 처리했습니다."); }
/// <summary> /// 요청정보중에 확인을 위해 응답정보에 조건들을 기록해둔다. /// </summary> /// <param name="request"></param> /// <param name="responseDocument"></param> private static void WriteRequestInfomation(XdsRequestItem request, XdsResponseDocument responseDocument) { var index = responseDocument.Responses.Count - 1; if(index >= 0) { responseDocument[index].PageSize = request.PageSize; responseDocument[index].PageNo = request.PageNo; responseDocument[index].Sort = request.Sort; responseDocument[index].TotalRecordCount = responseDocument[index].Records.Count; if(responseDocument[index].PageSize > 0) responseDocument[index].PageCount = responseDocument[index].TotalRecordCount / responseDocument[index].PageSize + 1; } }
/// <summary> /// 일반 Query문을 수행하여 DataSet을 받아서 ResponseDom 객체를 만든다. /// </summary> /// <param name="request">요청 항목</param> /// <param name="responseDocument">응답 정보</param> protected virtual void OpenQuery(XdsRequestItem request, XdsResponseDocument responseDocument) { request.ShouldNotBeNull("request"); if(IsDebugEnabled) log.Debug("쿼리문을 수행하여 결과셋을 얻습니다... request Id=[{0}], query=[{1}], requestType=[{2}], responseType=[{3}], sort=[{4}]", request.Id, request.Query, request.RequestKind, request.ResponseKind, request.Sort); try { var maxSequence = Math.Max(1, request.Values.Count); for(var seqId = 0; seqId < maxSequence; seqId++) { var adoParameters = PrepareParameters(request, seqId).ToArray(); using(var cmd = Ado.GetCommand(request.Query)) using(var pagingTable = Ado.ExecutePagingDataTable(cmd, Math.Max(0, request.PageNo - 1), request.PageSize, adoParameters)) using(var dv = pagingTable.Table.DefaultView) { if(request.Sort.IsNotWhiteSpace()) dv.Sort = request.Sort; responseDocument.Responses.AddResponseItem(dv, request.Id, seqId); } } } catch(Exception ex) { if(log.IsErrorEnabled) log.ErrorException(string.Format("쿼리문을 수행하여 결과셋을 얻는데 실패했습니다. query=[{0}]", request.Query), ex); throw; } if(IsDebugEnabled) log.Debug("쿼리문을 수행하여 결과셋을 얻는데 성공했습니다. query=[{0}]", request.Query); }
/// <summary> /// 일반 SQL Query 문 중에 DDL 과 관련된 문장을 수행한다. (결과 SET이 필요없는 것) /// </summary> /// <param name="request">요청 항목</param> /// <param name="responseDocument">응답 정보</param> protected virtual void ExecuteQuery(XdsRequestItem request, XdsResponseDocument responseDocument) { if(IsDebugEnabled) log.Debug("쿼리문장을 실행합니다... requestId=[{0}], queryString=[{1}], requestType=[{2}], responseType=[{3}]", request.Id, request.Query, request.RequestKind, request.ResponseKind); try { var isScalar = request.ResponseKind == XmlDataResponseKind.Scalar; var maxSequence = Math.Max(1, request.Values.Count); for(var seqId = 0; seqId < maxSequence; seqId++) { var adoParameters = PrepareParameters(request, seqId).ToArray(); using(var cmd = Ado.GetSqlStringCommand(request.Query)) { var result = (isScalar) ? Ado.ExecuteScalar(cmd, adoParameters) : Ado.ExecuteNonQuery(cmd, adoParameters); var responseItem = responseDocument.AddResponseItem(request.ResponseKind, request.Id, seqId); if(isScalar) { responseItem.Fields.AddField("RETURN_VALUE", typeof(int).Name, 4); responseItem.Records.AddColumnArray(result); } } } } catch(Exception ex) { if(log.IsErrorEnabled) log.ErrorException(string.Format("쿼리 문 실행에 실패했습니다. query=[{0}]", request.Query), ex); throw; } if(IsDebugEnabled) log.Debug("쿼리문 실행에 성공했습니다. query=[{0}]", request.Query); }
/// <summary> /// Stored Procedure를 수행하고, OUTPUT, RETURN_VALUE를 반환한다. /// </summary> /// <param name="request">요청 항목</param> /// <param name="responseDocument">응답 정보</param> protected virtual void ExecuteProcedure(XdsRequestItem request, XdsResponseDocument responseDocument) { if(IsDebugEnabled) log.Debug("프로시저를 실행합니다... requestId=[{0}], procedure=[{1}], requestType=[{2}], responseType=[{3}]", request.Id, request.Query, request.RequestKind, request.ResponseKind); try { var maxSequence = Math.Max(1, request.Values.Count); for(var seqId = 0; seqId < maxSequence; seqId++) { var adoParameters = PrepareParameters(request, seqId).ToArray(); using(var cmd = Ado.GetProcedureCommand(request.Query)) { Ado.ExecuteNonQuery(cmd, adoParameters); var response = responseDocument.AddResponseItem(XmlDataResponseKind.Scalar, request.Id, seqId); ExtractParameters(AdoTool.GetOutputParameters(Ado.Db, cmd), response, seqId); } } } catch(Exception ex) { if(log.IsErrorEnabled) log.ErrorException(string.Format("프로시저 실행에 실패했습니다. procedure=[{0}]", request.Query), ex); throw; } if(IsDebugEnabled) log.Debug("프로시저 실행에 성공했습니다. procedure=[{0}]", request.Query); }
/// <summary> /// <paramref name="request"/> 요청에 대해, 처리를 수행합니다. /// </summary> /// <param name="request">요청항목</param> /// <param name="responseDocument">응답 정보</param> protected void DoProcessRequestItem(XdsRequestItem request, XdsResponseDocument responseDocument) { request.ShouldNotBeNull("request"); var isDataSet = (request.ResponseKind == XmlDataResponseKind.DataSet); switch(request.RequestKind) { case XmlDataRequestKind.StoredProc: if(isDataSet) OpenProcedure(request, responseDocument); else ExecuteProcedure(request, responseDocument); break; case XmlDataRequestKind.Query: if(isDataSet) OpenQuery(request, responseDocument); else ExecuteQuery(request, responseDocument); break; default: throw new NotSupportedException("지원하지 않는 요청 종류입니다. RequestType=" + request.RequestKind); } // 요청정보중에 확인을 위해 응답정보에 조건들을 기록해둔다. // if(isDataSet) WriteRequestInfomation(request, responseDocument); }
/// <summary> /// 요청에 대한 실제 작업을 수행합니다. /// </summary> protected virtual void ExecuteRequestCore(XdsRequestDocument requestDocument, XdsResponseDocument responseDocument) { if(IsDebugEnabled) log.Debug("요청 정보를 옵션에 따라 동기적으로 실행합니다..."); foreach(var request in requestDocument.Requests) { // 메소드인 경우는 QueryProvider를 이용하여, 실제 Query 문장으로 변경한다. // XmlDataTool.ConvertToQuery(Ado, request); ExecuteSimpleQuery(Ado, request.PreQueries); //! 실제 수행 DoProcessRequestItem(request, responseDocument); ExecuteSimpleQuery(Ado, request.PostQueries); } }
/// <summary> /// /// </summary> /// <param name="requestBytes"></param> /// <param name="productName"></param> /// <param name="serializer"></param> /// <returns></returns> public static byte[] Execute(byte[] requestBytes, string productName, ISerializer serializer) { if(productName.IsWhiteSpace()) productName = AdoTool.DefaultDatabaseName; XdsResponseDocument xdsResponse = null; byte[] result = null; try { Guard.Assert(requestBytes != null && requestBytes.Length > 0, "요청 정보가 없습니다."); XmlDataServiceFacade.CheckProductExists(productName); var requestData = (byte[])serializer.Deserialize(requestBytes); var xdsRequest = requestData.ConvertToXdsRequestDocument(XmlTool.XmlEncoding); xdsResponse = XmlDataServiceFacade.Execute(xdsRequest, productName); } catch(Exception ex) { if(log.IsErrorEnabled) log.ErrorException("예외가 발생했습니다.", ex); if(xdsResponse == null) xdsResponse = new XdsResponseDocument(); xdsResponse.ReportError(ex); } finally { byte[] xdsResponseBytes; XmlTool.Serialize(xdsResponse, out xdsResponseBytes); result = serializer.Serialize(xdsResponseBytes); } return result; }
/// <summary> /// 처리 결과를 Http Response에 쓴다. /// </summary> /// <param name="response"></param> /// <param name="xdsResponse"></param> /// <param name="serializer"></param> internal static void WriteResponse(HttpResponse response, XdsResponseDocument xdsResponse, ISerializer serializer) { response.Clear(); response.Buffer = true; response.Expires = -1; response.ContentEncoding = XmlTool.XmlEncoding; response.ContentType = "text/xml"; var responseBytes = serializer.Serialize(xdsResponse.ConvertToBytes()); response.OutputStream.Write(responseBytes, 0, responseBytes.Length); // XmlTool.Serialize(xdsResponse, response.OutputStream); }
/// <summary> /// /// </summary> /// <param name="requestStream"></param> /// <param name="productName"></param> /// <param name="serializer"></param> /// <returns></returns> public static Stream ExecuteStreamInternal(Stream requestStream, string productName, ISerializer serializer) { XdsResponseDocument xdsResponse = null; MemoryStream result = null; try { Guard.Assert(requestStream != null && requestStream.Length > 0, "요청 정보가 없습니다."); CheckProductExists(productName); var xdsRequest = (XdsRequestDocument)serializer.Deserialize(requestStream.ToBytes()); xdsResponse = XmlDataServiceFacade.Execute(xdsRequest, productName); } catch(Exception ex) { if(log.IsErrorEnabled) log.ErrorException("예외가 발생했습니다.", ex); if(xdsResponse == null) xdsResponse = new XdsResponseDocument(); xdsResponse.ReportError(ex); } finally { result = new MemoryStream(serializer.Serialize(xdsResponse)); } return result; }
public void VerifyXdsResponseDocument(XdsResponseDocument responseMsg) { responseMsg.Should().Not.Be.Null(); responseMsg.HasError.Should().Be.False(); }