public abstract class Protocol extends Object
A protocol is responsible for the transport of packets. This base class offers all necessary methods to handle the protocol options, and it declares several abstract protocol specific methods for handling protocol destinations like connecting or writing packets.
The following table lists the available protocols together with their identifier in the connections string and a short description.
| Protocol | Identifier | Description |
|---|---|---|
| FileProtocol | "file" | Used for writing log files in the standard SmartInspect binary log file format which can be loaded into the Console. |
| MemoryProtocol | "mem" | Used for writing log data to memory and saving it to a stream on request. |
| PipeProtocol | "pipe" | Used for sending log data over a named pipe directly to a local Console. |
| TcpProtocol | "tcp" | Used for sending packets over a TCP connection directly to the Console. |
| TextProtocol | "text" | Used for writing log files in a customizable text format. Best suited for end-user notification purposes. |
There are several options which are common to all protocols and beyond that each protocol has its own set of additional options. For those protocol specific options, please refer to the documentation of the corresponding protocol class. Protocol options can be set with Initialize and derived classes can query option values using the Get methods.
The public members of this class are threadsafe.
| Modifier and Type | Field and Description |
|---|---|
protected boolean |
fConnected |
| Constructor and Description |
|---|
Protocol()
Creates and initializes a Protocol subclass instance.
|
| Modifier and Type | Method and Description |
|---|---|
void |
addListener(ProtocolListener listener)
Adds a new listener for the events of this object.
|
protected void |
buildOptions(ConnectionsBuilder builder)
Fills a ConnectionsBuilder instance with the options currently
used by this protocol.
|
protected LogHeader |
composeLogHeaderPacket() |
void |
connect()
Connects to the protocol destination.
|
void |
disconnect()
Disconnects from the protocol destination.
|
void |
dispatch(ProtocolCommand command)
Dispatches a custom action to a concrete implementation of a protocol.
|
void |
dispose()
Disconnects from the protocol destination.
|
protected void |
doError(Exception ex)
Invokes the ProtocolListener.onError event handlers.
|
boolean |
failed()
Returns if the last executed connection-related operation of
this protocol has failed.
|
String |
getAppName()
Returns the application name of this protocol.
|
protected boolean |
getAsyncEnabledDefaultValue()
Defines the default value for `async.enabled` option as `false`.
|
protected int |
getAsyncQueueDefaultValue()
Defines the default value for `async.queue` option as 2 megabytes.
|
protected boolean |
getBooleanOption(String key,
boolean defaultValue)
A Boolean value will be treated as true if the value of the key matches either "true", "yes" or "1" and as false otherwise.
|
byte[] |
getBytesOption(String key,
int size,
byte[] defaultValue)
Gets the byte array value of a key.
|
String |
getCaption()
Returns the caption of this protocol.
|
String |
getHostName()
Returns the hostname of this protocol.
|
protected int |
getIntegerOption(String key,
int defaultValue)
Gets the integer value of a key.
|
protected Level |
getLevelOption(String key,
Level defaultValue)
This method returns the defaultValue argument if either the supplied key is unknown
or the found value is not a valid Level value.
|
protected abstract String |
getName()
Specifies the name of a real protocol implementation.
|
protected boolean |
getReconnectDefaultValue()
Defines the default value for `reconnect` option as `true`.
|
protected FileRotate |
getRotateOption(String key,
FileRotate defaultValue)
Gets a FileRotate value of a key.
|
protected long |
getSizeOption(String key,
long defaultValue)
Gets an integer value of a key.
|
protected String |
getStringOption(String key,
String defaultValue)
Gets the string of a key.
|
protected long |
getTimespanOption(String key,
long defaultValue)
Gets an integer value of a key.
|
protected void |
handleException(String message)
Handles a protocol exception.
|
void |
implConnect() |
void |
implDisconnect() |
void |
implDispatch(ProtocolCommand command) |
void |
implWritePacket(Packet packet) |
void |
initialize(String options)
Sets and initializes the options of this protocol.
|
protected abstract void |
internalConnect()
Connects to the protocol destination.
|
protected abstract void |
internalDisconnect()
Disconnects from the protocol destination.
|
protected void |
internalDispatch(ProtocolCommand command)
Executes a protocol specific custom action.
|
protected boolean |
internalReconnect()
Reconnects to the protocol specific destination.
|
protected void |
internalWriteLogHeader() |
protected abstract void |
internalWritePacket(Packet packet)
Writes a packet to the protocol destination.
|
boolean |
isAsynchronous()
Indicates if this protocol is operating in asynchronous protocol mode.
|
protected boolean |
isValidOption(String name)
Validates if an option is supported by this protocol.
|
protected void |
loadOptions()
Loads and inspects protocol specific options.
|
void |
removeListener(ProtocolListener listener)
Removes a new listener for the events of this object.
|
protected void |
reset()
Resets the protocol and brings it into a consistent state.
|
void |
scheduleWritePacket(Packet packet,
SchedulerQueue.QueueEnd insertTo) |
void |
setAppName(String appName)
Sets the application name of this protocol.
|
void |
setHostName(String hostName)
Sets the hostname of this protocol.
|
void |
writePacket(Packet packet)
Writes a packet to the protocol specific destination.
|
public Protocol()
protected void handleException(String message) throws ProtocolException
This method handles an occurred protocol exception. It first sets the Failed flag and creates a ProtocolException object with the name and options of this protocol. In normal blocking mode (see IsValidOption), it then throws this exception. When operating in asynchronous mode, it invokes the Error event handlers instead and does not throw an exception.
message - The exception messageProtocolException - Always in normal blocking mode, never in asynchronous modeprotected void buildOptions(ConnectionsBuilder builder)
The filled options string consists of key, value option pairs separated by commas.
This function takes care of the options common to all protocols. To include protocol specific options, override this function.
builder - The ConnectionsBuilder object to fill with the
current options of this protocolpublic void initialize(String options) throws SmartInspectException
This method expects an options string which consists of key, value pairs separated by commas like this: "filename=log.sil, append=true". To use a comma in a value, you can use quotation marks like in the following example: "filename=\"log.sil\", append=true".
Please note that a SmartInspectException exception is thrown if a wrong options string is assigned. A wrong options string could use an invalid syntax or contain one or more unknown option keys. This method can be called only once. Further calls have no effect. Pass null or an empty string to use the default options of a particular protocol.
options - The new protocol optionsSmartInspectException - If invalid options syntax, an unknown option keyprotected String getStringOption(String key, String defaultValue)
key - The key to search fordefaultValue - The value to return if the key does not exist. Note that this
method can throw an exception of type NullPointerException if you pass a null
reference as keyNullPointerException - If the key argument is nullprotected int getIntegerOption(String key, int defaultValue)
Please note that if a related value could be found but is not a valid integer, the supplied default value will be returned. Only non-negative integers will be recognized as valid values. Note that this method can throw an exception of type NullPointerException if you pass a null reference as key.
key - The key to search fordefaultValue - The value to return if the key does not existNullPointerException - If the key argument is nullprotected boolean getBooleanOption(String key, boolean defaultValue)
key - The key to search fordefaultValue - The value to return if the key does not existNullPointerException - If the key argument is nullprotected Level getLevelOption(String key, Level defaultValue)
key - The key whose value to returndefaultValue - The value to return if the given key is unknownNullPointerException - if the key argument is nullprotected long getSizeOption(String key, long defaultValue)
It is possible to specify a size unit at the end of the value. If a known unit is found, this function multiplies the resulting value with the corresponding factor. For example, if the value of the element is "1KB", the return value of this function would be 1024.
The following table lists the available units together with a short description and the corresponding factor:
| Unit Name | Description | Factor |
|---|---|---|
| KB | Kilo Byte | 1024 |
| MB | Mega Byte | (1024)^2 |
| GB | Giga Byte | (1024)^3 |
If no unit is specified, this function defaults to the KB unit.
Note: This method can throw a NullPointerException if you pass a null reference as key.
key - The key whose value to returndefaultValue - The value to return if the given key is unknownNullPointerException - if the key argument is nullprotected long getTimespanOption(String key, long defaultValue)
This method returns the defaultValue argument if either the supplied key is unknown or the found value is not a valid integer or ends with an unknown time span unit. It is possible to specify a time span unit at the end of the value. If a known unit is found, this function multiplies the resulting value with the corresponding factor. For example, if the value of the element is "1s", the return value of this function would be 1000. The following table lists the available units together with a short description and the corresponding factor.
| Unit Name | Description | Factor |
|---|---|---|
| s | Seconds | 1000 |
| m | Minutes | 60*s |
| h | Hours | 60*m |
| d | Days | 24*h |
If no unit is specified, this function defaults to the Seconds unit. Please note that the value is always returned in milliseconds.
key - The key whose value to returndefaultValue - The value to return if the given key is unknownNullPointerException - if The key argument is nullprotected FileRotate getRotateOption(String key, FileRotate defaultValue)
key - The key whose value to returndefaultValue - The value to return if the given key is unknownNullPointerException - if the key argument is nullpublic byte[] getBytesOption(String key, int size, byte[] defaultValue)
The returned byte array always has the desired length as specified by the size argument. If the element value does not have the required size after conversion, it is shortened or padded (with zeros) automatically. This method returns the defaultValue argument if either the supplied key is unknown or the found value does not have a valid format (e.g. invalid characters when using hexadecimal strings).
Note that this method can throw an exception of type NullPointerException if you pass a null reference as key.
key - The key whose value to returnsize - The desired size in bytes of the returned byte array. If
the element value does not have the expected size, it is
shortened or padded automaticallydefaultValue - The value to return if the given key is unknown or if the
found value has an invalid formatNullPointerException - if the key argument is nullprotected boolean isValidOption(String name)
The following table lists all valid options, their default values and descriptions common to all protocols. See below for explanations:
| Option Name | Default | Description |
|---|---|---|
| - | - | - |
| level | debug | Specifies the log level of this protocol. |
| reconnect | false | Specifies if a reconnect should be initiated when a connection gets dropped. |
| reconnect.interval | 0 | If reconnecting is enabled, specifies the minimum time in seconds between two successive reconnect attempts. If 0 is specified, a reconnect attempt is initiated for each packet if needed. It is possible to specify time span units like this: "1s". Supported units are "s" (seconds), "m" (minutes), "h" (hours) and "d" (days). |
| caption | [name] | Specifies the caption of this protocol as used by SmartInspect.Dispatch. By default, it is set to the protocol identifier (e.g., "file" or "mem"). |
| async.enabled | false | Specifies if this protocol should operate in asynchronous instead of the default blocking mode. |
| async.queue | 2048 | Specifies the maximum size of the asynchronous queue in kilobytes. It is possible to specify size units like this: "1 MB". Supported units are "KB", "MB" and "GB". |
| async.throttle | true | Specifies if the application should be automatically throttled in asynchronous mode when more data is logged than the queue can handle. |
| async.clearondisconnect | false | Specifies if the current content of the asynchronous queue should be discarded before disconnecting. Useful if an application must not wait for the logging to complete before exiting. |
| backlog.enabled | false | Enables the backlog feature (see below). |
| backlog.queue | 2048 | Specifies the maximum size of the backlog queue in kilobytes. It is possible to specify size units like this: "1 MB". Supported units are "KB", "MB" and "GB". |
| backlog.flushon | error | Specifies the flush level for the backlog functionality. |
| backlog.keepopen | false | Specifies if the connection should be kept open between two successive writes when the backlog feature is used. |
With the log level of a protocol you can limit the amount of data being logged by excluding packets which don't have a certain minimum log level. For example, if you set the level to "message", all packets with a log level of "debug" or "verbose" are ignored. For a complete list of available log level values, please see the documentation of the Level enum.
The caption option specifies the caption for this protocol as used by the SmartInspect.Dispatch method. This method can send and initiate custom protocol actions and the caption is used to lookup the requested connection. By default, the caption is set to the identifier of a protocol (e.g., "file" or "mem"). For more information about the dispatching of custom protocol actions, please refer to the documentation of the Dispatch and SmartInspect.Dispatch methods.
If the backlog option is enabled, all packets whose log level is less than the flushon level and equal to or higher than the general log level of a protocol, will be written to a queue rather than directly to the protocol specific destination. When a packet arrives with a log level of at least the same value as the flushon option, the current content of the queue is written. The total amount of memory occupied by this queue can be set with the queue option. If the packet queue has been filled up with packets and a new packet is about to be stored, old packets are discarded.
As an example, if the backlog queue is set to "2 MB" and the flushon level to "error", all packets with a log level less than error are written to a queue first. By specifying a queue option of "2 MB", the baclog queue is set to a maximum memory size of 2 megabyte. Now, when a packet with a log level of error arrives, the current content of the queue and then the error itself is written.
With the keepopen option of the backlog feature you can specify if a connection should be kept open between two successive writes. When keepopen is set to false, a connection is only available during the actual write / flush. A connection is thus only created when absolutely necessary.
A protocol can either operate in normal blocking (the default) or in asynchronous mode. In blocking mode, the operations of this protocol (Connect, Disconnect, Dispatch and WritePacket) are executed synchronously and block the caller until they are done. In asynchronous mode, these operations are not executed directly but scheduled for execution in a different thread and return immediately. Asynchronous logging can increase the logging performance and reduce the blocking of applications.
When operating in asynchronous mode, this protocol uses a queue to buffer the logging data. The total amount of memory occupied by this queue can be set with the queue option. The throttle option specifies if an application should be automatically throttled in asynchronous mode when more data is logged / generated than the queue can handle. If this option is disabled and the queue is currently full, old packets are discarded when new data is logged. The throttle option ensures that no logging data is lost but can be disabled if logging performance is critical.
With the clearondisconnect option, you can specify if the current content of the asynchronous queue should be discarded before disconnecting. This can be useful if an application must not wait for the logging to complete before exiting.
The reconnect option allows a protocol to reconnect automatically before a packet is being written. A reconnect might be necessary if a working connection has been unexpectedly disconnected or could not be established in the first place. Possible errors during a reconnect attempt will silently be ignored and not reported.
Please note that the reconnect functionality causes a protocol by default to initiate a connection attempt for every packet until a connection has been successfully (re-) established. This can be a very time-consuming process, especially when using a protocol which requires a complex connection process like TCP, for example. This can slow down the logging performance. When using the reconnect option, it is thus recommended to also enable asynchronous logging to not block the application or to specify a reconnect interval to minimize the reconnect attempts.
name - The option name to validateprotected void loadOptions()
This method is intended to give real protocol implementations the opportunity to load and inspect options.
This method will be called automatically when the options have been changed.
The default implementation of this method takes care of the options isValidOption(java.lang.String) common to all protocols
and should thus always be called by derived classes which override this method.
protected boolean getReconnectDefaultValue()
protected boolean getAsyncEnabledDefaultValue()
protected int getAsyncQueueDefaultValue()
protected void reset()
throws Exception
This method resets the current protocol state by clearing the internal queue of packets, setting the connected status to false and calling the abstract internalDisconnect method of a real protocol implementation to clean up any protocol specific resources.
Exception - exceptionprotected abstract void internalConnect()
throws Exception
This method initiates a protocol specific connection attempt. The behavior of real implementations of this method can often be changed by setting protocol options with the initialize method. This method is always called in a threadsafe and exception-safe context.
Exception - If connecting to the destination failed.public void implConnect()
throws ProtocolException
ProtocolExceptionpublic void connect()
throws ProtocolException
In normal blocking mode (see isValidOption), this method does nothing more than to verify that
the protocol is not already connected and does not use the keep-open backlog feature,
and then calls the abstract protocol specific internalConnect method in a threadsafe
and exception-safe context.
When operating in asynchronous mode instead, this method schedules a connect operation
for asynchronous execution and returns immediately. Please note that possible exceptions
which occur during the eventually executed connect are not thrown directly but reported with
the error event.
ProtocolException - If connecting to the destination fails. Can only occur when operating in normal blocking mode.
In asynchronous mode, the error event is used for reporting exceptions insteadprotected boolean internalReconnect()
throws Exception
This method initiates a protocol specific reconnect attempt. The behavior of real method implementations can often be changed by setting protocol options with initialize. This method is always called in a threadsafe and exception-safe context.
The default implementation simply calls the protocol specific internalConnect method. Derived classes can change this behavior by overriding this method.
Exception - if reconnecting to the destination failedprotected abstract void internalDisconnect()
throws Exception
This method is intended for real protocol implementations to disconnect from the protocol specific source. This could be closing a file or disconnecting a TCP socket, for example. This method is always called in a threadsafe and exception-safe context.
Exception - If disconnecting from the destination failedpublic void implDisconnect()
throws ProtocolException
ProtocolExceptionpublic void disconnect()
throws ProtocolException
In normal blocking mode (see isValidOption), this method checks if this protocol has a working connection and then calls the protocol specific internalDisconnect method in a threadsafe and exception-safe context.
When operating in asynchronous mode instead, this method schedules a disconnect operation for asynchronous execution and then blocks until the internal protocol thread is done. Please note that possible exceptions which occur during the eventually executed disconnect are not thrown directly but reported with the ProtocolListener.onError, error event.
ProtocolException - Disconnecting from the destination
failed. Can only occur when operating
in normal blocking mode. In asynchronous
mode, the error event is used for
reporting exceptions insteadprotected LogHeader composeLogHeaderPacket()
protected abstract void internalWritePacket(Packet packet) throws Exception
This method is intended for real protocol implementations to write the supplied packet to the protocol specific destination. This method is always called in a threadsafe and exception-safe context.
packet - The packet to writeException - if writing the packet to the destination failedpublic void implWritePacket(Packet packet) throws ProtocolException
ProtocolExceptionpublic void scheduleWritePacket(Packet packet, SchedulerQueue.QueueEnd insertTo)
public void writePacket(Packet packet) throws ProtocolException
This method first checks if the log level of the supplied packet is sufficient to be logged. If this is not the case, this method returns immediately.
Otherwise, in normal blocking mode (see isValidOption(java.lang.String)),
this method verifies that this protocol is successfully
connected and then writes the supplied packet to the
backlog queue or passes it directly
to the protocol specific destination by calling the
InternalWritePacket method. Calling InternalWritePacket
is always done in a threadsafe and exception-safe way.
When operating in asynchronous mode instead, this method
schedules a write operation for asynchronous execution and
returns immediately. Please note that possible exceptions
which occur during the eventually executed write are not
thrown directly but reported with the
error event.
packet - The packet to writeProtocolException - Writing the packet to the destination
failed. Can only occur when operating
in normal blocking mode. In
asynchronous mode, the error event is
used for reporting exceptions insteadprotected abstract String getName()
Real implementations should return a meaningful name which represents the protocol. For example, the FileProtocol returns "file", the TcpProtocol "tcp" and the TextProtocol "text".
protected void internalDispatch(ProtocolCommand command) throws Exception
command - The protocol command which provides protocol specific information about the custom action.Exception - if executing the custom action failed.SmartInspect.dispatch(java.lang.String, int, java.lang.Object)public void implDispatch(ProtocolCommand command) throws ProtocolException
ProtocolExceptionpublic void dispatch(ProtocolCommand command) throws ProtocolException
In normal blocking mode (see isValidOption), this method does nothing more than to call the protocol-specific internalDispatch method with the supplied command argument in a threadsafe and exception-safe way. Please note that this method dispatches the custom action only if the protocol is currently connected.
When operating in asynchronous mode instead, this method schedules a dispatch operation for asynchronous execution
and returns immediately. Please note that possible exceptions which occur during the eventually executed dispatch are
not thrown directly but reported with the error event.
command - The protocol command object which provides protocol-specific information about the custom action. Can be nullProtocolException - An exception occurred in the custom action. Can only occur when operating
in normal blocking mode. In asynchronous mode, the error event is used for reporting exceptions insteadSmartInspect.dispatch(java.lang.String, int, java.lang.Object)public String getCaption()
The caption is used in the SmartInspect.dispatch method to lookup the requested connection. The caption can be set with initialize. If you use only one connection at once or does not use the SmartInspect.dispatch method, the caption option can safely be ignored. For more information, please refer to the documentation of the dispatch and SmartInspect.dispatch methods.
SmartInspect.dispatch(java.lang.String, int, java.lang.Object)public void dispose()
throws ProtocolException
In normal blocking mode (see isValidOption), this method checks if this protocol has a working connection and then calls the protocol specific internalDisconnect method in a threadsafe and exception-safe context.
When operating in asynchronous mode instead, this method schedules a disconnect operation for asynchronous execution and then blocks until the internal protocol thread is done. Please note that possible exceptions which occur during the eventually executed disconnect are not thrown directly but reported with the ProtocolListener.onError, error event.
ProtocolException - Disconnecting from the destination failed. Can only occur when operating in
normal blocking mode. In asynchronous mode, the error event is used for reporting exceptions insteadpublic boolean failed()
public void addListener(ProtocolListener listener)
listener - The listener to addpublic void removeListener(ProtocolListener listener)
This method removes the supplied listener from the event system of this object. After the listener has been removed, it will no longer be notified about any events of this object. Note that the error event is only used in combination with asynchronous logging (please see isValidOption for more information). In normal blocking mode, exceptions are reported by throwing.
listener - The listener to addprotected void doError(Exception ex)
ex - The occurred exceptionpublic boolean isAsynchronous()
public String getHostName()
The hostname of a protocol is usually set to the name of the machine this protocol is created in. The hostname can be used to write LogHeader packets after a successful protocol connect.
public void setHostName(String hostName)
The hostname of a protocol is usually set to the name of the machine this protocol is created in. The hostname can be used to write LogHeader packets after a successful protocol connect.
hostName - The new hostnamepublic String getAppName()
The application name of a protocol is usually set to the name of the application this protocol is created in. The application name can be used to write LogHeader packets after a successful protocol connect.
public void setAppName(String appName)
The application name of a protocol is usually set to the name of the application this protocol is created in. The application name can be used to write LogHeader packets after a successful protocol connect.
appName - The new application nameCopyright © 2023. All rights reserved.