2.去掉服务端计数器 3.增加HTTP客户端调用工具tags/pipeline-1.1.0
@@ -0,0 +1,15 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Text; | |||
namespace JT808.Gateway.Abstractions.Dtos | |||
{ | |||
public class JT808DefaultResultDto: JT808ResultDto<string> | |||
{ | |||
public JT808DefaultResultDto() | |||
{ | |||
Data = "Hello,JT808 WebAPI"; | |||
Code = JT808ResultCode.Ok; | |||
} | |||
} | |||
} |
@@ -0,0 +1,30 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Text; | |||
namespace JT808.Gateway.Abstractions.Dtos | |||
{ | |||
public class JT808ResultDto<T> | |||
{ | |||
public JT808ResultDto() | |||
{ | |||
Code = JT808ResultCode.Ok; | |||
} | |||
public string Message { get; set; } | |||
public int Code { get; set; } | |||
public T Data { get; set; } | |||
} | |||
public class JT808ResultCode | |||
{ | |||
public const int Ok = 200; | |||
public const int Empty = 201; | |||
public const int AuthFail = 401; | |||
public const int NotFound = 404; | |||
public const int Fail = 400; | |||
public const int Error = 500; | |||
} | |||
} |
@@ -0,0 +1,24 @@ | |||
using System; | |||
namespace JT808.Gateway.Abstractions.Dtos | |||
{ | |||
public class JT808TcpSessionInfoDto | |||
{ | |||
/// <summary> | |||
/// 最后上线时间 | |||
/// </summary> | |||
public DateTime LastActiveTime { get; set; } | |||
/// <summary> | |||
/// 上线时间 | |||
/// </summary> | |||
public DateTime StartTime { get; set; } | |||
/// <summary> | |||
/// 终端手机号 | |||
/// </summary> | |||
public string TerminalPhoneNo { get; set; } | |||
/// <summary> | |||
/// 远程ip地址 | |||
/// </summary> | |||
public string RemoteAddressIP { get; set; } | |||
} | |||
} |
@@ -0,0 +1,24 @@ | |||
using System; | |||
namespace JT808.Gateway.Abstractions.Dtos | |||
{ | |||
public class JT808UdpSessionInfoDto | |||
{ | |||
/// <summary> | |||
/// 最后上线时间 | |||
/// </summary> | |||
public DateTime LastActiveTime { get; set; } | |||
/// <summary> | |||
/// 上线时间 | |||
/// </summary> | |||
public DateTime StartTime { get; set; } | |||
/// <summary> | |||
/// 终端手机号 | |||
/// </summary> | |||
public string TerminalPhoneNo { get; set; } | |||
/// <summary> | |||
/// 远程ip地址 | |||
/// </summary> | |||
public string RemoteAddressIP { get; set; } | |||
} | |||
} |
@@ -0,0 +1,11 @@ | |||
namespace JT808.Gateway.Abstractions.Dtos | |||
{ | |||
/// <summary> | |||
/// 统一下发请求参数 | |||
/// </summary> | |||
public class JT808UnificationSendRequestDto | |||
{ | |||
public string TerminalPhoneNo { get; set; } | |||
public string Data { get; set; } | |||
} | |||
} |
@@ -0,0 +1,13 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Net; | |||
using System.Security.Principal; | |||
using System.Text; | |||
namespace JT808.Gateway.Abstractions | |||
{ | |||
public interface IJT808Authorization | |||
{ | |||
bool Authorization(HttpListenerContext context, out IPrincipal principal); | |||
} | |||
} |
@@ -26,17 +26,8 @@ | |||
<DocumentationFile>JT808.Gateway.Abstractions.xml</DocumentationFile> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<Protobuf Include="Protos\JT808Gateway.proto" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Google.Protobuf" Version="3.11.4" /> | |||
<PackageReference Include="Grpc.Core" Version="2.28.1" /> | |||
<PackageReference Include="Grpc.Tools" Version="2.28.1"> | |||
<PrivateAssets>all</PrivateAssets> | |||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets> | |||
</PackageReference> | |||
<PackageReference Include="JT808" Version="2.2.10" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting.Abstractions" Version="3.1.4" /> | |||
<PackageReference Include="JT808" Version="2.2.12" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting.Abstractions" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<None Include="..\..\LICENSE" Pack="true" PackagePath="" /> | |||
@@ -7,5 +7,44 @@ | |||
public const string SessionTopic = "jt808session"; | |||
public const string MsgTopic = "jt808msgdefault"; | |||
public const string MsgReplyTopic = "jt808msgreplydefault"; | |||
public static class JT808WebApiRouteTable | |||
{ | |||
public const string RouteTablePrefix = "/jt808api"; | |||
public const string SessionPrefix = "Session"; | |||
public const string TcpPrefix = "Tcp"; | |||
public const string UdpPrefix = "Udp"; | |||
/// <summary> | |||
/// 基于Tcp的会话服务集合 | |||
/// </summary> | |||
public static string SessionTcpGetAll = $"{RouteTablePrefix}/{TcpPrefix}/{SessionPrefix}/GetAll"; | |||
/// <summary> | |||
/// 会话服务-通过设备终端号移除对应会话 | |||
/// </summary> | |||
public static string SessionRemoveByTerminalPhoneNo = $"{RouteTablePrefix}/{TcpPrefix}/{SessionPrefix}/RemoveByTerminalPhoneNo"; | |||
/// <summary> | |||
/// 会话服务-通过设备终端号查询对应会话 | |||
/// </summary> | |||
public static string QueryTcpSessionByTerminalPhoneNo = $"{RouteTablePrefix}/{TcpPrefix}/{SessionPrefix}/QueryTcpSessionByTerminalPhoneNo"; | |||
/// <summary> | |||
/// 统一下发信息 | |||
/// </summary> | |||
public static string UnificationSend = $"{RouteTablePrefix}/UnificationSend"; | |||
/// <summary> | |||
/// 基于Udp的虚拟会话服务集合 | |||
/// </summary> | |||
public static string SessionUdpGetAll = $"{RouteTablePrefix}/{UdpPrefix}/{SessionPrefix}/GetAll"; | |||
/// <summary> | |||
/// 会话服务-通过设备终端号移除对应会话 | |||
/// </summary> | |||
public static string RemoveUdpByTerminalPhoneNo = $"{RouteTablePrefix}/{UdpPrefix}/{SessionPrefix}/RemoveUdpByTerminalPhoneNo"; | |||
/// <summary> | |||
/// 会话服务-通过设备终端号查询对应会话 | |||
/// </summary> | |||
public static string QueryUdpSessionByTerminalPhoneNo = $"{RouteTablePrefix}/{UdpPrefix}/{SessionPrefix}/QueryUdpSessionByTerminalPhoneNo"; | |||
} | |||
} | |||
} |
@@ -0,0 +1,90 @@ | |||
using JT808.Gateway.Abstractions.Dtos; | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Text; | |||
using System.Text.Json; | |||
namespace JT808.Gateway.Abstractions | |||
{ | |||
public abstract class JT808MsgIdHttpHandlerBase | |||
{ | |||
public Dictionary<string, Func<string,byte[]>> HandlerDict { get; } | |||
/// <summary> | |||
/// 初始化消息处理业务 | |||
/// </summary> | |||
protected JT808MsgIdHttpHandlerBase() | |||
{ | |||
HandlerDict = new Dictionary<string, Func<string, byte[]>>(); | |||
} | |||
protected void CreateRoute(string url, Func<string, byte[]> func) | |||
{ | |||
if (!HandlerDict.ContainsKey(url)) | |||
{ | |||
HandlerDict.Add(url, func); | |||
} | |||
else | |||
{ | |||
// 替换 | |||
HandlerDict[url] = func; | |||
} | |||
} | |||
protected byte[] CreateHttpResponse(dynamic dynamicObject) | |||
{ | |||
byte[] data = JsonSerializer.SerializeToUtf8Bytes(dynamicObject); | |||
return data; | |||
} | |||
public byte[] DefaultHttpResponse() | |||
{ | |||
byte[] json = JsonSerializer.SerializeToUtf8Bytes(new JT808DefaultResultDto()); | |||
return json; | |||
} | |||
public byte[] EmptyHttpResponse() | |||
{ | |||
byte[] json = JsonSerializer.SerializeToUtf8Bytes(new JT808ResultDto<string>() | |||
{ | |||
Code = JT808ResultCode.Empty, | |||
Message = "内容为空", | |||
Data = "Content Empty" | |||
}); | |||
return json; | |||
} | |||
public byte[] NotFoundHttpResponse() | |||
{ | |||
byte[] json = JsonSerializer.SerializeToUtf8Bytes(new JT808ResultDto<string>() | |||
{ | |||
Code = JT808ResultCode.NotFound, | |||
Message = "没有该服务", | |||
Data = "没有该服务" | |||
}); | |||
return json; | |||
} | |||
public byte[] AuthFailHttpResponse() | |||
{ | |||
byte[] json = JsonSerializer.SerializeToUtf8Bytes(new JT808ResultDto<string>() | |||
{ | |||
Code = JT808ResultCode.AuthFail, | |||
Message = "token认证失败", | |||
Data = "token认证失败" | |||
}); | |||
return json; | |||
} | |||
public byte[] ErrorHttpResponse(Exception ex) | |||
{ | |||
byte[] json = JsonSerializer.SerializeToUtf8Bytes(new JT808ResultDto<string>() | |||
{ | |||
Code = JT808ResultCode.Error, | |||
Message = ex.StackTrace, | |||
Data = ex.Message | |||
}); | |||
return json; | |||
} | |||
} | |||
} |
@@ -1,73 +0,0 @@ | |||
syntax = "proto3"; | |||
option csharp_namespace = "JT808.Gateway.GrpcService"; | |||
package JT808GatewayGrpc; | |||
service JT808Gateway{ | |||
// 会话服务-获取会话服务集合 | |||
rpc GetTcpSessionAll(Empty) returns (TcpSessionInfoReply); | |||
// 会话服务-获取会话总数 | |||
rpc GetTcpSessionCount(Empty) returns (SessionCountReply); | |||
// 会话服务-通过设备终端号获取当前会话信息 | |||
rpc GetTcpSessionByTerminalPhoneNo(SessionRequest) returns (SessionInfo); | |||
// 会话服务-通过设备终端号移除对应会话 | |||
rpc RemoveSessionByTerminalPhoneNo(SessionRemoveRequest) returns (SessionRemoveReply); | |||
// 统一下发信息 | |||
rpc UnificationSend(UnificationSendRequest) returns (UnificationSendReply); | |||
// 获取Tcp包计数器 | |||
rpc GetTcpAtomicCounter(Empty) returns (TcpAtomicCounterReply); | |||
// 会话服务-获取会话服务集合 | |||
rpc GetUdpSessionAll(Empty) returns (UdpSessionInfoReply); | |||
// 获取Udp包计数器 | |||
rpc GetUdpAtomicCounter(Empty) returns (UdpAtomicCounterReply); | |||
} | |||
message Empty{} | |||
message TcpSessionInfoReply{ | |||
repeated SessionInfo TcpSessions=1; | |||
} | |||
message SessionRequest{ | |||
string TerminalPhoneNo=1; | |||
} | |||
message SessionCountReply{ | |||
int64 Count=1; | |||
} | |||
message UdpSessionInfoReply{ | |||
repeated SessionInfo UdpSessions=1; | |||
} | |||
message SessionInfo{ | |||
string StartTime=1; | |||
string LastActiveTime=2; | |||
string TerminalPhoneNo=3; | |||
string RemoteAddressIP=4; | |||
} | |||
message SessionRemoveRequest{ | |||
string TerminalPhoneNo=1; | |||
} | |||
message SessionRemoveReply{ | |||
bool Success = 1; | |||
} | |||
message UnificationSendRequest{ | |||
string TerminalPhoneNo=1; | |||
bytes Data=2; | |||
} | |||
message UnificationSendReply{ | |||
bool Success = 1; | |||
} | |||
message TcpAtomicCounterReply{ | |||
int64 MsgSuccessCount=1; | |||
int64 MsgFailCount=2; | |||
} | |||
message UdpAtomicCounterReply{ | |||
int64 MsgSuccessCount=1; | |||
int64 MsgFailCount=2; | |||
} |
@@ -12,11 +12,11 @@ | |||
</ItemGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Configuration.FileExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.4" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.3" /> | |||
<PackageReference Include="Microsoft.Extensions.Configuration.FileExtensions" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.7" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.5" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
@@ -6,10 +6,10 @@ | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.10.8" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.3" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.5" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
@@ -22,12 +22,12 @@ | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="JT808" Version="2.2.10" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting.Abstractions" Version="3.1.4" /> | |||
<PackageReference Include="JT808" Version="2.2.12" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting.Abstractions" Version="3.1.7" /> | |||
<PackageReference Include="System.IO.Pipelines" Version="4.7.2" /> | |||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<None Include="..\..\LICENSE" Pack="true" PackagePath="" /> | |||
@@ -15,8 +15,11 @@ using Microsoft.Extensions.DependencyInjection; | |||
namespace JT808.Gateway.Client | |||
{ | |||
public class JT808TcpClient:IDisposable | |||
{ | |||
//todo: 客户端的断线重连 | |||
//todo: 客户端的消息处理handler | |||
private bool disposed = false; | |||
private Socket clientSocket; | |||
private readonly ILogger Logger; | |||
@@ -20,12 +20,12 @@ | |||
<Version>$(JT808GatewayPackageVersion)</Version> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Confluent.Kafka" Version="1.4.2" /> | |||
<PackageReference Include="Microsoft.Extensions.Configuration.Abstractions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Confluent.Kafka" Version="1.5.1" /> | |||
<PackageReference Include="Microsoft.Extensions.Configuration.Abstractions" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Options" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
@@ -22,7 +22,7 @@ | |||
<PackageLicenseFile>LICENSE</PackageLicenseFile> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<None Include="..\..\..\LICENSE" Pack="true" PackagePath="" /> | |||
@@ -21,7 +21,7 @@ | |||
<PackageLicenseFile>LICENSE</PackageLicenseFile> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<None Include="..\..\..\LICENSE" Pack="true" PackagePath="" /> | |||
@@ -22,7 +22,7 @@ | |||
<PackageLicenseFile>LICENSE</PackageLicenseFile> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<None Include="..\..\..\LICENSE" Pack="true" PackagePath="" /> | |||
@@ -22,7 +22,7 @@ | |||
<PackageLicenseFile>LICENSE</PackageLicenseFile> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<None Include="..\..\..\LICENSE" Pack="true" PackagePath="" /> | |||
@@ -5,12 +5,16 @@ | |||
<TargetFramework>netcoreapp3.1</TargetFramework> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<Compile Remove="Jobs\CallGrpcClientJob.cs" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.10.8" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.3" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.5" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
@@ -60,7 +60,6 @@ namespace JT808.Gateway.NormalHosting | |||
.AddTransmit(hostContext.Configuration) | |||
.AddTcp() | |||
.AddUdp() | |||
.AddGrpc() | |||
; | |||
//流量统计 | |||
services.AddHostedService<TrafficJob>(); | |||
@@ -6,10 +6,14 @@ | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.4" /> | |||
<Compile Remove="Jobs\CallGrpcClientJob.cs" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Hosting" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.10.8" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.3" /> | |||
<PackageReference Include="NLog.Extensions.Logging" Version="1.6.5" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
@@ -52,7 +52,6 @@ namespace JT808.Gateway.QueueHosting | |||
.AddServerKafkaMsgReplyConsumer(hostContext.Configuration) | |||
.AddTcp() | |||
.AddUdp() | |||
.AddGrpc() | |||
.Builder() | |||
//添加客户端工具 | |||
.AddClient() | |||
@@ -7,15 +7,15 @@ | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.6.1" /> | |||
<PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.7.1" /> | |||
<PackageReference Include="System.IO.Pipelines" Version="4.7.2" /> | |||
<PackageReference Include="xunit" Version="2.4.1" /> | |||
<PackageReference Include="xunit.runner.visualstudio" Version="2.4.1"> | |||
<PackageReference Include="xunit.runner.visualstudio" Version="2.4.3"> | |||
<PrivateAssets>all</PrivateAssets> | |||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets> | |||
</PackageReference> | |||
<PackageReference Include="coverlet.collector" Version="1.2.1"> | |||
<PackageReference Include="coverlet.collector" Version="1.3.0"> | |||
<PrivateAssets>all</PrivateAssets> | |||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets> | |||
</PackageReference> | |||
@@ -0,0 +1,34 @@ | |||
<Project Sdk="Microsoft.NET.Sdk"> | |||
<Import Project="..\Version.props" /> | |||
<PropertyGroup> | |||
<TargetFramework>netstandard2.1</TargetFramework> | |||
<LangVersion>8.0</LangVersion> | |||
<Copyright>Copyright 2019.</Copyright> | |||
<Authors>SmallChi(Koike)</Authors> | |||
<RepositoryUrl>https://github.com/SmallChi/JT808Gateway</RepositoryUrl> | |||
<PackageProjectUrl>https://github.com/SmallChi/JT808Gateway</PackageProjectUrl> | |||
<licenseUrl>https://github.com/SmallChi/JT808Gateway/blob/master/LICENSE</licenseUrl> | |||
<license>https://github.com/SmallChi/JT808Gateway/blob/master/LICENSE</license> | |||
<GeneratePackageOnBuild>false</GeneratePackageOnBuild> | |||
<Version>$(JT808GatewayPackageVersion)</Version> | |||
<SignAssembly>false</SignAssembly> | |||
<PackageLicenseFile>LICENSE</PackageLicenseFile> | |||
<PackageRequireLicenseAcceptance>true</PackageRequireLicenseAcceptance> | |||
<PackageId>JT808.Gateway.WebApiClientTool</PackageId> | |||
<Product>JT808.Gateway.WebApiClientTool</Product> | |||
<Description>基于Pipeline的WebApiClient客户端调用工具</Description> | |||
<PackageReleaseNotes>基于Pipeline的WebApiClient客户端调用工具</PackageReleaseNotes> | |||
</PropertyGroup> | |||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'"> | |||
<DocumentationFile>JT808.Gateway.WebApiClientTool.xml</DocumentationFile> | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<None Include="..\..\LICENSE" Pack="true" PackagePath="" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Http" Version="3.1.7" /> | |||
</ItemGroup> | |||
<ItemGroup> | |||
<ProjectReference Include="..\JT808.Gateway.Abstractions\JT808.Gateway.Abstractions.csproj" /> | |||
</ItemGroup> | |||
</Project> |
@@ -0,0 +1,81 @@ | |||
using JT808.Gateway.Abstractions; | |||
using JT808.Gateway.Abstractions.Dtos; | |||
using System; | |||
using System.Buffers.Text; | |||
using System.Collections.Generic; | |||
using System.Net.Http; | |||
using System.Text; | |||
using System.Text.Json; | |||
using System.Threading.Tasks; | |||
namespace JT808.Gateway.WebApiClientTool | |||
{ | |||
public class JT808HttpClient | |||
{ | |||
//todo:其余接口待接入 | |||
public HttpClient HttpClient { get; } | |||
public JT808HttpClient(HttpClient httpClient) | |||
{ | |||
HttpClient = httpClient; | |||
} | |||
/// <summary> | |||
/// 会话服务集合 | |||
/// </summary> | |||
/// <returns></returns> | |||
public async ValueTask<JT808ResultDto<List<JT808TcpSessionInfoDto>>> GetTcpSessionAll() | |||
{ | |||
var request = new HttpRequestMessage(HttpMethod.Get, JT808GatewayConstants.JT808WebApiRouteTable.SessionTcpGetAll); | |||
var response = HttpClient.SendAsync(request).Result; | |||
response.EnsureSuccessStatusCode(); | |||
var data = await response.Content.ReadAsStreamAsync(); | |||
var value = await JsonSerializer.DeserializeAsync<JT808ResultDto<List<JT808TcpSessionInfoDto>>>(data); | |||
return value; | |||
} | |||
/// <summary> | |||
/// 会话服务-通过设备终端号移除对应会话 | |||
/// </summary> | |||
/// <param name="terminalPhoneNo"></param> | |||
/// <returns></returns> | |||
public async ValueTask<JT808ResultDto<bool>> RemoveByTerminalPhoneNo(string terminalPhoneNo) | |||
{ | |||
var request = new HttpRequestMessage(HttpMethod.Post, JT808GatewayConstants.JT808WebApiRouteTable.SessionRemoveByTerminalPhoneNo); | |||
request.Content = new StringContent(terminalPhoneNo); | |||
var response = HttpClient.SendAsync(request).Result; | |||
response.EnsureSuccessStatusCode(); | |||
var data = await response.Content.ReadAsStreamAsync(); | |||
var value = await JsonSerializer.DeserializeAsync<JT808ResultDto<bool>>(data); | |||
return value; | |||
} | |||
/// <summary> | |||
/// 统一下发信息 | |||
/// </summary> | |||
/// <param name="jT808UnificationSendRequestDto"></param> | |||
/// <returns></returns> | |||
public async ValueTask<JT808ResultDto<bool>> UnificationSend(JT808UnificationSendRequestDto jT808UnificationSendRequestDto) | |||
{ | |||
var request = new HttpRequestMessage(HttpMethod.Post, JT808GatewayConstants.JT808WebApiRouteTable.UnificationSend); | |||
request.Content = new StringContent(JsonSerializer.Serialize(jT808UnificationSendRequestDto)); | |||
var response = HttpClient.SendAsync(request).Result; | |||
response.EnsureSuccessStatusCode(); | |||
var data = await response.Content.ReadAsStreamAsync(); | |||
var value = await JsonSerializer.DeserializeAsync<JT808ResultDto<bool>>(data); | |||
return value; | |||
} | |||
/// <summary> | |||
/// 会话服务集合 | |||
/// </summary> | |||
/// <returns></returns> | |||
public async ValueTask<JT808ResultDto<List<JT808UdpSessionInfoDto>>> GetUdpSessionAll() | |||
{ | |||
var request = new HttpRequestMessage(HttpMethod.Get, JT808GatewayConstants.JT808WebApiRouteTable.SessionUdpGetAll); | |||
var response = HttpClient.SendAsync(request).Result; | |||
response.EnsureSuccessStatusCode(); | |||
var data = await response.Content.ReadAsStreamAsync(); | |||
var value = await JsonSerializer.DeserializeAsync<JT808ResultDto<List<JT808UdpSessionInfoDto>>>(data); | |||
return value; | |||
} | |||
} | |||
} |
@@ -0,0 +1,33 @@ | |||
using Microsoft.Extensions.Configuration; | |||
using Microsoft.Extensions.DependencyInjection; | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Text; | |||
namespace JT808.Gateway.WebApiClientTool | |||
{ | |||
public static class JT808HttpClientExtensions | |||
{ | |||
public static IServiceCollection AddJT808WebApiClientTool(this IServiceCollection serviceDescriptors, Uri webapiUri) | |||
{ | |||
serviceDescriptors.AddHttpClient("JT808WebApiClientTool", c => | |||
{ | |||
c.BaseAddress = webapiUri; | |||
c.Timeout = TimeSpan.FromSeconds(3); | |||
}) | |||
.AddTypedClient<JT808HttpClient>(); | |||
return serviceDescriptors; | |||
} | |||
public static IServiceCollection AddJT808WebApiClientTool(this IServiceCollection serviceDescriptors, IConfiguration configuration) | |||
{ | |||
serviceDescriptors.AddHttpClient("JT808WebApiClientTool", c => | |||
{ | |||
c.BaseAddress = new Uri(configuration.GetSection("JT808WebApiClientToolConfig").Get<string>()); | |||
c.Timeout = TimeSpan.FromSeconds(3); | |||
}) | |||
.AddTypedClient<JT808HttpClient>(); | |||
return serviceDescriptors; | |||
} | |||
} | |||
} |
@@ -21,8 +21,6 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.ReplyMessage" | |||
EndProject | |||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.Transmit", "JT808.Gateway.Services\JT808.Gateway.Transmit\JT808.Gateway.Transmit.csproj", "{598E445A-AF2E-42F0-98F4-18EC22E473FC}" | |||
EndProject | |||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.Traffic", "JT808.Gateway.Services\JT808.Gateway.Traffic\JT808.Gateway.Traffic.csproj", "{8FCC6D65-8A49-4AE7-8B19-F255100849D6}" | |||
EndProject | |||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.Client", "JT808.Gateway.Client\JT808.Gateway.Client.csproj", "{AC3070AC-A938-4213-A562-C079BB4A3F9E}" | |||
EndProject | |||
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Tests", "Tests", "{7CBAACEE-19BF-499A-8C41-36A1324D45E9}" | |||
@@ -39,6 +37,10 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.CleintBenchma | |||
EndProject | |||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.ServerBenchmark", "JT808.Gateway.Benchmark\JT808.Gateway.ServerBenchmark\JT808.Gateway.ServerBenchmark.csproj", "{AF0C529A-D3CA-4FE4-93B4-735D0934EBEF}" | |||
EndProject | |||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.Traffic", "JT808.Gateway.Services\JT808.Gateway.Traffic\JT808.Gateway.Traffic.csproj", "{E5A0BFB6-4345-4592-A2B1-E3CB1FA423AE}" | |||
EndProject | |||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "JT808.Gateway.WebApiClientTool", "JT808.Gateway.WebApiClientTool\JT808.Gateway.WebApiClientTool.csproj", "{479DFD02-4777-4DC2-9E2E-8EA33BFB36C9}" | |||
EndProject | |||
Global | |||
GlobalSection(SolutionConfigurationPlatforms) = preSolution | |||
Debug|Any CPU = Debug|Any CPU | |||
@@ -77,10 +79,6 @@ Global | |||
{598E445A-AF2E-42F0-98F4-18EC22E473FC}.Debug|Any CPU.Build.0 = Debug|Any CPU | |||
{598E445A-AF2E-42F0-98F4-18EC22E473FC}.Release|Any CPU.ActiveCfg = Release|Any CPU | |||
{598E445A-AF2E-42F0-98F4-18EC22E473FC}.Release|Any CPU.Build.0 = Release|Any CPU | |||
{8FCC6D65-8A49-4AE7-8B19-F255100849D6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | |||
{8FCC6D65-8A49-4AE7-8B19-F255100849D6}.Debug|Any CPU.Build.0 = Debug|Any CPU | |||
{8FCC6D65-8A49-4AE7-8B19-F255100849D6}.Release|Any CPU.ActiveCfg = Release|Any CPU | |||
{8FCC6D65-8A49-4AE7-8B19-F255100849D6}.Release|Any CPU.Build.0 = Release|Any CPU | |||
{AC3070AC-A938-4213-A562-C079BB4A3F9E}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | |||
{AC3070AC-A938-4213-A562-C079BB4A3F9E}.Debug|Any CPU.Build.0 = Debug|Any CPU | |||
{AC3070AC-A938-4213-A562-C079BB4A3F9E}.Release|Any CPU.ActiveCfg = Release|Any CPU | |||
@@ -105,6 +103,14 @@ Global | |||
{AF0C529A-D3CA-4FE4-93B4-735D0934EBEF}.Debug|Any CPU.Build.0 = Debug|Any CPU | |||
{AF0C529A-D3CA-4FE4-93B4-735D0934EBEF}.Release|Any CPU.ActiveCfg = Release|Any CPU | |||
{AF0C529A-D3CA-4FE4-93B4-735D0934EBEF}.Release|Any CPU.Build.0 = Release|Any CPU | |||
{E5A0BFB6-4345-4592-A2B1-E3CB1FA423AE}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | |||
{E5A0BFB6-4345-4592-A2B1-E3CB1FA423AE}.Debug|Any CPU.Build.0 = Debug|Any CPU | |||
{E5A0BFB6-4345-4592-A2B1-E3CB1FA423AE}.Release|Any CPU.ActiveCfg = Release|Any CPU | |||
{E5A0BFB6-4345-4592-A2B1-E3CB1FA423AE}.Release|Any CPU.Build.0 = Release|Any CPU | |||
{479DFD02-4777-4DC2-9E2E-8EA33BFB36C9}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | |||
{479DFD02-4777-4DC2-9E2E-8EA33BFB36C9}.Debug|Any CPU.Build.0 = Debug|Any CPU | |||
{479DFD02-4777-4DC2-9E2E-8EA33BFB36C9}.Release|Any CPU.ActiveCfg = Release|Any CPU | |||
{479DFD02-4777-4DC2-9E2E-8EA33BFB36C9}.Release|Any CPU.Build.0 = Release|Any CPU | |||
EndGlobalSection | |||
GlobalSection(SolutionProperties) = preSolution | |||
HideSolutionNode = FALSE | |||
@@ -115,12 +121,12 @@ Global | |||
{1CB84599-5F56-4461-A451-DF16E3854AB9} = {3EF8490D-C993-49D8-8A3D-493B7F259D70} | |||
{604BB5CF-9ED1-4D78-9328-59436E2B4EB4} = {3EF8490D-C993-49D8-8A3D-493B7F259D70} | |||
{598E445A-AF2E-42F0-98F4-18EC22E473FC} = {3EF8490D-C993-49D8-8A3D-493B7F259D70} | |||
{8FCC6D65-8A49-4AE7-8B19-F255100849D6} = {3EF8490D-C993-49D8-8A3D-493B7F259D70} | |||
{E3DC260E-0B55-4993-B051-402E44D4E883} = {7CBAACEE-19BF-499A-8C41-36A1324D45E9} | |||
{22368AAD-A1F3-446B-B68F-98A0933BF1F6} = {7CBAACEE-19BF-499A-8C41-36A1324D45E9} | |||
{52D895BD-C60B-42D8-9229-C85927546FDA} = {7CBAACEE-19BF-499A-8C41-36A1324D45E9} | |||
{E34C6B7D-A48B-4871-895C-07AC12F959D3} = {6FAEC008-93CB-4730-8C58-D31FFD342C4F} | |||
{AF0C529A-D3CA-4FE4-93B4-735D0934EBEF} = {6FAEC008-93CB-4730-8C58-D31FFD342C4F} | |||
{E5A0BFB6-4345-4592-A2B1-E3CB1FA423AE} = {3EF8490D-C993-49D8-8A3D-493B7F259D70} | |||
EndGlobalSection | |||
GlobalSection(ExtensibilityGlobals) = postSolution | |||
SolutionGuid = {AA9303A7-6FB3-4572-88AA-3302E85330D1} | |||
@@ -9,7 +9,6 @@ namespace JT808.Gateway.Configurations | |||
public int TcpPort { get; set; } = 808; | |||
public int UdpPort { get; set; } = 808; | |||
public int WebApiPort { get; set; } = 828; | |||
public string WebApiHost{ get; set; } = "localhost"; | |||
/// <summary> | |||
/// WebApi 默认token 123456 | |||
/// </summary> | |||
@@ -0,0 +1,85 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Net; | |||
using System.Text; | |||
using System.Threading; | |||
using System.Threading.Tasks; | |||
namespace JT808.Gateway.Extensions | |||
{ | |||
public static class JT808HttpContextExtensions | |||
{ | |||
private const string jsonType = "application/json"; | |||
public static async ValueTask Http401(this HttpListenerContext context) | |||
{ | |||
byte[] b = Encoding.UTF8.GetBytes("auth error"); | |||
context.Response.StatusCode = (int)HttpStatusCode.Unauthorized; | |||
context.Response.ContentType = jsonType; | |||
context.Response.KeepAlive = false; | |||
context.Response.ContentLength64 = b.Length; | |||
var output = context.Response.OutputStream; | |||
await output.WriteAsync(b, 0, b.Length); | |||
context.Response.OutputStream.Close(); | |||
context.Response.Close(); | |||
} | |||
public static async ValueTask Http400(this HttpListenerContext context) | |||
{ | |||
byte[] b = Encoding.UTF8.GetBytes($"sim and channel parameter required."); | |||
context.Response.StatusCode = (int)HttpStatusCode.BadRequest; | |||
context.Response.KeepAlive = false; | |||
context.Response.ContentType = jsonType; | |||
context.Response.ContentLength64 = b.Length; | |||
var output = context.Response.OutputStream; | |||
await output.WriteAsync(b, 0, b.Length); | |||
context.Response.OutputStream.Close(); | |||
context.Response.Close(); | |||
} | |||
public static void Http404(this HttpListenerContext context) | |||
{ | |||
context.Response.StatusCode = (int)HttpStatusCode.NotFound; | |||
context.Response.KeepAlive = false; | |||
context.Response.ContentType = jsonType; | |||
context.Response.OutputStream.Close(); | |||
context.Response.Close(); | |||
} | |||
public static async ValueTask Http500(this HttpListenerContext context) | |||
{ | |||
byte[] b = Encoding.UTF8.GetBytes("inner error"); | |||
context.Response.StatusCode = (int)HttpStatusCode.InternalServerError; | |||
context.Response.KeepAlive = false; | |||
context.Response.ContentType = jsonType; | |||
context.Response.ContentLength64 = b.Length; | |||
var output = context.Response.OutputStream; | |||
await output.WriteAsync(b, 0, b.Length); | |||
context.Response.OutputStream.Close(); | |||
context.Response.Close(); | |||
} | |||
public static async ValueTask HttpSend(this HttpListenerContext context, ReadOnlyMemory<byte> buffer) | |||
{ | |||
context.Response.StatusCode = (int)HttpStatusCode.OK; | |||
context.Response.KeepAlive = true; | |||
context.Response.ContentType = jsonType; | |||
context.Response.ContentLength64 = buffer.Length; | |||
await context.Response.OutputStream.WriteAsync(buffer); | |||
context.Response.OutputStream.Close(); | |||
context.Response.Close(); | |||
} | |||
public static async ValueTask HttpSend(this HttpListenerContext context, string json) | |||
{ | |||
byte[] b = Encoding.UTF8.GetBytes(json); | |||
context.Response.StatusCode = (int)HttpStatusCode.OK; | |||
context.Response.KeepAlive = true; | |||
context.Response.ContentType = jsonType; | |||
context.Response.ContentLength64 = b.Length; | |||
await context.Response.OutputStream.WriteAsync(b); | |||
context.Response.OutputStream.Close(); | |||
context.Response.Close(); | |||
} | |||
} | |||
} |
@@ -0,0 +1,261 @@ | |||
using JT808.Gateway.Abstractions; | |||
using JT808.Gateway.Abstractions.Dtos; | |||
using JT808.Gateway.Session; | |||
using JT808.Protocol.Extensions; | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Linq; | |||
using System.Text.Json; | |||
using System.Threading.Tasks; | |||
namespace JT808.Gateway.Handlers | |||
{ | |||
/// <summary> | |||
/// 默认消息处理业务实现 | |||
/// </summary> | |||
public class JT808MsgIdDefaultWebApiHandler : JT808MsgIdHttpHandlerBase | |||
{ | |||
private JT808SessionManager JT808SessionManager; | |||
public JT808MsgIdDefaultWebApiHandler(JT808SessionManager jT808SessionManager) | |||
{ | |||
this.JT808SessionManager = jT808SessionManager; | |||
InitTcpRoute(); | |||
InitUdpRoute(); | |||
InitCommontRoute(); | |||
} | |||
/// <summary> | |||
/// 会话服务集合 | |||
/// </summary> | |||
/// <param name="json"></param> | |||
/// <returns></returns> | |||
public byte[] GetTcpSessionAll(string json) | |||
{ | |||
JT808ResultDto<List<JT808TcpSessionInfoDto>> resultDto = new JT808ResultDto<List<JT808TcpSessionInfoDto>>(); | |||
try | |||
{ | |||
resultDto.Data = JT808SessionManager.GetTcpAll().Select(s => new JT808TcpSessionInfoDto | |||
{ | |||
LastActiveTime = s.ActiveTime, | |||
StartTime = s.StartTime, | |||
TerminalPhoneNo = s.TerminalPhoneNo, | |||
RemoteAddressIP = s.RemoteEndPoint.ToString(), | |||
}).ToList(); | |||
resultDto.Code = JT808ResultCode.Ok; | |||
} | |||
catch (Exception ex) | |||
{ | |||
resultDto.Data = null; | |||
resultDto.Code = JT808ResultCode.Error; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
return CreateHttpResponse(resultDto); | |||
} | |||
/// <summary> | |||
/// 通过终端手机号查询对应会话 | |||
/// </summary> | |||
/// <param name="json"></param> | |||
/// <returns></returns> | |||
public byte[] QueryTcpSessionByTerminalPhoneNo(string json) | |||
{ | |||
if (string.IsNullOrEmpty(json)) | |||
{ | |||
return EmptyHttpResponse(); | |||
} | |||
JT808ResultDto<JT808TcpSessionInfoDto> resultDto = new JT808ResultDto<JT808TcpSessionInfoDto>(); | |||
try | |||
{ | |||
resultDto.Data = JT808SessionManager.GetTcpAll().Where(w => w.TerminalPhoneNo == json).Select(s => new JT808TcpSessionInfoDto | |||
{ | |||
LastActiveTime = s.ActiveTime, | |||
StartTime = s.StartTime, | |||
TerminalPhoneNo = s.TerminalPhoneNo, | |||
RemoteAddressIP = s.RemoteEndPoint.ToString(), | |||
}).FirstOrDefault(); | |||
resultDto.Code = JT808ResultCode.Ok; | |||
} | |||
catch (Exception ex) | |||
{ | |||
resultDto.Data = null; | |||
resultDto.Code = JT808ResultCode.Error; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
return CreateHttpResponse(resultDto); | |||
} | |||
/// <summary> | |||
/// 会话服务-通过设备终端号移除对应会话 | |||
/// </summary> | |||
/// <param name="json"></param> | |||
/// <returns></returns> | |||
public byte[] RemoveSessionByTerminalPhoneNo(string json) | |||
{ | |||
if (string.IsNullOrEmpty(json)) | |||
{ | |||
return EmptyHttpResponse(); | |||
} | |||
JT808ResultDto<bool> resultDto = new JT808ResultDto<bool>(); | |||
try | |||
{ | |||
JT808SessionManager.RemoveByTerminalPhoneNo(json); | |||
resultDto.Code = JT808ResultCode.Ok; | |||
resultDto.Data = true; | |||
} | |||
catch (AggregateException ex) | |||
{ | |||
resultDto.Data = false; | |||
resultDto.Code = 500; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
catch (Exception ex) | |||
{ | |||
resultDto.Data = false; | |||
resultDto.Code = JT808ResultCode.Error; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
return CreateHttpResponse(resultDto); | |||
} | |||
/// <summary> | |||
/// 会话服务集合 | |||
/// </summary> | |||
/// <param name="json"></param> | |||
/// <returns></returns> | |||
public byte[] GetUdpSessionAll(string json) | |||
{ | |||
JT808ResultDto<List<JT808UdpSessionInfoDto>> resultDto = new JT808ResultDto<List<JT808UdpSessionInfoDto>>(); | |||
try | |||
{ | |||
resultDto.Data = JT808SessionManager.GetUdpAll().Select(s => new JT808UdpSessionInfoDto | |||
{ | |||
LastActiveTime = s.ActiveTime, | |||
StartTime = s.StartTime, | |||
TerminalPhoneNo = s.TerminalPhoneNo, | |||
RemoteAddressIP = s.RemoteEndPoint.ToString(), | |||
}).ToList(); | |||
resultDto.Code = JT808ResultCode.Ok; | |||
} | |||
catch (Exception ex) | |||
{ | |||
resultDto.Data = null; | |||
resultDto.Code = JT808ResultCode.Error; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
return CreateHttpResponse(resultDto); | |||
} | |||
/// <summary> | |||
/// 通过终端手机号查询对应会话 | |||
/// </summary> | |||
/// <param name="json"></param> | |||
/// <returns></returns> | |||
public byte[] QueryUdpSessionByTerminalPhoneNo(string json) | |||
{ | |||
if (string.IsNullOrEmpty(json)) | |||
{ | |||
return EmptyHttpResponse(); | |||
} | |||
JT808ResultDto<JT808UdpSessionInfoDto> resultDto = new JT808ResultDto<JT808UdpSessionInfoDto>(); | |||
try | |||
{ | |||
resultDto.Data = JT808SessionManager.GetUdpAll().Where(w => w.TerminalPhoneNo == json).Select(s => new JT808UdpSessionInfoDto | |||
{ | |||
LastActiveTime = s.ActiveTime, | |||
StartTime = s.StartTime, | |||
TerminalPhoneNo = s.TerminalPhoneNo, | |||
RemoteAddressIP = s.RemoteEndPoint.ToString(), | |||
}).FirstOrDefault(); | |||
resultDto.Code = JT808ResultCode.Ok; | |||
} | |||
catch (Exception ex) | |||
{ | |||
resultDto.Data = null; | |||
resultDto.Code = JT808ResultCode.Error; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
return CreateHttpResponse(resultDto); | |||
} | |||
/// <summary> | |||
/// 会话服务-通过设备终端号移除对应会话 | |||
/// </summary> | |||
/// <param name="json"></param> | |||
/// <returns></returns> | |||
public byte[] RemoveUdpByTerminalPhoneNo(string json) | |||
{ | |||
if (string.IsNullOrEmpty(json)) | |||
{ | |||
return EmptyHttpResponse(); | |||
} | |||
JT808ResultDto<bool> resultDto = new JT808ResultDto<bool>(); | |||
try | |||
{ | |||
JT808SessionManager.RemoveByTerminalPhoneNo(json); | |||
resultDto.Code = JT808ResultCode.Ok; | |||
resultDto.Data = true; | |||
} | |||
catch (AggregateException ex) | |||
{ | |||
resultDto.Data = false; | |||
resultDto.Code = 500; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
catch (Exception ex) | |||
{ | |||
resultDto.Data = false; | |||
resultDto.Code = JT808ResultCode.Error; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
return CreateHttpResponse(resultDto); | |||
} | |||
/// <summary> | |||
/// 统一下发信息 | |||
/// </summary> | |||
/// <param name="json"></param> | |||
/// <returns></returns> | |||
public byte[] UnificationSend(string json) | |||
{ | |||
if (string.IsNullOrEmpty(json)) | |||
{ | |||
return EmptyHttpResponse(); | |||
} | |||
JT808ResultDto<bool> resultDto = new JT808ResultDto<bool>(); | |||
try | |||
{ | |||
JT808UnificationSendRequestDto jT808UnificationSendRequestDto = JsonSerializer.Deserialize<JT808UnificationSendRequestDto>(json); | |||
resultDto.Data = JT808SessionManager.TrySendByTerminalPhoneNoAsync(jT808UnificationSendRequestDto.TerminalPhoneNo, jT808UnificationSendRequestDto.Data.ToHexBytes()) | |||
.GetAwaiter() | |||
.GetResult(); | |||
resultDto.Code = JT808ResultCode.Ok; | |||
} | |||
catch (Exception ex) | |||
{ | |||
resultDto.Data = false; | |||
resultDto.Code = JT808ResultCode.Error; | |||
resultDto.Message = ex.StackTrace; | |||
} | |||
return CreateHttpResponse(resultDto); | |||
} | |||
protected virtual void InitCommontRoute() | |||
{ | |||
CreateRoute(JT808GatewayConstants.JT808WebApiRouteTable.UnificationSend, UnificationSend); | |||
} | |||
protected virtual void InitTcpRoute() | |||
{ | |||
CreateRoute(JT808GatewayConstants.JT808WebApiRouteTable.SessionTcpGetAll, GetTcpSessionAll); | |||
CreateRoute(JT808GatewayConstants.JT808WebApiRouteTable.QueryTcpSessionByTerminalPhoneNo, QueryTcpSessionByTerminalPhoneNo); | |||
CreateRoute(JT808GatewayConstants.JT808WebApiRouteTable.SessionRemoveByTerminalPhoneNo, RemoveSessionByTerminalPhoneNo); | |||
} | |||
protected virtual void InitUdpRoute() | |||
{ | |||
CreateRoute(JT808GatewayConstants.JT808WebApiRouteTable.SessionUdpGetAll, GetUdpSessionAll); | |||
CreateRoute(JT808GatewayConstants.JT808WebApiRouteTable.QueryUdpSessionByTerminalPhoneNo, QueryUdpSessionByTerminalPhoneNo); | |||
CreateRoute(JT808GatewayConstants.JT808WebApiRouteTable.RemoveUdpByTerminalPhoneNo, RemoveUdpByTerminalPhoneNo); | |||
} | |||
} | |||
} |
@@ -21,8 +21,8 @@ | |||
</PropertyGroup> | |||
<ItemGroup> | |||
<PackageReference Include="Microsoft.Extensions.Options" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.4" /> | |||
<PackageReference Include="Microsoft.Extensions.Options" Version="3.1.7" /> | |||
<PackageReference Include="Microsoft.Extensions.Options.ConfigurationExtensions" Version="3.1.7" /> | |||
<PackageReference Include="System.IO.Pipelines" Version="4.7.2" /> | |||
</ItemGroup> | |||
@@ -1,6 +1,7 @@ | |||
using JT808.Gateway.Abstractions; | |||
using JT808.Gateway.Configurations; | |||
using JT808.Gateway.Enums; | |||
using JT808.Gateway.Handlers; | |||
using JT808.Gateway.Internal; | |||
using JT808.Gateway.Services; | |||
using JT808.Gateway.Session; | |||
@@ -74,15 +75,23 @@ namespace JT808.Gateway | |||
return config; | |||
} | |||
public static IJT808GatewayBuilder AddGrpc(this IJT808GatewayBuilder config) | |||
public static IJT808GatewayBuilder AddHttp(this IJT808GatewayBuilder config) | |||
{ | |||
config.JT808Builder.Services.AddHostedService<JT808GrpcServer>(); | |||
config.JT808Builder.Services.AddSingleton<JT808MsgIdDefaultWebApiHandler>(); | |||
config.JT808Builder.Services.AddHostedService<JT808HttpServer>(); | |||
return config; | |||
} | |||
public static IJT808GatewayBuilder AddHttp<TJT808MsgIdDefaultWebApiHandler>(this IJT808GatewayBuilder config) | |||
where TJT808MsgIdDefaultWebApiHandler: JT808MsgIdDefaultWebApiHandler | |||
{ | |||
config.JT808Builder.Services.AddSingleton(typeof(JT808MsgIdDefaultWebApiHandler),typeof(TJT808MsgIdDefaultWebApiHandler)); | |||
config.JT808Builder.Services.AddHostedService<JT808HttpServer>(); | |||
return config; | |||
} | |||
private static IJT808GatewayBuilder AddJT808Core(this IJT808GatewayBuilder config) | |||
{ | |||
config.JT808Builder.Services.TryAddSingleton<JT808AtomicCounterServiceFactory>(); | |||
config.JT808Builder.Services.TryAddSingleton<JT808SessionManager>(); | |||
return config; | |||
} | |||
@@ -1,55 +0,0 @@ | |||
using System; | |||
using System.Threading; | |||
using System.Threading.Tasks; | |||
using Grpc.Core; | |||
using JT808.Gateway.Configurations; | |||
using JT808.Gateway.GrpcService; | |||
using JT808.Gateway.Services; | |||
using Microsoft.Extensions.Hosting; | |||
using Microsoft.Extensions.Logging; | |||
using Microsoft.Extensions.Options; | |||
namespace JT808.Gateway | |||
{ | |||
public class JT808GrpcServer : IHostedService | |||
{ | |||
private readonly ILogger Logger; | |||
private readonly JT808Configuration Configuration; | |||
private readonly IServiceProvider ServiceProvider; | |||
private Server server; | |||
public JT808GrpcServer( | |||
IServiceProvider serviceProvider, | |||
IOptions<JT808Configuration> jT808ConfigurationAccessor, | |||
ILoggerFactory loggerFactory) | |||
{ | |||
Logger = loggerFactory.CreateLogger("JT808GrpcServer"); | |||
Configuration = jT808ConfigurationAccessor.Value; | |||
ServiceProvider = serviceProvider; | |||
} | |||
public Task StartAsync(CancellationToken cancellationToken) | |||
{ | |||
server = new Server | |||
{ | |||
Services = { JT808Gateway.BindService(new JT808GatewayService(ServiceProvider)) }, | |||
Ports = { new ServerPort(Configuration.WebApiHost, Configuration.WebApiPort, ServerCredentials.Insecure) } | |||
}; | |||
Logger.LogInformation($"JT808 Grpc Server start at {Configuration.WebApiHost}:{Configuration.WebApiPort}."); | |||
try | |||
{ | |||
server.Start(); | |||
} | |||
catch (Exception ex) | |||
{ | |||
Logger.LogError(ex, "JT808 Grpc Server start error"); | |||
} | |||
return Task.CompletedTask; | |||
} | |||
public Task StopAsync(CancellationToken cancellationToken) | |||
{ | |||
Logger.LogInformation("JT808 Grpc Server Stop"); | |||
server.ShutdownAsync(); | |||
return Task.CompletedTask; | |||
} | |||
} | |||
} |
@@ -0,0 +1,125 @@ | |||
using JT808.Gateway.Abstractions; | |||
using JT808.Gateway.Configurations; | |||
using JT808.Gateway.Extensions; | |||
using JT808.Gateway.Handlers; | |||
using JT808.Gateway.Session; | |||
using Microsoft.Extensions.Hosting; | |||
using Microsoft.Extensions.Logging; | |||
using Microsoft.Extensions.Options; | |||
using System; | |||
using System.Buffers; | |||
using System.Collections.Generic; | |||
using System.IO; | |||
using System.Net; | |||
using System.Net.WebSockets; | |||
using System.Security.Principal; | |||
using System.Text; | |||
using System.Threading; | |||
using System.Threading.Tasks; | |||
namespace JT808.Gateway | |||
{ | |||
public class JT808HttpServer : IHostedService | |||
{ | |||
private readonly ILogger Logger; | |||
private readonly JT808Configuration Configuration; | |||
private readonly IJT808Authorization authorization; | |||
private HttpListener listener; | |||
private readonly JT808MsgIdDefaultWebApiHandler MsgIdDefaultWebApiHandler; | |||
public JT808HttpServer( | |||
JT808MsgIdDefaultWebApiHandler jT808MsgIdDefaultWebApiHandler, | |||
IOptions<JT808Configuration> jT808ConfigurationAccessor, | |||
IJT808Authorization authorization, | |||
ILoggerFactory loggerFactory) | |||
{ | |||
Logger = loggerFactory.CreateLogger<JT808HttpServer>(); | |||
Configuration = jT808ConfigurationAccessor.Value; | |||
MsgIdDefaultWebApiHandler = jT808MsgIdDefaultWebApiHandler; | |||
this.authorization = authorization; | |||
} | |||
public Task StartAsync(CancellationToken cancellationToken) | |||
{ | |||
if (!HttpListener.IsSupported) | |||
{ | |||
Logger.LogWarning("Windows XP SP2 or Server 2003 is required to use the HttpListener class."); | |||
return Task.CompletedTask; | |||
} | |||
listener = new HttpListener(); | |||
listener.AuthenticationSchemes = AuthenticationSchemes.Anonymous; | |||
try | |||
{ | |||
listener.Prefixes.Add($"http://*:{Configuration.WebApiPort}/"); | |||
listener.Start(); | |||
} | |||
catch (System.Net.HttpListenerException ex) | |||
{ | |||
Logger.LogWarning(ex, $"{ex.Message}:使用cmd命令[netsh http add urlacl url=http://*:{Configuration.WebApiPort}/ user=Everyone]"); | |||
} | |||
Logger.LogInformation($"JT808 Http Server start at {IPAddress.Any}:{Configuration.WebApiPort}."); | |||
Task.Factory.StartNew(async() => | |||
{ | |||
while (listener.IsListening) | |||
{ | |||
var context = await listener.GetContextAsync(); | |||
try | |||
{ | |||
if (authorization.Authorization(context,out var principal)) | |||
{ | |||
await ProcessRequestAsync(context, principal); | |||
} | |||
else | |||
{ | |||
await context.Http401(); | |||
} | |||
} | |||
catch (Exception ex) | |||
{ | |||
await context.Http500(); | |||
Logger.LogError(ex, ex.StackTrace); | |||
} | |||
} | |||
}, cancellationToken); | |||
return Task.CompletedTask; | |||
} | |||
private async ValueTask ProcessRequestAsync(HttpListenerContext context, IPrincipal principal) | |||
{ | |||
if(context.Request.RawUrl.StartsWith("/favicon.ico")) | |||
{ | |||
context.Http404(); | |||
return; | |||
} | |||
var uri = new Uri(context.Request.RawUrl); | |||
//todo: 处理对应的handler | |||
string url = uri.AbsolutePath; | |||
var queryParams = uri.Query.Substring(1, uri.Query.Length - 1).Split('&'); | |||
if (queryParams.Length < 2) { | |||
context.Http404(); | |||
return; | |||
} | |||
} | |||
public Task StopAsync(CancellationToken cancellationToken) | |||
{ | |||
try | |||
{ | |||
listener.Stop(); | |||
} | |||
catch (System.ObjectDisposedException ex) | |||
{ | |||
} | |||
catch (Exception ex) | |||
{ | |||
} | |||
return Task.CompletedTask; | |||
} | |||
} | |||
} |
@@ -34,8 +34,6 @@ namespace JT808.Gateway | |||
private readonly JT808Serializer Serializer; | |||
private readonly JT808AtomicCounterService AtomicCounterService; | |||
private readonly JT808Configuration Configuration; | |||
private readonly JT808NormalReplyMessageHandler JT808NormalReplyMessageHandler; | |||
@@ -56,14 +54,12 @@ namespace JT808.Gateway | |||
IJT808Config jT808Config, | |||
ILoggerFactory loggerFactory, | |||
JT808SessionManager jT808SessionManager, | |||
IJT808MsgProducer jT808MsgProducer, | |||
JT808AtomicCounterServiceFactory jT808AtomicCounterServiceFactory) | |||
IJT808MsgProducer jT808MsgProducer) | |||
{ | |||
SessionManager = jT808SessionManager; | |||
Logger = loggerFactory.CreateLogger("JT808TcpServer"); | |||
Serializer = jT808Config.GetSerializer(); | |||
MsgProducer = jT808MsgProducer; | |||
AtomicCounterService = jT808AtomicCounterServiceFactory.Create(JT808TransportProtocolType.tcp); | |||
Configuration = jT808ConfigurationAccessor.Value; | |||
JT808UseType = JT808UseType.Queue; | |||
InitServer(); | |||
@@ -82,14 +78,12 @@ namespace JT808.Gateway | |||
IJT808Config jT808Config, | |||
ILoggerFactory loggerFactory, | |||
JT808SessionManager jT808SessionManager, | |||
JT808NormalReplyMessageHandler replyMessageHandler, | |||
JT808AtomicCounterServiceFactory jT808AtomicCounterServiceFactory) | |||
JT808NormalReplyMessageHandler replyMessageHandler) | |||
{ | |||
SessionManager = jT808SessionManager; | |||
Logger = loggerFactory.CreateLogger("JT808TcpServer"); | |||
Serializer = jT808Config.GetSerializer(); | |||
JT808NormalReplyMessageHandler = replyMessageHandler; | |||
AtomicCounterService = jT808AtomicCounterServiceFactory.Create(JT808TransportProtocolType.tcp); | |||
Configuration = jT808ConfigurationAccessor.Value; | |||
JT808UseType = JT808UseType.Normal; | |||
InitServer(); | |||
@@ -235,8 +229,6 @@ namespace JT808.Gateway | |||
if (contentSpan.Length > 14) | |||
{ | |||
var package = Serializer.HeaderDeserialize(contentSpan, minBufferSize: 10240); | |||
AtomicCounterService.MsgSuccessIncrement(); | |||
if (Logger.IsEnabled(LogLevel.Debug)) Logger.LogDebug($"[Atomic Success Counter]:{AtomicCounterService.MsgSuccessCount}"); | |||
if (Logger.IsEnabled(LogLevel.Trace)) Logger.LogTrace($"[Accept Hex {session.Client.RemoteEndPoint}]:{package.OriginalData.ToArray().ToHexString()}"); | |||
SessionManager.TryLink(package.Header.TerminalPhoneNo, session); | |||
if(JT808UseType== JT808UseType.Normal) | |||
@@ -255,8 +247,6 @@ namespace JT808.Gateway | |||
} | |||
catch (JT808Exception ex) | |||
{ | |||
AtomicCounterService.MsgFailIncrement(); | |||
if (Logger.IsEnabled(LogLevel.Information)) Logger.LogInformation($"[Atomic Fail Counter]:{AtomicCounterService.MsgFailCount}"); | |||
Logger.LogError($"[HeaderDeserialize ErrorCode]:{ ex.ErrorCode},[ReaderBuffer]:{contentSpan.ToArray().ToHexString()}"); | |||
} | |||
totalConsumed += (seqReader.Consumed - totalConsumed); | |||
@@ -34,8 +34,6 @@ namespace JT808.Gateway | |||
private readonly JT808Serializer Serializer; | |||
private readonly JT808AtomicCounterService AtomicCounterService; | |||
private readonly JT808Configuration Configuration; | |||
private readonly IPEndPoint LocalIPEndPoint; | |||
@@ -49,14 +47,12 @@ namespace JT808.Gateway | |||
IJT808Config jT808Config, | |||
ILoggerFactory loggerFactory, | |||
JT808SessionManager jT808SessionManager, | |||
IJT808MsgProducer jT808MsgProducer, | |||
JT808AtomicCounterServiceFactory jT808AtomicCounterServiceFactory) | |||
IJT808MsgProducer jT808MsgProducer) | |||
{ | |||
SessionManager = jT808SessionManager; | |||
Logger = loggerFactory.CreateLogger("JT808UdpServer"); | |||
Serializer = jT808Config.GetSerializer(); | |||
MsgProducer = jT808MsgProducer; | |||
AtomicCounterService = jT808AtomicCounterServiceFactory.Create(JT808TransportProtocolType.udp); | |||
Configuration = jT808ConfigurationAccessor.Value; | |||
JT808UseType = JT808UseType.Queue; | |||
LocalIPEndPoint = new System.Net.IPEndPoint(IPAddress.Any, Configuration.UdpPort); | |||
@@ -69,14 +65,12 @@ namespace JT808.Gateway | |||
IJT808Config jT808Config, | |||
ILoggerFactory loggerFactory, | |||
JT808SessionManager jT808SessionManager, | |||
JT808NormalReplyMessageHandler replyMessageHandler, | |||
JT808AtomicCounterServiceFactory jT808AtomicCounterServiceFactory) | |||
JT808NormalReplyMessageHandler replyMessageHandler) | |||
{ | |||
SessionManager = jT808SessionManager; | |||
Logger = loggerFactory.CreateLogger("JT808UdpServer"); | |||
Serializer = jT808Config.GetSerializer(); | |||
JT808NormalReplyMessageHandler = replyMessageHandler; | |||
AtomicCounterService = jT808AtomicCounterServiceFactory.Create(JT808TransportProtocolType.udp); | |||
Configuration = jT808ConfigurationAccessor.Value; | |||
JT808UseType = JT808UseType.Normal; | |||
LocalIPEndPoint = new System.Net.IPEndPoint(IPAddress.Any, Configuration.UdpPort); | |||
@@ -120,8 +114,6 @@ namespace JT808.Gateway | |||
try | |||
{ | |||
var package = Serializer.HeaderDeserialize(buffer, minBufferSize: 10240); | |||
AtomicCounterService.MsgSuccessIncrement(); | |||
if (Logger.IsEnabled(LogLevel.Debug)) Logger.LogDebug($"[Atomic Success Counter]:{AtomicCounterService.MsgSuccessCount}"); | |||
if (Logger.IsEnabled(LogLevel.Trace)) Logger.LogTrace($"[Accept Hex {receiveMessageFromResult.RemoteEndPoint}]:{package.OriginalData.ToArray().ToHexString()}"); | |||
var session = SessionManager.TryLink(package.Header.TerminalPhoneNo, socket, receiveMessageFromResult.RemoteEndPoint); | |||
if (Logger.IsEnabled(LogLevel.Information)) | |||
@@ -143,14 +135,11 @@ namespace JT808.Gateway | |||
} | |||
catch (JT808Exception ex) | |||
{ | |||
AtomicCounterService.MsgFailIncrement(); | |||
if (Logger.IsEnabled(LogLevel.Information)) Logger.LogInformation($"[Atomic Fail Counter]:{AtomicCounterService.MsgFailCount}"); | |||
Logger.LogError($"[HeaderDeserialize ErrorCode]:{ ex.ErrorCode},[ReaderBuffer]:{buffer.ToArray().ToHexString()}"); | |||
} | |||
#pragma warning disable CA1031 // Do not catch general exception types | |||
catch (Exception ex) | |||
{ | |||
if (Logger.IsEnabled(LogLevel.Debug)) Logger.LogDebug($"[Atomic Fail Counter]:{AtomicCounterService.MsgFailCount}"); | |||
Logger.LogError(ex, $"[ReaderBuffer]:{ buffer.ToArray().ToHexString()}"); | |||
} | |||
#pragma warning restore CA1031 // Do not catch general exception types | |||
@@ -1,52 +0,0 @@ | |||
using JT808.Gateway.Metadata; | |||
namespace JT808.Gateway.Services | |||
{ | |||
/// <summary> | |||
/// 计数包服务 | |||
/// </summary> | |||
public class JT808AtomicCounterService | |||
{ | |||
private readonly JT808AtomicCounter MsgSuccessCounter; | |||
private readonly JT808AtomicCounter MsgFailCounter; | |||
public JT808AtomicCounterService() | |||
{ | |||
MsgSuccessCounter=new JT808AtomicCounter(); | |||
MsgFailCounter = new JT808AtomicCounter(); | |||
} | |||
public void Reset() | |||
{ | |||
MsgSuccessCounter.Reset(); | |||
MsgFailCounter.Reset(); | |||
} | |||
public long MsgSuccessIncrement() | |||
{ | |||
return MsgSuccessCounter.Increment(); | |||
} | |||
public long MsgSuccessCount | |||
{ | |||
get | |||
{ | |||
return MsgSuccessCounter.Count; | |||
} | |||
} | |||
public long MsgFailIncrement() | |||
{ | |||
return MsgFailCounter.Increment(); | |||
} | |||
public long MsgFailCount | |||
{ | |||
get | |||
{ | |||
return MsgFailCounter.Count; | |||
} | |||
} | |||
} | |||
} |
@@ -1,30 +0,0 @@ | |||
using JT808.Gateway.Abstractions.Enums; | |||
using System; | |||
using System.Collections.Concurrent; | |||
namespace JT808.Gateway.Services | |||
{ | |||
public class JT808AtomicCounterServiceFactory | |||
{ | |||
private readonly ConcurrentDictionary<JT808TransportProtocolType, JT808AtomicCounterService> cache; | |||
public JT808AtomicCounterServiceFactory() | |||
{ | |||
cache = new ConcurrentDictionary<JT808TransportProtocolType, JT808AtomicCounterService>(); | |||
} | |||
public JT808AtomicCounterService Create(JT808TransportProtocolType type) | |||
{ | |||
if(cache.TryGetValue(type,out var service)) | |||
{ | |||
return service; | |||
} | |||
else | |||
{ | |||
var serviceNew = new JT808AtomicCounterService(); | |||
cache.TryAdd(type, serviceNew); | |||
return serviceNew; | |||
} | |||
} | |||
} | |||
} |
@@ -1,172 +0,0 @@ | |||
using System; | |||
using System.Linq; | |||
using JT808.Gateway.GrpcService; | |||
using Grpc.Core; | |||
using System.Threading.Tasks; | |||
using JT808.Gateway.Abstractions.Enums; | |||
using JT808.Gateway.Session; | |||
using Microsoft.Extensions.DependencyInjection; | |||
using static Grpc.Core.Metadata; | |||
using Microsoft.Extensions.Options; | |||
using JT808.Gateway.Configurations; | |||
namespace JT808.Gateway.Services | |||
{ | |||
public class JT808GatewayService: JT808Gateway.JT808GatewayBase | |||
{ | |||
private readonly JT808AtomicCounterService jT808TcpAtomicCounterService; | |||
private readonly JT808AtomicCounterService jT808UdpAtomicCounterService; | |||
private readonly JT808SessionManager jT808SessionManager; | |||
private readonly IOptionsMonitor<JT808Configuration> ConfigurationOptionsMonitor; | |||
public JT808GatewayService( | |||
IOptionsMonitor<JT808Configuration> configurationOptionsMonitor, | |||
JT808SessionManager jT808SessionManager, | |||
JT808AtomicCounterServiceFactory jT808AtomicCounterServiceFactory | |||
) | |||
{ | |||
this.jT808SessionManager = jT808SessionManager; | |||
this.ConfigurationOptionsMonitor = configurationOptionsMonitor; | |||
this.jT808TcpAtomicCounterService = jT808AtomicCounterServiceFactory.Create(JT808TransportProtocolType.tcp); | |||
this.jT808UdpAtomicCounterService = jT808AtomicCounterServiceFactory.Create(JT808TransportProtocolType.udp); | |||
} | |||
public JT808GatewayService(IServiceProvider serviceProvider) | |||
{ | |||
this.jT808SessionManager = serviceProvider.GetRequiredService<JT808SessionManager>(); | |||
this.jT808TcpAtomicCounterService = serviceProvider.GetRequiredService<JT808AtomicCounterServiceFactory>().Create(JT808TransportProtocolType.tcp); | |||
this.jT808UdpAtomicCounterService = serviceProvider.GetRequiredService<JT808AtomicCounterServiceFactory>().Create(JT808TransportProtocolType.udp); | |||
this.ConfigurationOptionsMonitor = serviceProvider.GetRequiredService<IOptionsMonitor<JT808Configuration>>(); | |||
} | |||
public override Task<TcpSessionInfoReply> GetTcpSessionAll(Empty request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
var result = jT808SessionManager.GetTcpAll(); | |||
TcpSessionInfoReply reply = new TcpSessionInfoReply(); | |||
foreach (var item in result) | |||
{ | |||
reply.TcpSessions.Add(new SessionInfo | |||
{ | |||
LastActiveTime = item.ActiveTime.ToString("yyyy-MM-dd HH:mm:ss"), | |||
StartTime = item.StartTime.ToString("yyyy-MM-dd HH:mm:ss"), | |||
RemoteAddressIP = item.RemoteEndPoint.ToString(), | |||
TerminalPhoneNo = item.TerminalPhoneNo | |||
}); | |||
} | |||
return Task.FromResult(reply); | |||
} | |||
public override Task<SessionInfo> GetTcpSessionByTerminalPhoneNo(SessionRequest request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
var result = jT808SessionManager.GetTcpAll().FirstOrDefault(f=>f.TerminalPhoneNo==request.TerminalPhoneNo); | |||
SessionInfo sessionInfo = new SessionInfo(); | |||
if (result != null) | |||
{ | |||
sessionInfo.LastActiveTime = result.ActiveTime.ToString("yyyy-MM-dd HH:mm:ss"); | |||
sessionInfo.StartTime = result.StartTime.ToString("yyyy-MM-dd HH:mm:ss"); | |||
sessionInfo.RemoteAddressIP = result.RemoteEndPoint.ToString(); | |||
sessionInfo.TerminalPhoneNo = result.TerminalPhoneNo; | |||
return Task.FromResult(sessionInfo); | |||
} | |||
else | |||
{ | |||
throw new Grpc.Core.RpcException(new Status(StatusCode.FailedPrecondition, $"{request.TerminalPhoneNo} not exists")); | |||
} | |||
} | |||
public override Task<SessionCountReply> GetTcpSessionCount(Empty request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
return Task.FromResult(new SessionCountReply | |||
{ | |||
Count = jT808SessionManager.TcpSessionCount | |||
}); | |||
} | |||
public override Task<SessionRemoveReply> RemoveSessionByTerminalPhoneNo(SessionRemoveRequest request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
try | |||
{ | |||
jT808SessionManager.RemoveByTerminalPhoneNo(request.TerminalPhoneNo); | |||
return Task.FromResult(new SessionRemoveReply { Success = true }); | |||
} | |||
catch (Exception) | |||
{ | |||
return Task.FromResult(new SessionRemoveReply { Success = false }); | |||
} | |||
} | |||
public override Task<UdpSessionInfoReply> GetUdpSessionAll(Empty request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
var result = jT808SessionManager.GetUdpAll(); | |||
UdpSessionInfoReply reply = new UdpSessionInfoReply(); | |||
foreach (var item in result) | |||
{ | |||
reply.UdpSessions.Add(new SessionInfo | |||
{ | |||
LastActiveTime = item.ActiveTime.ToString("yyyy-MM-dd HH:mm:ss"), | |||
StartTime = item.StartTime.ToString("yyyy-MM-dd HH:mm:ss"), | |||
RemoteAddressIP = item.RemoteEndPoint.ToString(), | |||
TerminalPhoneNo = item.TerminalPhoneNo | |||
}); | |||
} | |||
return Task.FromResult(reply); | |||
} | |||
public override async Task<UnificationSendReply> UnificationSend(UnificationSendRequest request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
try | |||
{ | |||
var flag = await jT808SessionManager.TrySendByTerminalPhoneNoAsync(request.TerminalPhoneNo, request.Data.ToByteArray()); | |||
return new UnificationSendReply { Success = flag }; | |||
} | |||
catch (Exception) | |||
{ | |||
return new UnificationSendReply { Success = false }; | |||
} | |||
} | |||
public override Task<TcpAtomicCounterReply> GetTcpAtomicCounter(Empty request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
TcpAtomicCounterReply reply = new TcpAtomicCounterReply(); | |||
reply.MsgFailCount=jT808TcpAtomicCounterService.MsgFailCount; | |||
reply.MsgSuccessCount=jT808TcpAtomicCounterService.MsgSuccessCount; | |||
return Task.FromResult(reply); | |||
} | |||
public override Task<UdpAtomicCounterReply> GetUdpAtomicCounter(Empty request, ServerCallContext context) | |||
{ | |||
Auth(context); | |||
UdpAtomicCounterReply reply = new UdpAtomicCounterReply(); | |||
reply.MsgFailCount = jT808UdpAtomicCounterService.MsgFailCount; | |||
reply.MsgSuccessCount = jT808UdpAtomicCounterService.MsgSuccessCount; | |||
return Task.FromResult(reply); | |||
} | |||
private void Auth(ServerCallContext context) | |||
{ | |||
Entry tokenEntry = context.RequestHeaders.FirstOrDefault(w => w.Key == "token"); | |||
if (tokenEntry != null) | |||
{ | |||
if(tokenEntry.Value != ConfigurationOptionsMonitor.CurrentValue.WebApiToken) | |||
{ | |||
throw new Grpc.Core.RpcException(new Status(StatusCode.Unauthenticated, "token error")); | |||
} | |||
} | |||
else | |||
{ | |||
throw new Grpc.Core.RpcException(new Status(StatusCode.Unauthenticated,"token empty")); | |||
} | |||
} | |||
} | |||
} |