Added SinaglR
This commit is contained in:
parent
2c38ecb399
commit
9452454b8a
6
.gitignore
vendored
6
.gitignore
vendored
@ -341,3 +341,9 @@ ASALocalRun/
|
||||
|
||||
# Libman.json
|
||||
/wwwroot/lib/*
|
||||
|
||||
SignalRChat/*
|
||||
Server/wwwroot/js/chat.js
|
||||
Server/Hubs/ChatHub.cs
|
||||
Server/Pages/Chat.cshtml
|
||||
Server/Pages/Chat.cshtml.cs
|
@ -19,9 +19,12 @@ completedColumns:
|
||||
- [run-secrets-task](tasks/run-secrets-task.md)
|
||||
- [install-vscode-extensions](tasks/install-vscode-extensions.md)
|
||||
- [run-test-ports](tasks/run-test-ports.md)
|
||||
- [signalr](tasks/signalr.md)
|
||||
- [publish](tasks/publish.md)
|
||||
- [create-as-service](tasks/create-as-service.md)
|
||||
- [setup-nginx](tasks/setup-nginx.md)
|
||||
- [self-signed-certificate](tasks/self-signed-certificate.md)
|
||||
- [roll-out](tasks/roll-out.md)
|
||||
|
||||
## Todo
|
||||
|
||||
|
16
.kanbn/tasks/roll-out.md
Normal file
16
.kanbn/tasks/roll-out.md
Normal file
@ -0,0 +1,16 @@
|
||||
---
|
||||
---
|
||||
|
||||
# roll-out
|
||||
|
||||
- New page in the OI Viewer
|
||||
- Set ubuntu frame to new OI Viewer page
|
||||
- Does it refesh by it self?
|
||||
- EAF needs what for the batch field
|
||||
- SP1 needs to get the barcode from one of the two servers dependent on tool queued by EDA
|
||||
|
||||
## Sub-tasks
|
||||
|
||||
- [ ] phares3757
|
||||
- [ ] unity4
|
||||
- [ ] unity5
|
20
.kanbn/tasks/self-signed-certificate.md
Normal file
20
.kanbn/tasks/self-signed-certificate.md
Normal file
@ -0,0 +1,20 @@
|
||||
---
|
||||
---
|
||||
|
||||
# self-signed-certificate
|
||||
|
||||
```bash
|
||||
sudo -i
|
||||
nano /etc/hosts/
|
||||
apt-get install -y ca-certificates
|
||||
openssl s_client -showcerts -connect DESKTOP-H6JG91B:443 </dev/null 2>/dev/null|openssl x509 -outform PEM >DESKTOP-H6JG91B.crt
|
||||
cp /home/unity5/Barcode-Host/DESKTOP-H6JG91B.crt /usr/local/share/ca-certificates/DESKTOP-H6JG91B.crt
|
||||
update-ca-certificates
|
||||
exit
|
||||
```
|
||||
|
||||
## Sub-tasks
|
||||
|
||||
- [ ] phares3757
|
||||
- [ ] unity4
|
||||
- [x] unity5
|
@ -91,6 +91,11 @@ server {
|
||||
listen [::]:443 default_server ssl http2;
|
||||
location / {
|
||||
proxy_pass http://localhost:5003;
|
||||
proxy_http_version 1.1;
|
||||
proxy_set_header Upgrade $http_upgrade;
|
||||
proxy_set_header Connection $http_connection;
|
||||
proxy_set_header Host $host;
|
||||
proxy_cache_bypass $http_upgrade;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
21
.kanbn/tasks/signalr.md
Normal file
21
.kanbn/tasks/signalr.md
Normal file
@ -0,0 +1,21 @@
|
||||
---
|
||||
---
|
||||
|
||||
# signalr
|
||||
|
||||
- [Framework-4.5.1](https://learn.microsoft.com/en-us/aspnet/signalr/overview/getting-started/tutorial-getting-started-with-signalr?source=recommendations)
|
||||
- [OnNotificationReceivedAsync](https://learn.microsoft.com/en-us/training/modules/aspnet-core-signalr/3-how-signalr-works)
|
||||
|
||||
```bash
|
||||
# https://learn.microsoft.com/en-us/aspnet/core/tutorials/signalr?view=aspnetcore-7.0&tabs=visual-studio-code
|
||||
dotnet tool uninstall -g Microsoft.Web.LibraryManager.Cli
|
||||
dotnet tool install -g Microsoft.Web.LibraryManager.Cli
|
||||
libman install @microsoft/signalr@latest -p unpkg -d wwwroot/js/signalr --files dist/browser/signalr.js --files dist/browser/signalr.js
|
||||
# http://localhost:5003/notification
|
||||
```
|
||||
|
||||
## Sub-tasks
|
||||
|
||||
- [ ] phares3757
|
||||
- [ ] unity4
|
||||
- [ ] unity5
|
2
.vscode/launch.json
vendored
2
.vscode/launch.json
vendored
@ -17,7 +17,7 @@
|
||||
// Enable launching a web browser when ASP.NET Core starts. For more information: https://aka.ms/VSCode-CS-LaunchJson-WebBrowser
|
||||
"serverReadyAction": {
|
||||
"action": "openExternally",
|
||||
"pattern": "\\bNow listening on:\\s+(https?://\\S+)",
|
||||
"pattern": "\\bNow listening on:\\s+(http?://\\S+)",
|
||||
"uriFormat": "%s/swagger/index.html"
|
||||
},
|
||||
"env": {
|
||||
|
@ -1,4 +1,4 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
||||
<PropertyGroup>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
@ -31,7 +31,6 @@
|
||||
<PackageReference Include="Serilog.AspNetCore" Version="7.0.0" />
|
||||
<PackageReference Include="Serilog" Version="2.12.0" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
|
||||
<PackageReference Include="ShellProgressBar" Version="5.2.0" />
|
||||
<PackageReference Include="System.IO.Ports" Version="7.0.0" />
|
||||
<PackageReference Include="System.Text.Json" Version="7.0.2" />
|
||||
</ItemGroup>
|
||||
|
@ -1,9 +1,10 @@
|
||||
using Barcode.Host.Server.Hubs;
|
||||
using Barcode.Host.Server.Models;
|
||||
using Barcode.Host.Shared.DataModels;
|
||||
using Barcode.Host.Shared.KeyboardMouse;
|
||||
using Barcode.Host.Shared.Models;
|
||||
using Barcode.Host.Shared.Models.Stateless;
|
||||
using Microsoft.Extensions.Hosting;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using Microsoft.AspNetCore.SignalR;
|
||||
using Serilog.Context;
|
||||
|
||||
namespace Barcode.Host.Server.HostedService;
|
||||
@ -19,15 +20,18 @@ public class TimedHostedService : IHostedService, IAggregateInputReader, IDispos
|
||||
private readonly ILastScanService _LastScanService;
|
||||
private readonly ILogger<TimedHostedService> _Logger;
|
||||
private readonly ILinuxGroupManager _LinuxGroupManager;
|
||||
private readonly IHubContext<NotificationHub> _HubContext;
|
||||
private readonly Dictionary<string, InputReader> _Readers;
|
||||
private readonly Dictionary<EventCode, char> _CharToEventCodes;
|
||||
private readonly List<(string MethodName, Timer Timer)> _Timers;
|
||||
|
||||
public TimedHostedService(ILogger<TimedHostedService> logger, AppSettings appSettings, ILinuxGroupManager linuxGroupManager, ILastScanService lastScanService, ISerialService serialService)
|
||||
public TimedHostedService(ILogger<TimedHostedService> logger, AppSettings appSettings, ILinuxGroupManager linuxGroupManager, ILastScanService lastScanService, ISerialService serialService, IHubContext<NotificationHub> hubContext)
|
||||
{
|
||||
_Timers = new();
|
||||
_Readers = new();
|
||||
_Logger = logger;
|
||||
_ExecutionCount = 0;
|
||||
_HubContext = hubContext;
|
||||
_CharToEventCodes = new();
|
||||
_AppSettings = appSettings;
|
||||
_SerialService = serialService;
|
||||
@ -35,7 +39,11 @@ public class TimedHostedService : IHostedService, IAggregateInputReader, IDispos
|
||||
_LinuxGroupManager = linuxGroupManager;
|
||||
Timer writeTimer = new(Write, null, Timeout.Infinite, Timeout.Infinite);
|
||||
Timer scanForNewInputsTimer = new(ScanForNewInputs, null, Timeout.Infinite, Timeout.Infinite);
|
||||
_Timers = new List<(string, Timer)>() { (nameof(Write), writeTimer), (nameof(ScanForNewInputs), scanForNewInputsTimer) };
|
||||
if (!string.IsNullOrEmpty(_AppSettings.SerialPortName))
|
||||
_Timers.Add((nameof(Write), writeTimer));
|
||||
#if Linux
|
||||
_Timers.Add((nameof(ScanForNewInputs), scanForNewInputsTimer));
|
||||
#endif
|
||||
}
|
||||
|
||||
public Task StartAsync(CancellationToken stoppingToken)
|
||||
@ -44,7 +52,9 @@ public class TimedHostedService : IHostedService, IAggregateInputReader, IDispos
|
||||
using (LogContext.PushProperty("MethodName", methodName))
|
||||
{
|
||||
_Logger.LogInformation($"Timed Hosted Service: {_AppSettings.GitCommitSeven}:{Environment.ProcessId} running.");
|
||||
_SerialService.Open();
|
||||
if (!string.IsNullOrEmpty(_AppSettings.SerialPortName))
|
||||
_SerialService.Open();
|
||||
#if Linux
|
||||
if (!_LinuxGroupManager.IsInInputGroup().WaitAsync(stoppingToken).Result)
|
||||
{
|
||||
if (string.IsNullOrEmpty(_AppSettings.RootPassword))
|
||||
@ -52,6 +62,7 @@ public class TimedHostedService : IHostedService, IAggregateInputReader, IDispos
|
||||
_ = _LinuxGroupManager.AddUserToInputGroup(_AppSettings.RootPassword);
|
||||
_ = _LinuxGroupManager.RebootSystem(_AppSettings.RootPassword);
|
||||
}
|
||||
#endif
|
||||
List<(EventCode, char)> collection = _LastScanService.IncludeEventCodes();
|
||||
foreach ((EventCode eventCode, char @char) in collection)
|
||||
_CharToEventCodes.Add(eventCode, @char);
|
||||
@ -101,7 +112,19 @@ public class TimedHostedService : IHostedService, IAggregateInputReader, IDispos
|
||||
if (e.TimeSpan.TotalMilliseconds > _AppSettings.ClearLastScanServiceAfter)
|
||||
_LastScanService.Clear();
|
||||
if (e.KeyState == KeyState.KeyUp && _CharToEventCodes.TryGetValue(e.EventCode, out char @char))
|
||||
{
|
||||
_LastScanService.Add(e.EventCode, @char);
|
||||
int count = _LastScanService.GetCount();
|
||||
if (count > _AppSettings.NotifyMinimum)
|
||||
{
|
||||
Result<string> result = _LastScanService.GetScan();
|
||||
if (!string.IsNullOrEmpty(result.Results))
|
||||
{
|
||||
Notification notification = new(e, result.Results);
|
||||
_ = _HubContext.Clients.All.SendAsync(nameof(NotificationHub.NotifyAll), notification);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private Timer? GetTimer(string methodName)
|
||||
@ -157,12 +180,15 @@ public class TimedHostedService : IHostedService, IAggregateInputReader, IDispos
|
||||
|
||||
private void Write()
|
||||
{
|
||||
int count = _LastScanService.GetCount();
|
||||
if (count > 0)
|
||||
if (!string.IsNullOrEmpty(_AppSettings.SerialPortName))
|
||||
{
|
||||
Result<string> result = _LastScanService.GetScan();
|
||||
if (!string.IsNullOrEmpty(result.Results))
|
||||
_SerialService.SerialPortWrite(count, result.Results);
|
||||
int count = _LastScanService.GetCount();
|
||||
if (count > 0)
|
||||
{
|
||||
Result<string> result = _LastScanService.GetScan();
|
||||
if (!string.IsNullOrEmpty(result.Results))
|
||||
_SerialService.SerialPortWrite(count, result.Results);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
12
Server/Hubs/NotificationHub.cs
Normal file
12
Server/Hubs/NotificationHub.cs
Normal file
@ -0,0 +1,12 @@
|
||||
using Barcode.Host.Shared.Models;
|
||||
using Microsoft.AspNetCore.SignalR;
|
||||
|
||||
namespace Barcode.Host.Server.Hubs;
|
||||
|
||||
public class NotificationHub : Hub
|
||||
{
|
||||
|
||||
public async Task NotifyAll(Notification notification) =>
|
||||
await Clients.All.SendAsync(nameof(NotifyAll), notification);
|
||||
|
||||
}
|
@ -12,10 +12,12 @@ public record AppSettings(string BuildNumber,
|
||||
string LinuxDevicePath,
|
||||
bool IsDevelopment,
|
||||
bool IsStaging,
|
||||
int NotifyMinimum,
|
||||
string MockRoot,
|
||||
string MonAResource,
|
||||
string MonASite,
|
||||
string RootPassword,
|
||||
string SerialPortName,
|
||||
string URLs,
|
||||
string WorkingDirectoryName,
|
||||
int WriteToSerialEvery)
|
||||
|
@ -1,4 +1,3 @@
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using System.ComponentModel.DataAnnotations;
|
||||
using System.Text.Json;
|
||||
|
||||
@ -19,10 +18,12 @@ public class AppSettings
|
||||
[Display(Name = "Linux Device Path"), Required] public string LinuxDevicePath { get; set; }
|
||||
[Display(Name = "Is Development"), Required] public bool? IsDevelopment { get; set; }
|
||||
[Display(Name = "Is Staging"), Required] public bool? IsStaging { get; set; }
|
||||
[Display(Name = "Notify Minimum"), Required] public int? NotifyMinimum { get; set; }
|
||||
[Display(Name = "Mock Root"), Required] public string MockRoot { get; set; }
|
||||
[Display(Name = "MonA Resource"), Required] public string MonAResource { get; set; }
|
||||
[Display(Name = "MonA Site"), Required] public string MonASite { get; set; }
|
||||
[Display(Name = "RootPassword"), Required] public string RootPassword { get; set; }
|
||||
[Display(Name = "Serial Port Name"), Required] public string SerialPortName { get; set; }
|
||||
[Display(Name = "URLs"), Required] public string URLs { get; set; }
|
||||
[Display(Name = "Working Directory Name"), Required] public string WorkingDirectoryName { get; set; }
|
||||
[Display(Name = "WriteToSerialEvery"), Required] public int? WriteToSerialEvery { get; set; }
|
||||
@ -60,6 +61,8 @@ public class AppSettings
|
||||
throw new NullReferenceException(nameof(IsDevelopment));
|
||||
if (appSettings.IsStaging is null)
|
||||
throw new NullReferenceException(nameof(IsStaging));
|
||||
if (appSettings.NotifyMinimum is null)
|
||||
throw new NullReferenceException(nameof(NotifyMinimum));
|
||||
if (appSettings.MockRoot is null)
|
||||
throw new NullReferenceException(nameof(MockRoot));
|
||||
if (appSettings.MonAResource is null)
|
||||
@ -68,6 +71,8 @@ public class AppSettings
|
||||
throw new NullReferenceException(nameof(MonASite));
|
||||
if (appSettings.RootPassword is null)
|
||||
throw new NullReferenceException(nameof(RootPassword));
|
||||
if (appSettings.SerialPortName is null)
|
||||
throw new NullReferenceException(nameof(SerialPortName));
|
||||
if (appSettings.URLs is null)
|
||||
throw new NullReferenceException(nameof(URLs));
|
||||
if (appSettings.WorkingDirectoryName is null)
|
||||
@ -85,10 +90,12 @@ public class AppSettings
|
||||
appSettings.LinuxDevicePath,
|
||||
appSettings.IsDevelopment.Value,
|
||||
appSettings.IsStaging.Value,
|
||||
appSettings.NotifyMinimum.Value,
|
||||
appSettings.MockRoot,
|
||||
appSettings.MonAResource,
|
||||
appSettings.MonASite,
|
||||
appSettings.RootPassword,
|
||||
appSettings.SerialPortName,
|
||||
appSettings.URLs,
|
||||
appSettings.WorkingDirectoryName,
|
||||
appSettings.WriteToSerialEvery.Value);
|
||||
|
26
Server/Pages/Error.cshtml
Normal file
26
Server/Pages/Error.cshtml
Normal file
@ -0,0 +1,26 @@
|
||||
@page
|
||||
@model ErrorModel
|
||||
@{
|
||||
ViewData["Title"] = "Error";
|
||||
}
|
||||
|
||||
<h1 class="text-danger">Error.</h1>
|
||||
<h2 class="text-danger">An error occurred while processing your request.</h2>
|
||||
|
||||
@if (Model.ShowRequestId)
|
||||
{
|
||||
<p>
|
||||
<strong>Request ID:</strong> <code>@Model.RequestId</code>
|
||||
</p>
|
||||
}
|
||||
|
||||
<h3>Development Mode</h3>
|
||||
<p>
|
||||
Swapping to the <strong>Development</strong> environment displays detailed information about the error that occurred.
|
||||
</p>
|
||||
<p>
|
||||
<strong>The Development environment shouldn't be enabled for deployed applications.</strong>
|
||||
It can result in displaying sensitive information from exceptions to end users.
|
||||
For local debugging, enable the <strong>Development</strong> environment by setting the <strong>ASPNETCORE_ENVIRONMENT</strong> environment variable to <strong>Development</strong>
|
||||
and restarting the app.
|
||||
</p>
|
23
Server/Pages/Error.cshtml.cs
Normal file
23
Server/Pages/Error.cshtml.cs
Normal file
@ -0,0 +1,23 @@
|
||||
using System.Diagnostics;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.AspNetCore.Mvc.RazorPages;
|
||||
|
||||
namespace Barcode.Host.Server.Pages;
|
||||
|
||||
[ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
|
||||
[IgnoreAntiforgeryToken]
|
||||
public class ErrorModel : PageModel
|
||||
{
|
||||
public string? RequestId { get; set; }
|
||||
|
||||
public bool ShowRequestId => !string.IsNullOrEmpty(RequestId);
|
||||
|
||||
private readonly ILogger<ErrorModel> _Logger;
|
||||
|
||||
public ErrorModel(ILogger<ErrorModel> logger) =>
|
||||
_Logger = logger;
|
||||
|
||||
public void OnGet() =>
|
||||
RequestId = Activity.Current?.Id ?? HttpContext.TraceIdentifier;
|
||||
}
|
||||
|
10
Server/Pages/Notification.cshtml
Normal file
10
Server/Pages/Notification.cshtml
Normal file
@ -0,0 +1,10 @@
|
||||
@page
|
||||
<div class="container">
|
||||
<div class="row p-1">
|
||||
<div class="col-6">
|
||||
<h1 id="data" style="text-align:center"></h1>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<script src="~/js/signalr/dist/browser/signalr.js"></script>
|
||||
<script src="~/js/notification.js"></script>
|
16
Server/Pages/Notification.cshtml.cs
Normal file
16
Server/Pages/Notification.cshtml.cs
Normal file
@ -0,0 +1,16 @@
|
||||
using Microsoft.AspNetCore.Mvc.RazorPages;
|
||||
|
||||
namespace Barcode.Host.Server.Pages;
|
||||
|
||||
public class NotificationModel : PageModel
|
||||
{
|
||||
private readonly ILogger<NotificationModel> _Logger;
|
||||
|
||||
public NotificationModel(ILogger<NotificationModel> logger) =>
|
||||
_Logger = logger;
|
||||
|
||||
public void OnGet()
|
||||
{
|
||||
|
||||
}
|
||||
}
|
20
Server/Pages/Shared/_Layout.cshtml
Normal file
20
Server/Pages/Shared/_Layout.cshtml
Normal file
@ -0,0 +1,20 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Barcode Host</title>
|
||||
<link rel="stylesheet" href="~/css/site.css" asp-append-version="true" />
|
||||
</head>
|
||||
<body>
|
||||
<div class="container">
|
||||
<main role="main" class="pb-3">
|
||||
@RenderBody()
|
||||
</main>
|
||||
</div>
|
||||
|
||||
<script src="~/js/site.js" asp-append-version="true"></script>
|
||||
|
||||
@await RenderSectionAsync("Scripts", required: false)
|
||||
</body>
|
||||
</html>
|
48
Server/Pages/Shared/_Layout.cshtml.css
Normal file
48
Server/Pages/Shared/_Layout.cshtml.css
Normal file
@ -0,0 +1,48 @@
|
||||
/* Please see documentation at https://docs.microsoft.com/aspnet/core/client-side/bundling-and-minification
|
||||
for details on configuring this project to bundle and minify static web assets. */
|
||||
|
||||
a.navbar-brand {
|
||||
white-space: normal;
|
||||
text-align: center;
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
a {
|
||||
color: #0077cc;
|
||||
}
|
||||
|
||||
.btn-primary {
|
||||
color: #fff;
|
||||
background-color: #1b6ec2;
|
||||
border-color: #1861ac;
|
||||
}
|
||||
|
||||
.nav-pills .nav-link.active, .nav-pills .show > .nav-link {
|
||||
color: #fff;
|
||||
background-color: #1b6ec2;
|
||||
border-color: #1861ac;
|
||||
}
|
||||
|
||||
.border-top {
|
||||
border-top: 1px solid #e5e5e5;
|
||||
}
|
||||
.border-bottom {
|
||||
border-bottom: 1px solid #e5e5e5;
|
||||
}
|
||||
|
||||
.box-shadow {
|
||||
box-shadow: 0 .25rem .75rem rgba(0, 0, 0, .05);
|
||||
}
|
||||
|
||||
button.accept-policy {
|
||||
font-size: 1rem;
|
||||
line-height: inherit;
|
||||
}
|
||||
|
||||
.footer {
|
||||
position: absolute;
|
||||
bottom: 0;
|
||||
width: 100%;
|
||||
white-space: nowrap;
|
||||
line-height: 60px;
|
||||
}
|
2
Server/Pages/Shared/_ValidationScriptsPartial.cshtml
Normal file
2
Server/Pages/Shared/_ValidationScriptsPartial.cshtml
Normal file
@ -0,0 +1,2 @@
|
||||
<script src="~/lib/jquery-validation/dist/jquery.validate.min.js"></script>
|
||||
<script src="~/lib/jquery-validation-unobtrusive/jquery.validate.unobtrusive.min.js"></script>
|
3
Server/Pages/_ViewImports.cshtml
Normal file
3
Server/Pages/_ViewImports.cshtml
Normal file
@ -0,0 +1,3 @@
|
||||
@using Barcode.Host.Server
|
||||
@namespace Barcode.Host.Server.Pages
|
||||
@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers
|
3
Server/Pages/_ViewStart.cshtml
Normal file
3
Server/Pages/_ViewStart.cshtml
Normal file
@ -0,0 +1,3 @@
|
||||
@{
|
||||
Layout = "_Layout";
|
||||
}
|
@ -1,12 +1,9 @@
|
||||
using Barcode.Host.Server.HostedService;
|
||||
using Barcode.Host.Server.Hubs;
|
||||
using Barcode.Host.Server.Models;
|
||||
using Barcode.Host.Server.Services;
|
||||
using Barcode.Host.Shared.Models;
|
||||
using Barcode.Host.Shared.Models.Stateless;
|
||||
using Microsoft.AspNetCore.Builder;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using Microsoft.Extensions.Hosting;
|
||||
using Serilog;
|
||||
using System.Reflection;
|
||||
|
||||
@ -48,7 +45,7 @@ public class Program
|
||||
_ = ConfigurationLoggerConfigurationExtensions.Configuration(loggerConfiguration.ReadFrom, webApplicationBuilder.Configuration);
|
||||
_ = SerilogHostBuilderExtensions.UseSerilog(webApplicationBuilder.Host);
|
||||
Log.Logger = loggerConfiguration.CreateLogger();
|
||||
ILogger log = Log.ForContext<Program>();
|
||||
Serilog.ILogger log = Log.ForContext<Program>();
|
||||
try
|
||||
{
|
||||
if (appSettings.IsStaging && appSettings.IsDevelopment)
|
||||
@ -57,6 +54,8 @@ public class Program
|
||||
throw new NotSupportedException("Please check appsettings file(s)!");
|
||||
if (appSettings.IsDevelopment != webApplicationBuilder.Environment.IsDevelopment())
|
||||
throw new NotSupportedException("Please check appsettings file(s)!");
|
||||
_ = webApplicationBuilder.Services.AddRazorPages();
|
||||
_ = webApplicationBuilder.Services.AddSignalR();
|
||||
_ = webApplicationBuilder.Services.AddControllersWithViews();
|
||||
_ = webApplicationBuilder.Services.AddSingleton(_ => appSettings);
|
||||
_ = webApplicationBuilder.Services.AddSingleton<ISerialService, SerialService>();
|
||||
@ -76,11 +75,13 @@ public class Program
|
||||
_ = webApplication.UseExceptionHandler("/Error");
|
||||
_ = webApplication.UseHsts();
|
||||
}
|
||||
_ = webApplication.UseCors(corsPolicyBuilder => corsPolicyBuilder.AllowAnyOrigin().AllowAnyHeader().AllowAnyMethod());
|
||||
_ = webApplication.Lifetime.ApplicationStopped.Register(Log.CloseAndFlush);
|
||||
_ = webApplication.UseFileServer(enableDirectoryBrowsing: true);
|
||||
_ = webApplication.UseStaticFiles();
|
||||
_ = webApplication.UseRouting();
|
||||
_ = webApplication.UseAuthorization();
|
||||
_ = webApplication.MapControllers();
|
||||
_ = webApplication.MapRazorPages();
|
||||
_ = webApplication.MapHub<NotificationHub>($"/{nameof(NotificationHub)}");
|
||||
log.Information("Starting Web Application");
|
||||
webApplication.Run();
|
||||
return 0;
|
||||
|
@ -4,7 +4,7 @@
|
||||
"commandName": "Project",
|
||||
"dotnetRunMessages": true,
|
||||
"launchBrowser": false,
|
||||
"applicationUrl": "http://localhost:5126",
|
||||
"applicationUrl": "http://localhost:5003",
|
||||
"environmentVariables": {
|
||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
||||
}
|
||||
@ -13,7 +13,7 @@
|
||||
"commandName": "Project",
|
||||
"dotnetRunMessages": true,
|
||||
"launchBrowser": false,
|
||||
"applicationUrl": "https://localhost:7130;http://localhost:5126",
|
||||
"applicationUrl": "https://localhost:5004;http://localhost:5003",
|
||||
"environmentVariables": {
|
||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
||||
}
|
||||
@ -22,7 +22,7 @@
|
||||
"commandName": "Project",
|
||||
"dotnetRunMessages": true,
|
||||
"launchBrowser": false,
|
||||
"applicationUrl": "https://localhost:7130;http://localhost:5126",
|
||||
"applicationUrl": "https://localhost:5004;http://localhost:5003",
|
||||
"environmentVariables": {
|
||||
"ASPNETCORE_ENVIRONMENT": "Production"
|
||||
}
|
||||
|
@ -9,20 +9,23 @@ public class SerialService : ISerialService
|
||||
|
||||
private string _LastRaw;
|
||||
private readonly AppSettings _AppSettings;
|
||||
private readonly System.IO.Ports.SerialPort _SerialPort;
|
||||
private readonly System.IO.Ports.SerialPort? _SerialPort;
|
||||
|
||||
public SerialService(AppSettings appSettings)
|
||||
{
|
||||
_LastRaw = string.Empty;
|
||||
_AppSettings = appSettings;
|
||||
_SerialPort = new("/dev/ttyUSB0", 9600) { ReadTimeout = 2 };
|
||||
if (string.IsNullOrEmpty(appSettings.SerialPortName))
|
||||
_SerialPort = null;
|
||||
else
|
||||
_SerialPort = new(appSettings.SerialPortName, 9600) { ReadTimeout = 2 };
|
||||
}
|
||||
|
||||
void ISerialService.Open() =>
|
||||
_SerialPort.Open();
|
||||
_SerialPort?.Open();
|
||||
|
||||
void ISerialService.Close() =>
|
||||
_SerialPort.Close();
|
||||
_SerialPort?.Close();
|
||||
|
||||
void ISerialService.SerialPortWrite(int count, string raw)
|
||||
{
|
||||
@ -36,7 +39,7 @@ public class SerialService : ISerialService
|
||||
else
|
||||
message = $" {raw}";
|
||||
byte[] bytes = Encoding.ASCII.GetBytes(message);
|
||||
_SerialPort.Write(bytes, 0, bytes.Length);
|
||||
_SerialPort?.Write(bytes, 0, bytes.Length);
|
||||
_LastRaw = raw;
|
||||
}
|
||||
}
|
||||
|
@ -18,9 +18,11 @@
|
||||
},
|
||||
"IsDevelopment": false,
|
||||
"IsStaging": false,
|
||||
"NotifyMinimum": 3,
|
||||
"MockRoot": "",
|
||||
"MonAResource": "OI_Metrology_Viewer_EC",
|
||||
"MonASite": "auc",
|
||||
"SerialPortName": "/dev/ttyUSB0",
|
||||
"Serilog": {
|
||||
"Using": [
|
||||
"Serilog.Sinks.Console",
|
||||
|
22
Server/wwwroot/css/site.css
Normal file
22
Server/wwwroot/css/site.css
Normal file
@ -0,0 +1,22 @@
|
||||
html {
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
@media (min-width: 768px) {
|
||||
html {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
.btn:focus, .btn:active:focus, .btn-link.nav-link:focus, .form-control:focus, .form-check-input:focus {
|
||||
box-shadow: 0 0 0 0.1rem white, 0 0 0 0.25rem #258cfb;
|
||||
}
|
||||
|
||||
html {
|
||||
position: relative;
|
||||
min-height: 100%;
|
||||
}
|
||||
|
||||
body {
|
||||
margin-bottom: 60px;
|
||||
}
|
BIN
Server/wwwroot/favicon.ico
Normal file
BIN
Server/wwwroot/favicon.ico
Normal file
Binary file not shown.
After Width: | Height: | Size: 5.3 KiB |
13
Server/wwwroot/js/notification.js
Normal file
13
Server/wwwroot/js/notification.js
Normal file
@ -0,0 +1,13 @@
|
||||
"use strict";
|
||||
|
||||
var connection = new signalR.HubConnectionBuilder().withUrl("/NotificationHub").build();
|
||||
|
||||
connection.on("NotifyAll", function (data) {
|
||||
var message = `${data.keyPressEvent.dateTime} - [${data.lastScanServiceResultValue}]`;
|
||||
document.getElementById("data").innerText = message;
|
||||
});
|
||||
|
||||
connection.start().then(function () {
|
||||
}).catch(function (err) {
|
||||
return console.error(err.toString());
|
||||
});
|
3190
Server/wwwroot/js/signalr/dist/browser/signalr.js
vendored
Normal file
3190
Server/wwwroot/js/signalr/dist/browser/signalr.js
vendored
Normal file
File diff suppressed because it is too large
Load Diff
1
Server/wwwroot/js/site.js
Normal file
1
Server/wwwroot/js/site.js
Normal file
@ -0,0 +1 @@
|
||||
|
@ -115,9 +115,10 @@ public class InputReader : IDisposable
|
||||
{
|
||||
short code = GetCode();
|
||||
int value = GetValue();
|
||||
DateTime dateTime = DateTime.Now;
|
||||
KeyState keyState = (KeyState)value;
|
||||
EventCode eventCode = (EventCode)code;
|
||||
KeyPressEvent keyPressEvent = new(eventCode, keyState, new TimeSpan(DateTime.Now.Ticks - _Ticks));
|
||||
KeyPressEvent keyPressEvent = new(dateTime, eventCode, keyState, new TimeSpan(dateTime.Ticks - _Ticks));
|
||||
OnKeyPress?.Invoke(keyPressEvent);
|
||||
}
|
||||
|
||||
|
@ -2,13 +2,14 @@ namespace Barcode.Host.Shared.KeyboardMouse;
|
||||
|
||||
public readonly struct KeyPressEvent
|
||||
{
|
||||
|
||||
public DateTime DateTime { get; init; }
|
||||
public EventCode EventCode { get; init; }
|
||||
public KeyState KeyState { get; init; }
|
||||
public TimeSpan TimeSpan { get; init; }
|
||||
|
||||
public KeyPressEvent(EventCode eventCode, KeyState keyState, TimeSpan timeSpan)
|
||||
public KeyPressEvent(DateTime dateTime, EventCode eventCode, KeyState keyState, TimeSpan timeSpan)
|
||||
{
|
||||
DateTime = dateTime;
|
||||
EventCode = eventCode;
|
||||
KeyState = keyState;
|
||||
TimeSpan = timeSpan;
|
||||
|
5
Shared/Models/Notification.cs
Normal file
5
Shared/Models/Notification.cs
Normal file
@ -0,0 +1,5 @@
|
||||
using Barcode.Host.Shared.KeyboardMouse;
|
||||
|
||||
namespace Barcode.Host.Shared.Models;
|
||||
|
||||
public record Notification(KeyPressEvent KeyPressEvent, string LastScanServiceResultValue);
|
Loading…
x
Reference in New Issue
Block a user