어댑터 디자인 문제
사용자가 디자인 타임에 구성을 변경하면 어댑터 구성이 SSO(Single Sign-On) 데이터베이스에 저장됩니다. 런타임에 메시징 엔진은 어댑터 구성을 검색하여 어댑터로 전달합니다. 다음 네 가지 유형의 구성 정보가 어댑터로 전달됩니다.
수신 핸들러 구성
수신 위치(엔드포인트) 구성
송신 핸들러 구성
송신 위치(엔드포인트) 구성
수신 및 송신 핸들러 구성
어댑터의 처리기 구성은 선택적 IPersistPropertyBag 구현 시 어댑터에 전달됩니다. 로드 인터페이스. 핸들러 구성은 한 번만 전달되므로 BizTalk 서비스를 시작한 후 어댑터 핸들러 구성을 변경하면 어댑터가 업데이트되지 않습니다. 일반적인 모델은 어댑터가 핸들러 구성을 기본 구성으로 간주하는 것입니다. 엔드포인트별로 엔드포인트 구성이 핸들러 구성을 재정의합니다.
다음 일부 코드는 구성의 구문 분석을 보여 줍니다. 어댑터의 구성은 문자열 속성 AdapterConfig의 Load 호출에 전달된 속성에 있습니다. 이 속성 값에는 어댑터 구성을 나타내는 XML 문서가 포함됩니다. 어댑터는 이 구성을 DOM(문서 개체 모델) 또는 XML 판독기로 로드하고 XPath를 사용하여 개별 속성을 검색해야 합니다.
public class MyAdapter : IBTTransport,
IBTTransportConfig,
IBTTransportControl,
IPersistPropertyBag,
IBaseComponent
{
...
// Handler configuration properties...
private int defaultBatchSize = 0;
private string defaultHeader;
// IPersistPropertyBag.Load() implementation...
public void Load(IPropertyBag pb, int pErrorLog)
{
// The adapter configuration is in the property
// “AdapterConfig” in the form of an Xml blob...
object obj = null;
pb.Read("AdapterConfig", out obj, 0);
// Create a DOM and load the Xml blob...
XmlDocument dom = new XmlDocument();
string adapterConfig = (string)obj;
dom.LoadXml(adapterConfig);
// XPath the individual properties...
XmlNode node =
document.SelectSingleNode(“/Config/batchSize”);
defaultBatchSize = int.Parse(node.InnerText);
node = document.SelectSingleNode(“/Config/header”);
defaultHeader = node.InnerText;
}
}
수신 위치 구성
수신 위치 구성 정보는 IBTTransportConfig 구현 시 어댑터에 전달됩니다. 이 인터페이스에는 AddReceiveEndpoint, UpdateEndpointConfig 및 RemoveReceiveEndpoint의 세 가지 메서드가 포함되어 있습니다. 메시징 엔진은 메시지를 받기 위해 수신 대기해야 하는 엔드포인트를 어댑터에 알립니다. 개별 엔드포인트의 구성이 변경되면 해당 엔드포인트의 변경 내용을 어댑터에 알립니다. 이와 달리 핸들러 구성이 변경될 때는 어댑터에게 알리지 않습니다. 마찬가지로 서비스 윈도가 활성화되거나 비활성화되면 BizTalk Server에서 엔드포인트를 추가 또는 제거하므로 어댑터는 서비스 윈도를 처리할 필요가 없습니다.
AddReceiveEndpoint
어댑터가 엔드포인트에서 수신을 시작해야 하는 경우 엔진은 수신 위치의 URI를 전달하는 IBTTransportConfig.AddReceiveEndpoint, 해당 엔드포인트에 대한 어댑터의 구성을 포함하는 속성 모음 및 해당 엔드포인트에 대한 BizTalk Server 특정 구성이 포함된 두 번째 속성 모음을 호출합니다. 어댑터는 메시지 컨텍스트에 URI를 BizTalk Server 시스템 속성인 InboundTransportLocation으로 작성해야 합니다.
어댑터의 PropertyBag에서 수신 위치 속성을 읽는 것은 위에서 설명한 대로 핸들러 구성을 읽는 것과 같습니다. 어댑터에 전달된 BizTalk Server 구성에는 포트가 단방향인지 양방향인지 여부를 나타내는 단일 속성 TwoWayReceivePort가 포함됩니다. 다음 일부 코드는 BizTalk Server PropertyBag에서 수신 포트가 단방향인지 또는 양방향인지 평가하는 방법을 보여 줍니다.
public void AddReceiveEndpoint(
string url,
IPropertyBag adapterConfig,
IPropertyBag bizTalkConfig )
{
...
// The property "TwoWayReceivePort" in the BizTalk Config
// property bag indicates whether the port is one or two
// way...
// Add receive location to config cache (not shown here)
object obj = null;
bizTalkConfig.Read("TwoWayReceivePort", out obj, 0);
if ( null != obj )
this.twoWay = (bool)obj;
}
UpdateEndpointConfig
활성 수신 위치의 구성이 변경되면 엔진은 UpdateEndpointConfig API를 사용하여 어댑터에 다른 구성을 사용해야 한다고 알립니다. BizTalk Server 관련 구성을 비롯한 모든 구성이 어댑터로 전달됩니다.
RemoveReceiveEndpoint
수신 위치가 더 이상 활성화되지 않으면 RemoveReceiveEndpoint를 통해 어댑터에 알림이 표시됩니다. 어댑터가 RemoveReceiveEndpoint 에서 반환된 후에는 더 이상 해당 URI를 사용하여 엔진에 메시지를 제출할 수 없습니다.
송신 포트 구성
메시징 엔진은 메시지를 어댑터로 배달하기 전에 어댑터 네임스페이스의 메시지 컨텍스트에 송신 포트의 구성을 씁니다. 어댑터는 구성을 읽고 유효성을 검사한 다음 이 구성을 사용하여 메시지 전송을 제어합니다. 일괄 처리 송신을 지원하는 송신 어댑터의 경우 서로 다른 송신 포트로 향하는 메시지가 동일한 일괄 처리에 포함될 수 있으므로 어댑터는 이러한 "혼합된" 일괄 처리를 수행해야 합니다.
다음 코드 조각에서는 송신 포트의 URI인 OutboundTransportLocation 을 읽는 방법을 보여 줍니다. 또한 어댑터 구성이 포함된 XML Blob을 읽은 다음 개별 속성을 읽는 방법을 보여 줍니다.
...
private static readonly PropertyBase UriProperty =
new BTS.OutboundTransportLocation();
private string propertyNamespace =
"http://schemas.mySchemas.com/MyAdapter/myadapter-properties";
private string uri;
private string headers;
private int timeOut = 1000;
private void ReadSendPortConfig(IBaseMessage msg)
{
// Read the OutboundTransportLocation,
// i.e. the send port uri....
uri = (string)msg.Context.Read(
UriProperty.Name.Name, UriProperty.Name.Namespace);
// Read the adapters configuration Xml blob from
// the message...
XmlDocument locationConfigDom = null;
object obj = msg.Context.Read(
"AdapterConfig", this.propertyNamespace);
// If this is a dynamic send there will not be
// any configuration...
if ( null != obj )
{
locationConfigDom = new XmlDocument();
locationConfigDom.LoadXml((string)obj);
this.headers = Extract(
locationConfigDom, "/Config/headers", true);
this.timeOut = ExtractInt32(
locationConfigDom, "/Config/timeOut", true);
}
}
// Helper method to XPath string properties...
private static string Extract(
XmlDocument document, string path, bool required)
{
XmlNode node = document.SelectSingleNode(path);
if (!required && null == node)
return String.Empty;
if (null == node)
throw new ApplicationException(string.Format(
"No property was found at {0}", path));
return node.InnerText;
}
// Helper method to XPath int32 properties...
private static int ExtractInt32(
XmlDocument document, string path, bool required)
{
string s = Extract(document, path, required);
return int.Parse(s);
}
구현 팁: 어댑터는 일반적으로 OutboundTransportLocation 메시지 컨텍스트 속성을 사용하여 메시지를 보낼 주소를 결정해야 합니다. 이렇게 하면 어댑터가 정적 송신과 동적 송신을 위한 전송을 일관성 있게 처리할 수 있습니다. 또한 프로덕션 바인딩 파일에서 편리하게 주소를 수정할 수 있습니다.
XSD
SDK 파일 어댑터 샘플에 포함된 4개의 XSD 파일은 주로 어댑터 구성을 처리합니다. ReceiveHandler.xsd, ReceiveLocation.xsd, TransmitLocation.xsd 및 TransmitHandler.xsd.
다음 항목에서는 각 파일과 이러한 파일을 수정하는 방법에 대해 설명합니다.