<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<xsd:schema xmlns="http://www.mulesource.org/schema/mule/tcp/2.0"
            xmlns:xsd="http://www.w3.org/2001/XMLSchema"
            xmlns:mule="http://www.mulesource.org/schema/mule/core/2.0"
            targetNamespace="http://www.mulesource.org/schema/mule/tcp/2.0"
            elementFormDefault="qualified"
            attributeFormDefault="unqualified">

    <xsd:import namespace="http://www.w3.org/XML/1998/namespace"/>
    <xsd:import namespace="http://www.mulesource.org/schema/mule/core/2.0"
                schemaLocation="http://www.mulesource.org/schema/mule/core/2.0/mule.xsd" />

    <xsd:element name="connector" type="tcpConnectorType" substitutionGroup="mule:abstract-connector">
        <xsd:annotation>
            <xsd:documentation>
                Connect Mule to a TCP socket, to send or receive data via the network.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:complexType name="noProtocolTcpConnectorType">
        <xsd:complexContent>
            <xsd:extension base="mule:connectorType">
                <xsd:attribute name="sendBufferSize" type="mule:substitutableInt">
                    <xsd:annotation>
                        <xsd:documentation>
                            The size of the buffer (in bytes) used when sending data, set on the socket itself.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="receiveBufferSize" type="mule:substitutableInt">
                    <xsd:annotation>
                        <xsd:documentation>
                            The size of the buffer (in bytes) used when receiving data, set on the socket itself.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="receiveBacklog" type="mule:substitutableInt">
                    <xsd:annotation>
                        <xsd:documentation>
                            The maximum queue length for incoming connections.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="sendTcpNoDelay" type="mule:substitutableBoolean">
                    <xsd:annotation>
                        <xsd:documentation>
                            If set, transmitted data are not collected together for greater efficiency, but sent
                            immediately.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="reuseAddress" type="mule:substitutableBoolean">
                    <xsd:annotation>
                        <xsd:documentation>
                            If set (the default) then SO_REUSEADDRESS is set on server sockets before
                            binding.  This helps reduce "address already in use" errors when a socket
                            is re-used.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="clientSoTimeout" type="mule:substitutableInt">
                    <xsd:annotation>
                        <xsd:documentation>
                            This sets the socket's SO_TIMEOUT value when the socket is used as a client. Reading from
                            the socket will block for up to this long (in milliseconds) before the read fails.  A value
                            of 0 (the default) causes the read to wait indefinitely (if no data arrive).
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="serverSoTimeout" type="mule:substitutableInt">
                    <xsd:annotation>
                        <xsd:documentation>
                            This sets the socket's SO_TIMEOUT value when the socket is used as a server. Reading from
                            the socket will block for up to this long (in milliseconds) before the read fails.  A value
                            of 0 (the default) causes the read to wait indefinitely (if no data arrive).
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="socketSoLinger" type="mule:substitutableInt">
                    <xsd:annotation>
                        <xsd:documentation>
                            This sets the socket's SO_LINGER value.  This is related to how long (in milliseconds) the
                            socket will take to close so that any remaining data are transmitted correctly.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="keepSendSocketOpen" type="mule:substitutableBoolean">
                    <xsd:annotation>
                        <xsd:documentation>
                            If set, the socket is not closed after sending a message.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="keepAlive" type="mule:substitutableBoolean">
                    <xsd:annotation>
                        <xsd:documentation>
                            Enables SO_KEEPALIVE behaviour on open sockets. This automatically checks socket connections
                            which are open but unused for long periods and closes them if the connection becomes
                            unavailable.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
                <xsd:attribute name="validateConnections" type="mule:substitutableBoolean">
                    <xsd:annotation>
                        <xsd:documentation>
                            This "blips" the socket, opening and closing it to validate the connection, when first
                            accessed.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:complexType name="tcpConnectorType">
        <xsd:complexContent>
            <xsd:extension base="noProtocolTcpConnectorType">
                <xsd:sequence>
                    <xsd:element ref="abstract-protocol" minOccurs="0">
                        <xsd:annotation>
                            <xsd:documentation>
                                The class name for the protocol handler. This controls how the raw data stream is converted
                                into messages. By default messages are constructed as dara are received, with no correction
                                for multiple packets or fragmentation. You nearly always want to change this (or use a
                                transport that includes a protocol, like HTTP).
                            </xsd:documentation>
                        </xsd:annotation>
                    </xsd:element>
                </xsd:sequence>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:element name="abstract-protocol" abstract="true" type="abstractProtocolType"/>
    <xsd:complexType name="abstractProtocolType"/>

    <xsd:element name="streaming-protocol" type="abstractProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet,
                so if we want to transmit entire Mule messages reliably we must specify an additional protocol.
                However, this is not an issue with streaming, so this is an alias for the "direct" (null) protocol.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:element name="xml-protocol" type="abstractProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet,
                so if we want to transmit entire Mule messages reliably we must specify an additional protocol.
                This protocol uses XML syntax to isolate messages from the stream of bytes received, so it
                will only work with well-formed XML.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:element name="xml-eof-protocol" type="abstractProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet,
                so if we want to transmit entire Mule messages reliably we must specify an additional protocol.
                This protocol is similar to "xml-protocol", but will also use socket closure to terminate
                a message (even if the XML is not well-formed).
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:element name="eof-protocol" type="byteOrMessageProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet,
                so if we want to transmit entire Mule messages reliably we must specify an additional protocol.
                This protocol simply accumulates all data until the socket closes and places it in a single
                message.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:element name="direct-protocol" type="byteOrMessageProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet.
                Using this "null" protocol does not change the normal TCP behaviour, so message fragmentation
                may occur
                (ie a single sent message may be received in several pieces, each as a separate received message).
                This was the default behaviour in Mule 1.x - normally it is not a good choice for messaging
                within Mule, but it may be necessary to interface with external TCP-based protocols.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:complexType name="byteOrMessageProtocolType">
        <xsd:complexContent>
            <xsd:extension base="abstractProtocolType">
                <xsd:attribute name="payloadOnly" type="mule:substitutableBoolean" use="required">
                    <xsd:annotation>
                        <xsd:documentation>
                            Do not send the entire mule message object (including properties etc),
                            just the payload (contents)?  This defaults to true when the protocol
                            is not specified explicitly (when the safe protocol is used).
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:element name="safe-protocol" type="lengthProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet,
                so if we want to transmit entire Mule messages reliably we must specify an additional protocol.
                This protocol is similar to "length-protocol", but also includes a prefix.
                Verification of the prefix allows mis-matched protocols to be detected and avoids interpreting
                "random" data as a message length (which may give out of memory errors).
                This is the default protocol in Mule 2.x.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:element name="length-protocol" type="lengthProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet,
                so if we want to transmit entire Mule messages reliably we must specify an additional protocol.
                This protocol precedes each message with the number of bytes sent so that an entire message
                can be constructed on the received.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>

    <xsd:complexType name="lengthProtocolType">
        <xsd:complexContent>
            <xsd:extension base="byteOrMessageProtocolType">
                <xsd:attribute name="maxMessageLength" type="mule:substitutableInt">
                    <xsd:annotation>
                        <xsd:documentation>
                            An optional maximum length for the number of bytes in a single message.
                            Messages larger than this will trigger an error in the receiver, but
                            give an assurance that no out-of-memory error will occur.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:element name="custom-protocol" type="customProtocolType" substitutionGroup="abstract-protocol">
        <xsd:annotation>
            <xsd:documentation>
                TCP does not guarantee that a data written to a socket are transmitted in a single packet,
                so if we want to transmit entire Mule messages reliably we must specify an additional protocol.
                The user may supply their own protocol implementation via this element.
            </xsd:documentation>
        </xsd:annotation>
    </xsd:element>
    <xsd:complexType name="customProtocolType">
        <xsd:complexContent>
            <xsd:extension base="abstractProtocolType">
                <xsd:attribute name="class" type="mule:substitutableClass" use="required">
                    <xsd:annotation>
                        <xsd:documentation>
                            A class that implements the TcpProtocol interface.
                        </xsd:documentation>
                    </xsd:annotation>
                </xsd:attribute>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:element name="inbound-endpoint" type="inboundEndpointType" substitutionGroup="mule:abstract-inbound-endpoint"/>
    <xsd:complexType name="inboundEndpointType">
        <xsd:complexContent>
            <xsd:extension base="mule:inboundEndpointType">
                <xsd:attributeGroup ref="addressAttributes"/>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:element name="outbound-endpoint" type="outboundEndpointType" substitutionGroup="mule:abstract-outbound-endpoint"/>
    <xsd:complexType name="outboundEndpointType">
        <xsd:complexContent>
            <xsd:extension base="mule:outboundEndpointType">
                <xsd:attributeGroup ref="addressAttributes"/>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:element name="endpoint" type="globalEndpointType" substitutionGroup="mule:abstract-global-endpoint"/>
    <xsd:complexType name="globalEndpointType">
        <xsd:complexContent>
            <xsd:extension base="mule:globalEndpointType">
                <xsd:attributeGroup ref="addressAttributes"/>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>

    <xsd:attributeGroup name="addressAttributes">
        <xsd:attribute name="host" type="xsd:string"/>
        <xsd:attribute name="port" type="mule:substitutablePortNumber"/>
    </xsd:attributeGroup>

</xsd:schema>
