store temp changes

This commit is contained in:
Michal Buzik 2026-07-02 16:45:57 +02:00
parent 1fddd87f2b
commit 7129960b12
73 changed files with 724 additions and 159939 deletions

View File

@ -11,7 +11,27 @@
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Xylem.Common.CommonCore" publicKeyToken="null" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.17954" newVersion="2.8.18.17954" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.11157" newVersion="2.8.18.11157" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Xylem.Common.CommonCore.Configuration" publicKeyToken="null" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.11158" newVersion="2.8.18.11158" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Xylem.Common.Hardware.Interfaces.Ports.PortCore" publicKeyToken="null" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.11158" newVersion="2.8.18.11158" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Xylem.Common.Logic.SoftwareAccessHelper" publicKeyToken="null" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.11158" newVersion="2.8.18.11158" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Xylem.Common.Utils.Crc16Ccitt" publicKeyToken="null" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.11158" newVersion="2.8.18.11158" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Xylem.Common.Utils.Logging" publicKeyToken="null" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.11158" newVersion="2.8.18.11158" />
</dependentAssembly>
</assemblyBinding>
</runtime>

View File

@ -42,7 +42,7 @@
<HintPath>..\packages\Common\Logic.ProductionToProductMapper.dll</HintPath>
</Reference>
<Reference Include="Newtonsoft.Json, Version=13.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
<HintPath>..\packages\Newtonsoft.Json.13.0.3\lib\net45\Newtonsoft.Json.dll</HintPath>
<HintPath>..\packages\Newtonsoft.Json.13.0.4\lib\net45\Newtonsoft.Json.dll</HintPath>
</Reference>
<Reference Include="NLog, Version=5.0.0.0, Culture=neutral, PublicKeyToken=5120e14c03d0593c, processorArchitecture=MSIL">
<HintPath>..\packages\NLog.5.2.2\lib\net46\NLog.dll</HintPath>

View File

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="Newtonsoft.Json" version="13.0.3" targetFramework="net48" />
<package id="Newtonsoft.Json" version="13.0.4" targetFramework="net48" />
<package id="NLog" version="5.2.2" targetFramework="net48" />
</packages>

View File

@ -23,7 +23,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Newtonsoft.Json" Version="12.0.2" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.4" />
<PackageReference Include="System.IO.Ports" Version="10.0.0-rc.1.25451.107" />
<PackageReference Include="System.Security.Cryptography.Cng" Version="5.0.0" />
<PackageReference Include="System.Threading" Version="4.3.0" />

View File

@ -32,8 +32,8 @@
<PlatformTarget>x86</PlatformTarget>
</PropertyGroup>
<ItemGroup>
<Reference Include="Newtonsoft.Json, Version=12.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
<HintPath>..\packages\Newtonsoft.Json.12.0.2\lib\net45\Newtonsoft.Json.dll</HintPath>
<Reference Include="Newtonsoft.Json, Version=13.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
<HintPath>..\packages\Newtonsoft.Json.13.0.4\lib\net45\Newtonsoft.Json.dll</HintPath>
</Reference>
<Reference Include="System" />
<Reference Include="System.Core" />

View File

@ -1,4 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="Newtonsoft.Json" version="12.0.2" targetFramework="net472" />
<package id="Newtonsoft.Json" version="13.0.4" targetFramework="net48" />
</packages>

View File

@ -54,7 +54,8 @@ namespace TBF.Rig.Network.Camera.CJMS11
const string ClpPassword = "C1ern4V0d4";
private readonly SemaphoreSlim cameraReadLock = new SemaphoreSlim(1, 1);
private readonly SemaphoreSlim cameraWriteLock = new SemaphoreSlim(1, 1);
///
/// Properties
@ -201,26 +202,15 @@ namespace TBF.Rig.Network.Camera.CJMS11
/// Detect a camera
CameraDetectionResult cameraDetectionResult = null;
var detectJmsCamera = DetectJMSCamera();
var timeoutTask = Task.Delay(TimeSpan.FromSeconds(2));
//No Test
var completedTask = Task.WhenAny(detectJmsCamera, timeoutTask).Result;
if (completedTask == timeoutTask)
{
cameraDetectionResult = new CameraDetectionResult();
cameraDetectionResult.IsDetected = false;
}
cameraDetectionResult = DetectJMSCamera()
.GetAwaiter()
.GetResult();
//test
// var detectJmsCamera1 = DetectJMSCamera("192.168.0.170",32456);
// var detectJmsCamera2 = DetectJMSCamera("192.168.0.168",32456);
// Task.WaitAll(detectJmsCamera, detectJmsCamera1, detectJmsCamera2);
if (cameraDetectionResult == null)
{
cameraDetectionResult = detectJmsCamera.Result;
}
if (CameraCfg.DebugLevel == DebugMode.AutoDetect)
{
@ -424,68 +414,101 @@ namespace TBF.Rig.Network.Camera.CJMS11
using (NetworkStream stream = cameraTcpClient.GetStream())
using (StreamWriter writer = new StreamWriter(stream, Encoding.ASCII) { AutoFlush = true })
using (StreamReader reader = new StreamReader(stream, Encoding.ASCII))
//using (StreamReader reader = new StreamReader(stream, Encoding.ASCII))
{
stream.ReadTimeout = 1000;
// Send command
DateTime detectionStart = DateTime.Now;
DateTime detectionStartConnect = DateTime.Now;
// create config and send
string message = getConfigMessage();
JmsPacket answer = SendCommandAndWaitToAnswer(writer, reader, CommandM.type_camera_,message);
if (answer == null || answer.JmsMessage.Status != MessageStatus.ACK)
// Send command
DateTime detectionStart = DateTime.Now;
JmsPacket answer = null;
try
{
log.Error(answer);
}
//Prepare camera
JmsPacket answerPrepare = SendCommandAndWaitToAnswer(writer, reader, CommandM.prepare_camera_);
if (answerPrepare == null || answerPrepare.JmsMessage.Status != MessageStatus.ACK)
{
if (!(answerPrepare != null && answerPrepare.JmsMessage.Status == MessageStatus.NACK &&
answerPrepare.JmsMessage.Payload == "OPENED")) //correct if NACK & OPENED
//await ClearPendingResponsesAsync(reader);
// create config and send
string message = getConfigMessage();
answer = await SendCommandAndWaitToAnswerAsync(writer, stream, CommandM.type_camera_, message, 5000);
if (answer == null || answer.JmsMessage.Status != MessageStatus.ACK)
{
log.Error(answerPrepare);
log.Error(answer);
}
}
catch (Exception exc)
{
log.Error(exc.Message);
}
JmsPacket answerCfg = null;
try
{
//await ClearPendingResponsesAsync(reader);
//Prepare camera
JmsPacket answerPrepare = await SendCommandAndWaitToAnswerAsync(writer, stream, CommandM.prepare_camera_);
if (answerPrepare == null || answerPrepare.JmsMessage.Status != MessageStatus.ACK)
{
if (!(answerPrepare != null &&
answerPrepare.JmsMessage.Status == MessageStatus.NACK &&
answerPrepare.JmsMessage.Payload == "OPENED")) //correct if NACK & OPENED
{
log.Error(answerPrepare);
}
else
{
await SendCommandAndWaitToAnswerAsync(writer, stream, CommandM.close_);
var sendCommandAndWaitToAnswer = await SendCommandAndWaitToAnswerAsync(writer, stream, CommandM.prepare_camera_);
if (sendCommandAndWaitToAnswer == null ||
sendCommandAndWaitToAnswer.JmsMessage.Status == MessageStatus.NACK) //correct if NACK & OPENED
{
log.Error("Restart close, prepare camera not successfully! see: " +
answerPrepare);
}
}
}
//Status
JmsPacket answerStatus = await SendCommandAndWaitToAnswerAsync(writer, stream, CommandM.status_);
if (answerStatus == null || answerStatus.JmsMessage.Status != MessageStatus.ACK)
{
log.Error(answerStatus);
}
//Get config
answerCfg = await SendCommandAndWaitToAnswerAsync(writer, stream, CommandM.get_cfg_);
if (answerCfg == null || answerCfg.JmsMessage.Status != MessageStatus.ACK)
{
log.Error(answerCfg);
}
else
{
SendCommandAndWaitToAnswer(writer, reader, CommandM.close_);
var sendCommandAndWaitToAnswer = SendCommandAndWaitToAnswer(writer, reader, CommandM.prepare_camera_);
if (sendCommandAndWaitToAnswer == null || sendCommandAndWaitToAnswer.JmsMessage.Status == MessageStatus.NACK) //correct if NACK & OPENED
{
log.Error("Restart close, prepare camera not successfully! see: " + answerPrepare);
}
result.IpAddress = IPAddress.Parse(ipAddressParam);
}
}
//Status
JmsPacket answerStatus = SendCommandAndWaitToAnswer(writer, reader, CommandM.status_);
if (answerStatus == null || answerStatus.JmsMessage.Status != MessageStatus.ACK)
catch (Exception exc)
{
log.Error(answerStatus);
}
//Get config
JmsPacket answerCfg = SendCommandAndWaitToAnswer(writer, reader, CommandM.get_cfg_);
if (answerCfg == null || answerCfg.JmsMessage.Status != MessageStatus.ACK)
{
log.Error(answerCfg);
}else{
result.IpAddress = IPAddress.Parse(ipAddressParam);
log.Error(exc.Message);
}
result.Duration_ms = (DateTime.Now - detectionStart).TotalMilliseconds;
result.Hardware = string.Empty;
result.Revision = string.Empty;
result.Serial = string.Empty;
result.SdCardVersion = string.Empty;
string origin = answerCfg != null ? answerCfg.MessageOrigin : "no cfg response";
string msg = string.Format("Camera {0} detected in {1} ms: HWAddress={2} IPAddress={3} {4}",
CameraCfg.Name,
result.Duration_ms,
CameraCfg.HardwareAddress,
this.ipAddress == null ? "not detected" : this.ipAddress.ToString(),
answerCfg.MessageOrigin);
origin);
log.Debug(msg);
Console.WriteLine(msg);
@ -526,6 +549,31 @@ namespace TBF.Rig.Network.Camera.CJMS11
return result; /// No camera detected
}
private async Task ClearPendingResponsesAsync(StreamReader reader)
{
await cameraReadLock.WaitAsync();
try
{
while (reader.Peek() >= 0)
{
string oldLine = reader.ReadLine();
log.Debug("Discarded old camera response: " + oldLine);
}
}
catch (IOException)
{
}
catch (Exception exc)
{
log.Warn("ClearPendingResponses failed: " + exc.Message);
}
finally
{
cameraReadLock.Release();
}
}
class SensorConfig{
public string type { get; set; } = "all";
public int width { get; set; } = 640;
@ -1071,283 +1119,88 @@ namespace TBF.Rig.Network.Camera.CJMS11
public void StartGrabImageListener()
{
grabImageListenerThread = new Thread(GrabImageListener);
grabImageListenerThread = new Thread(() =>
{
GrabImageListenerAsync().GetAwaiter().GetResult();
});
grabImageListenerThread.Start();
}
void GrabImageListener()
private async Task EstablishCameraConnectionAsync(
TcpClient client,
string ip,
int port,
int timeoutMs)
{
Task connectTask = client.ConnectAsync(ip, port);
Task timeoutTask = Task.Delay(timeoutMs);
Task completedTask = await Task.WhenAny(connectTask, timeoutTask);
if (completedTask == timeoutTask)
throw new TimeoutException($"Connection attempt timed out after {timeoutMs} ms.");
await connectTask;
}
private async Task GrabImageListenerAsync()
{
using (this.cameraTcpClient = new TcpClient())
{
try
{
EstablishCameraConnection(ref this.cameraTcpClient, CameraCfg.IPAddressCJMS, iPort);
log.Info(string.Format("Camera connected to server {0}:{1}.", CameraCfg.IPAddressCJMS, iPort));
ipAddress = IPAddress.Parse(CameraCfg.IPAddressCJMS);
// Get network stream
await EstablishCameraConnectionAsync(this.cameraTcpClient, CameraCfg.IPAddressCJMS, iPort, 1000);
using (cameraStream = this.cameraTcpClient.GetStream())
using (cameraWriter = new StreamWriter(cameraStream, Encoding.ASCII) { AutoFlush = true })
using (cameraReader = new StreamReader(cameraStream, Encoding.ASCII))
//using (cameraReader = new StreamReader(cameraStream, Encoding.ASCII))
{
cameraStream.ReadTimeout = 1000;
try
{
SendCommand(CommandM.prepare_camera_);
}
catch (Exception exc)
{
log.Error($"Initialisation of connection readers failed: {exc.Message}");
return;
}
await SendCommandAndWaitToAnswerAsync(cameraWriter, cameraStream, CommandM.prepare_camera_, null, 3000);
await SendCommandAsync(cameraWriter, CommandM.grab_image_);
stopGrabImageListenerFlag = false;
int iCountOf_NACK = 0;
int iActualImageIndex = 0;
SendCommand(CommandM.grab_image_);
while (!stopGrabImageListenerFlag)
{
try
string responseAnswer = await ReadCameraLineAsync(cameraStream, 3000);
if (string.IsNullOrWhiteSpace(responseAnswer))
continue;
JmsPacket newPacket = new JmsPacket(responseAnswer);
if (newPacket.JmsMessage.Command == CommandM.grab_image_ &&
newPacket.JmsMessage.Status == MessageStatus.ACK)
{
ParsedImage parsedImage = newPacket.JmsMessage.getImage();
Task<string> responseAnswerTask = cameraReader.ReadLineAsync();
var timeoutAnswerTask = Task.Delay(TimeSpan.FromSeconds(1));
var completedAnswerTask = Task.WhenAny(responseAnswerTask, timeoutAnswerTask).Result;
if (completedAnswerTask == timeoutAnswerTask)
if (parsedImage.Encoding == ImageType.BASE_64)
{
throw new TimeoutException("Answer response attempt timed out after 1 second.");
Image image = parsedImage.Image;
OnImageReceived(this, this.cameraIdx, image, RoiConfiguration.ImageRotation);
stopGrabImageListenerFlag = true;
}
string responseAnswer = responseAnswerTask.Result;
if (responseAnswer.Length > 0)
{
/// Process the packet
JmsPacket newPacket = new JmsPacket(responseAnswer);
if (newPacket.JmsMessage.Status != MessageStatus.ACK)
{
if (iCountOf_NACK < 5)
{
iCountOf_NACK++;
continue;
}
log.ErrorFormat("Error occured more as 5 time in GrabImageListener: {0}",
newPacket.JmsMessage.Status);
stopGrabImageListenerFlag = true; // mam obrazok ukoncim a zavriem thread
break;
}
else
{
switch (newPacket.JmsMessage.Command)
{
case CommandM.grab_image_:
ParsedImage parsedImage = newPacket.JmsMessage.getImage();
if (parsedImage.Encoding == ImageType.BASE_64)
{
Image image = parsedImage.Image;
if (showOverlayRect && overlayRect != null && overlayThickness > 0)
{
int penWidth = 1;
Pen pen = new Pen(Color.Green, penWidth);
using (var grph = Graphics.FromImage(image))
{
if (penWidth != overlayThickness)
{
penWidth = overlayThickness;
pen = new Pen(Color.Green, penWidth);
}
grph.DrawRectangle(pen, overlayRect);
}
}
OnImageReceived(this, this.cameraIdx, image, RoiConfiguration.ImageRotation);
iActualImageIndex++;
if (iActualImageIndex >= RoiConfiguration.ImageOpacity.Count)
{
stopGrabImageListenerFlag =
true; // mam obrazok ukoncim a zavriem thread
}
}
break;
}
}
}
}
catch (Exception exc)
{
log.Error($"Grab Image - Hardware Addr: {CameraCfg.HardwareAddress} Camera IP: {CameraCfg.IPAddressCJMS}, Port: {iPort} Exception in MJpeg RTP listener thread: { exc.Message}");
}
}
stopGrabImageListenerFlag = false;
SendCommandAndWaitToAnswer(cameraWriter, cameraReader, CommandM.close_);
SendCommandAndWaitToAnswer(cameraWriter, cameraReader, CommandM.disconnect_);
CloseCameraResources();
return;
await SendCommandAndWaitToAnswerAsync(cameraWriter, cameraStream, CommandM.close_, null, 2000);
await SendCommandAndWaitToAnswerAsync(cameraWriter, cameraStream, CommandM.disconnect_, null, 2000);
}
}catch(Exception exc)
}
catch (Exception exc)
{
log.Error($"Grab Image - Hardware Addr: {CameraCfg.HardwareAddress} Camera IP: {CameraCfg.IPAddressCJMS}, Port: {iPort} exception: {exc.Message}");
log.Error($"Grab Image exception: {exc.Message}");
UiBridge.Bridge.OnImage(this.cameraIdx, null);
}
finally
{
CloseCameraResources();
}
}
}
void SendImageListener()
{
using (this.cameraTcpClient = new TcpClient())
{
try
{
EstablishCameraConnection(ref this.cameraTcpClient, CameraCfg.IPAddressCJMS, iPort);
log.Info(string.Format("Camera connected to server {0}:{1}.", CameraCfg.IPAddressCJMS, iPort));
ipAddress = IPAddress.Parse(CameraCfg.IPAddressCJMS);
// Get network stream
using (cameraStream = this.cameraTcpClient.GetStream())
using (cameraWriter = new StreamWriter(cameraStream, Encoding.ASCII) { AutoFlush = true })
using (cameraReader = new StreamReader(cameraStream, Encoding.ASCII))
{
cameraStream.ReadTimeout = 1000;
try
{
SendCommand(CommandM.prepare_camera_);
}
catch (Exception exc)
{
log.Error($"Initialisation of connection readers failed: {exc.Message}");
return;
}
stopGrabImageListenerFlag = false;
int iCountOf_NACK = 0;
int iActualImageIndex = 0;
//TODO BUMI send grab image or send - based on count of images - but must work similary
if (RoiConfiguration.ImageOpacity.Count <= 1)
{
SendCommand(CommandM.grab_image_);
}
else
{
SendCommand(CommandM.send_);
}
while (!stopGrabImageListenerFlag)
{
try
{
Task<string> responseAnswerTask = cameraReader.ReadLineAsync();
var timeoutAnswerTask = Task.Delay(TimeSpan.FromSeconds(1));
var completedAnswerTask = Task.WhenAny(responseAnswerTask, timeoutAnswerTask).Result;
if (completedAnswerTask == timeoutAnswerTask)
{
throw new TimeoutException("Answer response attempt timed out after 1 second.");
}
string responseAnswer = responseAnswerTask.Result;
if (responseAnswer.Length > 0)
{
/// Process the packet
JmsPacket newPacket = new JmsPacket(responseAnswer);
if (newPacket.JmsMessage.Status != MessageStatus.ACK)
{
if (iCountOf_NACK < 5)
{
iCountOf_NACK++;
continue;
}
log.ErrorFormat("Error occured more as 5 time in GrabImageListener: {0}",
newPacket.JmsMessage.Status);
stopGrabImageListenerFlag = true; // mam obrazok ukoncim a zavriem thread
break;
}
else
{
switch (newPacket.JmsMessage.Command)
{
case CommandM.send_:
case CommandM.grab_image_:
ParsedImage parsedImage = newPacket.JmsMessage.getImage();
if (parsedImage.Encoding == ImageType.BASE_64)
{
Image image = parsedImage.Image;
if (showOverlayRect && overlayRect != null && overlayThickness > 0)
{
int penWidth = 1;
Pen pen = new Pen(Color.Green, penWidth);
using (var grph = Graphics.FromImage(image))
{
if (penWidth != overlayThickness)
{
penWidth = overlayThickness;
pen = new Pen(Color.Green, penWidth);
}
grph.DrawRectangle(pen, overlayRect);
}
}
OnImageReceived(this, this.cameraIdx, image, RoiConfiguration.ImageRotation,iActualImageIndex,RoiConfiguration.ImageOpacity.Count);
iActualImageIndex++;
if (iActualImageIndex >= RoiConfiguration.ImageOpacity.Count)
{
stopGrabImageListenerFlag =
true; // mam obrazok ukoncim a zavriem thread
}
}
break;
}
}
}
}
catch (Exception exc)
{
log.Error($"Grab Image - Hardware Addr: {CameraCfg.HardwareAddress} Camera IP: {CameraCfg.IPAddressCJMS}, Port: {iPort} Exception in MJpeg RTP listener thread: { exc.Message}");
}
}
stopGrabImageListenerFlag = false;
SendCommandAndWaitToAnswer(cameraWriter, cameraReader, CommandM.close_);
SendCommandAndWaitToAnswer(cameraWriter, cameraReader, CommandM.disconnect_);
CloseCameraResources();
return;
}
}catch(Exception exc)
{
log.Error($"Grab Image - Hardware Addr: {CameraCfg.HardwareAddress} Camera IP: {CameraCfg.IPAddressCJMS}, Port: {iPort} exception: {exc.Message}");
UiBridge.Bridge.OnImage(this.cameraIdx, null);
}
}
}
private void CloseCameraResources()
{
@ -1395,7 +1248,7 @@ namespace TBF.Rig.Network.Camera.CJMS11
using (cameraStream = this.cameraTcpClient.GetStream())
using (cameraWriter = new StreamWriter(cameraStream, Encoding.ASCII) { AutoFlush = true })
using (cameraReader = new StreamReader(cameraStream, Encoding.ASCII))
//using (cameraReader = new StreamReader(cameraStream, Encoding.ASCII))
{
cameraStream.ReadTimeout = 1000;
@ -1472,7 +1325,7 @@ namespace TBF.Rig.Network.Camera.CJMS11
stopLiveStreamListenerFlag = false;
//we need to wait to answer, it works on thread loop - properly access
var sendCommandAndWaitToAnswer = SendCommandAndWaitToAnswer(cameraWriter, cameraReader, CommandM.prepare_camera_);
var sendCommandAndWaitToAnswer = SendCommandAndWaitToAnswerAsync(cameraWriter, cameraStream, CommandM.prepare_camera_).GetAwaiter().GetResult();
if (sendCommandAndWaitToAnswer == null || sendCommandAndWaitToAnswer.JmsMessage.Status == MessageStatus.NACK) //correct if NACK & OPENED
{
log.Error("Stop streaming not successfully! see: " + sendCommandAndWaitToAnswer.JmsMessage.Payload);
@ -1565,39 +1418,37 @@ namespace TBF.Rig.Network.Camera.CJMS11
//
private JmsPacket SendCommandAndWaitToAnswer(StreamWriter writer, StreamReader reader, CommandM command, string payload = null)
private async Task<JmsPacket> SendCommandAndWaitToAnswerAsync(
StreamWriter writer,
NetworkStream cameraStream,
CommandM command,
string payload = null,
int timeoutMs = 1000)
{
// Send command
String command_str = CommandMEnum.GetVal(command);
if (payload != null && payload.Length > 0)
{
command_str += "=" + payload;
}
command_str = command_str + " ";
writer.WriteLineAsync(command_str).Wait();
Console.WriteLine($@"Command '{command_str}' sent.");
JmsPacket result;
await SendCommandAsync(writer, command, payload);
string responseAnswer = "";
try
{
int iReads = 0;
while (true)
for (int iReads = 0; iReads <= 5; iReads++)
{
//get config
var readLineAsync = reader.ReadLineAsync();
var timeoutTaskRead = Task.Delay(TimeSpan.FromSeconds(1));
var waitAny = Task.WhenAny(readLineAsync, timeoutTaskRead).Result;
if (waitAny == timeoutTaskRead)
//responseAnswer = await ReadCameraLineAsync(cameraStream, timeoutMs);
responseAnswer = await Task.Run(() => ReadCameraLine(cameraStream, timeoutMs));
if (string.IsNullOrEmpty(responseAnswer))
{
log.Debug("Activation timeout.");
throw new TimeoutException("Activation timeout. No received response for command_CFG");
iReads++;
continue;
}
log.Debug(string.Format("received from camera: {0}", responseAnswer));
responseAnswer = readLineAsync.Result;
log.Debug($"received from camera: {responseAnswer}");
JmsPacket result = null;
try
{
@ -1605,7 +1456,6 @@ namespace TBF.Rig.Network.Camera.CJMS11
}
catch (Exception exc)
{
iReads++;
continue;
}
@ -1613,15 +1463,9 @@ namespace TBF.Rig.Network.Camera.CJMS11
{
return result;
}
if (iReads > 5)
{
log.Error($"Maximum Count of unexcepted answers excited!");
break;
}
iReads++;
}
log.Error($"Maximum Count of unexcepted answers excited!");
}
catch (IOException ioEx)
{
@ -1735,8 +1579,101 @@ namespace TBF.Rig.Network.Camera.CJMS11
}
}
private async Task<string> ReadCameraLineAsync(NetworkStream stream, int timeoutMs)
{
await cameraReadLock.WaitAsync();
try
{
var line = new List<byte>();
var buffer = new byte[1];
while (true)
{
Task<int> readTask = stream.ReadAsync(buffer, 0, 1);
Task timeoutTask = Task.Delay(timeoutMs);
Task completed = await Task.WhenAny(readTask, timeoutTask);
if (completed == timeoutTask)
{
try { cameraTcpClient?.Close(); } catch { }
throw new TimeoutException($"Camera read timeout after {timeoutMs} ms.");
}
int read = await readTask;
if (read == 0)
throw new IOException("Camera connection closed.");
if (buffer[0] == '\n')
break;
if (buffer[0] != '\r')
line.Add(buffer[0]);
}
return Encoding.ASCII.GetString(line.ToArray());
}
finally
{
cameraReadLock.Release();
}
}
private readonly object cameraReadSyncLock = new object();
private string ReadCameraLine(NetworkStream stream, int timeoutMs)
{
lock (cameraReadSyncLock)
{
stream.ReadTimeout = timeoutMs;
var line = new List<byte>();
while (true)
{
int b = stream.ReadByte(); // tu funguje ReadTimeout
if (b == -1)
throw new IOException("Camera connection closed.");
if (b == '\n')
break;
if (b != '\r')
line.Add((byte)b);
}
return Encoding.ASCII.GetString(line.ToArray());
}
}
private async Task SendCommandAsync(StreamWriter writer, CommandM command, string payload = null)
{
string commandStr = CommandMEnum.GetVal(command);
if (!string.IsNullOrEmpty(payload))
{
commandStr += "=" + payload;
}
commandStr += " ";
await cameraWriteLock.WaitAsync();
try
{
await writer.WriteLineAsync(commandStr);
await writer.FlushAsync();
log.Info($"Command '{commandStr}' sent.");
}
finally
{
cameraWriteLock.Release();
}
}
}

View File

@ -124,6 +124,9 @@
<Reference Include="MySql.Data">
<HintPath>..\packages\MySql.Data.6.6.5\lib\net40\MySql.Data.dll</HintPath>
</Reference>
<Reference Include="Newtonsoft.Json">
<HintPath>..\..\..\.nuget\packages\newtonsoft.json\13.0.4\lib\net45\Newtonsoft.Json.dll</HintPath>
</Reference>
<Reference Include="Newtonsoft.Json, Version=12.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
<HintPath>..\packages\Newtonsoft.Json.12.0.2\lib\net45\Newtonsoft.Json.dll</HintPath>
</Reference>

View File

@ -2,10 +2,13 @@ using System;
using System.Collections.Generic;
using System.Drawing;
using System.Threading.Tasks;
using Common;
using JetBrains.Annotations;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using TBF.Rig.Generic;
using TBF.Rig.Network.Camera.CJMS11;
using TBF.Rig.Network.Camera.RoiForFixedStartCJMS11;
using TBF.Rig.Network.Camera.RoiForFixedStartCJMS11.common;
using Factory = TBF.Rig.Network.Camera.CJMS11.Factory;
@ -17,25 +20,41 @@ namespace TBFTests.Rig.Network.Camera.CJMS11
public class CameraTest
{
private static string ipCamera1 = "192.168.0.170";
private static string ipCamera2 = "192.168.0.169";
private static string ipCamera2 = "192.168.0.129";
public string IPCamera1 { get { return ipCamera1; } }
public string IPCamera2 { get { return ipCamera2; } }
private RoiCfg CreateTestRoiCfg()
{
var factory = new TBF.Rig.Network.Camera.RoiForFixedStartCJMS11.Factory();
var roi = new RoiCfg("TestRoi", factory);
roi.BlackAndWhite = false;
roi.LowResolution = true;
roi.ImageRotation = ImageRotation.None;
roi.ImageFrame = Frame.StandardFrame();
return roi;
}
[TestMethod]
public void Initialize()
{
TBF.Rig.Network.Camera.CJMS11.Camera camera = GetCamera( IPCamera1);
TBF.Rig.Network.Camera.CJMS11.Camera camera = GetCamera(IPCamera1);
camera.RoiConfiguration = CreateTestRoiCfg();
camera.Initialize();
TBF.Rig.Network.Camera.CJMS11.Camera camera2 = GetCamera( IPCamera2);
camera2.RoiConfiguration = CreateTestRoiCfg();
camera2.Initialize();
TBF.Rig.Network.Camera.CJMS11.Camera camera11 = GetCamera( IPCamera1);
camera11.Initialize();
TBF.Rig.Network.Camera.CJMS11.Camera camera12 = GetCamera( IPCamera2);
camera12.Initialize();
// TBF.Rig.Network.Camera.CJMS11.Camera camera11 = GetCamera( IPCamera1);
// camera11.Initialize();
//
// TBF.Rig.Network.Camera.CJMS11.Camera camera12 = GetCamera( IPCamera2);
// camera12.Initialize();
}
@ -57,25 +76,25 @@ namespace TBFTests.Rig.Network.Camera.CJMS11
camera.Initialize();
});
var task3 = Task.Run(() =>
{
var camera = GetCamera(IPCamera2);
camera.Initialize();
});
// var task3 = Task.Run(() =>
// {
// var camera = GetCamera(IPCamera2);
// camera.Initialize();
// });
//
// var task4 = Task.Run(() =>
// {
// var camera = GetCamera(IPCamera1);
// camera.Initialize();
// });
var task4 = Task.Run(() =>
{
var camera = GetCamera(IPCamera1);
camera.Initialize();
});
Task.WaitAll(task1, task2, task3, task4); // blocks until both finish
Task.WaitAll(task1, task2/*, task3, task4*/); // blocks until both finish
// Optionally, add assertions or diagnostics
Assert.IsTrue(task1.IsCompleted);
Assert.IsTrue(task2.IsCompleted);
Assert.IsTrue(task3.IsCompleted);
Assert.IsTrue(task4.IsCompleted);
// Assert.IsTrue(task3.IsCompleted);
// Assert.IsTrue(task4.IsCompleted);
}
@ -129,35 +148,35 @@ namespace TBFTests.Rig.Network.Camera.CJMS11
camera.Initialize();
});
var task3 = Task.Run(() =>
{
var camera = GetCamera(IPCamera2);
// var task3 = Task.Run(() =>
// {
// var camera = GetCamera(IPCamera2);
//
// Task<Image> saveImageTask = Task.Run(() => camera.SaveImageListener());
// var timeoutAnswerTask = Task.Delay(TimeSpan.FromSeconds(3));
// var completedAnswerTask = Task.WhenAny(saveImageTask, timeoutAnswerTask).Result;
// if (completedAnswerTask == timeoutAnswerTask)
// {
// Assert.Fail();
// }
//
// //TODO BUMI enable check image
// //Assert.IsTrue(saveImageTask.Result != null);
// });
//
// var task4 = Task.Run(() =>
// {
// var camera = GetCamera(IPCamera1);
// camera.Initialize();
// });
Task<Image> saveImageTask = Task.Run(() => camera.SaveImageListener());
var timeoutAnswerTask = Task.Delay(TimeSpan.FromSeconds(3));
var completedAnswerTask = Task.WhenAny(saveImageTask, timeoutAnswerTask).Result;
if (completedAnswerTask == timeoutAnswerTask)
{
Assert.Fail();
}
//TODO BUMI enable check image
//Assert.IsTrue(saveImageTask.Result != null);
});
var task4 = Task.Run(() =>
{
var camera = GetCamera(IPCamera1);
camera.Initialize();
});
await Task.WhenAll(task1, task2,task3, task4); // blocks until both finish
await Task.WhenAll(task1, task2/*,task3, task4*/); // blocks until both finish
// Optionally, add assertions or diagnostics
Assert.IsTrue(task1.IsCompleted);
Assert.IsTrue(task2.IsCompleted);
Assert.IsTrue(task3.IsCompleted);
Assert.IsTrue(task4.IsCompleted);
// Assert.IsTrue(task3.IsCompleted);
// Assert.IsTrue(task4.IsCompleted);
}

Binary file not shown.

View File

@ -1641,7 +1641,7 @@
</member>
<member name="M:Newtonsoft.Json.JsonConvert.SerializeObject(System.Object,System.Type,Newtonsoft.Json.JsonSerializerSettings)">
<summary>
Serializes the specified object to a JSON string using a type, formatting and <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/>.
Serializes the specified object to a JSON string using a type and <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/>.
</summary>
<param name="value">The object to serialize.</param>
<param name="settings">The <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/> used to serialize the object.
@ -1660,7 +1660,7 @@
Serializes the specified object to a JSON string using formatting and <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/>.
</summary>
<param name="value">The object to serialize.</param>
<param name="formatting">Indicates how the output should be formatted.</param>
<param name="formatting">Indicates how the output should be formatted. This value overrides the formatting specified on <see cref="T:Newtonsoft.Json.JsonSerializerSettings" />.</param>
<param name="settings">The <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/> used to serialize the object.
If this is <c>null</c>, default serialization settings will be used.</param>
<returns>
@ -1672,7 +1672,7 @@
Serializes the specified object to a JSON string using a type, formatting and <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/>.
</summary>
<param name="value">The object to serialize.</param>
<param name="formatting">Indicates how the output should be formatted.</param>
<param name="formatting">Indicates how the output should be formatted. This value overrides the formatting specified on <see cref="T:Newtonsoft.Json.JsonSerializerSettings" />.</param>
<param name="settings">The <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/> used to serialize the object.
If this is <c>null</c>, default serialization settings will be used.</param>
<param name="type">
@ -1689,7 +1689,7 @@
Deserializes the JSON to a .NET object.
</summary>
<param name="value">The JSON to deserialize.</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeObject(System.String,Newtonsoft.Json.JsonSerializerSettings)">
<summary>
@ -1700,7 +1700,7 @@
The <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/> used to deserialize the object.
If this is <c>null</c>, default serialization settings will be used.
</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeObject(System.String,System.Type)">
<summary>
@ -1708,7 +1708,7 @@
</summary>
<param name="value">The JSON to deserialize.</param>
<param name="type">The <see cref="T:System.Type"/> of object being deserialized.</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeObject``1(System.String)">
<summary>
@ -1716,7 +1716,7 @@
</summary>
<typeparam name="T">The type of the object to deserialize to.</typeparam>
<param name="value">The JSON to deserialize.</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeAnonymousType``1(System.String,``0)">
<summary>
@ -1729,7 +1729,7 @@
</typeparam>
<param name="value">The JSON to deserialize.</param>
<param name="anonymousTypeObject">The anonymous type object.</param>
<returns>The deserialized anonymous type from the JSON string.</returns>
<returns>The deserialized anonymous type from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeAnonymousType``1(System.String,``0,Newtonsoft.Json.JsonSerializerSettings)">
<summary>
@ -1746,7 +1746,7 @@
The <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/> used to deserialize the object.
If this is <c>null</c>, default serialization settings will be used.
</param>
<returns>The deserialized anonymous type from the JSON string.</returns>
<returns>The deserialized anonymous type from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeObject``1(System.String,Newtonsoft.Json.JsonConverter[])">
<summary>
@ -1755,7 +1755,7 @@
<typeparam name="T">The type of the object to deserialize to.</typeparam>
<param name="value">The JSON to deserialize.</param>
<param name="converters">Converters to use while deserializing.</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeObject``1(System.String,Newtonsoft.Json.JsonSerializerSettings)">
<summary>
@ -1767,7 +1767,7 @@
The <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/> used to deserialize the object.
If this is <c>null</c>, default serialization settings will be used.
</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeObject(System.String,System.Type,Newtonsoft.Json.JsonConverter[])">
<summary>
@ -1776,7 +1776,7 @@
<param name="value">The JSON to deserialize.</param>
<param name="type">The type of the object to deserialize.</param>
<param name="converters">Converters to use while deserializing.</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.DeserializeObject(System.String,System.Type,Newtonsoft.Json.JsonSerializerSettings)">
<summary>
@ -1788,7 +1788,7 @@
The <see cref="T:Newtonsoft.Json.JsonSerializerSettings"/> used to deserialize the object.
If this is <c>null</c>, default serialization settings will be used.
</param>
<returns>The deserialized object from the JSON string.</returns>
<returns>The deserialized object from the JSON string. A <see langword="null"/> value is returned if the provided JSON is valid but represents a null value.</returns>
</member>
<member name="M:Newtonsoft.Json.JsonConvert.PopulateObject(System.String,System.Object)">
<summary>
@ -7186,6 +7186,21 @@
<param name="converters">A collection of <see cref="T:Newtonsoft.Json.JsonConverter"/> which will be used when writing the token.</param>
<returns>A <see cref="T:System.Threading.Tasks.Task"/> that represents the asynchronous write operation.</returns>
</member>
<member name="M:Newtonsoft.Json.Linq.JToken.WriteToAsync(Newtonsoft.Json.JsonWriter,System.Threading.CancellationToken)">
<summary>
Writes this token to a <see cref="T:Newtonsoft.Json.JsonWriter"/> asynchronously.
</summary>
<param name="writer">A <see cref="T:Newtonsoft.Json.JsonWriter"/> into which this method will write.</param>
<param name="cancellationToken">The token to monitor for cancellation requests.</param>
<returns>A <see cref="T:System.Threading.Tasks.Task"/> that represents the asynchronous write operation.</returns>
</member>
<member name="M:Newtonsoft.Json.Linq.JToken.WriteToAsync(Newtonsoft.Json.JsonWriter)">
<summary>
Writes this token to a <see cref="T:Newtonsoft.Json.JsonWriter"/> asynchronously.
</summary>
<param name="writer">A <see cref="T:Newtonsoft.Json.JsonWriter"/> into which this method will write.</param>
<returns>A <see cref="T:System.Threading.Tasks.Task"/> that represents the asynchronous write operation.</returns>
</member>
<member name="M:Newtonsoft.Json.Linq.JToken.ReadFromAsync(Newtonsoft.Json.JsonReader,System.Threading.CancellationToken)">
<summary>
Asynchronously creates a <see cref="T:Newtonsoft.Json.Linq.JToken"/> from a <see cref="T:Newtonsoft.Json.JsonReader"/>.
@ -7394,6 +7409,12 @@
</summary>
<param name="value">The value.</param>
</member>
<member name="M:Newtonsoft.Json.Linq.JToken.WriteTo(Newtonsoft.Json.JsonWriter)">
<summary>
Writes this token to a <see cref="T:Newtonsoft.Json.JsonWriter"/>.
</summary>
<param name="writer">A <see cref="T:Newtonsoft.Json.JsonWriter"/> into which this method will write.</param>
</member>
<member name="M:Newtonsoft.Json.Linq.JToken.WriteTo(Newtonsoft.Json.JsonWriter,Newtonsoft.Json.JsonConverter[])">
<summary>
Writes this token to a <see cref="T:Newtonsoft.Json.JsonWriter"/>.
@ -7413,6 +7434,13 @@
The indented JSON for this token.
</returns>
</member>
<member name="M:Newtonsoft.Json.Linq.JToken.ToString(Newtonsoft.Json.Formatting)">
<summary>
Returns the JSON for this token using the given formatting and converters.
</summary>
<param name="formatting">Indicates how the output should be formatted.</param>
<returns>The JSON for this token using the given formatting and converters.</returns>
</member>
<member name="M:Newtonsoft.Json.Linq.JToken.ToString(Newtonsoft.Json.Formatting,Newtonsoft.Json.JsonConverter[])">
<summary>
Returns the JSON for this token using the given formatting and converters.
@ -11321,6 +11349,180 @@
A <see cref="T:Newtonsoft.Json.JsonWriter"/> write method has not been called.
</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMembersAttribute">
<summary>
Indicates that certain members on a specified <see cref="T:System.Type"/> are accessed dynamically,
for example through <see cref="N:System.Reflection"/>.
</summary>
<remarks>
This allows tools to understand which members are being accessed during the execution
of a program.
This attribute is valid on members whose type is <see cref="T:System.Type"/> or <see cref="T:System.String"/>.
When this attribute is applied to a location of type <see cref="T:System.String"/>, the assumption is
that the string represents a fully qualified type name.
When this attribute is applied to a class, interface, or struct, the members specified
can be accessed dynamically on <see cref="T:System.Type"/> instances returned from calling
<see cref="M:System.Object.GetType"/> on instances of that class, interface, or struct.
If the attribute is applied to a method it's treated as a special case and it implies
the attribute should be applied to the "this" parameter of the method. As such the attribute
should only be used on instance methods of types assignable to System.Type (or string, but no methods
will use it there).
</remarks>
</member>
<member name="M:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMembersAttribute.#ctor(System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes)">
<summary>
Initializes a new instance of the <see cref="T:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMembersAttribute"/> class
with the specified member types.
</summary>
<param name="memberTypes">The types of members dynamically accessed.</param>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMembersAttribute.MemberTypes">
<summary>
Gets the <see cref="T:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes"/> which specifies the type
of members dynamically accessed.
</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes">
<summary>
Specifies the types of members that are dynamically accessed.
This enumeration has a <see cref="T:System.FlagsAttribute"/> attribute that allows a
bitwise combination of its member values.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.None">
<summary>
Specifies no members.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.PublicParameterlessConstructor">
<summary>
Specifies the default, parameterless public constructor.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.PublicConstructors">
<summary>
Specifies all public constructors.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.NonPublicConstructors">
<summary>
Specifies all non-public constructors.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.PublicMethods">
<summary>
Specifies all public methods.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.NonPublicMethods">
<summary>
Specifies all non-public methods.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.PublicFields">
<summary>
Specifies all public fields.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.NonPublicFields">
<summary>
Specifies all non-public fields.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.PublicNestedTypes">
<summary>
Specifies all public nested types.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.NonPublicNestedTypes">
<summary>
Specifies all non-public nested types.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.PublicProperties">
<summary>
Specifies all public properties.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.NonPublicProperties">
<summary>
Specifies all non-public properties.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.PublicEvents">
<summary>
Specifies all public events.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.NonPublicEvents">
<summary>
Specifies all non-public events.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.Interfaces">
<summary>
Specifies all interfaces implemented by the type.
</summary>
</member>
<member name="F:System.Diagnostics.CodeAnalysis.DynamicallyAccessedMemberTypes.All">
<summary>
Specifies all members.
</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.FeatureGuardAttribute">
<summary>
Indicates that the specified public static boolean get-only property
guards access to the specified feature.
</summary>
<remarks>
Analyzers can use this to prevent warnings on calls to code that is
annotated as requiring that feature, when the callsite is guarded by a
call to the property.
</remarks>
</member>
<member name="M:System.Diagnostics.CodeAnalysis.FeatureGuardAttribute.#ctor(System.Type)">
<summary>
Initializes a new instance of the <see cref="T:System.Diagnostics.CodeAnalysis.FeatureGuardAttribute"/> class
with the specified feature type.
</summary>
<param name="featureType">
The type that represents the feature guarded by the property.
</param>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.FeatureGuardAttribute.FeatureType">
<summary>
The type that represents the feature guarded by the property.
</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.FeatureSwitchDefinitionAttribute">
<summary>
Indicates that the specified public static boolean get-only property
corresponds to the feature switch specified by name.
</summary>
<remarks>
IL rewriters and compilers can use this to substitute the return value
of the specified property with the value of the feature switch.
</remarks>
</member>
<member name="M:System.Diagnostics.CodeAnalysis.FeatureSwitchDefinitionAttribute.#ctor(System.String)">
<summary>
Initializes a new instance of the <see cref="T:System.Diagnostics.CodeAnalysis.FeatureSwitchDefinitionAttribute"/> class
with the specified feature switch name.
</summary>
<param name="switchName">
The name of the feature switch that provides the value for the specified property.
</param>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.FeatureSwitchDefinitionAttribute.SwitchName">
<summary>
The name of the feature switch that provides the value for the specified property.
</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.NotNullAttribute">
<summary>Specifies that an output will not be null even if the corresponding type allows it.</summary>
</member>
@ -11359,5 +11561,138 @@
<member name="P:System.Diagnostics.CodeAnalysis.DoesNotReturnIfAttribute.ParameterValue">
<summary>Gets the condition parameter value.</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.RequiresDynamicCodeAttribute">
<summary>
Indicates that the specified method requires the ability to generate new code at runtime,
for example through <see cref="N:System.Reflection"/>.
</summary>
<remarks>
This allows tools to understand which methods are unsafe to call when compiling ahead of time.
</remarks>
</member>
<member name="M:System.Diagnostics.CodeAnalysis.RequiresDynamicCodeAttribute.#ctor(System.String)">
<summary>
Initializes a new instance of the <see cref="T:System.Diagnostics.CodeAnalysis.RequiresDynamicCodeAttribute"/> class
with the specified message.
</summary>
<param name="message">
A message that contains information about the usage of dynamic code.
</param>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.RequiresDynamicCodeAttribute.Message">
<summary>
Gets a message that contains information about the usage of dynamic code.
</summary>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.RequiresDynamicCodeAttribute.Url">
<summary>
Gets or sets an optional URL that contains more information about the method,
why it requires dynamic code, and what options a consumer has to deal with it.
</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute">
<summary>
Indicates that the specified method requires dynamic access to code that is not referenced
statically, for example through <see cref="N:System.Reflection"/>.
</summary>
<remarks>
This allows tools to understand which methods are unsafe to call when removing unreferenced
code from an application.
</remarks>
</member>
<member name="M:System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute.#ctor(System.String)">
<summary>
Initializes a new instance of the <see cref="T:System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute"/> class
with the specified message.
</summary>
<param name="message">
A message that contains information about the usage of unreferenced code.
</param>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute.Message">
<summary>
Gets a message that contains information about the usage of unreferenced code.
</summary>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute.Url">
<summary>
Gets or sets an optional URL that contains more information about the method,
why it requires unreferenced code, and what options a consumer has to deal with it.
</summary>
</member>
<member name="T:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute">
<summary>
Suppresses reporting of a specific rule violation, allowing multiple suppressions on a
single code artifact.
</summary>
<remarks>
<see cref="T:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute"/> is different than
<see cref="T:System.Diagnostics.CodeAnalysis.SuppressMessageAttribute"/> in that it doesn't have a
<see cref="T:System.Diagnostics.ConditionalAttribute"/>. So it is always preserved in the compiled assembly.
</remarks>
</member>
<member name="M:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.#ctor(System.String,System.String)">
<summary>
Initializes a new instance of the <see cref="T:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute"/>
class, specifying the category of the tool and the identifier for an analysis rule.
</summary>
<param name="category">The category for the attribute.</param>
<param name="checkId">The identifier of the analysis rule the attribute applies to.</param>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.Category">
<summary>
Gets the category identifying the classification of the attribute.
</summary>
<remarks>
The <see cref="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.Category"/> property describes the tool or tool analysis category
for which a message suppression attribute applies.
</remarks>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.CheckId">
<summary>
Gets the identifier of the analysis tool rule to be suppressed.
</summary>
<remarks>
Concatenated together, the <see cref="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.Category"/> and <see cref="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.CheckId"/>
properties form a unique check identifier.
</remarks>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.Scope">
<summary>
Gets or sets the scope of the code that is relevant for the attribute.
</summary>
<remarks>
The Scope property is an optional argument that specifies the metadata scope for which
the attribute is relevant.
</remarks>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.Target">
<summary>
Gets or sets a fully qualified path that represents the target of the attribute.
</summary>
<remarks>
The <see cref="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.Target"/> property is an optional argument identifying the analysis target
of the attribute. An example value is "System.IO.Stream.ctor():System.Void".
Because it is fully qualified, it can be long, particularly for targets such as parameters.
The analysis tool user interface should be capable of automatically formatting the parameter.
</remarks>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.MessageId">
<summary>
Gets or sets an optional argument expanding on exclusion criteria.
</summary>
<remarks>
The <see cref="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.MessageId"/> property is an optional argument that specifies additional
exclusion where the literal metadata target is not sufficiently precise. For example,
the <see cref="T:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute"/> cannot be applied within a method,
and it may be desirable to suppress a violation against a statement in the method that will
give a rule violation, but not against all statements in the method.
</remarks>
</member>
<member name="P:System.Diagnostics.CodeAnalysis.UnconditionalSuppressMessageAttribute.Justification">
<summary>
Gets or sets the justification for suppressing the code analysis message.
</summary>
</member>
</members>
</doc>

View File

@ -2,44 +2,48 @@
<configuration>
<configSections>
<sectionGroup name="userSettings" type="System.Configuration.UserSettingsGroup, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<section name="Xylem.Common.Ui.GenesisToolBox.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" allowExeDefinition="MachineToLocalUser" requirePermission="false"/>
<section name="Xylem.Common.Ui.GenesisToolBox.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" allowExeDefinition="MachineToLocalUser" requirePermission="false" />
</sectionGroup>
</configSections>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.8"/>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.8" />
</startup>
<userSettings>
<Xylem.Common.Ui.GenesisToolBox.Properties.Settings>
<setting name="InitialBinaryPath" serializeAs="String">
<value/>
<value />
</setting>
<setting name="InitialPackageFile" serializeAs="String">
<value/>
<value />
</setting>
</Xylem.Common.Ui.GenesisToolBox.Properties.Settings>
</userSettings>
<appSettings>
<add key="AdminName" value="My Name"/>
<add key="AdminEMail" value="MyEMailAddress"/>
<add key="ClientSettingsProvider.ServiceUri" value=""/>
<add key="AdminName" value="My Name" />
<add key="AdminEMail" value="MyEMailAddress" />
<add key="ClientSettingsProvider.ServiceUri" value="" />
</appSettings>
<runtime>
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
<dependentAssembly>
<assemblyIdentity name="Newtonsoft.Json" publicKeyToken="30ad4fe6b2a6aeed" culture="neutral"/>
<bindingRedirect oldVersion="0.0.0.0-13.0.0.0" newVersion="13.0.0.0"/>
<assemblyIdentity name="Newtonsoft.Json" publicKeyToken="30ad4fe6b2a6aeed" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-13.0.0.0" newVersion="13.0.0.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="Xylem.Common.CommonCore" publicKeyToken="null" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.8.18.29406" newVersion="2.8.18.29406" />
</dependentAssembly>
</assemblyBinding>
</runtime>
<system.web>
<membership defaultProvider="ClientAuthenticationMembershipProvider">
<providers>
<add name="ClientAuthenticationMembershipProvider" type="System.Web.ClientServices.Providers.ClientFormsAuthenticationMembershipProvider, System.Web.Extensions, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" serviceUri=""/>
<add name="ClientAuthenticationMembershipProvider" type="System.Web.ClientServices.Providers.ClientFormsAuthenticationMembershipProvider, System.Web.Extensions, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" serviceUri="" />
</providers>
</membership>
<roleManager defaultProvider="ClientRoleProvider" enabled="true">
<providers>
<add name="ClientRoleProvider" type="System.Web.ClientServices.Providers.ClientRoleProvider, System.Web.Extensions, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" serviceUri="" cacheTimeout="86400"/>
<add name="ClientRoleProvider" type="System.Web.ClientServices.Providers.ClientRoleProvider, System.Web.Extensions, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" serviceUri="" cacheTimeout="86400" />
</providers>
</roleManager>
</system.web>

Binary file not shown.

View File

@ -1,20 +0,0 @@
The MIT License (MIT)
Copyright (c) 2007 James Newton-King
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

Binary file not shown.

View File

@ -1,20 +0,0 @@
The MIT License (MIT)
Copyright (c) 2007 James Newton-King
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

View File

@ -1,71 +0,0 @@
# ![Logo](https://raw.githubusercontent.com/JamesNK/Newtonsoft.Json/master/Doc/icons/logo.jpg) Json.NET
[![NuGet version (Newtonsoft.Json)](https://img.shields.io/nuget/v/Newtonsoft.Json.svg?style=flat-square)](https://www.nuget.org/packages/Newtonsoft.Json/)
[![Build status](https://dev.azure.com/jamesnk/Public/_apis/build/status/JamesNK.Newtonsoft.Json?branchName=master)](https://dev.azure.com/jamesnk/Public/_build/latest?definitionId=8)
Json.NET is a popular high-performance JSON framework for .NET
## Serialize JSON
```csharp
Product product = new Product();
product.Name = "Apple";
product.Expiry = new DateTime(2008, 12, 28);
product.Sizes = new string[] { "Small" };
string json = JsonConvert.SerializeObject(product);
// {
// "Name": "Apple",
// "Expiry": "2008-12-28T00:00:00",
// "Sizes": [
// "Small"
// ]
// }
```
## Deserialize JSON
```csharp
string json = @"{
'Name': 'Bad Boys',
'ReleaseDate': '1995-4-7T00:00:00',
'Genres': [
'Action',
'Comedy'
]
}";
Movie m = JsonConvert.DeserializeObject<Movie>(json);
string name = m.Name;
// Bad Boys
```
## LINQ to JSON
```csharp
JArray array = new JArray();
array.Add("Manual text");
array.Add(new DateTime(2000, 5, 23));
JObject o = new JObject();
o["MyArray"] = array;
string json = o.ToString();
// {
// "MyArray": [
// "Manual text",
// "2000-05-23T00:00:00"
// ]
// }
```
## Links
- [Homepage](https://www.newtonsoft.com/json)
- [Documentation](https://www.newtonsoft.com/json/help)
- [NuGet Package](https://www.nuget.org/packages/Newtonsoft.Json)
- [Release Notes](https://github.com/JamesNK/Newtonsoft.Json/releases)
- [Contributing Guidelines](https://github.com/JamesNK/Newtonsoft.Json/blob/master/CONTRIBUTING.md)
- [License](https://github.com/JamesNK/Newtonsoft.Json/blob/master/LICENSE.md)
- [Stack Overflow](https://stackoverflow.com/questions/tagged/json.net)

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 8.7 KiB