You can use the instructions in this topic to build the XMLNSC Namespaces sample. Alternatively, you can import the completed message set and Integration project for the sample. You must import the XMLNSC Namespaces sample files into your workspace before you use the instructions to build the sample.
To build the XMLNSC Namespaces sample:
Node | Page | Property | Value |
---|---|---|---|
MQInput | Basic | Queue name | ADDNAMESPACEMF.IN |
Input Message Parsing | Message domain | XMLNSC | |
Validation | Validate | Inherit | |
Compute | Validation | Validate | Inherit |
MQOutput | Basic | Queue name |
ADDNAMESPACEMF.OUT |
CREATE FUNCTION ChangeNamespaceInOutputRoot(In rootNode REFERENCE, In oldNamespace CHARACTER, In newNamespace CHARACTER) BEGIN -- -- Need to remove schemalocation and namespace declarations -- IF newNamespace = '' THEN SET rootNode.(XMLNSC.Element)*[1].*:schemaLocation = NULL; DECLARE I1 INTEGER CARDINALITY(rootNode.(XMLNSC.Element)*[1].(XMLNSC.NamespaceDecl)*[]); DECLARE I2 INTEGER 1; WHILE I2 <= I1 DO SET rootNode.(XMLNSC.Element)*[1].(XMLNSC.NamespaceDecl)*[1] = NULL; SET I2 = I2 + 1; END WHILE; ELSE -- -- Need to modify the schema locations and the namespace declarations -- -- The target schemalocations can be identified within the source message's -- MQRFH2 header, <usr> folder, tag <TargetSchemaLocation> -- IF rootNode.(XMLNSC.Element)*[1].*:schemaLocation IS NOT NULL THEN SET rootNode.(XMLNSC.Element)*[1].*:schemaLocation = newNamespace; END IF; END IF; -- -- CHECKSIBLING is a flag which, when set to TRUE, ensures that the WHILE loop does an -- unconditional MOVE ... NEXTSIBLING (rather than MOVE ... FIRSTCHILD) -- We need this when we go up a level in the tree... otherwise we go back where we have -- just come from -- DECLARE CHECKSIBLING BOOLEAN FALSE; -- -- DEPTH determines when to finish. -- Every time we MOVE FIRSTCHILD we add 1 to DEPTH -- Every time we MOVE PARENT we subtract 1 from DEPTH -- MOVE NEXTSIBLING does not change DEPTH -- Initial value is 1, so we are finished when DEPTH = 0 -- DECLARE DEPTH INTEGER 1; -- -- Walk the tree top to bottom, left to right -- WHILE DEPTH <> 0 DO IF CHECKSIBLING = FALSE THEN MOVE rootNode FirstChild; IF LASTMOVE(rootNode) = TRUE THEN SET DEPTH = DEPTH + 1; CALL ChangeNamespace(rootNode, oldNamespace, newNamespace); ELSE MOVE rootNode NEXTSIBLING; IF LASTMOVE(rootNode) = TRUE THEN CALL ChangeNamespace(rootNode, oldNamespace, newNamespace); SET CHECKSIBLING = FALSE; ELSE SET DEPTH = DEPTH - 1; Move rootNode PARENT; SET CHECKSIBLING = TRUE; END IF; END IF; ELSE MOVE rootNode NEXTSIBLING; IF LASTMOVE(rootNode) = TRUE THEN CALL ChangeNamespace(rootNode, oldNamespace, newNamespace); SET CHECKSIBLING = FALSE; ELSE SET DEPTH = DEPTH - 1; Move rootNode PARENT; SET CHECKSIBLING = TRUE; END IF; END IF; END WHILE; END; CREATE FUNCTION ChangeNamespace(IN rootNode REFERENCE, In oldNamespace CHARACTER, In newNamespace CHARACTER) BEGIN -- -- Check for elements/attributes with the source namespace -- IF (FIELDTYPE(rootNode) = Name) OR (FIELDTYPE(rootNode) = NameValue) THEN IF FIELDNAMESPACE(rootNode) IN (oldNamespace) THEN -- -- Set the new target namespace -- SET rootNode NAMESPACE = newNamespace; -- -- Get rid of any inline namespace definitions -- SET rootNode.(XMLNSC.NamespaceDecl)* = NULL; END IF; END IF; END;
CREATE COMPUTE MODULE ADDNAMESPACEMF_Compute CREATE FUNCTION Main() RETURNS BOOLEAN BEGIN DECLARE SourceNamespace NAMESPACE ''; DECLARE TargetNamespace NAMESPACE 'http://www.samplemessage.brokertest.hursley.ibm.com'; CALL CopyMessageHeaders(); DECLARE oldNamespace CHARACTER ''; DECLARE newNamespace CHARACTER ''; SET oldNamespace = SourceNamespace; SET newNamespace = TargetNamespace; IF InputRoot.MQRFH2.usr.SourceNamespace IS NOT NULL THEN SET oldNamespace = InputRoot.MQRFH2.usr.SourceNamespace; END IF; -- The target namespace can be specified dynamically in the MQRFH2 header. -- The following logic checks whether the MQRFH2 contains this info; if it does not, -- defaults are supplied in the message flow. IF InputRoot.MQRFH2.usr.TargetNamespace IS NOT NULL THEN SET newNamespace = InputRoot.MQRFH2.usr.TargetNamespace; ELSE SET newNamespace = TargetNamespace; END IF; -- Make the output tree the same as the input tree. SET OutputRoot.XMLNSC = InputBody; -- Change the namespace of the root element. DECLARE rootNode REFERENCE TO OutputRoot.XMLNSC.*[<]; CALL ChangeNamespace (rootNode, oldNamespace, newNamespace); -- Alternatively, apply namespaces to local (nested) elements too. -- DECLARE rootNode REFERENCE TO OutputRoot.XMLNSC; -- CALL ChangeNamespace (rootNode, oldNamespace, newNamespace); RETURN TRUE; END; CREATE PROCEDURE CopyMessageHeaders() BEGIN DECLARE I INTEGER 1; DECLARE J INTEGER; SET J = CARDINALITY(InputRoot.*[]); WHILE I < J DO SET OutputRoot.*[I] = InputRoot.*[I]; SET I = I + 1; END WHILE; END; CREATE PROCEDURE CopyEntireMessage() BEGIN SET OutputRoot = InputRoot; END; END MODULE;
Node | Page | Property | Value |
---|---|---|---|
MQInput | Basic | Queue name | CHANGENAMESPACEMF.IN |
Input Message Parsing | Message domain | XMLNSC | |
Validation | Validate | Content and Value | |
Compute | Validation | Validate | Inherit |
MQOutput | Basic | Queue name |
CHANGENAMESPACEMF.OUT |
CREATE COMPUTE MODULE CHANGENAMESPACEMF_Compute CREATE FUNCTION Main() RETURNS BOOLEAN BEGIN DECLARE SourceNamespace NAMESPACE 'http://www.samplemessage.broker.hursley.ibm.com'; DECLARE TargetNamespace NAMESPACE 'http://www.samplemessage.brokertest.hursley.ibm.com'; CALL CopyMessageHeaders(); DECLARE oldNamespace CHARACTER ''; DECLARE newNamespace CHARACTER ''; SET oldNamespace = SourceNamespace; SET newNamespace = TargetNamespace; IF InputRoot.MQRFH2.usr.SourceNamespace IS NOT NULL THEN IF InputRoot.MQRFH2.usr.SourceNamespace = 'NONAMESPACE' THEN SET oldNamespace = ''; ELSE SET oldNamespace = InputRoot.MQRFH2.usr.SourceNamespace; END IF; ELSE SET oldNamespace = SourceNamespace; END IF; -- The target namespace can be specified dynamically in the MQRFH2 header. -- The following logic checks whether the MQRFH2 contains this info; if it does not, -- defaults are supplied in the message flow. IF InputRoot.MQRFH2.usr.TargetNamespace IS NOT NULL THEN IF InputRoot.MQRFH2.usr.TargetNamespace = 'NONAMESPACE' THEN SET newNamespace = ''; ELSE SET newNamespace = InputRoot.MQRFH2.usr.TargetNamespace; END IF; ELSE SET newNamespace = TargetNamespace; END IF; -- Make the output tree the same as the input tree. -- We will then walk the tree changing things as we go SET OutputRoot.XMLNSC = InputBody; DECLARE rootNode REFERENCE TO OutputRoot.XMLNSC; CALL ChangeNamespaceInOutputRoot (rootNode, oldNamespace, newNamespace); RETURN TRUE; END; CREATE PROCEDURE CopyMessageHeaders() BEGIN DECLARE I INTEGER 1; DECLARE J INTEGER; SET J = CARDINALITY(InputRoot.*[]); WHILE I < J DO SET OutputRoot.*[I] = InputRoot.*[I]; SET I = I + 1; END WHILE; END; CREATE PROCEDURE CopyEntireMessage() BEGIN SET OutputRoot = InputRoot; END; END MODULE;
Node | Page | Property | Value |
---|---|---|---|
MQInput | Basic | Queue name | DELETENAMESPACEMF.IN |
Input Message Parsing | Message domain | XMLNSC | |
Validation | Validate | Content and Value | |
Compute | Validation | Validate | Inherit |
MQOutput | Basic | Queue name |
DELETENAMESPACEMF.OUT |
CREATE COMPUTE MODULE DELETENAMESPACEMF_Compute CREATE FUNCTION Main() RETURNS BOOLEAN BEGIN DECLARE SourceNamespace NAMESPACE 'http://www.samplemessage.broker.hursley.ibm.com'; DECLARE TargetNamespace NAMESPACE ''; CALL CopyMessageHeaders(); DECLARE oldNamespace CHARACTER ''; DECLARE newNamespace CHARACTER ''; SET oldNamespace = SourceNamespace; SET newNamespace = TargetNamespace; -- The target namespace can be specified dynamically in the MQRFH2 header. -- The following logic checks whether the MQRFH2 contains this info; if it does not, -- defaults are supplied in the message flow. IF InputRoot.MQRFH2.usr.SourceNamespace IS NOT NULL THEN IF InputRoot.MQRFH2.usr.SourceNamespace = 'NONAMESPACE' THEN SET oldNamespace = ''; ELSE SET oldNamespace = InputRoot.MQRFH2.usr.SourceNamespace; END IF; ELSE SET oldNamespace = SourceNamespace; END IF; -- Make the output tree the same as the input tree. -- We will then walk the tree changing things as we go SET OutputRoot.XMLNSC = InputBody; DECLARE rootNode REFERENCE TO OutputRoot.XMLNSC; CALL ChangeNamespaceInOutputRoot (rootNode, oldNamespace, newNamespace); RETURN TRUE; END; CREATE PROCEDURE CopyMessageHeaders() BEGIN DECLARE I INTEGER 1; DECLARE J INTEGER; SET J = CARDINALITY(InputRoot.*[]); WHILE I < J DO SET OutputRoot.*[I] = InputRoot.*[I]; SET I = I + 1; END WHILE; END; CREATE PROCEDURE CopyEntireMessage() BEGIN SET OutputRoot = InputRoot; END; END MODULE;