TSV like PDSF ready to test
This commit is contained in:
@ -1,72 +0,0 @@
|
||||
using Adaptation.Shared;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text.Json;
|
||||
using System.Text.Json.Serialization;
|
||||
|
||||
namespace Adaptation.FileHandlers.Stratus;
|
||||
|
||||
#nullable enable
|
||||
|
||||
internal class Complete
|
||||
{
|
||||
|
||||
public Complete(Header header, Wafer[] wafers, Footer footer)
|
||||
{
|
||||
Header = header;
|
||||
Wafers = wafers;
|
||||
Footer = footer;
|
||||
}
|
||||
|
||||
public Header Header { get; }
|
||||
public Wafer[] Wafers { get; }
|
||||
public Footer Footer { get; }
|
||||
|
||||
internal static Complete? Get(Logistics logistics, List<FileInfo> fileInfoCollection)
|
||||
{
|
||||
Complete? result;
|
||||
Constant constant = new();
|
||||
int[] i = new int[] { 0 };
|
||||
string text = File.ReadAllText(logistics.ReportFullPath);
|
||||
Header? header = Header.Get(text, constant, i);
|
||||
if (header is null)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
ReadOnlyCollection<string> groups = Wafer.GetGroups(text, constant, i);
|
||||
if (groups.Count == 0)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
ReadOnlyCollection<Wafer> wafers = Wafer.Get(constant, groups);
|
||||
if (wafers.Count == 0)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
Footer? footer = Footer.Get(constant, groups);
|
||||
if (footer is null)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
result = new(header, wafers.ToArray(), footer);
|
||||
FileInfo fileInfo = new($"{logistics.ReportFullPath}.json");
|
||||
string json = JsonSerializer.Serialize(result, CompleteSourceGenerationContext.Default.Complete);
|
||||
File.WriteAllText(fileInfo.FullName, json);
|
||||
File.SetLastWriteTime(fileInfo.FullName, logistics.DateTimeFromSequence);
|
||||
fileInfoCollection.Add(fileInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
[JsonSourceGenerationOptions(WriteIndented = true)]
|
||||
[JsonSerializable(typeof(Complete))]
|
||||
internal partial class CompleteSourceGenerationContext : JsonSerializerContext
|
||||
{
|
||||
}
|
@ -110,10 +110,10 @@ public class FileRead : Shared.FileRead, IFileRead
|
||||
results.Item4.Add(_Logistics.FileInfo);
|
||||
else
|
||||
{
|
||||
Complete? complete = Complete.Get(_Logistics, results.Item4);
|
||||
if (complete is null)
|
||||
Run? run = Run.Get(_Logistics, results.Item4);
|
||||
if (run is null)
|
||||
throw new Exception(string.Concat("A) No Data - ", dateTime.Ticks));
|
||||
IProcessData iProcessData = new ProcessData(this, _Logistics, results.Item4, _OriginalDataBioRad, complete, dataText: string.Empty);
|
||||
IProcessData iProcessData = new ProcessData(this, _Logistics, results.Item4, _OriginalDataBioRad, run, dataText: string.Empty);
|
||||
if (iProcessData is not ProcessData processData)
|
||||
throw new Exception(string.Concat("B) No Data - ", dateTime.Ticks));
|
||||
string mid;
|
||||
|
@ -44,14 +44,15 @@ public partial class ProcessData : IProcessData
|
||||
|
||||
#nullable enable
|
||||
|
||||
internal ProcessData(IFileRead fileRead, Logistics logistics, List<FileInfo> fileInfoCollection, string originalDataBioRad, Complete? complete, string dataText)
|
||||
internal ProcessData(IFileRead fileRead, Logistics logistics, List<FileInfo> fileInfoCollection, string originalDataBioRad, Run? run, string dataText)
|
||||
{
|
||||
JobID = logistics.JobID;
|
||||
fileInfoCollection.Clear();
|
||||
if (!string.IsNullOrEmpty(dataText))
|
||||
fileInfoCollection.Clear();
|
||||
_Details = new List<object>();
|
||||
MesEntity = logistics.MesEntity;
|
||||
_Log = LogManager.GetLogger(typeof(ProcessData));
|
||||
Parse(fileRead, logistics, fileInfoCollection, originalDataBioRad, complete, dataText);
|
||||
Parse(fileRead, logistics, fileInfoCollection, originalDataBioRad, run, dataText);
|
||||
}
|
||||
|
||||
string IProcessData.GetCurrentReactor(IFileRead fileRead, Logistics logistics, Dictionary<string, string> reactors) => throw new Exception(string.Concat("See ", nameof(Parse)));
|
||||
@ -385,7 +386,7 @@ public partial class ProcessData : IProcessData
|
||||
return result;
|
||||
}
|
||||
|
||||
private void Set(Logistics logistics, Complete? complete)
|
||||
private void Set(Logistics logistics, Run? run)
|
||||
{
|
||||
string psn;
|
||||
string rds;
|
||||
@ -415,7 +416,7 @@ public partial class ProcessData : IProcessData
|
||||
batch = GetToText(startedKey);
|
||||
ScanPast(startedAtKey);
|
||||
}
|
||||
if (complete is not null)
|
||||
if (run is not null)
|
||||
{ }
|
||||
ScanPast(cassetteKey);
|
||||
if (!_Data.Substring(_I).Contains(startedKey))
|
||||
@ -449,15 +450,17 @@ public partial class ProcessData : IProcessData
|
||||
UniqueId = string.Concat("StratusBioRad_", reactor, "_", rds, "_", psn, "_", logistics.DateTimeFromSequence.ToString("yyyyMMddHHmmssffff"));
|
||||
}
|
||||
|
||||
private void Parse(IFileRead fileRead, Logistics logistics, List<FileInfo> fileInfoCollection, string originalDataBioRad, Complete? complete, string receivedData)
|
||||
private void Parse(IFileRead fileRead, Logistics logistics, List<FileInfo> fileInfoCollection, string originalDataBioRad, Run? run, string dataText)
|
||||
{
|
||||
if (fileRead is null)
|
||||
throw new ArgumentNullException(nameof(fileRead));
|
||||
_I = 0;
|
||||
_Data = string.Empty;
|
||||
List<Detail> details = new();
|
||||
if (string.IsNullOrEmpty(dataText))
|
||||
dataText = File.ReadAllText(logistics.ReportFullPath);
|
||||
_Log.Debug($"****ParseData - Source file contents:");
|
||||
_Log.Debug(receivedData);
|
||||
_Log.Debug(dataText);
|
||||
List<string> moveFiles = new();
|
||||
string fileNameWithoutExtension = Path.GetFileNameWithoutExtension(logistics.ReportFullPath);
|
||||
string directoryName = Path.GetDirectoryName(logistics.ReportFullPath) ?? throw new Exception();
|
||||
@ -465,7 +468,7 @@ public partial class ProcessData : IProcessData
|
||||
moveFiles.AddRange(Directory.GetFiles(directoryName, string.Concat(originalDataBioRad, "*", fileNameWithoutExtension.Split('_').Last(), "*"), SearchOption.TopDirectoryOnly));
|
||||
foreach (string moveFile in moveFiles.Distinct())
|
||||
fileInfoCollection.Add(new FileInfo(moveFile));
|
||||
if (!string.IsNullOrEmpty(receivedData))
|
||||
if (!string.IsNullOrEmpty(dataText))
|
||||
{
|
||||
int i;
|
||||
int num;
|
||||
@ -476,8 +479,8 @@ public partial class ProcessData : IProcessData
|
||||
string recipe;
|
||||
string nextLine;
|
||||
_I = 0;
|
||||
_Data = receivedData;
|
||||
Set(logistics, complete);
|
||||
_Data = dataText;
|
||||
Set(logistics, run);
|
||||
nextLine = PeekNextLine();
|
||||
string cassette = "Cassette";
|
||||
if (nextLine.Contains("Wafer"))
|
||||
@ -597,7 +600,7 @@ public partial class ProcessData : IProcessData
|
||||
StdDev = StdDev.Remove(StdDev.Length - 1, 1);
|
||||
}
|
||||
}
|
||||
if (receivedData.Contains("------------- Process failed -------------"))
|
||||
if (dataText.Contains("------------- Process failed -------------"))
|
||||
details.Add(new());
|
||||
}
|
||||
StringBuilder stringBuilder = new();
|
||||
|
55
Adaptation/FileHandlers/Stratus/Row.cs
Normal file
55
Adaptation/FileHandlers/Stratus/Row.cs
Normal file
@ -0,0 +1,55 @@
|
||||
using System.Text.Json.Serialization;
|
||||
|
||||
namespace Adaptation.FileHandlers.Stratus;
|
||||
|
||||
#nullable enable
|
||||
|
||||
internal class Row
|
||||
{
|
||||
|
||||
public Row(Run run, int i, int j)
|
||||
{
|
||||
Batch = run.Header.Batch;
|
||||
Cassette = run.Header.Cassette;
|
||||
DateTime = run.Header.DateTime;
|
||||
//
|
||||
Destination = run.Wafers[i].Destination;
|
||||
Mean = run.Wafers[i].Mean;
|
||||
PassFail = run.Wafers[i].PassFail;
|
||||
Recipe = run.Wafers[i].Recipe;
|
||||
Reference = run.Wafers[i].Reference;
|
||||
Site = run.Wafers[i].Sites[j];
|
||||
Slot = run.Wafers[i].Slot;
|
||||
Source = run.Wafers[i].Source;
|
||||
WaferStdDev = run.Wafers[i].StdDev;
|
||||
Text = run.Wafers[i].Text;
|
||||
//
|
||||
MeanThickness = run.Footer.MeanThickness;
|
||||
StdDev = run.Footer.StdDev;
|
||||
}
|
||||
|
||||
public string Batch { get; }
|
||||
public string Cassette { get; }
|
||||
public string DateTime { get; }
|
||||
//
|
||||
public string Destination { get; }
|
||||
public string Mean { get; }
|
||||
public string PassFail { get; }
|
||||
public string Recipe { get; }
|
||||
public string Reference { get; }
|
||||
public string Site { get; }
|
||||
public string Slot { get; }
|
||||
public string Source { get; }
|
||||
public string WaferStdDev { get; }
|
||||
public string Text { get; }
|
||||
//
|
||||
public string MeanThickness { get; }
|
||||
public string StdDev { get; }
|
||||
|
||||
}
|
||||
|
||||
[JsonSourceGenerationOptions(WriteIndented = true)]
|
||||
[JsonSerializable(typeof(Row))]
|
||||
internal partial class RowSourceGenerationContext : JsonSerializerContext
|
||||
{
|
||||
}
|
151
Adaptation/FileHandlers/Stratus/Run.cs
Normal file
151
Adaptation/FileHandlers/Stratus/Run.cs
Normal file
@ -0,0 +1,151 @@
|
||||
using Adaptation.Shared;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.IO;
|
||||
using System.Text;
|
||||
using System.Text.Json;
|
||||
using System.Text.Json.Serialization;
|
||||
|
||||
namespace Adaptation.FileHandlers.Stratus;
|
||||
|
||||
#nullable enable
|
||||
|
||||
internal class Run
|
||||
{
|
||||
|
||||
public Run(Header header, ReadOnlyCollection<Wafer> wafers, Footer footer)
|
||||
{
|
||||
Header = header;
|
||||
Wafers = wafers;
|
||||
Footer = footer;
|
||||
}
|
||||
|
||||
public Header Header { get; }
|
||||
public ReadOnlyCollection<Wafer> Wafers { get; }
|
||||
public Footer Footer { get; }
|
||||
|
||||
private static void WriteJson(Logistics logistics, List<FileInfo> fileInfoCollection, Run? result)
|
||||
{
|
||||
FileInfo fileInfo = new($"{logistics.ReportFullPath}.json");
|
||||
string json = JsonSerializer.Serialize(result, RunSourceGenerationContext.Default.Run);
|
||||
File.WriteAllText(fileInfo.FullName, json);
|
||||
File.SetLastWriteTime(fileInfo.FullName, logistics.DateTimeFromSequence);
|
||||
fileInfoCollection.Add(fileInfo);
|
||||
}
|
||||
|
||||
private static ReadOnlyCollection<string> GetLines(JsonElement[]? jsonElements)
|
||||
{
|
||||
List<string> results = new();
|
||||
int columns = 0;
|
||||
StringBuilder stringBuilder = new();
|
||||
for (int i = 0; i < jsonElements?.Length;)
|
||||
{
|
||||
foreach (JsonProperty jsonProperty in jsonElements[0].EnumerateObject())
|
||||
{
|
||||
columns += 1;
|
||||
_ = stringBuilder.Append('"').Append(jsonProperty.Name).Append('"').Append('\t');
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (jsonElements?.Length != 0)
|
||||
_ = stringBuilder.Remove(stringBuilder.Length - 1, 1);
|
||||
results.Add(stringBuilder.ToString());
|
||||
for (int i = 0; i < jsonElements?.Length; i++)
|
||||
{
|
||||
_ = stringBuilder.Clear();
|
||||
foreach (JsonProperty jsonProperty in jsonElements[i].EnumerateObject())
|
||||
{
|
||||
if (jsonProperty.Value.ValueKind == JsonValueKind.Object)
|
||||
_ = stringBuilder.Append('\t');
|
||||
else if (jsonProperty.Value.ValueKind != JsonValueKind.String)
|
||||
_ = stringBuilder.Append(jsonProperty.Value).Append('\t');
|
||||
else
|
||||
_ = stringBuilder.Append('"').Append(jsonProperty.Value).Append('"').Append('\t');
|
||||
}
|
||||
_ = stringBuilder.Remove(stringBuilder.Length - 1, 1);
|
||||
results.Add(stringBuilder.ToString());
|
||||
}
|
||||
return results.AsReadOnly();
|
||||
}
|
||||
|
||||
private static ReadOnlyCollection<string> GetLines(JsonElement jsonElement) =>
|
||||
GetLines(new JsonElement[] { jsonElement });
|
||||
|
||||
private static void WriteTabSeparatedValues(Logistics logistics, List<FileInfo> fileInfoCollection, Run run)
|
||||
{
|
||||
List<Row> results = new();
|
||||
Row row;
|
||||
FileInfo fileInfo = new($"{logistics.ReportFullPath}.tsv");
|
||||
for (int i = 0; i < run.Wafers.Count; i++)
|
||||
{
|
||||
for (int j = 0; j < run.Wafers[i].Sites.Count; j++)
|
||||
{
|
||||
row = new(run, i, j);
|
||||
results.Add(row);
|
||||
}
|
||||
}
|
||||
string json = JsonSerializer.Serialize(results);
|
||||
JsonElement[]? jsonElements = JsonSerializer.Deserialize<JsonElement[]>(json);
|
||||
ReadOnlyCollection<string> lines = GetLines(jsonElements);
|
||||
File.WriteAllText(fileInfo.FullName, string.Join(Environment.NewLine, lines));
|
||||
File.SetLastWriteTime(fileInfo.FullName, logistics.DateTimeFromSequence);
|
||||
fileInfoCollection.Add(fileInfo);
|
||||
}
|
||||
|
||||
private static void WriteException(Logistics logistics, Exception ex)
|
||||
{
|
||||
FileInfo fileInfo = new($"{logistics.ReportFullPath}.{nameof(Exception)}.txt");
|
||||
File.WriteAllText(fileInfo.FullName, $"{ex.Message}{Environment.NewLine}{ex.StackTrace}");
|
||||
}
|
||||
|
||||
internal static Run? Get(Logistics logistics, List<FileInfo> fileInfoCollection)
|
||||
{
|
||||
Run? result;
|
||||
Constant constant = new();
|
||||
int[] i = new int[] { 0 };
|
||||
string text = File.ReadAllText(logistics.ReportFullPath);
|
||||
Header? header = Header.Get(text, constant, i);
|
||||
if (header is null)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
ReadOnlyCollection<string> groups = Wafer.GetGroups(text, constant, i);
|
||||
if (groups.Count == 0)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
ReadOnlyCollection<Wafer> wafers = Wafer.Get(constant, groups);
|
||||
if (wafers.Count == 0)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
Footer? footer = Footer.Get(constant, groups);
|
||||
if (footer is null)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
result = new(header, wafers, footer);
|
||||
WriteJson(logistics, fileInfoCollection, result);
|
||||
try
|
||||
{
|
||||
WriteTabSeparatedValues(logistics, fileInfoCollection, result);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteException(logistics, ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
[JsonSourceGenerationOptions(WriteIndented = true)]
|
||||
[JsonSerializable(typeof(Run))]
|
||||
internal partial class RunSourceGenerationContext : JsonSerializerContext
|
||||
{
|
||||
}
|
@ -9,7 +9,7 @@ namespace Adaptation.FileHandlers.Stratus;
|
||||
public class Wafer
|
||||
{
|
||||
|
||||
public Wafer(string destination, string mean, string passFail, string recipe, string reference, List<string> sites, string slot, string source, string stdDev, string waferText)
|
||||
public Wafer(string destination, string mean, string passFail, string recipe, string reference, ReadOnlyCollection<string> sites, string slot, string source, string stdDev, string waferText)
|
||||
{
|
||||
Destination = destination;
|
||||
Mean = mean;
|
||||
@ -28,7 +28,7 @@ public class Wafer
|
||||
public string PassFail { get; }
|
||||
public string Recipe { get; }
|
||||
public string Reference { get; }
|
||||
public List<string> Sites { get; }
|
||||
public ReadOnlyCollection<string> Sites { get; }
|
||||
public string Slot { get; }
|
||||
public string Source { get; }
|
||||
public string StdDev { get; }
|
||||
@ -216,7 +216,7 @@ public class Wafer
|
||||
passFail: passFail,
|
||||
recipe: recipe,
|
||||
reference: reference,
|
||||
sites: sites,
|
||||
sites: sites.AsReadOnly(),
|
||||
slot: slot,
|
||||
source: source,
|
||||
stdDev: stdDev,
|
||||
|
@ -226,7 +226,7 @@ public partial class ProcessData : IProcessData
|
||||
}
|
||||
else
|
||||
{
|
||||
Stratus.Complete? complete = null;
|
||||
Stratus.Run? complete = null;
|
||||
processData = new Stratus.ProcessData(fileRead, logistics, fileInfoCollection, originalDataBioRad, complete, dataText: dataText);
|
||||
iProcessData = processData;
|
||||
if (iProcessData.Details.Count == 0)
|
||||
|
Reference in New Issue
Block a user