@@ -240,6 +240,20 @@ namespace JT1078.Protocol.Test | |||||
Assert.Equal("B7 6D FF EF 7D FB A9 9D FE A9 1F 37 77 F3 37 BE EF FB F7 FB FB BE 7D DF B7 FD FB 76 AF DE 77 65 C7 EF E3 FB BE FF DB 4E FF DB B7 63 FF EE EF D8 BE 1D 37 B7 7D E7 7D F3 C6 F7 FD F4 BE 1F F7 B7 55 FF 76 FC FE CE 7B FF B7 7D 3F F5 FF FE 76 6C DF FE 53 DB CF 6D FB BF FD DE B1 EF 3E 77 D3 3F 6E 9A BF BF FF DB F7 FD DB 7F 63 FF 6E EC F8 EE 1F FB FD 7F FB 7D 7C DB".ToHexBytes(), package.Bodies.ToArray()); | Assert.Equal("B7 6D FF EF 7D FB A9 9D FE A9 1F 37 77 F3 37 BE EF FB F7 FB FB BE 7D DF B7 FD FB 76 AF DE 77 65 C7 EF E3 FB BE FF DB 4E FF DB B7 63 FF EE EF D8 BE 1D 37 B7 7D E7 7D F3 C6 F7 FD F4 BE 1F F7 B7 55 FF 76 FC FE CE 7B FF B7 7D 3F F5 FF FE 76 6C DF FE 53 DB CF 6D FB BF FD DE B1 EF 3E 77 D3 3F 6E 9A BF BF FF DB F7 FD DB 7F 63 FF 6E EC F8 EE 1F FB FD 7F FB 7D 7C DB".ToHexBytes(), package.Bodies.ToArray()); | ||||
} | } | ||||
[Fact] | |||||
public void Json1() | |||||
{ | |||||
var bytes = "30 31 63 64 81 88 11 35 01 12 34 56 78 10 01 30 00 00 01 6B B3 92 DA 05 00 78 B7 6D FF EF 7D FB A9 9D FE A9 1F 37 77 F3 37 BE EF FB F7 FB FB BE 7D DF B7 FD FB 76 AF DE 77 65 C7 EF E3 FB BE FF DB 4E FF DB B7 63 FF EE EF D8 BE 1D 37 B7 7D E7 7D F3 C6 F7 FD F4 BE 1F F7 B7 55 FF 76 FC FE CE 7B FF B7 7D 3F F5 FF FE 76 6C DF FE 53 DB CF 6D FB BF FD DE B1 EF 3E 77 D3 3F 6E 9A BF BF FF DB F7 FD DB 7F 63 FF 6E EC F8 EE 1F FB FD 7F FB 7D 7C DB".ToHexBytes(); | |||||
string json = JT1078Serializer.Analyze(bytes); | |||||
} | |||||
[Fact] | |||||
public void Json2() | |||||
{ | |||||
var bytes = "30 31 63 64 81 E2 10 88 01 12 34 56 78 10 01 10 00 00 01 6B B3 92 CA 7C 02 80 00 28 00 2E 00 00 00 01 61 E1 A2 BF 00 98 CF C0 EE 1E 17 28 34 07 78 8E 39 A4 03 FD DB D1 D5 46 BF B0 63 01 3F 59 AC 34 C9 7A 02 1A B9 6A 28 A4 2C 08".ToHexBytes(); | |||||
string json = JT1078Serializer.Analyze(bytes); | |||||
} | |||||
[Fact] | [Fact] | ||||
public void Label1Test1() | public void Label1Test1() | ||||
{ | { | ||||
@@ -71,11 +71,54 @@ namespace JT1078.Protocol.Extensions | |||||
return hex; | return hex; | ||||
} | } | ||||
/// <summary> | public static string ReadNumber(this byte value, string format = "X2") | ||||
/// Copyright (c) Microsoft. All rights reserved. | { | ||||
/// Licensed under the MIT license. See LICENSE file in the project root for full license information. | return value.ToString(format); | ||||
/// <see cref="DotNetty.Buffers.ByteBufferUtil"/> | } | ||||
/// </summary> | public static string ReadNumber(this int value, string format = "X8") | ||||
{ | |||||
return value.ToString(format); | |||||
} | |||||
public static string ReadNumber(this uint value, string format = "X8") | |||||
{ | |||||
return value.ToString(format); | |||||
} | |||||
public static string ReadNumber(this long value, string format = "X16") | |||||
{ | |||||
return value.ToString(format); | |||||
} | |||||
public static string ReadNumber(this ulong value, string format = "X16") | |||||
{ | |||||
return value.ToString(format); | |||||
} | |||||
public static string ReadNumber(this short value, string format = "X4") | |||||
{ | |||||
return value.ToString(format); | |||||
} | |||||
public static string ReadNumber(this ushort value, string format = "X4") | |||||
{ | |||||
return value.ToString(format); | |||||
} | |||||
public static ReadOnlySpan<char> ReadBinary(this ushort value) | |||||
{ | |||||
return System.Convert.ToString(value, 2).PadLeft(16, '0').AsSpan(); | |||||
} | |||||
public static ReadOnlySpan<char> ReadBinary(this short value) | |||||
{ | |||||
return System.Convert.ToString(value, 2).PadLeft(16, '0').AsSpan(); | |||||
} | |||||
public static ReadOnlySpan<char> ReadBinary(this uint value) | |||||
{ | |||||
return System.Convert.ToString(value, 2).PadLeft(32, '0').AsSpan(); | |||||
} | |||||
public static ReadOnlySpan<char> ReadBinary(this int value) | |||||
{ | |||||
return System.Convert.ToString(value, 2).PadLeft(32, '0').AsSpan(); | |||||
} | |||||
public static ReadOnlySpan<char> ReadBinary(this byte value) | |||||
{ | |||||
return System.Convert.ToString(value, 2).PadLeft(8, '0').AsSpan(); | |||||
} | |||||
} | } | ||||
@@ -14,7 +14,7 @@ | |||||
<licenseUrl>https://github.com/SmallChi/JT1078/blob/master/LICENSE</licenseUrl> | <licenseUrl>https://github.com/SmallChi/JT1078/blob/master/LICENSE</licenseUrl> | ||||
<license>https://github.com/SmallChi/JT1078/blob/master/LICENSE</license> | <license>https://github.com/SmallChi/JT1078/blob/master/LICENSE</license> | ||||
<GeneratePackageOnBuild>false</GeneratePackageOnBuild> | <GeneratePackageOnBuild>false</GeneratePackageOnBuild> | ||||
<Version>1.0.2</Version> | <Version>1.0.3</Version> | ||||
<SignAssembly>false</SignAssembly> | <SignAssembly>false</SignAssembly> | ||||
<PackageRequireLicenseAcceptance>true</PackageRequireLicenseAcceptance> | <PackageRequireLicenseAcceptance>true</PackageRequireLicenseAcceptance> | ||||
<PackageLicenseFile>LICENSE</PackageLicenseFile> | <PackageLicenseFile>LICENSE</PackageLicenseFile> | ||||
@@ -22,7 +22,7 @@ | |||||
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' "> | <ItemGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' "> | ||||
<PackageReference Include="System.Memory" Version="4.5.3" /> | <PackageReference Include="System.Memory" Version="4.5.4" /> | ||||
</ItemGroup> | </ItemGroup> | ||||
<ItemGroup> | <ItemGroup> | ||||
@@ -32,4 +32,7 @@ | |||||
</None> | </None> | ||||
</ItemGroup> | </ItemGroup> | ||||
<ItemGroup> | |||||
<PackageReference Include="System.Text.Json" Version="4.7.2" /> | |||||
</ItemGroup> | |||||
</Project> | </Project> |
@@ -1,9 +1,13 @@ | |||||
using JT1078.Protocol.Enums; | using JT1078.Protocol.Enums; | ||||
using JT1078.Protocol.Extensions; | |||||
using JT1078.Protocol.MessagePack; | using JT1078.Protocol.MessagePack; | ||||
using System; | using System; | ||||
using System.Collections.Concurrent; | using System.Collections.Concurrent; | ||||
using System.Collections.Generic; | using System.Collections.Generic; | ||||
using System.IO; | |||||
using System.Linq; | |||||
using System.Text; | using System.Text; | ||||
using System.Text.Json; | |||||
namespace JT1078.Protocol | namespace JT1078.Protocol | ||||
{ | { | ||||
@@ -111,5 +115,81 @@ namespace JT1078.Protocol | |||||
return jT1078Package; | return jT1078Package; | ||||
} | } | ||||
} | } | ||||
public static byte[] AnalyzeJsonBuffer(ReadOnlySpan<byte> bytes, JsonWriterOptions options = default, int minBufferSize = 8096) | |||||
{ | |||||
byte[] buffer = JT1078ArrayPool.Rent(minBufferSize); | |||||
try | |||||
{ | |||||
JT1078MessagePackReader jT1078MessagePackReader = new JT1078MessagePackReader(bytes); | |||||
using (MemoryStream memoryStream = new MemoryStream()) | |||||
using (Utf8JsonWriter writer = new Utf8JsonWriter(memoryStream, options)) | |||||
{ | |||||
writer.WriteStartObject(); | |||||
var header = jT1078MessagePackReader.ReadUInt32(); | |||||
writer.WriteString($"[{header}]头部", header.ReadNumber()); | |||||
var val1 = jT1078MessagePackReader.ReadByte(); | |||||
var label1 = new JT1078Label1(val1); | |||||
var labelSpan = val1.ReadBinary(); | |||||
writer.WriteStartObject($"[{labelSpan.ToString()}]object1[{val1.ReadNumber()}]"); | |||||
writer.WriteNumber($"({labelSpan.Slice(0,2).ToString()})V[固定为2]", label1.V); | |||||
writer.WriteNumber($"({labelSpan[2]})P[固定为0]", label1.P); | |||||
writer.WriteNumber($"({labelSpan[3]})X[RTP头是否需要扩展位固定为0]", label1.X); | |||||
writer.WriteNumber($"({labelSpan.Slice(4).ToString()})CC[固定为1]", label1.CC); | |||||
writer.WriteEndObject(); | |||||
var val2 = jT1078MessagePackReader.ReadByte(); | |||||
var label2 = new JT1078Label2(val2); | |||||
var label2Span = val2.ReadBinary(); | |||||
writer.WriteStartObject($"[{label2Span.ToString()}]object2[{val2.ReadNumber()}]"); | |||||
writer.WriteNumber($"({label2Span.Slice(0, 4).ToString()})M[确定是否是完整数据帧的边界]", label2.M); | |||||
writer.WriteString($"({label2Span.Slice(4).ToString()})PT[负载类型]", label2.PT.ToString()); | |||||
writer.WriteEndObject(); | |||||
var sn = jT1078MessagePackReader.ReadUInt16(); | |||||
writer.WriteNumber($"{sn.ReadNumber()}[序列号]", sn); | |||||
var sim = jT1078MessagePackReader.ReadBCD(12); | |||||
writer.WriteString($"[终端设备SIM卡号]", sim); | |||||
var logicChannelNumber = jT1078MessagePackReader.ReadByte(); | |||||
writer.WriteNumber($"{logicChannelNumber.ReadNumber()}[逻辑通道号]", logicChannelNumber); | |||||
var val3 = jT1078MessagePackReader.ReadByte(); | |||||
var label3 = new JT1078Label3(val3); | |||||
var label3Span = val3.ReadBinary(); | |||||
writer.WriteStartObject($"[{label3Span.ToString()}]object3[{val3.ReadNumber()}]"); | |||||
writer.WriteString($"({label3Span.Slice(0, 4).ToString()})[数据类型]", label3.DataType.ToString()); | |||||
writer.WriteString($"({label3Span.Slice(4).ToString()})[分包处理标记]", label3.SubpackageType.ToString()); | |||||
writer.WriteEndObject(); | |||||
if (label3.DataType != JT1078DataType.透传数据) | |||||
{ | |||||
var timestamp = jT1078MessagePackReader.ReadUInt64(); | |||||
writer.WriteNumber($"{timestamp.ReadNumber()}[标识此RTP数据包当前帧的相对时间,单位毫秒(ms)]", timestamp); | |||||
} | |||||
if (label3.DataType != JT1078DataType.透传数据 && | |||||
label3.DataType != JT1078DataType.音频帧) | |||||
{ | |||||
var lastIFrameInterval = jT1078MessagePackReader.ReadUInt16(); | |||||
writer.WriteNumber($"{lastIFrameInterval.ReadNumber()}[该帧与上一个关键帧之间的时间间隔,单位毫秒(ms)]", lastIFrameInterval); | |||||
var lastFrameInterval = jT1078MessagePackReader.ReadUInt16(); | |||||
writer.WriteNumber($"{lastFrameInterval.ReadNumber()}[该帧与上一个关键帧之间的时间间隔,单位毫秒(ms)]", lastFrameInterval); | |||||
} | |||||
var dataBodyLength = jT1078MessagePackReader.ReadUInt16(); | |||||
writer.WriteNumber($"{dataBodyLength.ReadNumber()}[数据体长度]", dataBodyLength); | |||||
var bodies = jT1078MessagePackReader.ReadRemainArray().ToArray(); | |||||
writer.WriteString("[数据体]", string.Join(" ", (bodies).Select(p => p.ToString("X2")))); | |||||
writer.WriteEndObject(); | |||||
writer.Flush(); | |||||
return memoryStream.ToArray(); | |||||
} | |||||
} | |||||
finally | |||||
{ | |||||
JT1078ArrayPool.Return(buffer); | |||||
} | |||||
} | |||||
public static string Analyze(ReadOnlySpan<byte> bytes,JsonWriterOptions options = default, int minBufferSize = 8096) | |||||
{ | |||||
string json = Encoding.UTF8.GetString(AnalyzeJsonBuffer(bytes, options, minBufferSize)); | |||||
return json; | |||||
} | |||||
} | } | ||||
} | } |