diff --git a/Core/Enum.cs b/Core/Enum.cs
new file mode 100644
index 0000000..bc27d86
--- /dev/null
+++ b/Core/Enum.cs
@@ -0,0 +1,18 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace Core
+{
+ ///
+ /// Tipologia di ticket
+ ///
+ public enum TipologiaTicket
+ {
+ ND = 0,
+ Licenze,
+ FileUpload
+ }
+}
diff --git a/Core/SupportRequest.cs b/Core/SupportRequest.cs
index cab22a3..5cdf111 100644
--- a/Core/SupportRequest.cs
+++ b/Core/SupportRequest.cs
@@ -18,6 +18,8 @@ namespace Core
public string ContactPhone { get; set; } = "";
public int idxSubLic { get; set; } = 0;
+ public TipologiaTicket Tipo { get; set; } = TipologiaTicket.ND;
+
public bool IsValid
{
get => !string.IsNullOrEmpty(MasterKey) && !string.IsNullOrEmpty(ContactEmail) && !string.IsNullOrEmpty(CodInst) && !string.IsNullOrEmpty(CodApp);
diff --git a/Core/UploadResult.cs b/Core/UploadResult.cs
new file mode 100644
index 0000000..282af3b
--- /dev/null
+++ b/Core/UploadResult.cs
@@ -0,0 +1,10 @@
+namespace Core
+{
+ public class UploadResult
+ {
+ public bool Uploaded { get; set; }
+ public string? FileName { get; set; }
+ public string? StoredFileName { get; set; }
+ public int ErrorCode { get; set; }
+ }
+}
diff --git a/LiMan.Api/Controllers/FilesaveController.cs b/LiMan.Api/Controllers/FilesaveController.cs
new file mode 100644
index 0000000..3937abd
--- /dev/null
+++ b/LiMan.Api/Controllers/FilesaveController.cs
@@ -0,0 +1,197 @@
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Net;
+using System.Threading.Tasks;
+using Core;
+using LiMan.APi.Data;
+using Microsoft.AspNetCore.Hosting;
+using Microsoft.AspNetCore.Http;
+using Microsoft.AspNetCore.Mvc;
+using Microsoft.Extensions.Logging;
+
+namespace LiMan.APi.Controllers
+{
+ ///
+ /// Controller caricamento file
+ ///
+ [ApiController]
+ [Route("api/filesave")]
+ public class FilesaveController : ControllerBase
+ {
+ private readonly IWebHostEnvironment env;
+ private readonly ILogger logger;
+
+ ///
+ /// Dataservice x accesso DB
+ ///
+ protected ApiDataService dataService { get; set; }
+
+ ///
+ /// Init generico
+ ///
+ ///
+ public FilesaveController(ApiDataService DataService, IWebHostEnvironment env, ILogger logger)
+ {
+ dataService = DataService;
+ this.env = env;
+ this.logger = logger;
+ logger.LogInformation("Avviata classe FilesaveController");
+ }
+
+
+ ///
+ /// Caricamento file effettivo via POST
+ ///
+ /// TicketId x riferimento
+ /// Elenco files da caricare
+ ///
+ [HttpPost("single")]
+ public async Task> PostSingleFile([FromForm] int ticketId, [FromForm] IFormFile file)
+ {
+ // max 20 mb
+ long maxFileSize = 1024 * 1024 * 20;
+ string ticketDir = $"T{ticketId:000000000}";
+ var resourcePath = new Uri($"{Request.Scheme}://{Request.Host}/api/filesave/{ticketDir}");
+ List uploadResults = new();
+ string fileDir = env.ContentRootPath;
+ string relDir = env.EnvironmentName;
+
+ var uploadResult = new UploadResult();
+ string trustedFileNameForFileStorage;
+ var untrustedFileName = file.FileName;
+ uploadResult.FileName = untrustedFileName;
+ var trustedFileNameForDisplay = WebUtility.HtmlEncode(untrustedFileName);
+
+ if (file.Length == 0)
+ {
+ logger.LogInformation("{FileName} length is 0 (Err: 1)", trustedFileNameForDisplay);
+ uploadResult.ErrorCode = 1;
+ }
+ else if (file.Length > maxFileSize)
+ {
+ logger.LogInformation("{FileName} of {Length} bytes is larger than the limit of {Limit} bytes (Err: 2)", trustedFileNameForDisplay, file.Length, maxFileSize);
+ uploadResult.ErrorCode = 2;
+ }
+ else
+ {
+ try
+ {
+ DateTime oggi = DateTime.Today;
+ trustedFileNameForFileStorage = Path.GetRandomFileName();
+ relDir = Path.Combine(env.EnvironmentName, "unsafe_uploads", ticketDir);
+ fileDir = Path.Combine(env.ContentRootPath, relDir);
+ //string fileDir = Path.Combine(env.ContentRootPath, env.EnvironmentName, "unsafe_uploads", $"{oggi:yyyy}", $"{oggi:MM}", $"{oggi:dd}");
+ if (!Directory.Exists(fileDir))
+ {
+ Directory.CreateDirectory(fileDir);
+ }
+ var path = Path.Combine(fileDir, trustedFileNameForFileStorage);
+
+ await using FileStream fs = new(path, FileMode.Create);
+ await file.CopyToAsync(fs);
+
+ logger.LogInformation("{FileName} saved at {Path}", trustedFileNameForDisplay, path);
+ uploadResult.Uploaded = true;
+ uploadResult.StoredFileName = trustedFileNameForFileStorage;
+ }
+ catch (IOException ex)
+ {
+ logger.LogError("{FileName} error on upload (Err: 3): {Message}", trustedFileNameForDisplay, ex.Message);
+ uploadResult.ErrorCode = 3;
+ }
+ }
+
+ uploadResults.Add(uploadResult);
+ // salvo su DB
+ var fatto = dataService.FileAdd(ticketId, relDir, uploadResults);
+
+ return new CreatedResult(resourcePath, uploadResult);
+ }
+
+ ///
+ /// Caricamento file effettivo via POST
+ ///
+ /// TicketId x riferimento
+ /// Elenco files da caricare
+ ///
+ [HttpPost()]
+ public async Task>> PostFiles([FromForm] int ticketId, [FromForm] IEnumerable files)
+ {
+ // max 3 files
+ var maxAllowedFiles = 3;
+ // max 20 mb
+ long maxFileSize = 1024 * 1024 * 20;
+ var filesProcessed = 0;
+ string ticketDir = $"T{ticketId:000000000}";
+ var resourcePath = new Uri($"{Request.Scheme}://{Request.Host}/api/filesave/{ticketDir}");
+ List uploadResults = new();
+ string fileDir = env.ContentRootPath;
+ string relDir = env.EnvironmentName;
+
+ foreach (var file in files)
+ {
+ var uploadResult = new UploadResult();
+ string trustedFileNameForFileStorage;
+ var untrustedFileName = file.FileName;
+ uploadResult.FileName = untrustedFileName;
+ var trustedFileNameForDisplay = WebUtility.HtmlEncode(untrustedFileName);
+
+ if (filesProcessed < maxAllowedFiles)
+ {
+ if (file.Length == 0)
+ {
+ logger.LogInformation("{FileName} length is 0 (Err: 1)", trustedFileNameForDisplay);
+ uploadResult.ErrorCode = 1;
+ }
+ else if (file.Length > maxFileSize)
+ {
+ logger.LogInformation("{FileName} of {Length} bytes is larger than the limit of {Limit} bytes (Err: 2)", trustedFileNameForDisplay, file.Length, maxFileSize);
+ uploadResult.ErrorCode = 2;
+ }
+ else
+ {
+ try
+ {
+ DateTime oggi = DateTime.Today;
+ trustedFileNameForFileStorage = Path.GetRandomFileName();
+ relDir = Path.Combine(env.EnvironmentName, "unsafe_uploads", ticketDir);
+ fileDir = Path.Combine(env.ContentRootPath, relDir);
+ //string fileDir = Path.Combine(env.ContentRootPath, env.EnvironmentName, "unsafe_uploads", $"{oggi:yyyy}", $"{oggi:MM}", $"{oggi:dd}");
+ if (!Directory.Exists(fileDir))
+ {
+ Directory.CreateDirectory(fileDir);
+ }
+ var path = Path.Combine(fileDir, trustedFileNameForFileStorage);
+
+ await using FileStream fs = new(path, FileMode.Create);
+ await file.CopyToAsync(fs);
+
+ logger.LogInformation("{FileName} saved at {Path}", trustedFileNameForDisplay, path);
+ uploadResult.Uploaded = true;
+ uploadResult.StoredFileName = trustedFileNameForFileStorage;
+ }
+ catch (IOException ex)
+ {
+ logger.LogError("{FileName} error on upload (Err: 3): {Message}", trustedFileNameForDisplay, ex.Message);
+ uploadResult.ErrorCode = 3;
+ }
+ }
+
+ filesProcessed++;
+ }
+ else
+ {
+ logger.LogInformation("{FileName} not uploaded because the request exceeded the allowed {Count} of files (Err: 4)", trustedFileNameForDisplay, maxAllowedFiles);
+ uploadResult.ErrorCode = 4;
+ }
+
+ uploadResults.Add(uploadResult);
+ }
+ // salvo su DB
+ var fatto = dataService.FileAdd(ticketId, relDir, uploadResults);
+
+ return new CreatedResult(resourcePath, uploadResults);
+ }
+ }
+}
diff --git a/LiMan.Api/Controllers/LicenzaController.cs b/LiMan.Api/Controllers/LicenzaController.cs
index f86e8f6..84ce909 100644
--- a/LiMan.Api/Controllers/LicenzaController.cs
+++ b/LiMan.Api/Controllers/LicenzaController.cs
@@ -74,7 +74,7 @@ namespace LiMan.APi.Controllers
/// Info licenza in formato LicenseCoord
///
[HttpPost()]
- public async Task> Get([FromBody] LicenseCoord AppInfo)
+ public async Task> Post([FromBody] LicenseCoord AppInfo)
{
var result = await dataService.LicenzeSearch(AppInfo.CodInst, AppInfo.CodApp, AppInfo.MasterKey, false);
await dataService.recordCall(AppInfo.CodInst, AppInfo.CodApp, $"POST:api/licenza:{AppInfo.MasterKey}");
diff --git a/LiMan.Api/Controllers/TicketController.cs b/LiMan.Api/Controllers/TicketController.cs
index 640110f..0965b08 100644
--- a/LiMan.Api/Controllers/TicketController.cs
+++ b/LiMan.Api/Controllers/TicketController.cs
@@ -54,7 +54,7 @@ namespace LiMan.APi.Controllers
/// GET api/ticket/id
///
- /// Recupera elenco applicativi dati cliente
+ /// Recupera elenco Ticket dato cliente / applicazione / chiave
///
/// Codice cliente/Installazione
/// Codice Applicazione
@@ -74,9 +74,9 @@ namespace LiMan.APi.Controllers
/// Obj Richiesta
// POST api/ticket/sendReq
[HttpPost("sendReq")]
- public async Task> sendReq([FromBody] SupportRequest CurrRequest)
+ public async Task sendReq([FromBody] SupportRequest CurrRequest)
{
- List result = new List();
+ TicketDTO result = new TicketDTO();
// controllo valori
if (CurrRequest.IsValid)
{
@@ -84,7 +84,8 @@ namespace LiMan.APi.Controllers
var insRes = await dataService.TicketAdd(CurrRequest);
}
// restituisco richieste aperte
- result = await dataService.TicketByCliente(CurrRequest.CodInst, CurrRequest.CodApp, CurrRequest.MasterKey);
+ var rawResult= await dataService.TicketByCliente(CurrRequest.CodInst, CurrRequest.CodApp, CurrRequest.MasterKey, 1);
+ result = rawResult.FirstOrDefault();
await dataService.recordCall(CurrRequest.CodInst, CurrRequest.CodApp, $"POST:api/ticket/sendReq:{CurrRequest.MasterKey}");
return result;
}
diff --git a/LiMan.Api/Data/ApiDataService.cs b/LiMan.Api/Data/ApiDataService.cs
index f85d8c7..acdb9d9 100644
--- a/LiMan.Api/Data/ApiDataService.cs
+++ b/LiMan.Api/Data/ApiDataService.cs
@@ -1,20 +1,19 @@
using Core;
using LiMan.DB.DBModels;
+using LiMan.DB.DTO;
using Microsoft.AspNetCore.Identity.UI.Services;
using Microsoft.Extensions.Caching.Distributed;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using NLog;
+using StackExchange.Redis.Extensions.Core.Abstractions;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
-using System.Text;
using System.Threading.Tasks;
using static LiMan.DB.Enum;
-using StackExchange.Redis.Extensions.Core.Abstractions;
-using LiMan.DB.DTO;
namespace LiMan.APi.Data
{
@@ -23,48 +22,24 @@ namespace LiMan.APi.Data
///
public class ApiDataService : IDisposable
{
- #region Public Fields
-
- ///
- /// Classe Accesso metodi DB
- ///
- public static LiMan.DB.Controllers.DbController dbController;
-
- #endregion Public Fields
-
- #region Protected Fields
-
- ///
- /// TTL da 1 h x cache Redis
- ///
- protected const int hourTTL = 60 * 60;
-
- ///
- /// Chiave redis x statistiche in acquisizione
- ///
- protected const string rKeySampleStats = "LiMan.UI:SampleStats:Curr";
-
- ///
- /// Chiave redis x statistiche in acquisizione
- ///
- protected const string rKeySampleVars = "LiMan.UI:SampleStats:Vars";
- ///
- /// Chiave redis x licenze da MasterKey
- ///
- protected const string rKeyLicenze = "LiMan.UI:Licenze:ListByKey";
-
- #endregion Protected Fields
-
#region Private Fields
private static IConfiguration _configuration;
+
private static ILogger _logger;
+
private static NLog.Logger Log = LogManager.GetCurrentClassLogger();
+
private readonly IEmailSender _emailSender;
//private readonly IDistributedCache distributedCache;
private readonly IRedisCacheClient _redisCacheClient;
+ ///
+ /// Elenco obj in cache
+ ///
+ private List cachedDataList = new List();
+
///
/// Durata assoluta massima della cache IN SECONDI
///
@@ -78,6 +53,49 @@ namespace LiMan.APi.Data
#endregion Private Fields
+ #region Protected Fields
+
+ ///
+ /// TTL da 1 h x cache Redis
+ ///
+ protected const int hourTTL = 60 * 60;
+
+ ///
+ /// Chiave redis x attivazioni da IdxLic
+ ///
+ protected const string rKeyAttivByLic = "LiMan.UI:Licenze:AttByIdxLic";
+
+ ///
+ /// Chiave redis x licenze da MasterKey
+ ///
+ protected const string rKeyLicByMKey = "LiMan.UI:Licenze:ListByKey";
+
+ ///
+ /// Chiave redis x statistiche in acquisizione
+ ///
+ protected const string rKeySampleStats = "LiMan.UI:SampleStats:Curr";
+
+ ///
+ /// Chiave redis x statistiche in acquisizione
+ ///
+ protected const string rKeySampleVars = "LiMan.UI:SampleStats:Vars";
+
+ ///
+ /// TTL da 1 min x cache Redis
+ ///
+ protected const int shortTTL = 60 * 5;
+
+ #endregion Protected Fields
+
+ #region Public Fields
+
+ ///
+ /// Classe Accesso metodi DB
+ ///
+ public static LiMan.DB.Controllers.DbController dbController;
+
+ #endregion Public Fields
+
#region Public Constructors
///
@@ -112,6 +130,174 @@ namespace LiMan.APi.Data
#endregion Public Constructors
+ #region Private Methods
+
+ ///
+ /// Parametri per generare opzioni cache
+ ///
+ /// Fattore di moltiplica cache (se 1 --> 2 e 5 min)
+ ///
+ private DistributedCacheEntryOptions cacheOpt(int multFact)
+ {
+ var numSecAbsExp = multFact <= 0 ? chAbsExp : chAbsExp * multFact;
+ var numSecSliExp = multFact <= 0 ? chSliExp : chSliExp * multFact;
+ return new DistributedCacheEntryOptions().SetAbsoluteExpiration(DateTime.Now.AddSeconds(numSecAbsExp)).SetSlidingExpiration(TimeSpan.FromSeconds(numSecSliExp));
+ }
+
+ #endregion Private Methods
+
+ #region Protected Methods
+
+ ///
+ /// Recupera statistiche correnti
+ ///
+ ///
+ protected async Task getCurrStats()
+ {
+ DateTime adesso = DateTime.Now;
+ SampleStats answ = new SampleStats()
+ {
+ Name = "ApiStats"
+ };
+ // in primis check data/ora prima/ultima scrittura del set... (2 date, lista chiavi gestite)
+ string rawData = await getRSV(rKeySampleStats);
+ if (rawData != null)
+ {
+ answ = JsonConvert.DeserializeObject(rawData);
+ // aggiorno ultimo controllo e salvo...
+ answ.DtLast = adesso;
+ // salvo!
+ await setCurrStats(answ);
+ }
+ // controllo se scadute...
+ if (adesso.Subtract(answ.DtFirst).TotalMinutes > 60)
+ {
+ // se scaduto --> registrazione set sul DB (async), resettando i vari contatori...
+ bool salvato = await saveStatsToDb(answ.VList);
+ // inizio NUOVO set vuoto con record corrente
+ answ = new SampleStats()
+ {
+ Name = "ApiStats"
+ };
+ // salvo!
+ await setCurrStats(answ);
+ }
+ // restituisco record!
+ return answ;
+ }
+
+ ///
+ /// Recupero chiave da redis
+ ///
+ ///
+ ///
+ protected async Task getRSV(string rKey)
+ {
+ string answ = await _redisCacheClient.GetDbFromConfiguration().GetAsync(rKey);
+ return answ;
+ }
+
+ ///
+ /// Recupera contatore x la chiave redis indicata...
+ ///
+ ///
+ protected async Task redCount(string rKey)
+ {
+ int currCount = 0;
+ string rawVal = await getRSV(rKey);
+ if (!string.IsNullOrEmpty(rawVal))
+ {
+ int.TryParse(rawVal, out currCount);
+ }
+ return currCount;
+ }
+
+ ///
+ /// Resetta contatore x la chiave redis indicata...
+ ///
+ ///
+ protected async Task redCountClear(string rKey)
+ {
+ bool answ = false;
+ int currCount = 0;
+ answ = await setRSV(rKey, currCount, 2 * hourTTL);
+ return answ;
+ }
+
+ ///
+ /// Incrementa contatore x la chiave redis indicata...
+ ///
+ ///
+ protected async Task redCountIncr(string rKey)
+ {
+ bool answ = false;
+ int currCount = 0;
+ string rawVal = await getRSV(rKey);
+ if (!string.IsNullOrEmpty(rawVal))
+ {
+ int.TryParse(rawVal, out currCount);
+ }
+ currCount++;
+ answ = await setRSV(rKey, currCount, 2 * hourTTL);
+ return answ;
+ }
+
+ ///
+ /// Salva statistiche correnti
+ ///
+ ///
+ protected async Task setCurrStats(SampleStats newVal)
+ {
+ bool answ = false;
+ string rawData = JsonConvert.SerializeObject(newVal);
+ answ = await setRSV(rKeySampleStats, rawData, 24 * hourTTL);
+ return answ;
+ }
+
+ ///
+ /// Salvataggio chiave in redis
+ ///
+ ///
+ ///
+ ///
+ ///
+ protected async Task setRSV(string rKey, string rVal, int ttlSec)
+ {
+ bool fatto = false;
+ await _redisCacheClient.GetDbFromConfiguration().AddAsync(rKey, rVal, DateTimeOffset.Now.AddSeconds(ttlSec));
+ fatto = true;
+ return fatto;
+ }
+
+ ///
+ /// Salvataggio chiave in redis
+ ///
+ ///
+ ///
+ ///
+ ///
+ protected async Task setRSV(string rKey, int rValInt, int ttlSec)
+ {
+ bool fatto = false;
+ await _redisCacheClient.GetDbFromConfiguration().AddAsync(rKey, rValInt, DateTimeOffset.Now.AddSeconds(ttlSec));
+ fatto = true;
+ return fatto;
+ }
+
+ ///
+ /// Registra in cache chiave se non fosse già in elenco
+ ///
+ ///
+ protected void trackCache(string newKey)
+ {
+ if (!cachedDataList.Contains(newKey))
+ {
+ cachedDataList.Add(newKey);
+ }
+ }
+
+ #endregion Protected Methods
+
#region Public Methods
///
@@ -121,9 +307,9 @@ namespace LiMan.APi.Data
/// Codice Applicazione
/// Indica se nascondere i dati sensibili
///
- public async Task> ApplicativiSearch(string CodInst, string CodApp, bool HideData)
+ public async Task> ApplicativiSearch(string CodInst, string CodApp, bool HideData)
{
- List dbResult = new List();
+ List dbResult = new List();
Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();
@@ -142,9 +328,9 @@ namespace LiMan.APi.Data
/// Codice Impiego licenza
/// Indica se nascondere i dati sensibili
///
- public async Task AttivazioneSearch(string Chiave, string CodImpiego, bool HideData)
+ public async Task AttivazioneSearch(string Chiave, string CodImpiego, bool HideData)
{
- DB.DTO.AttivazioneDTO dbResult = new DB.DTO.AttivazioneDTO();
+ AttivazioneDTO dbResult = new AttivazioneDTO();
Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();
@@ -160,20 +346,30 @@ namespace LiMan.APi.Data
///
/// Elenco Attivaizoni da ID Licenza master
///
- /// Idx Licenza Master
- /// Indica se nascondere i dati sensibili
+ /// Idx Licenza Master
+ /// Indica se nascondere i dati sensibili
///
- public async Task> AttivazioniByLic(int IdxLic, bool HideData)
+ public async Task> AttivazioniByLic(int idxLic, bool hideData)
{
- List dbResult = new List();
-
- Stopwatch stopWatch = new Stopwatch();
- stopWatch.Start();
-
- dbResult = dbController.GetAttivazioniByLic(IdxLic, HideData);
- stopWatch.Stop();
- TimeSpan ts = stopWatch.Elapsed;
- Log.Trace($"Effettuata lettura da DB per AttivazioniByLic: {ts.TotalMilliseconds} ms");
+ List dbResult = new List();
+ string cacheKey = $"{rKeyAttivByLic}:{hideData}:{idxLic}";
+ trackCache(cacheKey);
+ string rawData = await getRSV(cacheKey);
+ if (!string.IsNullOrEmpty(rawData))
+ {
+ dbResult = JsonConvert.DeserializeObject>(rawData);
+ }
+ else
+ {
+ Stopwatch stopWatch = new Stopwatch();
+ stopWatch.Start();
+ dbResult = dbController.GetAttivazioniByLic(idxLic, hideData);
+ rawData = JsonConvert.SerializeObject(dbResult);
+ await setRSV(cacheKey, rawData, shortTTL);
+ stopWatch.Stop();
+ TimeSpan ts = stopWatch.Elapsed;
+ Log.Trace($"Effettuata lettura da DB per AttivazioniByLic: {ts.TotalMilliseconds} ms");
+ }
return await Task.FromResult(dbResult);
}
@@ -184,21 +380,24 @@ namespace LiMan.APi.Data
/// Licenza Master
/// Indica se nascondere i dati sensibili
///
- public async Task> AttivazioniByMasterKey(string MasterKey, bool HideData)
+ public async Task> AttivazioniByMasterKey(string MasterKey, bool HideData)
{
- List dbResult = new List();
+ List dbResult = new List();
Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();
- var licenza = dbController.GetLicenza(MasterKey);
+#if false
+ LicenzaModel licenza = dbController.GetLicenza(MasterKey);
+#endif
+ LicenzaModel licenza = await LicenzaByMasterKey(MasterKey);
if (licenza != null)
{
- dbResult = dbController.GetAttivazioniByLic(licenza.IdxLic, HideData);
+ dbResult = await AttivazioniByLic(licenza.IdxLic, HideData);
}
stopWatch.Stop();
TimeSpan ts = stopWatch.Elapsed;
- Log.Trace($"Effettuata lettura da DB per AttivazioniByLic: {ts.TotalMilliseconds} ms");
+ Log.Trace($"Effettuata lettura da DB per AttivazioniByMasterKey: {ts.TotalMilliseconds} ms");
return await Task.FromResult(dbResult);
}
@@ -215,11 +414,11 @@ namespace LiMan.APi.Data
Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();
-
- var licenza = dbController.GetLicenza(MasterKey);
+ LicenzaModel licenza = await LicenzaByMasterKey(MasterKey);
if (licenza != null)
{
answ = dbController.AttivazioniDelete(ParamDict, MasterKey);
+ await InvalidateAllCache();
}
stopWatch.Stop();
TimeSpan ts = stopWatch.Elapsed;
@@ -239,11 +438,12 @@ namespace LiMan.APi.Data
Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();
+ LicenzaModel licenza = await LicenzaByMasterKey(MasterKey);
- var licenza = dbController.GetLicenza(MasterKey);
if (licenza != null)
{
answ = dbController.AttivazioniResetAvail(MasterKey);
+ await InvalidateAllCache();
}
stopWatch.Stop();
TimeSpan ts = stopWatch.Elapsed;
@@ -268,6 +468,7 @@ namespace LiMan.APi.Data
stopWatch.Start();
taskDone = dbController.AttivazioniTryAdd(MasterKey, ParamDict, DayVeto);
+ await InvalidateAllCache();
stopWatch.Stop();
TimeSpan ts = stopWatch.Elapsed;
Log.Trace($"Effettuata scrittura + rilettura da DB per AttivazioniTryAdd: {ts.TotalMilliseconds} ms");
@@ -290,6 +491,7 @@ namespace LiMan.APi.Data
stopWatch.Start();
taskDone = dbController.AttivazioniTryRefresh(MasterKey, ParamDict);
+ await InvalidateAllCache();
stopWatch.Stop();
TimeSpan ts = stopWatch.Elapsed;
Log.Trace($"Effettuata scrittura + rilettura da DB per AttivazioniTryRefresh: {ts.TotalMilliseconds} ms");
@@ -306,6 +508,41 @@ namespace LiMan.APi.Data
dbController.Dispose();
}
+ ///
+ /// Esegue aggiunta file dato ticket e list uploadResult
+ ///
+ /// Identificativo del ticket
+ /// Directory di salvataggio dei file
+ /// lista risultati della funzione di upload
+ ///
+ public async Task FileAdd(int idxTicket, string baseDir, List fileUploaded)
+ {
+ bool fatto = false;
+ // inserimento!
+ Stopwatch stopWatch = new Stopwatch();
+ stopWatch.Start();
+ fatto = dbController.FileAdd(idxTicket, baseDir, fileUploaded);
+ stopWatch.Stop();
+ TimeSpan ts = stopWatch.Elapsed;
+ Log.Trace($"Effettuata inserimento con FileAdd: {ts.TotalMilliseconds} ms");
+
+ // restituisce elenco
+ return await Task.FromResult(fatto);
+ }
+
+ ///
+ /// invalida tutta la cache in caso di update
+ ///
+ ///
+ public async Task InvalidateAllCache()
+ {
+ foreach (var item in cachedDataList)
+ {
+ await _redisCacheClient.GetDbFromConfiguration().RemoveAsync(item);
+ }
+ cachedDataList = new List();
+ }
+
///
/// Elenco licenze dato cliente
///
@@ -314,7 +551,8 @@ namespace LiMan.APi.Data
public async Task LicenzaByMasterKey(string chiave)
{
LicenzaModel dbResult = new LicenzaModel();
- string cacheKey = $"{rKeyLicenze}:{chiave}";
+ string cacheKey = $"{rKeyLicByMKey}:{chiave}";
+ trackCache(cacheKey);
string rawData = await getRSV(cacheKey);
if (!string.IsNullOrEmpty(rawData))
{
@@ -340,10 +578,11 @@ namespace LiMan.APi.Data
///
///
///
- public async Task LicenzaRefreshPayload(LicenseCoord appInfo)
+ public async Task LicenzaRefreshPayload(LicenseCoord appInfo)
{
// chiamo metodo x ricalcolare payload dato enigma
bool done = await dbController.LicenseUpdatePayload(appInfo.CodInst, appInfo.CodApp, appInfo.MasterKey, appInfo.Enigma);
+ await InvalidateAllCache();
// ora recupero i dati
var licList = await LicenzeSearch(appInfo.CodInst, appInfo.CodApp, appInfo.MasterKey, false);
return licList.FirstOrDefault();
@@ -376,9 +615,9 @@ namespace LiMan.APi.Data
/// Chiave Licenza da validare
/// Indica se nascondere i dati sensibili
///
- public async Task> LicenzeSearch(string CodInst, string CodApp, string Chiave, bool HideData)
+ public async Task> LicenzeSearch(string CodInst, string CodApp, string Chiave, bool HideData)
{
- List dbResult = new List();
+ List dbResult = new List();
Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();
@@ -452,7 +691,7 @@ namespace LiMan.APi.Data
{
CodInst = valStr[0],
CodApp = valStr[1],
- TargetUrl = valStr[2],
+ TargetUrl = item.Replace($"{rKeySampleVars}:", ""), //valStr[2],
DataRif = DateTime.Now,
NumCall = currCount
};
@@ -516,13 +755,13 @@ namespace LiMan.APi.Data
///
///
///
- public async Task> TicketByCliente(string CodInst, string CodApp, string MasterKey, int numRec = 50)
+ public async Task> TicketByCliente(string CodInst, string CodApp, string MasterKey, int numRec = 10)
{
List dbResult = new List();
Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();
- dbResult = dbController.TicketGetFilt(true, CodApp, CodInst, MasterKey, numRec);
+ dbResult = dbController.TicketGetFilt(true, TipologiaTicket.ND, CodApp, CodInst, MasterKey, numRec);
stopWatch.Stop();
TimeSpan ts = stopWatch.Elapsed;
Log.Trace($"Effettuata lettura da DB per TicketByCliente: {ts.TotalMilliseconds} ms");
@@ -553,181 +792,5 @@ namespace LiMan.APi.Data
#endregion Public Methods
- #region Protected Methods
-
- ///
- /// Recupera statistiche correnti
- ///
- ///
- protected async Task getCurrStats()
- {
- DateTime adesso = DateTime.Now;
- SampleStats answ = new SampleStats()
- {
- Name = "ApiStats"
- };
- // in primis check data/ora prima/ultima scrittura del set... (2 date, lista chiavi gestite)
- string rawData = await getRSV(rKeySampleStats);
- if (rawData != null)
- {
- answ = JsonConvert.DeserializeObject(rawData);
- // aggiorno ultimo controllo e salvo...
- answ.DtLast = adesso;
- // salvo!
- await setCurrStats(answ);
- }
- // controllo se scadute...
- if (adesso.Subtract(answ.DtFirst).TotalMinutes > 60)
- {
- // se scaduto --> registrazione set sul DB (async), resettando i vari contatori...
- bool salvato = await saveStatsToDb(answ.VList);
- // inizio NUOVO set vuoto con record corrente
- answ = new SampleStats()
- {
- Name = "ApiStats"
- };
- // salvo!
- await setCurrStats(answ);
- }
- // restituisco record!
- return answ;
- }
-
- ///
- /// Recupero chiave da redis
- ///
- ///
- ///
- protected async Task getRSV(string rKey)
- {
- string answ = await _redisCacheClient.GetDbFromConfiguration().GetAsync(rKey);
- return answ;
- }
-
- ///
- /// Resetta contatore x la chiave redis indicata...
- ///
- ///
- protected async Task redCountClear(string rKey)
- {
- bool answ = false;
- int currCount = 0;
- answ = await setRSV(rKey, currCount, 2 * hourTTL);
- return answ;
- }
- ///
- /// Recupera contatore x la chiave redis indicata...
- ///
- ///
- protected async Task redCount(string rKey)
- {
- int currCount = 0;
- string rawVal = await getRSV(rKey);
- if (!string.IsNullOrEmpty(rawVal))
- {
- int.TryParse(rawVal, out currCount);
- }
- return currCount;
- }
-
- ///
- /// Incrementa contatore x la chiave redis indicata...
- ///
- ///
- protected async Task redCountIncr(string rKey)
- {
- bool answ = false;
- int currCount = 0;
- string rawVal = await getRSV(rKey);
- if (!string.IsNullOrEmpty(rawVal))
- {
- int.TryParse(rawVal, out currCount);
- }
- currCount++;
- answ = await setRSV(rKey, currCount, 2 * hourTTL);
- return answ;
- }
-
- ///
- /// Salva statistiche correnti
- ///
- ///
- protected async Task setCurrStats(SampleStats newVal)
- {
- bool answ = false;
- string rawData = JsonConvert.SerializeObject(newVal);
- answ = await setRSV(rKeySampleStats, rawData, 24 * hourTTL);
- return answ;
- }
-
- ///
- /// Salvataggio chiave in redis
- ///
- ///
- ///
- ///
- ///
- protected async Task setRSV(string rKey, string rVal, int ttlSec)
- {
- bool fatto = false;
- await _redisCacheClient.GetDbFromConfiguration().AddAsync(rKey, rVal, DateTimeOffset.Now.AddSeconds(ttlSec));
- fatto = true;
- return fatto;
- }
-
- ///
- /// Salvataggio chiave in redis
- ///
- ///
- ///
- ///
- ///
- protected async Task setRSV(string rKey, int rValInt, int ttlSec)
- {
- bool fatto = false;
- await _redisCacheClient.GetDbFromConfiguration().AddAsync(rKey, rValInt, DateTimeOffset.Now.AddSeconds(ttlSec));
- fatto = true;
- return fatto;
- }
-
- #endregion Protected Methods
-
- #region Private Methods
-
- ///
- /// Parametri per generare opzioni cache
- ///
- /// Fattore di moltiplica cache (se 1 --> 2 e 5 min)
- ///
- private DistributedCacheEntryOptions cacheOpt(int multFact)
- {
- var numSecAbsExp = multFact <= 0 ? chAbsExp : chAbsExp * multFact;
- var numSecSliExp = multFact <= 0 ? chSliExp : chSliExp * multFact;
- return new DistributedCacheEntryOptions().SetAbsoluteExpiration(DateTime.Now.AddSeconds(numSecAbsExp)).SetSlidingExpiration(TimeSpan.FromSeconds(numSecSliExp));
- }
-
- #endregion Private Methods
-
-#if false
- ///
- /// Elenco ticket dato licenza (limitato a maxRec)
- ///
- ///
- ///
- ///
- public async Task> TicketByLic(int idxLic, int maxRec = 100)
- {
- List dbResult = new List();
- Stopwatch stopWatch = new Stopwatch();
- stopWatch.Start();
-
- dbResult = dbController.TicketGetByLic(idxLic, maxRec);
- stopWatch.Stop();
- TimeSpan ts = stopWatch.Elapsed;
- Log.Trace($"Effettuata lettura da DB per TicketByLic: {ts.TotalMilliseconds} ms");
-
- return await Task.FromResult(dbResult);
- }
-#endif
}
}
\ No newline at end of file
diff --git a/LiMan.Api/Development/unsafe_uploads/.placeholder.file b/LiMan.Api/Development/unsafe_uploads/.placeholder.file
new file mode 100644
index 0000000..5f28270
--- /dev/null
+++ b/LiMan.Api/Development/unsafe_uploads/.placeholder.file
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/LiMan.Api/LiMan.APi.csproj b/LiMan.Api/LiMan.APi.csproj
index 61666c4..5b11f5c 100644
--- a/LiMan.Api/LiMan.APi.csproj
+++ b/LiMan.Api/LiMan.APi.csproj
@@ -31,11 +31,20 @@
+
+ PreserveNewest
+
Always
Always
+
+ PreserveNewest
+
+
+ PreserveNewest
+
\ No newline at end of file
diff --git a/LiMan.Api/LiMan.APi.xml b/LiMan.Api/LiMan.APi.xml
index 76c280d..41bbade 100644
--- a/LiMan.Api/LiMan.APi.xml
+++ b/LiMan.Api/LiMan.APi.xml
@@ -93,6 +93,38 @@
Codice univoco impiego licenza
+
+
+ Controller caricamento file
+
+
+
+
+ Dataservice x accesso DB
+
+
+
+
+ Init generico
+
+
+
+
+
+ Caricamento file effettivo via POST
+
+ TicketId x riferimento
+ Elenco files da caricare
+
+
+
+
+ Caricamento file effettivo via POST
+
+ TicketId x riferimento
+ Elenco files da caricare
+
+
Controller livello INSTALLAZIONI
@@ -153,7 +185,7 @@
Chiave licenza da validare
-
+
POST api/licenza
Recupera dati Licenza Applicativa (id licenza + num utenze) dati cliente + programma + licenza ATTUALE
@@ -192,7 +224,7 @@
GET api/ticket/id
- Recupera elenco applicativi dati cliente
+ Recupera elenco Ticket dato cliente / applicazione / chiave
Codice cliente/Installazione
Codice Applicazione
@@ -210,29 +242,9 @@
Classe astrazione accesso dati
-
+
- Classe Accesso metodi DB
-
-
-
-
- TTL da 1 h x cache Redis
-
-
-
-
- Chiave redis x statistiche in acquisizione
-
-
-
-
- Chiave redis x statistiche in acquisizione
-
-
-
-
- Chiave redis x licenze da MasterKey
+ Elenco obj in cache
@@ -246,6 +258,41 @@
NON estende oltre il tempo massimo di validità della cache (chAbsExp)
+
+
+ TTL da 1 h x cache Redis
+
+
+
+
+ Chiave redis x attivazioni da IdxLic
+
+
+
+
+ Chiave redis x licenze da MasterKey
+
+
+
+
+ Chiave redis x statistiche in acquisizione
+
+
+
+
+ Chiave redis x statistiche in acquisizione
+
+
+
+
+ TTL da 1 min x cache Redis
+
+
+
+
+ Classe Accesso metodi DB
+
+
Init classe
@@ -256,6 +303,74 @@
+
+
+ Parametri per generare opzioni cache
+
+ Fattore di moltiplica cache (se 1 --> 2 e 5 min)
+
+
+
+
+ Recupera statistiche correnti
+
+
+
+
+
+ Recupero chiave da redis
+
+
+
+
+
+
+ Recupera contatore x la chiave redis indicata...
+
+
+
+
+
+ Resetta contatore x la chiave redis indicata...
+
+
+
+
+
+ Incrementa contatore x la chiave redis indicata...
+
+
+
+
+
+ Salva statistiche correnti
+
+
+
+
+
+ Salvataggio chiave in redis
+
+
+
+
+
+
+
+
+ Salvataggio chiave in redis
+
+
+
+
+
+
+
+
+ Registra in cache chiave se non fosse già in elenco
+
+
+
Elenco licenze dato cliente
@@ -278,8 +393,8 @@
Elenco Attivaizoni da ID Licenza master
- Idx Licenza Master
- Indica se nascondere i dati sensibili
+ Idx Licenza Master
+ Indica se nascondere i dati sensibili
@@ -329,6 +444,21 @@
Dispose classe
+
+
+ Esegue aggiunta file dato ticket e list uploadResult
+
+ Identificativo del ticket
+ Directory di salvataggio dei file
+ lista risultati della funzione di upload
+
+
+
+
+ invalida tutta la cache in caso di update
+
+
+
Elenco licenze dato cliente
@@ -416,67 +546,5 @@
-
-
- Recupera statistiche correnti
-
-
-
-
-
- Recupero chiave da redis
-
-
-
-
-
-
- Resetta contatore x la chiave redis indicata...
-
-
-
-
-
- Recupera contatore x la chiave redis indicata...
-
-
-
-
-
- Incrementa contatore x la chiave redis indicata...
-
-
-
-
-
- Salva statistiche correnti
-
-
-
-
-
- Salvataggio chiave in redis
-
-
-
-
-
-
-
-
- Salvataggio chiave in redis
-
-
-
-
-
-
-
-
- Parametri per generare opzioni cache
-
- Fattore di moltiplica cache (se 1 --> 2 e 5 min)
-
-
diff --git a/LiMan.Api/Production/unsafe_uploads/.placeholder.file b/LiMan.Api/Production/unsafe_uploads/.placeholder.file
new file mode 100644
index 0000000..5f28270
--- /dev/null
+++ b/LiMan.Api/Production/unsafe_uploads/.placeholder.file
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/LiMan.Api/Staging/unsafe_uploads/.placeholder.file b/LiMan.Api/Staging/unsafe_uploads/.placeholder.file
new file mode 100644
index 0000000..5f28270
--- /dev/null
+++ b/LiMan.Api/Staging/unsafe_uploads/.placeholder.file
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/LiMan.DB/Controllers/DbController.cs b/LiMan.DB/Controllers/DbController.cs
index c315665..ca492d0 100644
--- a/LiMan.DB/Controllers/DbController.cs
+++ b/LiMan.DB/Controllers/DbController.cs
@@ -6,6 +6,7 @@ using Microsoft.Extensions.Configuration;
using NLog;
using System;
using System.Collections.Generic;
+using System.IO;
using System.Linq;
using System.Security.Cryptography;
using System.Text;
@@ -277,6 +278,74 @@ namespace LiMan.DB.Controllers
//Log.Info("Dispose di GWMSController");
}
+ ///
+ /// Elenco files attach da registrare
+ ///
+ /// Identificativo del ticket
+ /// Directory di salvataggio dei file
+ /// lista risultati della funzione di upload
+ ///
+ public bool FileAdd(int idxTicket, string baseDir, List fileUploaded)
+ {
+ bool fatto = false;
+ if (fileUploaded == null || fileUploaded.Count == 0)
+ {
+ Log.Error("Errore FileAdd: fileUploaded è vuoto/nullo");
+ }
+ else
+ {
+ using (LMDbContext localDbCtx = new LMDbContext(_configuration))
+ {
+ // verifico Ticket sia esistente
+ var currTicket = localDbCtx
+ .DbSetTicket
+ .Where(x => x.IdxTicket == idxTicket)
+ .FirstOrDefault();
+
+ if (currTicket != null)
+ {
+ var newFiles = fileUploaded
+ .Select(x => new FileAttachModel()
+ {
+ IdxTicket = idxTicket,
+ OriginalName = x.FileName,
+ StorageName = x.StoredFileName,
+ DtEvent = DateTime.Now,
+ FullStoragePath = Path.Combine(baseDir, x.StoredFileName)
+ }).ToList();
+
+ localDbCtx
+ .DbSetFileAttach
+ .AddRange(newFiles);
+
+ localDbCtx.SaveChanges();
+
+ fatto = true;
+ }
+ }
+ }
+ return fatto;
+ }
+
+ ///
+ /// Elenco file registrati dato ticket id
+ ///
+ /// Identificativo del ticket
+ ///
+ public List FileGetFilt(int idxTicket)
+ {
+ List dbResult = new List();
+ using (LMDbContext localDbCtx = new LMDbContext(_configuration))
+ {
+ // recupero locenza...
+ dbResult = localDbCtx
+ .DbSetFileAttach
+ .Where(x => x.IdxTicket == idxTicket)
+ .ToList();
+ }
+ return dbResult;
+ }
+
public List GetApplicativiFilt(bool OnlyActive, string CodApp, string CodInst, bool hideData)
{
List dbResult = new List();
@@ -775,7 +844,8 @@ namespace LiMan.DB.Controllers
ContactPhone = currRequest.ContactPhone,
ReqBody = currRequest.ReqBody,
Status = Enum.StatoRichiesta.Richiesta,
- Tipo = Enum.TipoLicenza.UserKey
+ Tipo = Enum.TipoLicenza.UserKey,
+ TType = currRequest.Tipo
};
localDbCtx
@@ -790,12 +860,12 @@ namespace LiMan.DB.Controllers
return fatto;
}
- public List TicketGetFilt(bool onlyOpen, string CodApp, string CodInst, string MasterKey, int maxNum)
+ public List TicketGetFilt(bool onlyOpen, TipologiaTicket Tipo, string CodApp, string CodInst, string MasterKey, int maxNum)
{
List dbResult = new List();
using (LMDbContext localDbCtx = new LMDbContext(_configuration))
{
- // recupero locenza...
+ // recupero licenza...
var currLic = localDbCtx
.DbSetLicenze
.Where(x => x.CodApp == CodApp && x.CodInst == CodInst && x.Chiave == MasterKey)
@@ -805,8 +875,8 @@ namespace LiMan.DB.Controllers
{
dbResult = localDbCtx
.DbSetTicket
- .Where(x => x.IdxLic == currLic.IdxLic)
- .OrderByDescending(x => x.DtReq)
+ .Where(x => x.IdxLic == currLic.IdxLic && (x.Status <= StatoRichiesta.Valutazione || !onlyOpen) && (x.TType == Tipo || Tipo == TipologiaTicket.ND))
+ .OrderByDescending(x => x.IdxTicket)
.Take(maxNum)
.Select(x => new TicketDTO
{
@@ -823,7 +893,7 @@ namespace LiMan.DB.Controllers
SupplAnsw = x.SupplAnsw,
SupplEmail = x.SupplEmail,
SupplUserCode = x.SupplUserCode,
- Tipo= x.Tipo
+ Tipo = x.Tipo
})
.ToList();
}
diff --git a/LiMan.DB/DBModels/FileAttachModel.cs b/LiMan.DB/DBModels/FileAttachModel.cs
new file mode 100644
index 0000000..97c748e
--- /dev/null
+++ b/LiMan.DB/DBModels/FileAttachModel.cs
@@ -0,0 +1,53 @@
+using System;
+using System.Collections.Generic;
+using System.ComponentModel.DataAnnotations;
+using System.ComponentModel.DataAnnotations.Schema;
+using static LiMan.DB.Enum;
+
+#nullable disable
+
+namespace LiMan.DB.DBModels
+{
+ //
+ // This is here so CodeMaid doesn't reorganize this document
+ //
+ //[Index(nameof(Installazione), nameof(Active), nameof(DiskStatus))]
+ [Table("FileAttach")]
+ public partial class FileAttachModel
+ {
+ #region Public Properties
+
+ [Key, DatabaseGenerated(DatabaseGeneratedOption.Identity)]
+ public int IdxFileAttach { get; set; }
+
+ ///
+ /// Id del ticket cui è collegato
+ ///
+ public int IdxTicket { get; set; }
+
+ ///
+ /// DataOra evento
+ ///
+ public DateTime DtEvent { get; set; } = DateTime.Now;
+
+ ///
+ /// Codice univoco della sub licenza (opzionale)
+ ///
+ public string OriginalName { get; set; } = "";
+
+ ///
+ /// Nome con cui è salvato il file localmente
+ ///
+ public string StorageName { get; set; } = "";
+
+ ///
+ /// Path completo del file
+ ///
+ public string FullStoragePath { get; set; } = "";
+
+ [ForeignKey("IdxTicket")]
+ public virtual TicketModel TicketNav { get; set; }
+
+ #endregion Public Properties
+ }
+}
\ No newline at end of file
diff --git a/LiMan.DB/DBModels/TicketModel.cs b/LiMan.DB/DBModels/TicketModel.cs
index ee3f55a..ad03fbf 100644
--- a/LiMan.DB/DBModels/TicketModel.cs
+++ b/LiMan.DB/DBModels/TicketModel.cs
@@ -1,5 +1,5 @@
-using System;
-using System.Collections.Generic;
+using Core;
+using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using static LiMan.DB.Enum;
@@ -11,7 +11,6 @@ namespace LiMan.DB.DBModels
//
// This is here so CodeMaid doesn't reorganize this document
//
- //[Index(nameof(Installazione), nameof(Active), nameof(DiskStatus))]
[Table("TicketLog")]
public partial class TicketModel
{
@@ -22,6 +21,11 @@ namespace LiMan.DB.DBModels
public DateTime DtReq { get; set; } = DateTime.Now;
+ ///
+ /// Tipologia di ticket
+ ///
+ public TipologiaTicket TType { get; set; } = TipologiaTicket.Licenze;
+
///
/// Tipologia di licenza gestita
///
diff --git a/LiMan.DB/Enum.cs b/LiMan.DB/Enum.cs
index 7c7feec..1ed38f6 100644
--- a/LiMan.DB/Enum.cs
+++ b/LiMan.DB/Enum.cs
@@ -51,6 +51,8 @@ namespace LiMan.DB
CheckSumKey
}
+
+
#endregion Public Enums
}
}
\ No newline at end of file
diff --git a/LiMan.DB/LMDbContext.cs b/LiMan.DB/LMDbContext.cs
index 27a1305..3b2ee9d 100644
--- a/LiMan.DB/LMDbContext.cs
+++ b/LiMan.DB/LMDbContext.cs
@@ -49,6 +49,7 @@ namespace LiMan.DB
#region Public Properties
public virtual DbSet DbSetApp { get; set; }
+ public virtual DbSet DbSetFileAttach { get; set; }
public virtual DbSet DbSetInst { get; set; }
public virtual DbSet DbSetLicenze { get; set; }
public virtual DbSet DbSetLogCall { get; set; }
@@ -57,7 +58,7 @@ namespace LiMan.DB
public virtual DbSet DbSetTicket { get; set; }
#endregion Public Properties
-
+
partial void OnModelCreatingPartial(ModelBuilder modelBuilder);
diff --git a/LiMan.DB/Migrations/20211220181913_AddFileAttach.Designer.cs b/LiMan.DB/Migrations/20211220181913_AddFileAttach.Designer.cs
new file mode 100644
index 0000000..4717162
--- /dev/null
+++ b/LiMan.DB/Migrations/20211220181913_AddFileAttach.Designer.cs
@@ -0,0 +1,371 @@
+//
+using System;
+using LiMan.DB;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
+
+namespace LiMan.DB.Migrations
+{
+ [DbContext(typeof(LMDbContext))]
+ [Migration("20211220181913_AddFileAttach")]
+ partial class AddFileAttach
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+#pragma warning disable 612, 618
+ modelBuilder
+ .HasAnnotation("Relational:Collation", "SQL_Latin1_General_CP1_CI_AS")
+ .HasAnnotation("Relational:MaxIdentifierLength", 128)
+ .HasAnnotation("ProductVersion", "5.0.10")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LiMan.DB.DBModels.ApplicativoModel", b =>
+ {
+ b.Property("CodApp")
+ .HasMaxLength(50)
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("Descrizione")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.HasKey("CodApp");
+
+ b.ToTable("Applicativi");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.FileAttachModel", b =>
+ {
+ b.Property("IdxFileAttach")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("DtEvent")
+ .HasColumnType("datetime2");
+
+ b.Property("FullStoragePath")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("IdxTicket")
+ .HasColumnType("int");
+
+ b.Property("OriginalName")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("StorageName")
+ .HasColumnType("nvarchar(max)");
+
+ b.HasKey("IdxFileAttach");
+
+ b.HasIndex("IdxTicket");
+
+ b.ToTable("FileAttach");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.InstallazioneModel", b =>
+ {
+ b.Property("CodInst")
+ .HasMaxLength(50)
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("Cliente")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.Property("Contatto")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.Property("Descrizione")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.Property("Email")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.HasKey("CodInst");
+
+ b.ToTable("Installazioni");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LicenzaModel", b =>
+ {
+ b.Property("IdxLic")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("Chiave")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("CodApp")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("CodInst")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("DataEnigma")
+ .HasColumnType("datetime2");
+
+ b.Property("Descrizione")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Enigma")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Locked")
+ .HasColumnType("bit");
+
+ b.Property("NumLicenze")
+ .HasColumnType("int");
+
+ b.Property("Payload")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Scadenza")
+ .HasColumnType("datetime2");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.HasKey("IdxLic");
+
+ b.HasIndex("CodApp");
+
+ b.HasIndex("CodInst");
+
+ b.ToTable("Licenze");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LogCallModel", b =>
+ {
+ b.Property("DataRif")
+ .HasColumnType("datetime2");
+
+ b.Property("CodInst")
+ .HasColumnType("nvarchar(450)");
+
+ b.Property("CodApp")
+ .HasColumnType("nvarchar(450)");
+
+ b.Property("TargetUrl")
+ .HasColumnType("nvarchar(450)");
+
+ b.Property("NumCall")
+ .HasColumnType("int");
+
+ b.HasKey("DataRif", "CodInst", "CodApp", "TargetUrl");
+
+ b.ToTable("LogCall");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LogLicenzaModel", b =>
+ {
+ b.Property("IdxLogLic")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("Chiave")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("CodApp")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("CodInst")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("Descrizione")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("IdxLic")
+ .HasColumnType("int");
+
+ b.Property("NumLicenze")
+ .HasColumnType("int");
+
+ b.Property("Scadenza")
+ .HasColumnType("datetime2");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.HasKey("IdxLogLic");
+
+ b.HasIndex("CodApp");
+
+ b.HasIndex("CodInst");
+
+ b.HasIndex("IdxLic");
+
+ b.ToTable("LogLicenze");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.SubLicenzaModel", b =>
+ {
+ b.Property("IdxSubLic")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("Chiave")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("CodImpiego")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("IdxLic")
+ .HasColumnType("int");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.Property("VetoUnlock")
+ .HasColumnType("datetime2");
+
+ b.HasKey("IdxSubLic");
+
+ b.HasIndex("IdxLic");
+
+ b.ToTable("SubLicenze");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.TicketModel", b =>
+ {
+ b.Property("IdxTicket")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("CodImpiego")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("ContactEmail")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("ContactName")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("ContactPhone")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("DtReq")
+ .HasColumnType("datetime2");
+
+ b.Property("IdxLic")
+ .HasColumnType("int");
+
+ b.Property("IdxSubLic")
+ .HasColumnType("int");
+
+ b.Property("ReqBody")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Status")
+ .HasColumnType("int");
+
+ b.Property("SupplAnsw")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("SupplEmail")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("SupplUserCode")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.HasKey("IdxTicket");
+
+ b.HasIndex("IdxLic");
+
+ b.ToTable("TicketLog");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.FileAttachModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.TicketModel", "TicketNav")
+ .WithMany()
+ .HasForeignKey("IdxTicket")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("TicketNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LicenzaModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.ApplicativoModel", "ApplicativoNav")
+ .WithMany()
+ .HasForeignKey("CodApp");
+
+ b.HasOne("LiMan.DB.DBModels.InstallazioneModel", "InstallazioneNav")
+ .WithMany()
+ .HasForeignKey("CodInst");
+
+ b.Navigation("ApplicativoNav");
+
+ b.Navigation("InstallazioneNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LogLicenzaModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.ApplicativoModel", "ApplicativoNav")
+ .WithMany()
+ .HasForeignKey("CodApp");
+
+ b.HasOne("LiMan.DB.DBModels.InstallazioneModel", "InstallazioneNav")
+ .WithMany()
+ .HasForeignKey("CodInst");
+
+ b.HasOne("LiMan.DB.DBModels.LicenzaModel", "LicenzaNav")
+ .WithMany()
+ .HasForeignKey("IdxLic")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("ApplicativoNav");
+
+ b.Navigation("InstallazioneNav");
+
+ b.Navigation("LicenzaNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.SubLicenzaModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.LicenzaModel", "LicenzaNav")
+ .WithMany("Attivazioni")
+ .HasForeignKey("IdxLic")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("LicenzaNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.TicketModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.LicenzaModel", "LicenzaNav")
+ .WithMany("Tickets")
+ .HasForeignKey("IdxLic")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("LicenzaNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LicenzaModel", b =>
+ {
+ b.Navigation("Attivazioni");
+
+ b.Navigation("Tickets");
+ });
+#pragma warning restore 612, 618
+ }
+ }
+}
diff --git a/LiMan.DB/Migrations/20211220181913_AddFileAttach.cs b/LiMan.DB/Migrations/20211220181913_AddFileAttach.cs
new file mode 100644
index 0000000..2c547b8
--- /dev/null
+++ b/LiMan.DB/Migrations/20211220181913_AddFileAttach.cs
@@ -0,0 +1,45 @@
+using System;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LiMan.DB.Migrations
+{
+ public partial class AddFileAttach : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.CreateTable(
+ name: "FileAttach",
+ columns: table => new
+ {
+ IdxFileAttach = table.Column(type: "int", nullable: false)
+ .Annotation("SqlServer:Identity", "1, 1"),
+ IdxTicket = table.Column(type: "int", nullable: false),
+ DtEvent = table.Column(type: "datetime2", nullable: false),
+ OriginalName = table.Column(type: "nvarchar(max)", nullable: true),
+ StorageName = table.Column(type: "nvarchar(max)", nullable: true),
+ FullStoragePath = table.Column(type: "nvarchar(max)", nullable: true)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_FileAttach", x => x.IdxFileAttach);
+ table.ForeignKey(
+ name: "FK_FileAttach_TicketLog_IdxTicket",
+ column: x => x.IdxTicket,
+ principalTable: "TicketLog",
+ principalColumn: "IdxTicket",
+ onDelete: ReferentialAction.Cascade);
+ });
+
+ migrationBuilder.CreateIndex(
+ name: "IX_FileAttach_IdxTicket",
+ table: "FileAttach",
+ column: "IdxTicket");
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropTable(
+ name: "FileAttach");
+ }
+ }
+}
diff --git a/LiMan.DB/Migrations/20211221090447_UpdTicket_TType.Designer.cs b/LiMan.DB/Migrations/20211221090447_UpdTicket_TType.Designer.cs
new file mode 100644
index 0000000..ac5070b
--- /dev/null
+++ b/LiMan.DB/Migrations/20211221090447_UpdTicket_TType.Designer.cs
@@ -0,0 +1,374 @@
+//
+using System;
+using LiMan.DB;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
+
+namespace LiMan.DB.Migrations
+{
+ [DbContext(typeof(LMDbContext))]
+ [Migration("20211221090447_UpdTicket_TType")]
+ partial class UpdTicket_TType
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+#pragma warning disable 612, 618
+ modelBuilder
+ .HasAnnotation("Relational:Collation", "SQL_Latin1_General_CP1_CI_AS")
+ .HasAnnotation("Relational:MaxIdentifierLength", 128)
+ .HasAnnotation("ProductVersion", "5.0.10")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LiMan.DB.DBModels.ApplicativoModel", b =>
+ {
+ b.Property("CodApp")
+ .HasMaxLength(50)
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("Descrizione")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.HasKey("CodApp");
+
+ b.ToTable("Applicativi");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.FileAttachModel", b =>
+ {
+ b.Property("IdxFileAttach")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("DtEvent")
+ .HasColumnType("datetime2");
+
+ b.Property("FullStoragePath")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("IdxTicket")
+ .HasColumnType("int");
+
+ b.Property("OriginalName")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("StorageName")
+ .HasColumnType("nvarchar(max)");
+
+ b.HasKey("IdxFileAttach");
+
+ b.HasIndex("IdxTicket");
+
+ b.ToTable("FileAttach");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.InstallazioneModel", b =>
+ {
+ b.Property("CodInst")
+ .HasMaxLength(50)
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("Cliente")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.Property("Contatto")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.Property("Descrizione")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.Property("Email")
+ .HasMaxLength(250)
+ .HasColumnType("nvarchar(250)");
+
+ b.HasKey("CodInst");
+
+ b.ToTable("Installazioni");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LicenzaModel", b =>
+ {
+ b.Property("IdxLic")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("Chiave")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("CodApp")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("CodInst")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("DataEnigma")
+ .HasColumnType("datetime2");
+
+ b.Property("Descrizione")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Enigma")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Locked")
+ .HasColumnType("bit");
+
+ b.Property("NumLicenze")
+ .HasColumnType("int");
+
+ b.Property("Payload")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Scadenza")
+ .HasColumnType("datetime2");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.HasKey("IdxLic");
+
+ b.HasIndex("CodApp");
+
+ b.HasIndex("CodInst");
+
+ b.ToTable("Licenze");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LogCallModel", b =>
+ {
+ b.Property("DataRif")
+ .HasColumnType("datetime2");
+
+ b.Property("CodInst")
+ .HasColumnType("nvarchar(450)");
+
+ b.Property("CodApp")
+ .HasColumnType("nvarchar(450)");
+
+ b.Property("TargetUrl")
+ .HasColumnType("nvarchar(450)");
+
+ b.Property("NumCall")
+ .HasColumnType("int");
+
+ b.HasKey("DataRif", "CodInst", "CodApp", "TargetUrl");
+
+ b.ToTable("LogCall");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LogLicenzaModel", b =>
+ {
+ b.Property("IdxLogLic")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("Chiave")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("CodApp")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("CodInst")
+ .HasColumnType("nvarchar(50)");
+
+ b.Property("Descrizione")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("IdxLic")
+ .HasColumnType("int");
+
+ b.Property("NumLicenze")
+ .HasColumnType("int");
+
+ b.Property("Scadenza")
+ .HasColumnType("datetime2");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.HasKey("IdxLogLic");
+
+ b.HasIndex("CodApp");
+
+ b.HasIndex("CodInst");
+
+ b.HasIndex("IdxLic");
+
+ b.ToTable("LogLicenze");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.SubLicenzaModel", b =>
+ {
+ b.Property("IdxSubLic")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("Chiave")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("CodImpiego")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("IdxLic")
+ .HasColumnType("int");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.Property("VetoUnlock")
+ .HasColumnType("datetime2");
+
+ b.HasKey("IdxSubLic");
+
+ b.HasIndex("IdxLic");
+
+ b.ToTable("SubLicenze");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.TicketModel", b =>
+ {
+ b.Property("IdxTicket")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("CodImpiego")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("ContactEmail")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("ContactName")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("ContactPhone")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("DtReq")
+ .HasColumnType("datetime2");
+
+ b.Property("IdxLic")
+ .HasColumnType("int");
+
+ b.Property("IdxSubLic")
+ .HasColumnType("int");
+
+ b.Property("ReqBody")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("Status")
+ .HasColumnType("int");
+
+ b.Property("SupplAnsw")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("SupplEmail")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("SupplUserCode")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("TType")
+ .HasColumnType("int");
+
+ b.Property("Tipo")
+ .HasColumnType("int");
+
+ b.HasKey("IdxTicket");
+
+ b.HasIndex("IdxLic");
+
+ b.ToTable("TicketLog");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.FileAttachModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.TicketModel", "TicketNav")
+ .WithMany()
+ .HasForeignKey("IdxTicket")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("TicketNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LicenzaModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.ApplicativoModel", "ApplicativoNav")
+ .WithMany()
+ .HasForeignKey("CodApp");
+
+ b.HasOne("LiMan.DB.DBModels.InstallazioneModel", "InstallazioneNav")
+ .WithMany()
+ .HasForeignKey("CodInst");
+
+ b.Navigation("ApplicativoNav");
+
+ b.Navigation("InstallazioneNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LogLicenzaModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.ApplicativoModel", "ApplicativoNav")
+ .WithMany()
+ .HasForeignKey("CodApp");
+
+ b.HasOne("LiMan.DB.DBModels.InstallazioneModel", "InstallazioneNav")
+ .WithMany()
+ .HasForeignKey("CodInst");
+
+ b.HasOne("LiMan.DB.DBModels.LicenzaModel", "LicenzaNav")
+ .WithMany()
+ .HasForeignKey("IdxLic")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("ApplicativoNav");
+
+ b.Navigation("InstallazioneNav");
+
+ b.Navigation("LicenzaNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.SubLicenzaModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.LicenzaModel", "LicenzaNav")
+ .WithMany("Attivazioni")
+ .HasForeignKey("IdxLic")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("LicenzaNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.TicketModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.LicenzaModel", "LicenzaNav")
+ .WithMany("Tickets")
+ .HasForeignKey("IdxLic")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("LicenzaNav");
+ });
+
+ modelBuilder.Entity("LiMan.DB.DBModels.LicenzaModel", b =>
+ {
+ b.Navigation("Attivazioni");
+
+ b.Navigation("Tickets");
+ });
+#pragma warning restore 612, 618
+ }
+ }
+}
diff --git a/LiMan.DB/Migrations/20211221090447_UpdTicket_TType.cs b/LiMan.DB/Migrations/20211221090447_UpdTicket_TType.cs
new file mode 100644
index 0000000..555f5a6
--- /dev/null
+++ b/LiMan.DB/Migrations/20211221090447_UpdTicket_TType.cs
@@ -0,0 +1,24 @@
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LiMan.DB.Migrations
+{
+ public partial class UpdTicket_TType : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.AddColumn(
+ name: "TType",
+ table: "TicketLog",
+ type: "int",
+ nullable: false,
+ defaultValue: 0);
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropColumn(
+ name: "TType",
+ table: "TicketLog");
+ }
+ }
+}
diff --git a/LiMan.DB/Migrations/LMDbContextModelSnapshot.cs b/LiMan.DB/Migrations/LMDbContextModelSnapshot.cs
index b52d5fc..0d6859c 100644
--- a/LiMan.DB/Migrations/LMDbContextModelSnapshot.cs
+++ b/LiMan.DB/Migrations/LMDbContextModelSnapshot.cs
@@ -35,6 +35,35 @@ namespace LiMan.DB.Migrations
b.ToTable("Applicativi");
});
+ modelBuilder.Entity("LiMan.DB.DBModels.FileAttachModel", b =>
+ {
+ b.Property("IdxFileAttach")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("int")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("DtEvent")
+ .HasColumnType("datetime2");
+
+ b.Property("FullStoragePath")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("IdxTicket")
+ .HasColumnType("int");
+
+ b.Property("OriginalName")
+ .HasColumnType("nvarchar(max)");
+
+ b.Property("StorageName")
+ .HasColumnType("nvarchar(max)");
+
+ b.HasKey("IdxFileAttach");
+
+ b.HasIndex("IdxTicket");
+
+ b.ToTable("FileAttach");
+ });
+
modelBuilder.Entity("LiMan.DB.DBModels.InstallazioneModel", b =>
{
b.Property("CodInst")
@@ -247,6 +276,9 @@ namespace LiMan.DB.Migrations
b.Property("SupplUserCode")
.HasColumnType("nvarchar(max)");
+ b.Property("TType")
+ .HasColumnType("int");
+
b.Property("Tipo")
.HasColumnType("int");
@@ -257,6 +289,17 @@ namespace LiMan.DB.Migrations
b.ToTable("TicketLog");
});
+ modelBuilder.Entity("LiMan.DB.DBModels.FileAttachModel", b =>
+ {
+ b.HasOne("LiMan.DB.DBModels.TicketModel", "TicketNav")
+ .WithMany()
+ .HasForeignKey("IdxTicket")
+ .OnDelete(DeleteBehavior.Cascade)
+ .IsRequired();
+
+ b.Navigation("TicketNav");
+ });
+
modelBuilder.Entity("LiMan.DB.DBModels.LicenzaModel", b =>
{
b.HasOne("LiMan.DB.DBModels.ApplicativoModel", "ApplicativoNav")
diff --git a/LiMan.UI/Components/Tickets.razor.cs b/LiMan.UI/Components/Tickets.razor.cs
index 9c867da..aaf2e3d 100644
--- a/LiMan.UI/Components/Tickets.razor.cs
+++ b/LiMan.UI/Components/Tickets.razor.cs
@@ -48,6 +48,11 @@ namespace LiMan.UI.Components
}
}
+ protected override async Task OnInitializedAsync()
+ {
+ await ReloadAllData();
+ }
+
private bool isLoading { get; set; } = false;
[Inject]
diff --git a/LiMan.UI/LiMan.UI.csproj b/LiMan.UI/LiMan.UI.csproj
index 8c5acef..d7fd238 100644
--- a/LiMan.UI/LiMan.UI.csproj
+++ b/LiMan.UI/LiMan.UI.csproj
@@ -2,7 +2,7 @@
net5.0
- 1.1.2111.1815
+ 1.1.2201.1317
LiMan.UI
LiMan.UI
diff --git a/LiMan.UI/Pages/ListaTicket.razor b/LiMan.UI/Pages/ListaTicket.razor
new file mode 100644
index 0000000..c45a328
--- /dev/null
+++ b/LiMan.UI/Pages/ListaTicket.razor
@@ -0,0 +1,17 @@
+@page "/ListaTicket"
+
+@using LiMan.UI.Components
+@using LiMan.UI.Data
+
+@inject MessageService AppMService
+
+
+
+@code {
+ protected override void OnInitialized()
+ {
+ AppMService.ShowSearch = false;
+ AppMService.PageName = "Elenco Tickets";
+ AppMService.PageIcon = "oi oi-list-rich";
+ }
+}
\ No newline at end of file
diff --git a/LiMan.UI/Properties/PublishProfiles/IIS02.pubxml b/LiMan.UI/Properties/PublishProfiles/IIS02.pubxml
index aaca518..98761f9 100644
--- a/LiMan.UI/Properties/PublishProfiles/IIS02.pubxml
+++ b/LiMan.UI/Properties/PublishProfiles/IIS02.pubxml
@@ -13,7 +13,7 @@ by editing this MSBuild file. In order to learn more about this please visit htt
True
False
34200ca2-489c-435a-a60b-34de7b7ba04d
- https://IIS02:8172/MsDeploy.axd
+ https://IIS02.egalware.com:8172/MsDeploy.axd
Default Web Site/ELM.UI
False
diff --git a/LiMan.UI/Resources/ChangeLog.html b/LiMan.UI/Resources/ChangeLog.html
index ab0a3aa..fa2c866 100644
--- a/LiMan.UI/Resources/ChangeLog.html
+++ b/LiMan.UI/Resources/ChangeLog.html
@@ -1,6 +1,6 @@
License Manager
- Versione: 1.1.2111.1815
+ Versione: 1.1.2201.1317
Note di rilascio:
diff --git a/LiMan.UI/Resources/VersNum.txt b/LiMan.UI/Resources/VersNum.txt
index c98fbef..c102023 100644
--- a/LiMan.UI/Resources/VersNum.txt
+++ b/LiMan.UI/Resources/VersNum.txt
@@ -1 +1 @@
-1.1.2111.1815
+1.1.2201.1317
diff --git a/LiMan.UI/Resources/manifest.xml b/LiMan.UI/Resources/manifest.xml
index f0effe2..a6c0709 100644
--- a/LiMan.UI/Resources/manifest.xml
+++ b/LiMan.UI/Resources/manifest.xml
@@ -1,6 +1,6 @@
-
- 1.1.2111.1815
+ 1.1.2201.1317
https://nexus.steamware.net/repository/SWS/LiMan/stable/LAST/LiMan.UI.zip
https://nexus.steamware.net/repository/SWS/LiMan/stable/LAST/ChangeLog.html
false
diff --git a/LiMan.UI/Shared/NavMenu.razor b/LiMan.UI/Shared/NavMenu.razor
index afe66be..506e8dc 100644
--- a/LiMan.UI/Shared/NavMenu.razor
+++ b/LiMan.UI/Shared/NavMenu.razor
@@ -29,6 +29,11 @@
+
-
+
+
+
+
-