Add new Backend structure with proper .NET 8 projects
This commit is contained in:
28
src/Backend/DiunaBI.WebAPI/Controllers/AdminController.cs
Normal file
28
src/Backend/DiunaBI.WebAPI/Controllers/AdminController.cs
Normal file
@@ -0,0 +1,28 @@
|
||||
using System.Data;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.Data.SqlClient;
|
||||
using DiunaBI.Core.Models;
|
||||
|
||||
namespace DiunaBI.Core.Controllers;
|
||||
|
||||
[ApiController]
|
||||
[Route("api/[controller]")]
|
||||
public class AdminController : Controller
|
||||
{
|
||||
|
||||
private readonly IConfiguration _configuration;
|
||||
|
||||
public AdminController(
|
||||
IConfiguration configuration)
|
||||
{
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("Version")]
|
||||
public IActionResult GetVersion()
|
||||
{
|
||||
return Ok(new { version = _configuration["app-version"] });
|
||||
}
|
||||
}
|
||||
60
src/Backend/DiunaBI.WebAPI/Controllers/AuthController.cs
Normal file
60
src/Backend/DiunaBI.WebAPI/Controllers/AuthController.cs
Normal file
@@ -0,0 +1,60 @@
|
||||
using Google.Apis.Auth;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using Microsoft.IdentityModel.Tokens;
|
||||
using System.IdentityModel.Tokens.Jwt;
|
||||
using System.Security.Claims;
|
||||
using System.Text;
|
||||
using DiunaBI.Core.Models;
|
||||
using DiunaBI.Database.Context;
|
||||
|
||||
namespace DiunaBI.WebAPI.Controllers;
|
||||
|
||||
[ApiController]
|
||||
[Route("api/[controller]")]
|
||||
// [Authorize]
|
||||
public class AuthController : Controller
|
||||
{
|
||||
private readonly AppDbContext _db;
|
||||
private readonly IConfiguration _configuration;
|
||||
public AuthController(
|
||||
AppDbContext db, IConfiguration configuration)
|
||||
{ _db = db; _configuration = configuration; }
|
||||
|
||||
[HttpPost]
|
||||
[Route("apiToken")]
|
||||
public async Task<IActionResult> ApiToken([FromBody] string credential)
|
||||
{
|
||||
var settings = new GoogleJsonWebSignature.ValidationSettings
|
||||
{
|
||||
Audience = new List<string> { _configuration.GetValue<string>("GoogleClientId")! }
|
||||
};
|
||||
var payload = await GoogleJsonWebSignature.ValidateAsync(credential, settings);
|
||||
var user = _db.Users.AsNoTracking().FirstOrDefault(x => x.Email == payload.Email);
|
||||
return user != null ? (IActionResult)Ok(JwtGenerator(user)) : Unauthorized();
|
||||
}
|
||||
|
||||
private dynamic JwtGenerator(User user)
|
||||
{
|
||||
var key = Encoding.ASCII.GetBytes(_configuration.GetValue<string>("Secret")!);
|
||||
var expirationTime = DateTime.UtcNow.AddMinutes(5);
|
||||
var tokenDescriptor = new SecurityTokenDescriptor
|
||||
{
|
||||
Subject = new ClaimsIdentity(new[]
|
||||
{
|
||||
new Claim("Id", Guid.NewGuid().ToString()),
|
||||
new Claim(JwtRegisteredClaimNames.Sub, user.Id.ToString()),
|
||||
new Claim(JwtRegisteredClaimNames.Jti,
|
||||
Guid.NewGuid().ToString())
|
||||
}),
|
||||
Expires = expirationTime,
|
||||
SigningCredentials = new SigningCredentials
|
||||
(new SymmetricSecurityKey(key),
|
||||
SecurityAlgorithms.HmacSha512Signature)
|
||||
};
|
||||
var tokenHandler = new JwtSecurityTokenHandler();
|
||||
var token = tokenHandler.CreateToken(tokenDescriptor);
|
||||
var stringToken = tokenHandler.WriteToken(token);
|
||||
return new { token = stringToken, id = user.Id, expirationTime };
|
||||
}
|
||||
}
|
||||
168
src/Backend/DiunaBI.WebAPI/Controllers/DataInboxController.cs
Normal file
168
src/Backend/DiunaBI.WebAPI/Controllers/DataInboxController.cs
Normal file
@@ -0,0 +1,168 @@
|
||||
using System.Text;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using DiunaBI.Database.Context;
|
||||
using Google.Cloud.Firestore;
|
||||
using DiunaBI.Core.Models;
|
||||
|
||||
namespace DiunaBI.WebAPI.Controllers;
|
||||
|
||||
[ApiController]
|
||||
[Route("api/[controller]")]
|
||||
public class DataInboxController : Controller
|
||||
{
|
||||
private readonly AppDbContext _db;
|
||||
private readonly IConfiguration _configuration;
|
||||
private readonly LogsController _logsController;
|
||||
|
||||
public DataInboxController(
|
||||
AppDbContext db,
|
||||
IConfiguration configuration,
|
||||
FirestoreDb firestoreDb)
|
||||
{
|
||||
_db = db;
|
||||
_configuration = configuration;
|
||||
_logsController = new LogsController(firestoreDb);
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("Add/{apiKey}")]
|
||||
[AllowAnonymous]
|
||||
public IActionResult Add(string apiKey, [FromBody] DataInbox dataInbox)
|
||||
{
|
||||
if (apiKey != _configuration["apiKey"])
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - wrong apiKey ({dataInbox.Source})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.DataInbox,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
if (
|
||||
!Request.Headers.TryGetValue("Authorization", out var authHeader))
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - no authorization header ({dataInbox.Source})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.DataInbox,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var credentialsArr = authHeader.ToString().Split(" ");
|
||||
if (credentialsArr.Length != 2)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - wrong auth header format ({dataInbox.Source})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.DataInbox,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var authValue = Encoding.UTF8.GetString(Convert.FromBase64String(credentialsArr[1]));
|
||||
var username = authValue.Split(':')[0];
|
||||
var password = authValue.Split(':')[1];
|
||||
if (username != _configuration["morska-user"] || password != _configuration["morska-pass"])
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - bad credentials ({dataInbox.Source})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.DataInbox,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
// check if datainbox.data is base64 encoded value
|
||||
if (!string.IsNullOrEmpty(dataInbox.Data) && !IsBase64String(dataInbox.Data))
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Invalid data format - not base64 encoded ({dataInbox.Source})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.DataInbox,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return BadRequest("Invalid data format - not base64 encoded");
|
||||
}
|
||||
|
||||
|
||||
dataInbox.Id = Guid.NewGuid();
|
||||
dataInbox.CreatedAt = DateTime.UtcNow;
|
||||
_db.DataInbox.Add(dataInbox);
|
||||
_db.SaveChanges();
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Insert success: {dataInbox.Source}, {dataInbox.Name}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.DataInbox,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
|
||||
if (dataInbox.Name == "morska.d3.importer")
|
||||
{
|
||||
// TODO: import dataInbox as Layer
|
||||
}
|
||||
|
||||
return Ok();
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Insert error: {dataInbox.Source}, {dataInbox.Name}",
|
||||
Type = LogEntryType.Error,
|
||||
LogType = LogType.DataInbox,
|
||||
Message = e.ToString(),
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return BadRequest(e.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
public IActionResult GetAll()
|
||||
{
|
||||
return Ok(_db.DataInbox.AsNoTracking().ToList());
|
||||
}
|
||||
|
||||
// helpers
|
||||
private bool IsBase64String(string data)
|
||||
{
|
||||
if (string.IsNullOrEmpty(data))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
try
|
||||
{
|
||||
var base64Bytes = Convert.FromBase64String(data);
|
||||
|
||||
var utf8String = Encoding.UTF8.GetString(base64Bytes);
|
||||
|
||||
var reEncoded = Convert.ToBase64String(Encoding.UTF8.GetBytes(utf8String));
|
||||
return data.TrimEnd('=') == reEncoded.TrimEnd('=');
|
||||
}
|
||||
catch (FormatException)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
catch (DecoderFallbackException)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
857
src/Backend/DiunaBI.WebAPI/Controllers/LayersController.cs
Normal file
857
src/Backend/DiunaBI.WebAPI/Controllers/LayersController.cs
Normal file
@@ -0,0 +1,857 @@
|
||||
using System.Globalization;
|
||||
using System.Text;
|
||||
using Google.Apis.Sheets.v4;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using DiunaBI.Core.Models;
|
||||
using DiunaBI.Database.Context;
|
||||
using DiunaBI.Core.Services;
|
||||
using Google.Cloud.Firestore;
|
||||
using DiunaBI.Plugins.Morska.Importers;
|
||||
using DiunaBI.Plugins.Morska.Processors;
|
||||
using DiunaBI.Core.Services.Exports;
|
||||
|
||||
namespace DiunaBI.WebAPI.Controllers;
|
||||
|
||||
[ApiController]
|
||||
[Route("api/[controller]")]
|
||||
public class LayersController : Controller
|
||||
{
|
||||
private readonly AppDbContext _db;
|
||||
private readonly SpreadsheetsResource.ValuesResource? _googleSheetValues;
|
||||
private readonly GoogleDriveHelper _googleDriveHelper;
|
||||
private readonly IConfiguration _configuration;
|
||||
private readonly LogsController _logsController;
|
||||
|
||||
public LayersController(
|
||||
AppDbContext db,
|
||||
GoogleSheetsHelper googleSheetsHelper,
|
||||
GoogleDriveHelper googleDriveHelper,
|
||||
IConfiguration configuration,
|
||||
FirestoreDb firestoreDb
|
||||
)
|
||||
{
|
||||
_db = db;
|
||||
if (googleSheetsHelper.Service is not null)
|
||||
{
|
||||
_googleSheetValues = googleSheetsHelper.Service.Spreadsheets.Values;
|
||||
}
|
||||
|
||||
_googleDriveHelper = googleDriveHelper;
|
||||
_configuration = configuration;
|
||||
_logsController = new LogsController(firestoreDb);
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
public IActionResult GetAll(int start, int limit, string? name, LayerType? type)
|
||||
{
|
||||
try
|
||||
{
|
||||
var response = _db.Layers.Where(x => !x.IsDeleted);
|
||||
if (name != null)
|
||||
{
|
||||
response = response.Where(x => x.Name != null && x.Name.Contains(name));
|
||||
}
|
||||
|
||||
if (type != null)
|
||||
{
|
||||
response = response.Where(x => x.Type == type);
|
||||
}
|
||||
|
||||
return Ok(response
|
||||
.OrderByDescending(x => x.Number)
|
||||
.Skip(start).Take(limit).AsNoTracking().ToList());
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
return BadRequest(e.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("{id:guid}")]
|
||||
public IActionResult Get(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
return Ok(_db.Layers
|
||||
.Include(x => x.CreatedBy)
|
||||
.Include(x => x.ModifiedBy)
|
||||
.Include(x => x.Records).AsNoTracking().First(x => x.Id == id && !x.IsDeleted));
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
return BadRequest(e.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("getForPowerBI/{apiKey}/{number:int}")]
|
||||
public IActionResult GetByNumber(string apiKey, int number)
|
||||
{
|
||||
if (apiKey != _configuration["apiKey"])
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - wrong apiKey ({number})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.PowerBi,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
if (
|
||||
!Request.Headers.TryGetValue("Authorization", out var authHeader))
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - no authorization header ({number})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.PowerBi,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var credentialsArr = authHeader.ToString().Split(" ");
|
||||
if (credentialsArr.Length != 2)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - wrong auth header format ({number})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.PowerBi,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var authValue = Encoding.UTF8.GetString(Convert.FromBase64String(credentialsArr[1]));
|
||||
var username = authValue.Split(':')[0];
|
||||
var password = authValue.Split(':')[1];
|
||||
if (username != _configuration["powerBI-user"] || password != _configuration["powerBI-pass"])
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Unauthorized request - bad credentials ({number})",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.PowerBi,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Sending data for layer {number}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.PowerBi,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
|
||||
return Ok(_db.Layers
|
||||
.Include(x => x.CreatedBy)
|
||||
.Include(x => x.Records).AsNoTracking().First(x => x.Number == number && !x.IsDeleted));
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = e.ToString(),
|
||||
Type = LogEntryType.Error,
|
||||
LogType = LogType.PowerBi,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return BadRequest(e.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("getConfiguration/{apiKey}/{number:int}")]
|
||||
public IActionResult GetConfigurationByNumber(string apiKey, int number)
|
||||
{
|
||||
if (apiKey != _configuration["apiKey"])
|
||||
{
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
if (
|
||||
!Request.Headers.TryGetValue("Authorization", out var authHeader))
|
||||
{
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var credentialsArr = authHeader.ToString().Split(" ");
|
||||
if (credentialsArr.Length != 2)
|
||||
{
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var authValue = Encoding.UTF8.GetString(Convert.FromBase64String(credentialsArr[1]));
|
||||
var username = authValue.Split(':')[0];
|
||||
var password = authValue.Split(':')[1];
|
||||
if (username != _configuration["morska-user"] || password != _configuration["morska-pass"])
|
||||
{
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var config = _db.Layers
|
||||
.Include(x => x.Records)
|
||||
.AsNoTracking()
|
||||
.First(x => x.Number == number && !x.IsDeleted);
|
||||
|
||||
if (config is null)
|
||||
{
|
||||
return BadRequest();
|
||||
}
|
||||
|
||||
var type = config.Records?.Where(x => x.Code == "Type").FirstOrDefault();
|
||||
if (type is null || type.Desc1 != "ExternalConfiguration")
|
||||
{
|
||||
return BadRequest();
|
||||
}
|
||||
|
||||
return Ok(config);
|
||||
}
|
||||
catch
|
||||
{
|
||||
return BadRequest();
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("exportToGoogleSheet/{id:guid}")]
|
||||
public IActionResult ExportToGoogleSheet(Guid id)
|
||||
{
|
||||
if (_googleSheetValues is null)
|
||||
{
|
||||
throw new Exception("Google Sheets API not initialized");
|
||||
}
|
||||
|
||||
var layer = _db.Layers
|
||||
.Include(x => x.Records!.OrderByDescending(y => y.Code)).AsNoTracking().First(x => x.Id == id && !x.IsDeleted);
|
||||
|
||||
var export = new GoogleSheetExport(_googleDriveHelper, _googleSheetValues, _configuration);
|
||||
export.Export(layer);
|
||||
return Ok(true);
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("AutoImportWithQueue/{apiKey}")]
|
||||
[AllowAnonymous]
|
||||
public IActionResult AutoImportWithQueue(string apiKey)
|
||||
{
|
||||
if (Request.Host.Value != _configuration["apiLocalUrl"] || apiKey != _configuration["apiKey"])
|
||||
{
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
var importWorkerLayers = _db.Layers
|
||||
.Include(x => x.Records)
|
||||
.Where(x =>
|
||||
x.Records!.Any(y => y.Code == "Type" && y.Desc1 == "ImportWorker") &&
|
||||
x.Records!.Any(y => y.Code == "IsEnabled" && y.Desc1 == "True")
|
||||
)
|
||||
.OrderBy(x => x.CreatedAt)
|
||||
.AsNoTracking()
|
||||
.ToList();
|
||||
|
||||
if (importWorkerLayers.Count == 0)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = "No Layers to import.",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Queue,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Ok();
|
||||
}
|
||||
|
||||
foreach (var importWorker in importWorkerLayers)
|
||||
{
|
||||
try
|
||||
{
|
||||
/*
|
||||
await _queue.AddJob(new QueueJob
|
||||
{
|
||||
LayerId = importWorker.Id,
|
||||
Type = JobType.ImportWorker,
|
||||
});
|
||||
*/
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Error while adding job into queue (import): {importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Error,
|
||||
LogType = LogType.Queue,
|
||||
Message = e.ToString(),
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
}
|
||||
return Ok();
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("ProcessQueue/{apiKey}")]
|
||||
[AllowAnonymous]
|
||||
public IActionResult ProcessQueue(string apiKey)
|
||||
{
|
||||
/*
|
||||
var allJobs = await _queue.GetJobs();
|
||||
var importJobs = allJobs
|
||||
.Where(x => x.Type == JobType.ImportWorker && x.Status == JobStatus.New);
|
||||
|
||||
foreach (var job in importJobs)
|
||||
{
|
||||
job.Attempts = job.Attempts + 1;
|
||||
//await _queue.UpdateJob(job);
|
||||
}
|
||||
*/
|
||||
return Ok();
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("AutoImport/{apiKey}/{nameFilter}")]
|
||||
[AllowAnonymous]
|
||||
public IActionResult AutoImport(string apiKey, string nameFilter)
|
||||
{
|
||||
if (Request.Host.Value != _configuration["apiLocalUrl"] || apiKey != _configuration["apiKey"])
|
||||
{
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
if (_googleSheetValues is null)
|
||||
{
|
||||
throw new Exception("Google Sheets API not initialized");
|
||||
}
|
||||
|
||||
var importWorkerLayers = _db.Layers
|
||||
.Include(x => x.Records)
|
||||
.Where(x =>
|
||||
x.Name != null && x.Name.Contains(nameFilter) &&
|
||||
x.Records!.Any(y => y.Code == "Type" && y.Desc1 == "ImportWorker") &&
|
||||
x.Records!.Any(y => y.Code == "IsEnabled" && y.Desc1 == "True")
|
||||
)
|
||||
.OrderByDescending(x => x.CreatedAt)
|
||||
.AsNoTracking()
|
||||
.ToList();
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"Starting import: {nameFilter}, Admin layers count ({importWorkerLayers.Count})",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Import,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
try
|
||||
{
|
||||
if (importWorkerLayers.Count == 0)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = "No Layers to import.",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Import,
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return Ok();
|
||||
}
|
||||
|
||||
foreach (var importWorker in importWorkerLayers)
|
||||
{
|
||||
try
|
||||
{
|
||||
var type = importWorker.Records!.FirstOrDefault(x => x.Code == "ImportType")?.Desc1 ??
|
||||
"Standard";
|
||||
var source = importWorker.Records!.FirstOrDefault(x => x.Code == "Source")?.Desc1 ??
|
||||
"GoogleSheet";
|
||||
if (source == "DataInbox" && type == "Import-D3")
|
||||
{
|
||||
var d3Importer = new MorskaD3Importer(_db);
|
||||
d3Importer.Import(importWorker);
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Import,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
continue;
|
||||
}
|
||||
switch (type)
|
||||
{
|
||||
case "D1":
|
||||
var d1Importer = new MorskaD1Importer(_db, _googleSheetValues);
|
||||
d1Importer.Import(importWorker);
|
||||
Thread.Sleep(5000); // be aware of GSheet API quota
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Import,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
break;
|
||||
case "FK2":
|
||||
{
|
||||
var fk2Importer = new MorskaFk2Importer(_db, _googleSheetValues);
|
||||
fk2Importer.Import(importWorker);
|
||||
Thread.Sleep(5000); // be aware of GSheet API quota
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Import,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
var startDate = importWorker.Records!.FirstOrDefault(x => x.Code == "StartDate")?.Desc1;
|
||||
if (startDate == null)
|
||||
{
|
||||
throw new Exception("StartDate record nod found");
|
||||
}
|
||||
|
||||
var endDate = importWorker.Records!.First(x => x.Code == "EndDate").Desc1;
|
||||
if (endDate == null)
|
||||
{
|
||||
throw new Exception("EndDate record nod found");
|
||||
}
|
||||
|
||||
var startDateParsed = DateTime.ParseExact(startDate, "yyyy.MM.dd", null);
|
||||
var endDateParsed = DateTime.ParseExact(endDate, "yyyy.MM.dd", null);
|
||||
if (startDateParsed.Date <= DateTime.UtcNow.Date &&
|
||||
endDateParsed.Date >= DateTime.UtcNow.Date)
|
||||
{
|
||||
var importer = new MorskaImporter(_db, _googleSheetValues);
|
||||
importer.Import(importWorker);
|
||||
Thread.Sleep(5000); // be aware of GSheet API quota
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Import,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
else if (IsImportedLayerUpToDate(importWorker) == false)
|
||||
{
|
||||
var importer = new MorskaImporter(_db, _googleSheetValues);
|
||||
importer.Import(importWorker);
|
||||
Thread.Sleep(5000); // be aware of GSheet API quota
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.Import,
|
||||
Message = "Success (reimported)",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
else
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Warning,
|
||||
LogType = LogType.Import,
|
||||
Message = "importLayer records are up to date. Not processed.",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{importWorker.Name}, {importWorker.Id}",
|
||||
Type = LogEntryType.Error,
|
||||
LogType = LogType.Import,
|
||||
Message = e.ToString(),
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return Ok();
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = "Process error",
|
||||
Type = LogEntryType.Error,
|
||||
LogType = LogType.Import,
|
||||
Message = e.ToString(),
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return BadRequest(e.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("AutoProcess/{apiKey}")]
|
||||
[AllowAnonymous]
|
||||
public IActionResult AutoProcess(string apiKey)
|
||||
{
|
||||
if (Request.Host.Value != _configuration["apiLocalUrl"] || apiKey != _configuration["apiKey"])
|
||||
{
|
||||
return Unauthorized();
|
||||
}
|
||||
|
||||
if (_googleSheetValues is null)
|
||||
{
|
||||
throw new Exception("Google Sheets API not initialized");
|
||||
}
|
||||
|
||||
string[] processTypes =
|
||||
[
|
||||
"T3-SingleSource",
|
||||
"T3-SourceYearSummary",
|
||||
"T3-MultiSourceSummary", // AA
|
||||
"T3-MultiSourceYearSummary", // AA/13
|
||||
"T4-SingleSource",
|
||||
"T5-LastValues",
|
||||
"T1-R1",
|
||||
"T4-R2",
|
||||
"T1-R3"
|
||||
];
|
||||
|
||||
foreach (var type in processTypes)
|
||||
{
|
||||
try
|
||||
{
|
||||
var processWorkerLayers = _db.Layers
|
||||
.Include(x => x.Records)
|
||||
.Where(x =>
|
||||
x.Records!.Any(y => y.Code == "Type" && y.Desc1 == "ProcessWorker") &&
|
||||
x.Records!.Any(y => y.Code == "IsEnabled" && y.Desc1 == "True") &&
|
||||
x.Records!.Any(y => y.Code == "ProcessType" && y.Desc1 == type)
|
||||
)
|
||||
.OrderBy(x => x.CreatedAt)
|
||||
.AsNoTracking()
|
||||
.ToList();
|
||||
|
||||
foreach (var processWorker in processWorkerLayers)
|
||||
{
|
||||
try
|
||||
{
|
||||
ProcessLayer(processWorker);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Error,
|
||||
LogType = LogType.Process,
|
||||
Message = e.ToString(),
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = "Process error",
|
||||
Type = LogEntryType.Error,
|
||||
LogType = LogType.Process,
|
||||
Message = e.ToString(),
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return Ok();
|
||||
}
|
||||
|
||||
private void ProcessLayer(Layer processWorker)
|
||||
{
|
||||
if (_googleSheetValues == null)
|
||||
{
|
||||
throw new Exception("Google Sheets API not initialized");
|
||||
}
|
||||
|
||||
var year = processWorker.Records?.SingleOrDefault(x => x.Code == "Year")?.Desc1;
|
||||
if (year == null)
|
||||
{
|
||||
throw new Exception("Year record nod found");
|
||||
}
|
||||
|
||||
var processType = processWorker.Records?.SingleOrDefault(x => x.Code == "ProcessType")?.Desc1;
|
||||
switch (processType)
|
||||
{
|
||||
case null:
|
||||
throw new Exception("ProcessType record not found");
|
||||
case "T3-SourceYearSummary":
|
||||
{
|
||||
var processor =
|
||||
new T3SourceYearSummaryProcessor(_db);
|
||||
processor.Process(processWorker);
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Process,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return;
|
||||
}
|
||||
case "T3-MultiSourceYearSummary":
|
||||
{
|
||||
var processor =
|
||||
new T3MultiSourceYearSummaryProcessor(_db);
|
||||
processor.Process(processWorker);
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Process,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return;
|
||||
}
|
||||
case "T3-MultiSourceCopySelectedCodesYearSummary":
|
||||
{
|
||||
var processor =
|
||||
new T3MultiSourceCopySelectedCodesYearSummaryProcessor(_db);
|
||||
processor.Process(processWorker);
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Process,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return;
|
||||
}
|
||||
case "T1-R1":
|
||||
{
|
||||
var processor = new T1R1Processor(_db, _googleSheetValues);
|
||||
processor.Process(processWorker);
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Process,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return;
|
||||
}
|
||||
case "T4-R2":
|
||||
{
|
||||
var processor = new T4R2Processor(_db, _googleSheetValues);
|
||||
processor.Process(processWorker);
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Process,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return;
|
||||
}
|
||||
case "T1-R3":
|
||||
{
|
||||
var processor = new T1R3Processor(_db, _googleSheetValues);
|
||||
processor.Process(processWorker);
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Process,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
var month = processWorker.Records?.SingleOrDefault(x => x.Code == "Month")?.Desc1;
|
||||
if (month == null)
|
||||
{
|
||||
throw new Exception("Month record not found");
|
||||
}
|
||||
|
||||
switch (processType!)
|
||||
{
|
||||
case "T3-SingleSource":
|
||||
{
|
||||
var t3SingleSource = new T3SingleSourceProcessor(_db);
|
||||
t3SingleSource.Process(processWorker);
|
||||
break;
|
||||
}
|
||||
case "T4-SingleSource":
|
||||
{
|
||||
var t4SingleSource = new T4SingleSourceProcessor(_db);
|
||||
t4SingleSource.Process(processWorker);
|
||||
break;
|
||||
}
|
||||
case "T5-LastValues":
|
||||
{
|
||||
var t5LastValues = new T5LastValuesProcessor(_db);
|
||||
t5LastValues.Process(processWorker);
|
||||
break;
|
||||
}
|
||||
case "T3-MultiSourceSummary":
|
||||
{
|
||||
var t3MultiSourceSummary =
|
||||
new T3MultiSourceSummaryProcessor(_db);
|
||||
t3MultiSourceSummary.Process(processWorker);
|
||||
break;
|
||||
}
|
||||
case "T3-MultiSourceCopySelectedCodes":
|
||||
{
|
||||
var t3MultiSourceCopySelectedCode =
|
||||
new T3MultiSourceCopySelectedCodesProcessor(_db);
|
||||
t3MultiSourceCopySelectedCode.Process(processWorker);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
_logsController.AddEntry(new LogEntry
|
||||
{
|
||||
Title = $"{processWorker.Name}, {processWorker.Id}",
|
||||
Type = LogEntryType.Info,
|
||||
LogType = LogType.Process,
|
||||
Message = "Success",
|
||||
CreatedAt = DateTime.UtcNow
|
||||
});
|
||||
}
|
||||
|
||||
internal void SaveRecords(Guid id, ICollection<Record> records, Guid currentUserId)
|
||||
{
|
||||
var toDelete = _db.Records.Where(x => x.LayerId == id).ToList();
|
||||
if (toDelete.Count > 0)
|
||||
{
|
||||
_db.Records.RemoveRange(toDelete);
|
||||
}
|
||||
|
||||
foreach (var record in records)
|
||||
{
|
||||
record.CreatedById = currentUserId;
|
||||
record.CreatedAt = DateTime.UtcNow;
|
||||
record.ModifiedById = currentUserId;
|
||||
record.ModifiedAt = DateTime.UtcNow;
|
||||
record.LayerId = id;
|
||||
_db.Records.Add(record);
|
||||
}
|
||||
}
|
||||
|
||||
private static void WriteToConsole(params string[] messages)
|
||||
{
|
||||
foreach (var message in messages)
|
||||
{
|
||||
Console.WriteLine($"DiunaLog: {message}");
|
||||
}
|
||||
}
|
||||
|
||||
private bool IsImportedLayerUpToDate(Layer importWorker)
|
||||
{
|
||||
if (_googleSheetValues is null)
|
||||
{
|
||||
throw new Exception("Google Sheets API not initialized");
|
||||
}
|
||||
|
||||
var newestLayer = _db.Layers
|
||||
.Include(x => x.Records)
|
||||
.Where(x => x.ParentId == importWorker.Id)
|
||||
.OrderByDescending(x => x.CreatedAt)
|
||||
.AsNoTracking()
|
||||
.FirstOrDefault();
|
||||
|
||||
if (newestLayer is null)
|
||||
{
|
||||
return true; // importWorker is not active yet, no check needed
|
||||
}
|
||||
|
||||
var sheetId = importWorker.Records!.FirstOrDefault(x => x.Code == "SheetId")?.Desc1;
|
||||
if (sheetId == null)
|
||||
{
|
||||
throw new Exception($"SheetId not found, {importWorker.Name}");
|
||||
}
|
||||
|
||||
var sheetTabName = importWorker.Records!.FirstOrDefault(x => x.Code == "SheetTabName")?.Desc1;
|
||||
if (sheetTabName == null)
|
||||
{
|
||||
throw new Exception($"SheetTabName not found, {importWorker.Name}");
|
||||
}
|
||||
|
||||
var dataRange = importWorker.Records!.FirstOrDefault(x => x.Code == "DataRange")?.Desc1;
|
||||
if (dataRange == null)
|
||||
{
|
||||
throw new Exception($"DataRange not found, {importWorker.Name}");
|
||||
}
|
||||
|
||||
var dataRangeResponse = _googleSheetValues.Get(sheetId, $"{sheetTabName}!{dataRange}").Execute();
|
||||
var data = dataRangeResponse.Values;
|
||||
|
||||
var isUpToDate = true;
|
||||
|
||||
for (var i = 0; i < data[1].Count; i++)
|
||||
{
|
||||
if (data[0][i].ToString() == "") continue;
|
||||
var record = newestLayer.Records!.FirstOrDefault(x => x.Code == data[0][i].ToString());
|
||||
if (record == null)
|
||||
{
|
||||
WriteToConsole("Code not found in DiunaBI", data[0][i].ToString()!);
|
||||
isUpToDate = false;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!double.TryParse(data[1][i].ToString(), CultureInfo.GetCultureInfo("pl-PL"),
|
||||
out var value) ||
|
||||
double.Abs((double)(record.Value1 - value)!) < 0.01) continue;
|
||||
isUpToDate = false;
|
||||
}
|
||||
|
||||
foreach (var record in newestLayer.Records!)
|
||||
{
|
||||
if (data[0].Contains(record.Code))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
WriteToConsole($"Code not found in GoogleSheet: {record.Code}");
|
||||
isUpToDate = false;
|
||||
}
|
||||
|
||||
return isUpToDate;
|
||||
}
|
||||
}
|
||||
46
src/Backend/DiunaBI.WebAPI/Controllers/LogsController.cs
Normal file
46
src/Backend/DiunaBI.WebAPI/Controllers/LogsController.cs
Normal file
@@ -0,0 +1,46 @@
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using DiunaBI.Core.Models;
|
||||
using Google.Cloud.Firestore;
|
||||
|
||||
namespace DiunaBI.WebAPI.Controllers;
|
||||
|
||||
public class LogsController : Controller
|
||||
{
|
||||
|
||||
private readonly FirestoreDb _firestoreDb;
|
||||
private readonly Guid _SessionId = Guid.NewGuid();
|
||||
public LogsController(
|
||||
FirestoreDb firestoreDb
|
||||
)
|
||||
{
|
||||
_firestoreDb = firestoreDb;
|
||||
}
|
||||
|
||||
public void AddEntry(LogEntry entry)
|
||||
{
|
||||
entry.SessionId = _SessionId;
|
||||
entry.Instance = LogInstance.Morska;
|
||||
|
||||
if (entry.Type == LogEntryType.Info) { return; }
|
||||
|
||||
try
|
||||
{
|
||||
var collection = _firestoreDb.Collection("ApiLogs");
|
||||
var document = collection.Document();
|
||||
document.SetAsync(new
|
||||
{
|
||||
entry.Message,
|
||||
entry.Title,
|
||||
Type = Enum.GetName(typeof(LogEntryType), entry.Type),
|
||||
LogType = Enum.GetName(typeof(LogType), entry.LogType),
|
||||
Instance = Enum.GetName(typeof(LogInstance), entry.Instance),
|
||||
entry.CreatedAt,
|
||||
SessionId = entry.SessionId.ToString()
|
||||
}).Wait();
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Console.WriteLine(e.Message);
|
||||
}
|
||||
}
|
||||
}
|
||||
25
src/Backend/DiunaBI.WebAPI/Controllers/PingController.cs
Normal file
25
src/Backend/DiunaBI.WebAPI/Controllers/PingController.cs
Normal file
@@ -0,0 +1,25 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
|
||||
namespace DiunaBI.WebAPI.Controllers;
|
||||
|
||||
[ApiController]
|
||||
[Route("api/[controller]")]
|
||||
[Authorize]
|
||||
public class PingController : Controller
|
||||
{
|
||||
private readonly IConfiguration _configuration;
|
||||
public PingController(
|
||||
IConfiguration configuration)
|
||||
{
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("Ping")]
|
||||
[AllowAnonymous]
|
||||
public IActionResult Ping()
|
||||
{
|
||||
return Ok(_configuration["PONG"]);
|
||||
}
|
||||
}
|
||||
100
src/Backend/DiunaBI.WebAPI/Program.cs
Normal file
100
src/Backend/DiunaBI.WebAPI/Program.cs
Normal file
@@ -0,0 +1,100 @@
|
||||
using FirebaseAdmin;
|
||||
using Google.Apis.Auth.OAuth2;
|
||||
using Google.Cloud.Firestore;
|
||||
using Microsoft.AspNetCore.Authentication.JwtBearer;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using Microsoft.IdentityModel.Tokens;
|
||||
using System.IdentityModel.Tokens.Jwt;
|
||||
using System.Text;
|
||||
using DiunaBI.Core.Models;
|
||||
using DiunaBI.Database.Context;
|
||||
using DiunaBI.Core.Services;
|
||||
|
||||
var builder = WebApplication.CreateBuilder(args);
|
||||
|
||||
var connectionString = builder.Configuration.GetConnectionString("SQLDatabase");
|
||||
builder.Services.AddDbContext<AppDbContext>(x =>
|
||||
{
|
||||
x.UseSqlServer(connectionString);
|
||||
x.EnableSensitiveDataLogging();
|
||||
});
|
||||
|
||||
builder.Services.AddCors(options =>
|
||||
{
|
||||
options.AddPolicy("CORSPolicy", corsPolicyBuilder =>
|
||||
{
|
||||
corsPolicyBuilder.WithOrigins("http://localhost:4200")
|
||||
.AllowAnyMethod()
|
||||
.AllowAnyHeader()
|
||||
.AllowCredentials();
|
||||
|
||||
corsPolicyBuilder.WithOrigins("https://diuna.bim-it.pl")
|
||||
.AllowAnyMethod()
|
||||
.AllowAnyHeader()
|
||||
.AllowCredentials();
|
||||
});
|
||||
});
|
||||
|
||||
builder.Services.AddControllers();
|
||||
|
||||
|
||||
builder.Services.AddAuthentication(options =>
|
||||
{
|
||||
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
options.DefaultScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
}).AddJwtBearer(options =>
|
||||
{
|
||||
options.TokenValidationParameters = new TokenValidationParameters
|
||||
{
|
||||
ValidateIssuer = false,
|
||||
ValidateAudience = false,
|
||||
ValidateLifetime = true,
|
||||
ValidateIssuerSigningKey = true,
|
||||
IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(builder.Configuration["Secret"]!))
|
||||
};
|
||||
|
||||
});
|
||||
builder.Services.AddAuthentication();
|
||||
|
||||
builder.Services.AddSingleton(typeof(GoogleSheetsHelper));
|
||||
builder.Services.AddSingleton(typeof(GoogleDriveHelper));
|
||||
|
||||
var fileName = "diunabi-admin-firebase.json";
|
||||
#if DEBUG
|
||||
fileName = "diunabi-admin-firebase-Development.json";
|
||||
#endif
|
||||
var credentialPath = Path.Combine(Directory.GetCurrentDirectory(), fileName);
|
||||
System.Environment.SetEnvironmentVariable("GOOGLE_APPLICATION_CREDENTIALS", credentialPath);
|
||||
FirebaseAdmin.FirebaseApp.Create(new AppOptions()
|
||||
{
|
||||
Credential = GoogleCredential.GetApplicationDefault()
|
||||
});
|
||||
builder.Services.AddSingleton(FirestoreDb.Create("diunabi-admin"));
|
||||
|
||||
var app = builder.Build();
|
||||
|
||||
|
||||
app.Use(async (context, next) =>
|
||||
{
|
||||
var token = context.Request.Headers.Authorization.ToString();
|
||||
if (token.Length > 0
|
||||
&& !context.Request.Path.ToString().Contains("getForPowerBI")
|
||||
&& !context.Request.Path.ToString().Contains("getConfiguration")
|
||||
&& !context.Request.Path.ToString().Contains("DataInbox/Add"))
|
||||
{
|
||||
var handler = new JwtSecurityTokenHandler();
|
||||
var data = handler.ReadJwtToken(token.Split(' ')[1]);
|
||||
context.Request.Headers.Append("UserId", new Microsoft.Extensions.Primitives.StringValues(data.Subject));
|
||||
}
|
||||
await next(context);
|
||||
});
|
||||
|
||||
app.UseCors("CORSPolicy");
|
||||
|
||||
app.UseAuthentication();
|
||||
app.UseAuthorization();
|
||||
|
||||
app.MapControllers();
|
||||
|
||||
app.Run();
|
||||
23
src/Backend/DiunaBI.WebAPI/Properties/launchSettings.json
Normal file
23
src/Backend/DiunaBI.WebAPI/Properties/launchSettings.json
Normal file
@@ -0,0 +1,23 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/launchsettings.json",
|
||||
"profiles": {
|
||||
"http": {
|
||||
"commandName": "Project",
|
||||
"dotnetRunMessages": true,
|
||||
"launchBrowser": false,
|
||||
"applicationUrl": "http://localhost:5163",
|
||||
"environmentVariables": {
|
||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
||||
}
|
||||
},
|
||||
"https": {
|
||||
"commandName": "Project",
|
||||
"dotnetRunMessages": true,
|
||||
"launchBrowser": false,
|
||||
"applicationUrl": "https://localhost:7148;http://localhost:5163",
|
||||
"environmentVariables": {
|
||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
12
src/Backend/DiunaBI.WebAPI/client_secrets.Development.json
Normal file
12
src/Backend/DiunaBI.WebAPI/client_secrets.Development.json
Normal file
@@ -0,0 +1,12 @@
|
||||
{
|
||||
"type": "service_account",
|
||||
"project_id": "diuna-370117",
|
||||
"private_key_id": "f48fd588724e6733b9639fe7d7933091b96be34f",
|
||||
"private_key": "-----BEGIN PRIVATE KEY-----MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCenqveXpGKXA10psAQ4Wreeiom9GMbZywnqMAhxc0wobI7EfnbP4FPOjfS8oWFRRrVzRil78zeUGWXb1WMHYvUyU3IrGXp6kVxuxbjBvwooOB5cEgz928A3aUUZRXxwjPV3+KuuAeQydVwPMQo2a0AQ+YAOK2QMG+BGAPAzYB+/35Zf6JsDOIDgWMaJq3etKgIijk40Nmf+uaGRAQlEbMhnAaAYz2B6I7W3z0pFDq2btgYJII+DWRC2DjSrA4UUeuds8Kz5qwfafJ8ki9N1RdYdbB/q6T74xQ3G/aEOK+CYmkWQz2woY5y8b5RCbKoGGIXpu6FVuWTnVxYJpP5QvIFAgMBAAECggEAJC3Evb+MKqa8WvL9s9v2aDAtFR2AzWtG4vTWfd2D46e940NCXgOqFswMl4zBb5hHeqSBDrgXXk2wHk5CkObcUfhoSXEo/aV1mW821SluskWfbZNypIe3RddII9K6op3M/OdH6NoIv7mJeUQi6b5ce0cBWuOSkuS5ShSUJpG40T5RQfl0iMuEYDpU1tvKmwhFlPTUTUGH7RdeqGFYIfE3kzFQiiSrS8V5L1GJKWcxMLdTq4P9JzaSW7eAAYKJiFTMSQvqs7pssCIj1JNLzD9PTsQmid2V2mUJIg3joXMNGbxNqMcIqbEesidIsDOkQ06taUIYG39og6rc9bar6XWRgQKBgQDK/+a8jCmUByhedUT5ZnREtHm4HcVo1tfBcmmqSEV0VJPJd14+CYvaUzCCJ9+xiLo6yOWRUk2h1GANAp50AdiVAHNibfwtri7vKWNhpnd111N/ebh6GIksT0ZTvu7sq5qbYXU3q6l6YRCyXSdF1oRfQED8I8G1xZP5j6fspBgoKQKBgQDICIKo3gmUEeFSt+o+Lucd2BljaFq/hUMA6WFdKbRyyd2iKBmGR15VNihiuJWy5i2nmuFaXMkeHo/PUJeEYC+vkc7M7UCYtD9l2xwp78o3ss7vxdPvOKhrcvux/Wpk1nuAEpM459MC0bmtOGIKU+QmDbsBbMHZ6p0R8DvECJ9mfQKBgEj60PAOD9CY9ilnTYHAFKKyo2POyC7VtkFkqZo/W0DkOzFdybLR6cZ2y+SvAxunRRRnLykchq5cVJ+4xlB8bWm7/L9xPQ0LJvJyVblAiIgD/o/AqdKzSXV1lpn69Zh+ZRnhYqu9+jL1/HOzS7Au2+4GgpZjIHwB6R36SGup3slpAoGAZW2jSxsjQjh6x2XIWfWQbVqZLQXKFhjta7XrD8FI5XekcUfiAWuI0q5edghgp9D9T2JCaH5p4GLgyt9zpMTdCSpm8RRQT93905jxw/X51JpPQddO6psRE0K/i3YTD8SN5NgGXLF4FpLfkozncZMuOXl23HcYKHZFZMYql/FDWkUCgYAjGQKzYV7IXA7UDAY3ejawWMbsDttSPQ0E1ouuJWIX/eb4SXYr0u/gdLuX1uM7EsxqIGVFWfgtUGopoVGr604Sg+dfOPZgUzaGAlUE2iRMVp6YoRRbrvPsYJwDrV0Xwil1k6UEzn8bgXO/IQ4fgIWjkxS5sDkZ6LVSCfDn5tLThg==-----END PRIVATE KEY-----",
|
||||
"client_email": "diuna-backend@diuna-370117.iam.gserviceaccount.com",
|
||||
"client_id": "101546901561736131820",
|
||||
"auth_uri": "https://accounts.google.com/o/oauth2/auth",
|
||||
"token_uri": "https://oauth2.googleapis.com/token",
|
||||
"auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
|
||||
"client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/diuna-backend%40diuna-370117.iam.gserviceaccount.com"
|
||||
}
|
||||
12
src/Backend/DiunaBI.WebAPI/client_secrets.json
Normal file
12
src/Backend/DiunaBI.WebAPI/client_secrets.json
Normal file
@@ -0,0 +1,12 @@
|
||||
{
|
||||
"type": "service_account",
|
||||
"project_id": "#{google-backend-project-id}#",
|
||||
"private_key_id": "#{google-backend-private-key-id}#",
|
||||
"private_key": "#{google-backend-private-key}#",
|
||||
"client_email": "#{google-backend-client-email}#",
|
||||
"client_id": "#{google-backend-client-id}#",
|
||||
"auth_uri": "https://accounts.google.com/o/oauth2/auth",
|
||||
"token_uri": "https://oauth2.googleapis.com/token",
|
||||
"auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
|
||||
"client_x509_cert_url": "#{google-backend-client-cert-url}#"
|
||||
}
|
||||
13
src/Backend/DiunaBI.WebAPI/diunabi-admin-firebase.json
Normal file
13
src/Backend/DiunaBI.WebAPI/diunabi-admin-firebase.json
Normal file
@@ -0,0 +1,13 @@
|
||||
{
|
||||
"type": "service_account",
|
||||
"project_id": "#{firebase-project-id}#",
|
||||
"private_key_id": "#{firebase-private-key-id}#",
|
||||
"private_key": "#{firebase-private-key}#",
|
||||
"client_email": "#{firebase-client-email}#",
|
||||
"client_id": "#{firebase-client-id}#",
|
||||
"auth_uri": "https://accounts.google.com/o/oauth2/auth",
|
||||
"token_uri": "https://oauth2.googleapis.com/token",
|
||||
"auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
|
||||
"client_x509_cert_url": "#{firebase-client-cert-url}#",
|
||||
"universe_domain": "googleapis.com"
|
||||
}
|
||||
Reference in New Issue
Block a user