All Downloads are FREE. Search and download functionalities are using the official Maven repository.

io.hekate.network.NetworkService Maven / Gradle / Ivy

There is a newer version: 4.1.3
Show newest version
/*
 * Copyright 2020 The Hekate Project
 *
 * The Hekate Project licenses this file to you under the Apache License,
 * version 2.0 (the "License"); you may not use this file except in compliance
 * with the License. You may obtain a copy of the License at:
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
 * License for the specific language governing permissions and limitations
 * under the License.
 */

package io.hekate.network;

import io.hekate.codec.Codec;
import io.hekate.codec.CodecFactory;
import io.hekate.core.Hekate;
import io.hekate.core.HekateBootstrap;
import io.hekate.core.service.DefaultServiceFactory;
import io.hekate.core.service.Service;
import java.net.InetSocketAddress;
import java.util.List;

/**
 * « start hereEntry point to TCP-based client/server communication API.
 *
 * 

Overview

*

* {@link NetworkService} provides an abstraction layer on top of sockets API for building connection-oriented communication protocols. *

* * * * *

Service Configuration

*

* {@link NetworkService} can be configured and registered within the {@link HekateBootstrap} via the {@link NetworkServiceFactory} class * as in the example below: *

* *
* *
* ${source: network/NetworkServiceJavadocTest.java#config} *
*
* Note: This example requires Spring Framework integration * (see HekateSpringBootstrap). * ${source: network/service-xsd.xml#example} *
*
* Note: This example requires Spring Framework integration * (see HekateSpringBootstrap). * ${source: network/service-bean.xml#example} *
*
* *

* Please see the documentation of {@link NetworkServiceFactory} class for more details about the available configuration options. *

* * *

Connectors

*

* Communication units in the {@link NetworkService} are represented by the {@link NetworkConnector} interface. This interface provides API * for creating client connections based on the connector options as well as accepting connections from remote clients (optional). *

* *

* The client side of a connector API is represented by the {@link NetworkClient} interface. Each client manages a single socket * connection and provides API for connecting to remote endpoints and sending/receiving messages to/from them. Instances if this interface * can be be obtained from {@link NetworkConnector} as illustrated in the example below. *

* *

* The server side of a connector API is represented by the {@link NetworkServerHandler} interface. This interface provides callback * methods that get notified upon various events of remote clients (connects, disconnects, new messages, etc). Instances of this * interface can be registered via {@link NetworkConnectorConfig#setServerHandler(NetworkServerHandler)} method as illustrated in the * example below. *

* *

* Note: {@link NetworkServerHandler} is optional and if not specified for particular {@link NetworkConnector} then such connector * will act in a pure client mode and will not be able to accept connections from remote addresses. *

* * *

Connectors Configuration

*

* {@link NetworkConnector} configuration is represented by the {@link NetworkConnectorConfig} class. Please see its documentation for the * complete list of all available configuration options. *

* *

* Instances of this class can be registered within the {@link NetworkService} via {@link NetworkServiceFactory#setConnectors(List)} * method. *

* * *

Protocol Identifier

*

* Each connector must have a protocol identifier. This identifier is used by the {@link NetworkService} to select which {@link * NetworkConnector} should be responsible for processing each particular connection from a remote {@link NetworkClient}. When {@link * NetworkClient} established a new connection to a remote {@link NetworkService} it submits its protocol identifier as part of an initial * handshake message. This identifier is used by the remote {@link NetworkService} to select a {@link NetworkConnector} instance that is * configured with exactly the same protocol identifier. If such instance can be found then all subsequent communication events will be * handled by its {@link NetworkServerHandler}. If such instance can't be found then connection will be rejected. *

* * *

SSL Encryption

*

* It is possible to configure {@link NetworkService} to use secure communications by setting {@link * NetworkServiceFactory#setSsl(NetworkSslConfig) SSL configuration}. Please see the documentation of the {@link NetworkSslConfig} * class for available configuration options. *

* *

* Note that SSL encryption will be applied to all network communications at the cluster node level, thus it is important to make sure that * all nodes in the cluster are configured to use SSL encryption. Mixed mode, when some nodes do use SSL and some do not use it, is not * supported. In such case non-SSL nodes will not be able to connect to SSL-enabled nodes and vice versa. *

* *

* Protocol identifier must be specified within the {@link NetworkConnector} configuration via {@link * NetworkConnectorConfig#setProtocol(String)} method. *

* * *

Data Serialization

*

* Data serialization and deserialization within connectors is handled by the {@link Codec} interface. Instances of this interface can * be specified for each connector independently via {@link NetworkConnectorConfig#setMessageCodec(CodecFactory)} method. If not * specified the the default general purpose codec of a {@link Hekate} instance will be used (see {@link * HekateBootstrap#setDefaultCodec(CodecFactory)}). *

* *

* Please see the documentation of {@link Codec} interface for more details about data serialization. *

* * *

Thread Management

*

* {@link NetworkService} manages a core NIO thread pool of {@link NetworkServiceFactory#setNioThreads(int)} size. This thread pools * is used to process all incoming and outgoing connections by default. *

* *

* It is also possible to configure each {@link NetworkConnector} to use its own thread pool via {@link * NetworkConnectorConfig#setNioThreads(int)} option. In such case all incoming and outgoing connections of that connector will be * handled by a dedicated thread pool of the specified size and will not interfere with {@link NetworkService}'s core thread nor with * thread pool of any other connector. *

* *

* Whenever a new connection is created by the connector (either {@link NetworkClient client connection} or {@link * NetworkServerHandler#onConnect(Object, NetworkEndpoint)} server connection}) it obtains a worker thread from the {@link * NetworkConnector}'s thread pool and uses this thread to process all of the NIO events. Due to the event-based nature of NIO each thread * can handle multiple connections and doesn't require a one-to-one relationship between the pool size and the amount of active * connections. Typically thread pool size must be much less than the number of active connections. When connection gets closed it * unregisters itself from its worker thread. *

* * *

Example

*

* The code example below shows how {@link NetworkService} can be used to implement client/server communications. For the sake of brevity * this example uses the default Java serialization and messages of {@link String} type. For real world applications it is recommended to * implement custom message classes and provide a more optimized implementation of {@link Codec} in order to increase communication * speed and to support a more complex application logic. *

* * *

Server Example

*

* 1) Prepare server handler. * ${source: network/NetworkServiceJavadocTest.java#server_handler_example} *

* * *

* 2) Prepare connector configuration. * ${source: network/NetworkServiceJavadocTest.java#server_handler_config_example} *

* *

* 3) Start new node. * ${source: network/NetworkServiceJavadocTest.java#server_example} *

* * *

Client Example

*

* Note: This example uses the same connector configuration as in the server example. *

* *

* 1) Instantiate a new client and connect to the server. * ${source: network/NetworkServiceJavadocTest.java#client_connect_example} *

* *

* 2) Start sending messages (can be done even if connection establishment is still in progress). * ${source: network/NetworkServiceJavadocTest.java#client_send_example} *

* * @see NetworkServiceFactory */ @DefaultServiceFactory(NetworkServiceFactory.class) public interface NetworkService extends Service { /** * Returns a connector instance for the specified {@link NetworkConnectorConfig#setProtocol(String) protocol name}. * *

* Please see the overview section of this class for more details about connectors. *

* * @param protocol Protocol name (see {@link NetworkConnectorConfig#setProtocol(String)}). * @param Base type of connector protocol messages. * * @return TCP connector instance. * * @throws IllegalArgumentException If there is no such connector with the specified protocol name. */ NetworkConnector connector(String protocol) throws IllegalArgumentException; /** * Returns {@code true} if this service has a connector with the specified protocol name. * * @param protocol Protocol name (see {@link NetworkConnectorConfig#setProtocol(String)}). * * @return {@code true} if connector exists. */ boolean hasConnector(String protocol); /** * Asynchronously checks if connection can be established with a {@link NetworkService} at the specified address and notifies the * provided callback on operation result. * *

* Example: * ${source: network/NetworkServiceJavadocTest.java#ping} *

* * @param address Address. * @param callback Callback to be notified. * * @see NetworkPingResult */ void ping(InetSocketAddress address, NetworkPingCallback callback); }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy