예제 #1
0
        private SIF_Ack ProcessPush(SifMessagePayload parsed)
        {
            try {
                //  Dispatch. When the result is an Integer it is an ack code to
                //  return; otherwise it is ack data to return and the code is assumed
                //  to be 1 for an immediate acknowledgement.
                int ackStatus = this.Zone.Dispatcher.dispatch(parsed);

                //  Ask the original message to generate a SIF_Ack for itself
                return(parsed.ackStatus(ackStatus));
            }
            catch (SifException se) {
                return
                    (parsed.AckError(se));
            }
            catch (AdkException adke) {
                return
                    (parsed.AckError
                         (SifErrorCategoryCode.Generic, SifErrorCodes.GENERIC_GENERIC_ERROR_1,
                         adke.Message));
            }
            catch (Exception thr) {
                if ((Adk.Debug & AdkDebugFlags.Messaging) != 0)
                {
                    this.Zone.Log.Debug("Uncaught exception dispatching push message: " + thr);
                }

                return
                    (parsed.AckError
                         (SifErrorCategoryCode.Generic, SifErrorCodes.GENERIC_GENERIC_ERROR_1,
                         "An unexpected error has occurred", thr.ToString()));
            }
        }
예제 #2
0
        private void assertNormalHandling(ErrorMessageHandler handler, SifMessagePayload payload, ZoneImpl zone)
        {
            MessageDispatcher testDispatcher = new MessageDispatcher(zone);
            int result = testDispatcher.dispatch(payload);

            Assert.IsTrue(handler.wasCalled(), "Handler was not called");
            Assert.AreEqual(1, result, "Result code should always be 1 because this version does not support SMB");
        }
예제 #3
0
 public override void ApplyOutboundPolicy(SifMessagePayload msg, IZone zone )
 {
     SifMessageType pload = Adk.Dtd.GetElementType(msg.ElementDef.Name);
     switch( pload ){
     case SifMessageType.SIF_Request:
         SetRequestPolicy((SIF_Request)msg, zone );
         break;
     }
 }
예제 #4
0
	public override void ApplyOutboundPolicy(SifMessagePayload msg, IZone zone ) {
		
		SifMessageType pload = Adk.Dtd.GetElementType(msg.ElementDef.Name);
		switch( pload ){
            case SifMessageType.SIF_Request:
			    SetRequestPolicy((SIF_Request)msg, zone );
		        break;
		}
		
	}
예제 #5
0
 public static void WriteObject(SifVersion writeVersion, string fileName, SifMessagePayload smp)
 {
     using (FileStream outputStream = new FileStream(fileName, FileMode.Create))
     {
         SifWriter writer = new SifWriter(outputStream);
         smp.SetChanged(true);
         smp.SifVersion = writeVersion;
         writer.Write(smp);
         writer.Flush();
         writer.Close();
         outputStream.Close();
     }
 }
예제 #6
0
        private void assertMessagesInVersion(SifVersion version, String[] expectedMessages)
        {
            Zone.Connect(ProvisioningFlags.Register);
            InMemoryProtocolHandler handler = (InMemoryProtocolHandler)Zone.ProtocolHandler;

            for (int a = 0; a < expectedMessages.Length; a++)
            {
                SifMessagePayload smp = (SifMessagePayload)handler.readMsg();
                Assert.AreEqual(expectedMessages[a], smp.Tag, "Should be a " + expectedMessages[a]);
                Assert.AreEqual(version, smp.SifVersion, "Version should be " + version);
            }

            Assert.IsNull(handler.readMsg(), " Should have no more messages ");
        }
예제 #7
0
        public bool Validate(SifElement se, SifVersion testedVerson)
        {
            // Before we can validate with the schema, we need to ensure that the
            // data object is wrapped in a SIF_Message elements, because the SIF
            // Schema makes that assumption
            SifMessagePayload smp = MakeSIFMessagePayload(se);

            String tmpFileName = se.ElementDef.Name + ".SchemaValidator."
                                 + testedVerson.ToString() + ".adk";

            // 2) Write the message out to a file
            WriteObject(testedVerson, tmpFileName, smp);

            return(Validate(tmpFileName));
        }
예제 #8
0
 private void AssertRetryHandling(ErrorMessageHandler handler, SifMessagePayload payload, ZoneImpl zone)
 {
     try
     {
         assertNormalHandling(handler, payload, zone);
     }
     catch (SifException ex)
     {
         Assert.IsTrue(handler.wasCalled(), "Handler was not called");
         Assert.AreEqual(SifErrorCategoryCode.Transport, ex.ErrorCategory,
                         "SIF Error category should be 10: " + ex.Message);
     }
     Assert.IsTrue(handler.wasCalled(), "Handler was not called");
     AssertThreadIsOK();
 }
 ///<summary> Pop off the message that was written to the queue.  Returns null if there 
 /// were no messages written.</summary>
 public SifMessagePayload readMsg()
 {
     lock ( this )
     {
         if ( fMessages.Count < 1 )
         {
             return null;
         }
         else
         {
             SifMessagePayload smp = fMessages[0];
             fMessages.RemoveAt( 0 );
             return smp;
         }
     }
 }
예제 #10
0
 public bool OnDispatchError(SifMessagePayload message, IZone zone, IMessageInfo info)
 {
     try
     {
         doBehavior(zone);
     }
     catch (SifException sifex)
     {
         throw sifex;
     }
     catch (AdkException adke)
     {
         throw new SifException(0, 0, "This shouldn't happen", zone, adke);
     }
     return(false);
 }
예제 #11
0
        private void AssertExceptionHandling(ErrorMessageHandler handler, SifMessagePayload payload, ZoneImpl zone,
                                             Type expectedExceptionType)
        {
            Exception exc = null;

            try
            {
                assertNormalHandling(handler, payload, zone);
            }
            catch (Exception ex)
            {
                exc = ex;
                Assert.IsTrue(handler.wasCalled(), "Handler was not called");

                AdkMessagingException adkme = ex as AdkMessagingException;
                Assert.IsNotNull(adkme,
                                 "Expected an ADKMessagingException, but was " + ex.GetType().Name + ":" + ex.ToString());

                Exception source  = adkme;
                Exception innerEx = null;
                while (source.InnerException != null)
                {
                    innerEx = source.InnerException;
                    source  = innerEx;
                }
                Assert.IsNotNull(innerEx, "AdkMessaginException was thrown but inner exception was not set");

                if (innerEx.GetType() != expectedExceptionType)
                {
                    Assert.Fail("Exception thrown was not a " + expectedExceptionType.Name + ", but was " +
                                innerEx.GetType().Name + ":" + innerEx.ToString());
                }
            }

            Assert.IsNotNull(exc, "An exception was not thrown by the handler");
            AssertThreadIsOK();
        }
        //public string Send(string msg)
        //{
        //   lock (this)
        //   {
        //      fMessages.AddLast(msg);
        //   }
        //   return makeAck();
        //}

        public IMessageInputStream Send( IMessageOutputStream msg )
        {
            lock ( this )
            {
                try
                {
                    MemoryStream stream = new MemoryStream();
                    msg.CopyTo( stream );
                    stream.Seek( 0, SeekOrigin.Begin );
                    SifParser parser = SifParser.NewInstance();
                    SifMessagePayload smp = (SifMessagePayload) parser.Parse( stream, fZone );

                    fMessages.Add( smp );
                    parser = null;

                    SIF_Ack ack = smp.ackStatus( 0 );
                    SIF_Header hdr = ack.Header;
                    hdr.SIF_Timestamp = DateTime.Now;
                    hdr.SIF_MsgId = Adk.MakeGuid();
                    hdr.SIF_SourceId = fZone.Agent.Id;

                    StringWriter str = new StringWriter();
                    SifWriter writer = new SifWriter( str );
                    writer.Write( ack );
                    writer.Flush();
                    writer.Close();
                    writer = null;
                    return new MessageStreamImpl( str.ToString() );
                }
                catch( Exception ex )
                {
                    // Possible error parsing. Write the message to console out
                    Console.Out.WriteLine(msg.Decode());
                    throw new AdkMessagingException(ex.Message, fZone, ex);
                }
            }
        }
예제 #13
0
 /// <summary>
 /// Applies ADK policy to the outbound message
 /// </summary>
 /// <param name="payload">The message being sent from the ADK</param>
 /// <param name="zone">The zone that the message is being sent to</param>
 public abstract void ApplyOutboundPolicy(SifMessagePayload payload, IZone zone);
예제 #14
0
        /// <summary>  Dispatch a message.
        /// 
        /// </summary>
        /// <param name="msg">The infrastructure message to dispatch
        /// </param>
        public virtual int dispatch(SifMessagePayload msg)
        {
            string errTyp = null;
            int status = 1;

            try
            {
                SifMessageType pload =
                    (SifMessageType)Adk.Dtd.GetElementType(msg.ElementDef.Name);

                if (pload == SifMessageType.SIF_SystemControl)
                {
                    IList<SifElement> ch =
                        ((SIF_SystemControl)msg).SIF_SystemControlData.GetChildList();

                    if (ch != null && ch.Count > 0)
                    {
                        if (ch[0].ElementDef == InfraDTD.SIF_SLEEP)
                        {
                            fZone.ExecSleep();
                        }
                        else if (ch[0].ElementDef == InfraDTD.SIF_WAKEUP)
                        {
                            fZone.ExecWakeup();
                        }
                        else if (ch[0].ElementDef == InfraDTD.SIF_PING)
                        {
                            //	Notify MessagingListeners...
                            SifMessageInfo msginfo = new SifMessageInfo(msg, fZone);
                            NotifyMessagingListeners_OnMessageProcessed
                                (SifMessageType.SIF_SystemControl, msginfo);

                            if (fZone.IsSleeping(AdkQueueLocation.QUEUE_LOCAL))
                            {
                                return 8;
                            }

                            return 1;
                        }
                        else
                        {
                            fZone.Log.Warn("Received unknown SIF_SystemControlData: " + ch[0].Tag);

                            throw new SifException
                                (SifErrorCategoryCode.Xml,
                                  SifErrorCodes.XML_MISSING_MANDATORY_ELEMENT_6,
                                  "SIF_SystemControlData must contain SIF_Ping, SIF_Wakeup, or SIF_Sleep",
                                  fZone);
                        }

                        //	Notify MessagingListeners...
                        SifMessageInfo msginfo2 = new SifMessageInfo(msg, fZone);
                        NotifyMessagingListeners_OnMessageProcessed
                            (SifMessageType.SIF_SystemControl, msginfo2);
                    }

                    return status;
                }

                //  If zone is asleep, return status code
                if (fZone.IsSleeping(AdkQueueLocation.QUEUE_LOCAL))
                {
                    return 8;
                }

                //  Some agents don't want to receive messages - for example, the
                //  SIFSend Adk Example agent. This is very rare but we offer a property
                //  to allow for it
                if (fZone.Properties.DisableMessageDispatcher)
                {
                    return status;
                }

                switch (pload)
                {
                    case SifMessageType.SIF_Event:
                        errTyp = "Subscriber.onEvent";
                        status = dispatchEvent((SIF_Event)msg);
                        break;

                    case SifMessageType.SIF_Request:
                        errTyp = "Publisher.onRequest";
                        dispatchRequest((SIF_Request)msg);
                        break;

                    case SifMessageType.SIF_Response:
                        errTyp = "QueryResults";
                        dispatchResponse((SIF_Response)msg);
                        break;

                    default:
                        fZone.Log.Warn
                            ("Agent does not know how to dispatch " + msg.ElementDef.Name +
                              " messages");
                        throw new SifException
                            (SifErrorCategoryCode.Generic,
                              SifErrorCodes.GENERIC_MESSAGE_NOT_SUPPORTED_2, "Message not supported",
                              msg.ElementDef.Name, fZone);
                }
            }
            catch (LifecycleException)
            {
                throw;
            }
            catch (SifException se)
            {
                //	Check if AdkException.setRetry() was called; use transport
                //	error category to force ZIS to resend message
                if (se.Retry)
                {
                    se.ErrorCategory = SifErrorCategoryCode.Transport;
                    se.ErrorCode = SifErrorCodes.WIRE_GENERIC_ERROR_1;
                }

                logAndRethrow("SIFException in " + errTyp + " message handler for " + msg.ElementDef.Name, se);
            }
            catch (AdkZoneNotConnectedException adkznce)
            {
                // Received a message while the zone was disconnected. Return a system transport
                // error so that the message is not removed from the queue
                SifException sifEx = new SifException(
                        SifErrorCategoryCode.Transport,
                        SifErrorCodes.WIRE_GENERIC_ERROR_1,
                        adkznce.Message, fZone);
                logAndRethrow("Message received while zone is not connected", sifEx);
            }

            catch (AdkException adke)
            {
                //	Check if ADKException.setRetry() was called; use transport
                //	error category to force ZIS to resent message
                if (adke.Retry)
                {
                    logAndThrowRetry(adke.Message, adke);
                }
                logAndThrowSIFException("ADKException in " + errTyp + " message handler for " + msg.ElementDef.Name, adke);
            }
            catch (Exception uncaught)
            {
                logAndThrowSIFException("Uncaught exception in " + errTyp + " message handler for " + msg.ElementDef.Name, uncaught);
            }

            return status;
        }
예제 #15
0
        /**
	 * Sends a SIF_Ack in response to a pulled message
	 * @param sifGetMessageAck The original SIF_Ack from the SIF_GetMessage. This is sometimes null, when
	 * 						parsing fails
	 * @param pulledMEssage The message delivered inside of the above ack. NOTE that even if parsing fails,
	 *          the SIFParser tries to return what it can, and will return this message payload (in getParsed()),
	 *          instead of the above container message.
	 * @param ackStatus The status to ack (NOTE: This is ignored if the err property is set)
	 * @param err The error to set in the SIF_Ack
	 */
	private void sendPushAck(SIF_Ack sifGetMessageAck,
			SifMessagePayload pulledMEssage, int ackStatus, SifException err) {
		try
		{
			SIF_Ack ack2 = null;
			if( fAckAckOnPull && sifGetMessageAck != null){
				ack2 = sifGetMessageAck.ackStatus( ackStatus );
			} else {
				ack2 = pulledMEssage.ackStatus(ackStatus);
			}


			//  If an error occurred processing the message, return
			//  the details in the SIF_Ack
			if( err != null )
			{
				fZone.Log.Debug( "Handling exception by creating a SIF_Error", err );

				SIF_Error newErr = new SIF_Error();
				newErr.SIF_Category =  (int)err.ErrorCategory;
				newErr.SIF_Code = err.ErrorCode;
				newErr.SIF_Desc = err.ErrorDesc;
				newErr.SIF_ExtendedDesc = err.ErrorExtDesc;
				ack2.SIF_Error = newErr;

				//  Get rid of the <SIF_Status>
				SIF_Status status = ack2.SIF_Status;
				if( status != null ) {
					ack2.RemoveChild( status );
				}
			}

			//  Send the ack
			send(ack2);
		}
		catch( Exception ackEx )
		{
			fZone.Log.Debug( "Failed to send acknowledgement to pulled message: " + ackEx, ackEx );
		}
	}
예제 #16
0
        /// <summary>
        /// Sends the message to the SIF Zone and returns the SIFAck that was received
        /// </summary>
        /// <param name="msg"></param>
        /// <param name="isPullMessage"></param>
        /// <returns></returns>
        public virtual SIF_Ack send(SifMessagePayload msg,
                                     bool isPullMessage)
        {
            if (fZone.ProtocolHandler == null)
            {
                throw new AdkTransportException("Zone is not connected", fZone);
            }

            try
            {
                PolicyManager policyMan = PolicyManager.GetInstance(fZone);
                if (policyMan != null)
                {
                    policyMan.ApplyOutboundPolicy(msg, fZone);
                }
            }
            catch (AdkException adkex)
            {
                throw new AdkMessagingException("Unable to apply outbound message policy: " + adkex, fZone, adkex);
            }

            SIF_Ack ack = null;
            SifWriter w = null;
            byte stage = 1;
            bool queued = false;
            SifMessageType pload = 0;
            bool cancelled = false;
            ICollection<IMessagingListener> msgList = null;

            try
            {
                //  Assign values to message header
                SIF_Header hdr = msg.Header;
                hdr.SIF_Timestamp = DateTime.Now;
                hdr.SIF_MsgId = SifFormatter.GuidToSifRefID(Guid.NewGuid());
                hdr.SIF_SourceId = fSourceId;
                hdr.SIF_Security = secureChannel();

                //	Adk 1.5+: SIF_LogEntry requires that we *duplicate* the
                //	header within the object payload. This is really the only
                //	place we can do that and ensure that the SIF_Header and
                //	the SIF_LogEntry/SIF_LogEntryHeader are identical.

                if (msg is SIF_Event)
                {
                    // TODO: Should this be done at a higher level, such as zone.ReportEvent()?
                    SIF_Event ev = ((SIF_Event)msg);
                    SIF_ObjectData od =
                        (SIF_ObjectData)ev.GetChild(InfraDTD.SIF_EVENT_SIF_OBJECTDATA);
                    SIF_EventObject eo = od == null ? null : od.SIF_EventObject;
                    if (eo != null)
                    {
                        SIF_LogEntry logentry = (SIF_LogEntry)eo.GetChild(InfraDTD.SIF_LOGENTRY);
                        if (logentry != null)
                        {
                            SIF_LogEntryHeader sleh = new SIF_LogEntryHeader();
                            sleh.SIF_Header = (SIF_Header)hdr.Clone();
                            logentry.SIF_LogEntryHeader = sleh;
                        }
                    }
                }

                if (!isPullMessage || (Adk.Debug & AdkDebugFlags.Messaging_Pull) != 0)
                {
                    msg.LogSend(fZone.Log);
                }
            }
            catch (Exception thr)
            {
                throw new AdkMessagingException
                    ("MessageDispatcher could not assign outgoing message header: " + thr,
                      fZone, thr);
            }

            try
            {
                //  Convert message to a stream
                using (MessageStreamImpl memBuf = new MessageStreamImpl())
                {
                    w = new SifWriter(memBuf.GetInputStream());
                    w.Write(msg);
                    w.Flush();

                    stage = 2;

                    //  SIF_Event and SIF_Response are posted to the agent local queue
                    //  if enabled, otherwise sent immediately. All other message types
                    //  are sent immediately even when the queue is enabled.
                    //
                    if (fQueue != null &&
                         (msg is SIF_Event ||
                          msg is SIF_Response))
                    {
                        fQueue.PostMessage(msg);
                        queued = true;
                    }

                    //	Notify MessagingListeners...
                    pload = (SifMessageType)Adk.Dtd.GetElementType(msg.ElementDef.Name);
                    if (pload != SifMessageType.SIF_Ack)
                    {
                        msgList = GetMessagingListeners(fZone);
                        if (msgList.Count > 0)
                        {
                            StringBuilder stringBuffer = new StringBuilder(memBuf.Decode());
                            SifMessageInfo msgInfo = new SifMessageInfo(msg, fZone);
                            foreach (IMessagingListener listener in msgList)
                            {
                                try
                                {
                                    if (!listener.OnSendingMessage(pload, msgInfo, stringBuffer)
                                        )
                                    {
                                        cancelled = true;
                                    }
                                }
                                catch { } // Do Nothing
                            }
                        }
                    }

                    if (!cancelled)
                    {
                        //  Send the message
                        IMessageInputStream ackStream = fZone.fProtocolHandler.Send(memBuf);
                        {
                            try
                            {
                                //  Parse the results into a SIF_Ack
                                ack =
                                    (SIF_Ack)
                                    fParser.Parse
                                        ( ackStream.GetInputStream(), fZone,
                                          isPullMessage
                                              ? SifParserFlags.ExpectInnerEnvelope
                                              : SifParserFlags.None );
                            }
                            catch (Exception parseEx)
                            {
                                if (isPullMessage && (parseEx is AdkParsingException || parseEx is SifException || parseEx is System.Xml.XmlException))
                                {
                                    String ackStr = ackStream.ToString();
                                    if ((Adk.Debug & AdkDebugFlags.Message_Content ) != 0)
                                    {
                                        fZone.Log.Info( ackStr );
                                    }
                                    // The SIFParse was unable to parse this message. Try to create an appropriate
                                    // SIF_Ack, if SIFMessageInfo is able to parse enough of the message
                                    throw new PullMessageParseException(parseEx, ackStr, fZone);

                                }

                                throw new AdkMessagingException(parseEx.Message, fZone);
                            }
                        }

                        if (ack != null)
                        {
                            ack.message = msg;
                            if (!isPullMessage || (Adk.Debug & AdkDebugFlags.Messaging_Pull) != 0)
                            {
                                ack.LogRecv(fZone.Log);
                            }
                        }

                        //	Notify MessagingListeners...
                        if (msgList != null && msgList.Count > 0)
                        {
                            SifMessageInfo msgInfo = new SifMessageInfo(msg, fZone);

                            foreach (IMessagingListener listener in msgList)
                            {
                                try
                                {
                                    listener.OnMessageSent(pload, msgInfo, ack);
                                }
                                catch { } // Do Nothing
                            }
                        }
                    }
                    else
                    {
                        //	Prepare a success SIF_Ack to return
                        ack = msg.AckImmediate();
                    }
                }
            }
            catch (AdkMessagingException)
            {
                throw;
            }
            catch (AdkTransportException)
            {
                throw;
            }
            catch (Exception thr)
            {
                if (stage == 1)
                {
                    throw new AdkMessagingException
                        (
                        "MessageDispatcher could not convert outgoing infrastructure message to a string: " +
                        thr, fZone);
                }
                if (stage == 2)
                {
                    throw new AdkMessagingException
                        (
                        "MessageDispatcher could not convert SIF_Ack response to an object: " + thr,
                        fZone);
                }
            }
            finally
            {
                //  Removed queued message from queue
                if (queued)
                {
                    try
                    {
                        fQueue.RemoveMessage(msg.MsgId);
                    }
                    catch
                    {
                        // Do nothing
                    }
                }
            }

            return ack;
        }
예제 #17
0
        public void testSchoolInfo010()
        {
            String schoolInfoResp = "	<SIF_Message  xmlns=\"http://www.sifinfo.org/infrastructure/1.x\" Version=\"1.5r1\">"
                                    + "	  <SIF_Response>"
                                    + "		<SIF_Header>"
                                    + "		  <SIF_MsgId>B329CA6E5BC342339F135880CEE0578E</SIF_MsgId>"
                                    + "		  <SIF_Date>20070813</SIF_Date>"
                                    + "		  <SIF_Time Zone=\"UTC-06:00\">13:55:57</SIF_Time>"
                                    + "		  <SIF_Security>"
                                    + "			<SIF_SecureChannel>"
                                    + "			  <SIF_AuthenticationLevel>0</SIF_AuthenticationLevel>"
                                    + "			  <SIF_EncryptionLevel>0</SIF_EncryptionLevel>"
                                    + "			</SIF_SecureChannel>"
                                    + "		  </SIF_Security>"
                                    + "		  <SIF_SourceId>SASIxp</SIF_SourceId>"
                                    + "		  <SIF_DestinationId>Destiny</SIF_DestinationId>"
                                    + "		</SIF_Header>"
                                    + "		<SIF_RequestMsgId>88BE30BA0B8746809598854A1F58C8CC</SIF_RequestMsgId>"
                                    + "		<SIF_PacketNumber>1</SIF_PacketNumber>"
                                    + "		<SIF_MorePackets>No</SIF_MorePackets>"
                                    + "		<SIF_ObjectData>"
                                    + "		 <SchoolInfo RefId=\"B3E73AC5E8C7392044015E25A454AC6F\">"
                                    + "			<LocalId>997</LocalId>"
                                    + "			<SchoolName>Junior High Demo</SchoolName>"
                                    + "			<PrincipalInfo>"
                                    + "			  <ContactName>Mrs. Pleasant</ContactName>"
                                    + "			</PrincipalInfo>\r\n"
                                    +
                                    /* " <PhoneNumber Format=\"NA\" Type=\"TE\">(949) 888-7655</PhoneNumber>" + */
                                    "			<PhoneNumber Format=\"NA\" Type=\"FE\">888-9877</PhoneNumber>\r\n"
                                    + "			<Address Type=\"SS\">"
                                    + "			  <Street>"
                                    + "				<Line1>Grand Avenue</Line1>"
                                    + "			  </Street>"
                                    + "			  <City>Plesantville</City>"
                                    + "			  <StatePr Code=\"CA\" />"
                                    + "			  <Country Code=\"US\" />"
                                    + "			  <PostalCode>12345</PostalCode>"
                                    + "			</Address>"
                                    + "			<IdentificationInfo Code=\"76\">997</IdentificationInfo>"
                                    + "		  </SchoolInfo>"
                                    + "		</SIF_ObjectData>"
                                    + "	  </SIF_Response>" + "	</SIF_Message>";

            SifParser         parser = SifParser.NewInstance();
            SifMessagePayload smi    = (SifMessagePayload)parser.Parse(
                schoolInfoResp, null);

            // Verify that it is parsing the correct version
            Assertion.AssertEquals("Version", SifVersion.SIF15r1, smi.SifVersion);
            Assertion.AssertEquals("Version attribute", "1.5r1", smi.VersionAttribute);

            SifDataObject sdo = (SifDataObject)((SIF_Response)smi)
                                .SIF_ObjectData.GetChildList()[0];

            // Now attempt an inbound mapping
            IDictionary      fields = new ListDictionary();
            StringMapAdaptor sma    = new StringMapAdaptor(fields);
            Mappings         m      = fCfg.Mappings.GetMappings("Default").Select("asdf", "SASIxp", smi.SifVersion);

            m.MapInbound(sdo, sma, smi.SifVersion);
            Assertion.Assert("Elements Mapped", fields.Count > 0);
            Assertion.AssertEquals("Phone Number", "888-9877", fields["FAX"]);
        }
예제 #18
0
        public void ProcessRequest(AdkHttpRequestContext context)
        {
            if ((Adk.Debug & AdkDebugFlags.Messaging) != 0)
            {
                Zone.Log.Debug
                    ("Received push message from " + context.Request.RemoteAddress + " (" +
                    context.Request.Url.Scheme + ")");
            }

            SIF_Ack           ack    = null;
            SifMessagePayload parsed = null;

            //Check request length and type
            if (!SifIOFormatter.IsValidContentLength(context.Request.ContentLength))
            {
                throw new AdkHttpException
                          (AdkHttpStatusCode.ClientError_400_Bad_Request,
                          "Content length Must be greater than zero");
            }

            if (!SifIOFormatter.IsValidContentMediaType(context.Request.ContentType))
            {
                throw new AdkHttpException(AdkHttpStatusCode.ClientError_415_Unsupported_Media_Type,
                                           "Content header does not support the specified media type: " + context.Request.ContentType);
            }

            //  Read raw content
            Stream        requestStream = context.Request.GetRequestStream();
            StringBuilder requestXml    = null;

            // If we need to convert the request stream to a string for either logging or messaging, do so
            if ((Adk.Debug & AdkDebugFlags.Message_Content) != 0)
            {
                requestXml = ConvertRequestToString(requestStream);
                Zone.Log.Debug
                    ("Received " + context.Request.ContentLength + " bytes:\r\n" +
                    requestXml.ToString());
            }

            TextReader requestReader = new StreamReader(requestStream, SifIOFormatter.ENCODING);

            Exception parseEx   = null;
            bool      reparse   = false;
            bool      cancelled = false;
            int       reparsed  = 0;

            do
            {
                try {
                    parseEx = null;

                    //  Parse content
                    parsed  = (SifMessagePayload)CreateParser().Parse(requestReader, Zone);
                    reparse = false;
                    parsed.LogRecv(Zone.Log);
                }
                catch (AdkParsingException adke) {
                    parseEx = adke;
                }
                catch (Exception ex) {
                    parseEx = ex;
                }

                //
                //	Notify listeners...
                //
                //	If we're asked to reparse the message, do so but do not notify
                //	listeners the second time around.
                //
                if (reparsed == 0)
                {
                    ICollection <IMessagingListener> msgList = MessageDispatcher.GetMessagingListeners(Zone);
                    if (msgList.Count > 0)
                    {
                        // Convert the stream to a string builder
                        if (requestXml == null)
                        {
                            requestXml = ConvertRequestToString(requestStream);
                        }

                        //	Determine message type before parsing
                        foreach (IMessagingListener listener in msgList)
                        {
                            try {
                                SifMessageType pload =
                                    Adk.Dtd.GetElementType(parsed.ElementDef.Name);
                                MessagingReturnCode code =
                                    listener.OnMessageReceived(pload, requestXml);
                                switch (code)
                                {
                                case MessagingReturnCode.Discard:
                                    cancelled = true;
                                    break;

                                case MessagingReturnCode.Reparse:
                                    requestReader = new StringReader(requestXml.ToString());
                                    reparse       = true;
                                    break;
                                }
                            }
                            catch (AdkException adke) {
                                parseEx = adke;
                            }
                        }
                    }
                }

                if (cancelled)
                {
                    return;
                }

                reparsed++;
            }while (reparse);

            if (parseEx != null)
            {
                //  TODO: Handle the case where SIF_OriginalSourceId and SIF_OriginalMsgId
                //  are not available because parsing failed. See SIFInfra
                //  Resolution #157.
                if (parseEx is SifException && parsed != null)
                {
                    //  Specific SIF error already provided to us by SIFParser
                    ack = parsed.AckError((SifException)parseEx);
                }
                else
                {
                    String errorMessage = null;
                    if (parseEx is AdkException)
                    {
                        errorMessage = parseEx.Message;
                    }
                    else
                    {
                        // Unchecked Throwable
                        errorMessage = "Could not parse message";
                    }

                    if (parsed == null)
                    {
                        SifException sifError = null;
                        if (parseEx is SifException)
                        {
                            sifError = (SifException)parseEx;
                        }
                        else
                        {
                            sifError = new SifException(
                                SifErrorCategoryCode.Xml,
                                SifErrorCodes.XML_GENERIC_ERROR_1,
                                "Could not parse message",
                                parseEx.ToString(),
                                this.Zone,
                                parseEx);
                        }
                        if (requestXml == null)
                        {
                            requestXml = ConvertRequestToString(requestStream);
                        }
                        ack = SIFPrimitives.ackError(
                            requestXml.ToString( ),
                            sifError,
                            this.Zone);
                    }
                    else
                    {
                        ack = parsed.AckError(
                            SifErrorCategoryCode.Generic,
                            SifErrorCodes.GENERIC_GENERIC_ERROR_1,
                            errorMessage,
                            parseEx.ToString());
                    }
                }

                if ((Adk.Debug & AdkDebugFlags.Messaging) != 0)
                {
                    Zone.Log.Warn
                        ("Failed to parse push message from zone \"" + Zone + "\": " + parseEx);
                }

                if (ack != null)
                {
                    //  Ack messages in the same version of SIF as the original message
                    if (parsed != null)
                    {
                        ack.SifVersion = parsed.SifVersion;
                    }
                    AckPush(ack, context.Response);
                }
                else
                {
                    //  If we couldn't build a SIF_Ack, returning an HTTP 500 is
                    //  probably the best we can do to let the server know that
                    //  we didn't get the message. Note this should cause the ZIS
                    //  to resend the message, which could result in a deadlock
                    //  condition. The administrator would need to manually remove
                    //  the offending message from the agent's queue.

                    if ((Adk.Debug & AdkDebugFlags.Messaging) != 0)
                    {
                        Zone.Log.Debug
                            ("Could not generate SIF_Ack for failed push message (returning HTTP/1.1 500)");
                    }
                    throw new AdkHttpException
                              (AdkHttpStatusCode.ServerError_500_Internal_Server_Error,
                              "Could not generate SIF_Ack for failed push message (returning HTTP/1.1 500)");
                }

                return;
            }

            //  Check SourceId to see if it matches this agent's SourceId
            String destId = parsed.DestinationId;

            if (destId != null && !destId.Equals(Zone.Agent.Id))
            {
                Zone.Log.Warn
                    ("Received push message for DestinationId \"" + destId +
                    "\", but agent is registered as \"" + Zone.Agent.Id + "\"");

                ack = parsed.AckError
                      (
                    SifErrorCategoryCode.Transport,
                    SifErrorCodes.WIRE_GENERIC_ERROR_1,
                    "Message not intended for this agent (SourceId of agent does not match DestinationId of message)",
                    "Message intended for \"" + destId + "\" but this agent is registered as \"" +
                    Zone.Agent.Id + "\"");

                AckPush(ack, context.Response);

                return;
            }

            //  Convert content to SIF message object and dispatch it
            ack = ProcessPush(parsed);

            //  Send SIF_Ack reply
            AckPush(ack, context.Response);
        }
예제 #19
0
 /// <summary>
 /// Applies ADK policy to the outbound message
 /// </summary>
 /// <param name="payload">The message being sent from the ADK</param>
 /// <param name="zone">The zone that the message is being sent to</param>
 public abstract void ApplyOutboundPolicy(SifMessagePayload payload, IZone zone);
예제 #20
0
        private bool RunSingleTest(
            SifVersion parseVersion,
            SifVersion writeVersion,
            string fileName,
            TextWriter output,
            SchemaValidator sv)
        {
            sv.Clear();

            if (VERBOSE)
            {
                output.Write("Running test on " + fileName + "\r\n");
            }

            // 1) Read the object into memory
            SifElement se = null;

            try
            {
                se = AdkObjectParseHelper.ParseFile(fileName, parseVersion);
            }
            catch (AdkException adke)
            {
                // Parsing failed. However, since this unit test is a complete
                // test of all available objects, just emit the problem and allow
                // the test to continue (with a notification of false)
                output
                .WriteLine("Error parsing file " + fileName + "\r\n  - "
                           + adke);
                output.WriteLine();
                return(false);
            }
            catch (Exception re)
            {
                output.WriteLine("Error parsing file " + fileName + "\r\n  - " + re);
                output.WriteLine();
                return(false);
            }

//            if (VERBOSE)
//            {
//                SifWriter writer = new SifWriter(output);
//                writer.Write(se,parseVersion);
//                output.Flush();
//            }

            // Before we can validate with the schema, we need to ensure that the
            // data object is wrapped in a SIF_Message elements, because the SIF
            // Schema makes that assumption
            SifMessagePayload smp = SchemaValidator.MakeSIFMessagePayload(se);

            String tmpFileName = fileName + "." + writeVersion.ToString() + ".adk";

            // 2) Write the message out to a file
            SchemaValidator.WriteObject(writeVersion, tmpFileName, smp);

            // 3) Validate the file
            bool validated = sv.Validate(tmpFileName);

            // 4) If validation failed, write the object out for tracing purposes
            if (!validated)
            {
                if (VERBOSE)
                {
                    SifWriter outWriter = new SifWriter(output);
                    outWriter.Write(se, writeVersion);
                    outWriter.Flush();
                }
                output.WriteLine("Errors reading/writing " + fileName);
                sv.PrintProblems(output);
                return(false);
            }

            // 5) Read the object again into memory
            try
            {
                se = AdkObjectParseHelper.ParseFile(fileName, parseVersion);
            }
            catch (AdkException adke)
            {
                // Parsing failed. However, since this unit test is a complete
                // test of all available objects, just emit the problem and allow
                // the test to continue (with a notification of false)
                output.WriteLine("Error parsing file " + fileName + ": "
                                 + adke.Message);
                return(false);
            }
            catch (Exception re)
            {
                output.Write("Error parsing file " + fileName + ": "
                             + re.Message + "\r\n");
                return(false);
            }

            return(validated);
        }
예제 #21
0
 /// <summary>  Sends a message.</summary>
 /// <remarks>
 /// <para>
 /// If the message is a SIF_Event or SIF_Response message it is persisted to
 /// the Agent Local Queue (if enabled) to ensure reliable delivery. The
 /// message is then sent. Upon successful delivery to the ZIS, the message
 /// is removed from the queue. For all other message types the message is
 /// sent immediately without being posted to the queue.</para>
 /// <para>
 /// If an exception occurs and a message has been persisted to the queue,
 /// it is removed from the queue if possible (the queue is operational) and
 /// the send operation fails.</para>
 /// </remarks>
 public virtual SIF_Ack send(SifMessagePayload msg)
 {
     return send(msg, false);
 }