/// <summary> /// Submit /// </summary> /// <param name="securityToken"></param> /// <param name="transactionId"></param> /// <param name="dataflow"></param> /// <param name="documents"></param> /// <returns></returns> string INetworkNodeBinding.Submit(string securityToken, string transactionId, string dataflow, NodeDocument[] documents) { Init(); LOG.Debug("Submit"); if (documents == null || documents.Length == 0) { throw _service11Provider.FaultProvider.GetFault(EndpointVersionType.EN11, ENExceptionCodeType.E_InvalidParameter, "Document not provided"); } SoapContext context = HttpSoapContext.RequestContext; bool useDimeAttachments = true; if (context == null || context.Attachments == null || context.Attachments.Count == 0) { bool allContentNull = true; bool anyContentMissing = false; foreach (NodeDocument document in documents) { if (document.content == null) { anyContentMissing = true; } else { allContentNull = false; } } if (anyContentMissing) { if (!allContentNull) { // Some documents contain content, some don't, what the heck is this??? throw _service11Provider.FaultProvider.GetFault(EndpointVersionType.EN11, ENExceptionCodeType.E_InvalidParameter, "Some documents do not contain any content."); } // All document content is null, attempt to locate all <content> elements in the xml itself XmlNodeList nodeList = context.Envelope.Body.GetElementsByTagName("content"); if ((nodeList == null) || (nodeList.Count != documents.Length)) { throw _service11Provider.FaultProvider.GetFault(EndpointVersionType.EN11, ENExceptionCodeType.E_InvalidParameter, "Could not locate the data content for the submitted documents."); } int index = 0; foreach (NodeDocument document in documents) { XmlNode contentContentNode = nodeList[index++]; if (string.IsNullOrEmpty(contentContentNode.InnerXml)) { throw _service11Provider.FaultProvider.GetFault(EndpointVersionType.EN11, ENExceptionCodeType.E_InvalidParameter, "Some documents do not contain any content."); } document.content = System.Convert.FromBase64String(contentContentNode.InnerXml); } } useDimeAttachments = false; } else if (context.Attachments.Count != documents.Length) { throw _service11Provider.FaultProvider.GetFault(EndpointVersionType.EN11, ENExceptionCodeType.E_InvalidParameter, "DIME attachment count does not equal to the number of documents."); } try { LOG.Debug("Getting visit"); NamedEndpointVisit visit = _service11Provider.VisitProvider.GetVisit(securityToken); AsyncComplexContent content = new AsyncComplexContent(); content.Documents = new List <Document>(); content.Flow = new OperationDataFlow(dataflow); content.Transaction = new SimpleId(transactionId); int attachmentCounter = 0; LOG.Debug("Spooling documents"); foreach (NodeDocument wsdlDoc in documents) { Document doc = new Document(); doc.Content = useDimeAttachments ? GetContent(context.Attachments[attachmentCounter++].Stream) : wsdlDoc.content; doc.Type = CommonContentAndFormatProvider.Convert(wsdlDoc.type); doc.DocumentId = string.Empty; doc.DocumentName = wsdlDoc.name; LOG.Debug(" doc:" + doc); content.Documents.Add(doc); } LOG.Debug("Submitting: " + content); TransactionStatus status = _service11Provider.ContentService.Submit(content, visit); LOG.Debug("Status: " + status); return(status.Id); //Status ID in this case is the transaction id } catch (Exception ex) { LOG.Error("Error while submitting", ex); throw _service11Provider.FaultProvider.GetFault(EndpointVersionType.EN11, ex); } }
public TransactionStatus Submit(AsyncComplexContent content, NamedEndpointVisit visit) { Activity activity = null; IList <string> newDocumentIds = null; bool isNewTransaction = false; try { // Validate inputs NodeVisit nodeVisit; MakeEndpointActivity(visit, ActivityType.Audit, NodeMethod.Submit, out nodeVisit, out activity); if (content == null) { throw FaultProvider.GetFault(visit.Version, ENExceptionCodeType.E_InvalidParameter, "Input content is null"); } if (CollectionUtils.IsNullOrEmpty(content.Documents)) { throw FaultProvider.GetFault(visit.Version, ENExceptionCodeType.E_InvalidParameter, "Input document list is empty"); } if (content.Transaction == null) { throw FaultProvider.GetFault(visit.Version, ENExceptionCodeType.E_InvalidParameter, "Input transaction is null"); } if ((content.Flow == null) || string.IsNullOrEmpty(content.Flow.FlowName)) { throw FaultProvider.GetFault(visit.Version, ENExceptionCodeType.E_InvalidParameter, "Input flow is null"); } bool isFlowProtected; string flowId = FlowManager.GetDataFlowIdByName(content.Flow.FlowName, out isFlowProtected); if (flowId == null) { throw FaultProvider.GetFault(visit.Version, ENExceptionCodeType.E_InvalidDataflow, "Flow \"{0}\" was not found", content.Flow.FlowName); } activity.FlowName = content.Flow.FlowName; activity.Operation = content.Flow.Operation; isNewTransaction = string.IsNullOrEmpty(content.Transaction.Id); string networkId = null; // Get the flow id associated with the transaction if (isNewTransaction) { } else { // Existing transaction isNewTransaction = ValidateTransaction(visit.Version, NodeMethod.Submit, content, (visit.Version != EndpointVersionType.EN11), flowId, out networkId); if (!isNewTransaction) { activity.TransactionId = content.Transaction.Id; } } DataService documentService = FlowManager.GetSubmitDocumentServiceForFlow(flowId, content.Flow.Operation); if (documentService == null) { if (!string.IsNullOrEmpty(content.Flow.Operation)) { throw FaultProvider.GetFault(visit.Version, ENExceptionCodeType.E_ServiceUnavailable, "A valid Submit service was not found for the flow \"{0}\"", content.Flow.FlowName); } // Let empty operation pass through, even without a valid service, per Mark } else if (!documentService.IsActive) { throw FaultProvider.GetFault(visit.Version, ENExceptionCodeType.E_ServiceUnavailable, "The Submit service is not active for the flow \"{0}\"", content.Flow.FlowName); } if (isFlowProtected) { ValidateUserPermissions(nodeVisit, content.Flow.FlowName, content.Flow.Operation, NodeMethod.Submit, activity); } if (isNewTransaction) { // Create a new transaction content.Transaction.Id = TransactionManager.CreateTransaction(NodeMethod.Submit, visit.Version, flowId, content.Flow.Operation, nodeVisit.Account.Id, CommonTransactionStatusCode.Unknown, null, content.Notifications, content.Recipients, false); activity.TransactionId = content.Transaction.Id; if (networkId != null) { TransactionManager.SetNetworkId(content.Transaction.Id, networkId, EndpointVersionType.Undefined, null, null, null); } activity.AppendFormat("Created new submit transaction id: {0}.", activity.TransactionId); } else { activity.AppendFormat("Retrieved existing submit transaction id: {0}.", activity.TransactionId); } foreach (Document document in content.Documents) { activity.AppendFormat("Adding submit document to transaction: {0}.", document); } // Add the documents to repository and DB newDocumentIds = DocumentManager.AddDocuments(content.Transaction.Id, content.Documents); #if DEBUG //NodeTransaction nodeTransaction = TransactionManager.GetTransaction(content.Transaction.Id, // CommonTransactionStatusCode.Received); #endif // DEBUG TransactionStatus rtnTransactionStatus = TransactionManager.SetTransactionStatus(content.Transaction.Id, nodeVisit.Account.Id, CommonTransactionStatusCode.Received, null, false); NotificationManager.DoSubmitNotifications(rtnTransactionStatus, flowId, content.Flow.FlowName, content.Flow.Operation, nodeVisit.Account.NaasAccount); SubmitProcessor.Wakeup(); return(rtnTransactionStatus); } catch (Exception ex) { if (newDocumentIds != null) { DocumentManager.RollbackDocuments(content.Transaction.Id, newDocumentIds); } if (isNewTransaction && !string.IsNullOrEmpty(content.Transaction.Id)) { TransactionManager.SetTransactionStatusNoThrow(content.Transaction.Id, CommonTransactionStatusCode.Failed, ex.Message, false); } if (activity != null) { activity.Append(ExceptionUtils.ToShortString(ex)); activity.Type = ActivityType.Error; } if (ex is SoapException) { throw; // Throw directly since already SoapException } else { throw FaultProvider.GetFault(visit.Version, ex); } } finally { if (activity != null) { ActivityManager.Log(activity); } } }