From c5f522f916b4c30dfc9776553c01f45f08bd3d17 Mon Sep 17 00:00:00 2001 From: stop-cran Date: Mon, 3 Dec 2018 18:06:29 +0200 Subject: [PATCH] Protocol fix. Updated README. --- README.md | 10 ++-- ZabbixSender.Async/Formatter.cs | 53 +++++++++----------- ZabbixSender.Async/ProtocolException.cs | 12 ----- ZabbixSender.Async/ZabbixSender.Async.csproj | 4 +- 4 files changed, 34 insertions(+), 45 deletions(-) diff --git a/README.md b/README.md index 50635e4..2a0b27f 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -# Synopsis +# Overview The package provides a tool to send data to Zabbix in the same way as [zabbix_sender](https://www.zabbix.com/documentation/4.0/ru/manual/concepts/sender) tool. It implements [Zabbix Sender Protocol 4.0](https://www.zabbix.org/wiki/Docs/protocols/zabbix_sender/4.0). @@ -14,7 +14,11 @@ PM> Install-Package ZabbixSender.Async ```C# var sender = new ZabbixSender.Async.Sender("192.168.0.10"); -var response = sender.Send("MonitoredHost1", "trapper.item1", "10"); +var response = sender.Send("MonitoredHost1", "trapper.item1", "12"); Console.WriteLine(reponse.Response); // "success" or "fail" Console.WriteLine(response.Info); // e.g. "Processed 1 Failed 0 Total 1 Seconds spent 0.000253" -``` \ No newline at end of file +``` + +# Remarks + +Note, that in order for the request to be accepted, hosts like `MonitoredHost1` above, should be [configured](https://www.zabbix.com/documentation/4.0/manual/config/hosts/host). The same should do the items (like `trapper.item1` above). The item type should have [Zabbix trapper](https://www.zabbix.com/documentation/4.0/manual/config/items/itemtypes/trapper). Also the values passed (`12` above) should respect the type of information, configured for each item. \ No newline at end of file diff --git a/ZabbixSender.Async/Formatter.cs b/ZabbixSender.Async/Formatter.cs index d30a6d0..df63f94 100644 --- a/ZabbixSender.Async/Formatter.cs +++ b/ZabbixSender.Async/Formatter.cs @@ -4,6 +4,7 @@ using System; using System.Collections.Generic; using System.IO; +using System.Linq; using System.Text; using System.Threading; using System.Threading.Tasks; @@ -104,48 +105,44 @@ await stream.WriteAsync(BitConverter.GetBytes(ms.Length), 0, public SenderResponse ReadResponse(Stream stream) { - int responseSize = Math.Max(bufferSize, 128); - var response = new byte[responseSize]; - var count = stream.Read(response, 0, response.Length); - var begin = Array.IndexOf(response, (byte)'{'); - - if (count <= 0) - throw new ProtocolException("empty reponse received"); + try + { + var buffer = new byte[13]; - if (begin == -1) - throw new ProtocolException("start of Json ({) not found", response); + stream.Read(buffer, 0, buffer.Length); // skip the length - if (count >= responseSize) - throw new ProtocolException("the response is too big", response); + if (ZabbixHeader.Zip(buffer, (x, y) => x != y).Any(b => b)) + throw new ProtocolException("the response has an incorrect header"); - try - { - using (var ms = new MemoryStream(response, begin, count - begin)) - { - using (var reader = new StreamReader(ms, Encoding.ASCII)) - using (var jsonReader = new JsonTextReader(reader)) - return serializer.Deserialize(jsonReader); - } + using (var reader = new StreamReader(stream, Encoding.ASCII)) + using (var jsonReader = new JsonTextReader(reader)) + return serializer.Deserialize(jsonReader); } catch (JsonException ex) { - throw new ProtocolException("invalid response format", ex, response); + throw new ProtocolException("invalid response format", ex); } } - public async Task ReadResponseAsync(Stream stream, - CancellationToken cancellationToken) + public async Task ReadResponseAsync(Stream stream, CancellationToken cancellationToken) { - var response = new byte[1024]; - var count = await stream.ReadAsync(response, 0, response.Length, cancellationToken); - var begin = Array.IndexOf(response, (byte)'{'); - - using (var ms = new MemoryStream(response, begin, count - begin)) + try { - using (var reader = new StreamReader(ms, Encoding.ASCII)) + var buffer = new byte[13]; + + await stream.ReadAsync(buffer, 0, buffer.Length, cancellationToken); // skip the length + + if (ZabbixHeader.Zip(buffer, (x, y) => x != y).Any(b => b)) + throw new ProtocolException("the response has an incorrect header"); + + using (var reader = new StreamReader(stream, Encoding.ASCII)) using (var jsonReader = new JsonTextReader(reader)) return serializer.Deserialize(jsonReader); } + catch (JsonException ex) + { + throw new ProtocolException("invalid response format", ex); + } } } } diff --git a/ZabbixSender.Async/ProtocolException.cs b/ZabbixSender.Async/ProtocolException.cs index 1f57db5..c1106f9 100644 --- a/ZabbixSender.Async/ProtocolException.cs +++ b/ZabbixSender.Async/ProtocolException.cs @@ -11,17 +11,5 @@ public ProtocolException(string message) : public ProtocolException(string message, Exception innerException) : base($"Protocol error - {message}.", innerException) { } - - public ProtocolException(string message, byte[] response) : - base($"Protocol error - {message}. See the whole response in Data property by Response key.") - { - Data.Add("Response", response); - } - - public ProtocolException(string message, Exception innerException, byte[] response) : - base($"Protocol error - {message}. See the whole response in Data property by Response key.", innerException) - { - Data.Add("Response", response); - } } } diff --git a/ZabbixSender.Async/ZabbixSender.Async.csproj b/ZabbixSender.Async/ZabbixSender.Async.csproj index c8a7d3c..74ba35f 100644 --- a/ZabbixSender.Async/ZabbixSender.Async.csproj +++ b/ZabbixSender.Async/ZabbixSender.Async.csproj @@ -2,13 +2,13 @@ netcoreapp2.1;net461 - 1.0.1 + 1.0.2 true Apache License 2.0 (stop-cran, 2018) stop-cran <stop-cran@list.ru> stop-cran <stop-cran@list.ru> https://github.com/stop-cran/ZabbixSender.Async - Added clock. Added interfaces for a possibility of DI. + Protocol fix. The package provides a tool to send data to Zabbix in the same way as zabbix_sender tool. It implements Zabbix Sender Protocol 4.0.