Compare commits
6 Commits
Feature/pr
...
Feature/ro
| Author | SHA1 | Date | |
|---|---|---|---|
| d1ac8e49ba | |||
| c10ae17f8c | |||
| c13ad3a8a7 | |||
| e0c247d07b | |||
| 1a3558df52 | |||
| d3cd7e5b3c |
9
.github/workflows/dotnet-developPublish.yml
vendored
9
.github/workflows/dotnet-developPublish.yml
vendored
@@ -5,6 +5,8 @@ on:
|
|||||||
branches:
|
branches:
|
||||||
- Main
|
- Main
|
||||||
|
|
||||||
|
env:
|
||||||
|
DOTNET_ENVIRONMENT: Development
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
build-and-deploy:
|
build-and-deploy:
|
||||||
@@ -35,11 +37,12 @@ jobs:
|
|||||||
& "C:\Program Files\IIS\Microsoft Web Deploy V3\msdeploy.exe" `
|
& "C:\Program Files\IIS\Microsoft Web Deploy V3\msdeploy.exe" `
|
||||||
-verb:sync `
|
-verb:sync `
|
||||||
-source:contentPath="$publishFolder" `
|
-source:contentPath="$publishFolder" `
|
||||||
-dest:contentPath="dadmehrg",computerName="https://$env:SERVER_HOST:8172/msdeploy.axd?site=gozareshgir",userName="$env:DEPLOY_USER",password="$env:DEPLOY_PASSWORD",authType="Basic" `
|
-dest:contentPath="dadmehrg",computerName="https://171.22.24.15:8172/msdeploy.axd?site=dadmehrg",userName="Administrator",password="R2rNpdnetP3j>q5b18",authType="Basic" `
|
||||||
-allowUntrusted `
|
-allowUntrusted `
|
||||||
-enableRule:AppOffline
|
-enableRule:AppOffline
|
||||||
|
|
||||||
|
|
||||||
env:
|
env:
|
||||||
SERVER_HOST: 171.22.24.15
|
SERVER_HOST: your-server-ip-or-domain
|
||||||
DEPLOY_USER: ${{ secrets.DEPLOY_USER }}
|
DEPLOY_USER: ${{ secrets.DEPLOY_USER }}
|
||||||
DEPLOY_PASSWORD: ${{ secrets.DEPLOY_PASSWORD }}
|
DEPLOY_PASSWORD: ${{ secrets.DEPLOY_PASSWORD }}
|
||||||
|
|||||||
2
.gitignore
vendored
2
.gitignore
vendored
@@ -362,5 +362,3 @@ MigrationBackup/
|
|||||||
# # Fody - auto-generated XML schema
|
# # Fody - auto-generated XML schema
|
||||||
# FodyWeavers.xsd
|
# FodyWeavers.xsd
|
||||||
.idea
|
.idea
|
||||||
/ServiceHost/appsettings.Development.json
|
|
||||||
/ServiceHost/appsettings.json
|
|
||||||
|
|||||||
@@ -1,26 +1,21 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
<RootNamespace>_0_Framework</RootNamespace>
|
<RootNamespace>_0_Framework</RootNamespace>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="FluentValidation" Version="12.1.1" />
|
<PackageReference Include="IPE.SmsIR" Version="1.0.5" />
|
||||||
<PackageReference Include="IPE.SmsIR" Version="1.2.7" />
|
<PackageReference Include="EPPlus" Version="7.5.2" />
|
||||||
<PackageReference Include="EPPlus" Version="8.4.0" />
|
<PackageReference Include="Microsoft.AspNetCore.Authentication.Cookies" Version="2.1.34" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Authentication.Cookies" Version="2.3.0" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="8.0.4" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http" Version="2.3.0" />
|
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.3.0" />
|
<PackageReference Include="Newtonsoft.Json.Bson" Version="1.0.2" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="10.0.1" />
|
|
||||||
<PackageReference Include="Microsoft.Extensions.Caching.Memory" Version="10.0.1" />
|
|
||||||
<PackageReference Include="Newtonsoft.Json" Version="13.0.4" />
|
|
||||||
<PackageReference Include="Newtonsoft.Json.Bson" Version="1.0.3" />
|
|
||||||
<PackageReference Include="PersianTools.Core" Version="2.0.4" />
|
<PackageReference Include="PersianTools.Core" Version="2.0.4" />
|
||||||
<PackageReference Include="System.Drawing.Common" Version="10.0.1" />
|
<PackageReference Include="System.Drawing.Common" Version="9.0.0" />
|
||||||
<PackageReference Include="MD.PersianDateTime.Standard" Version="2.6.0" />
|
<PackageReference Include="MD.PersianDateTime.Standard" Version="2.5.0" />
|
||||||
<PackageReference Include="Swashbuckle.AspNetCore.Annotations" Version="10.0.1" />
|
<PackageReference Include="Swashbuckle.AspNetCore.Annotations" Version="7.2.0" />
|
||||||
<PackageReference Include="System.Security.Cryptography.Xml" Version="10.0.1" />
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -56,11 +56,6 @@ public class AuthHelper : IAuthHelper
|
|||||||
return Tools.DeserializeFromBsonList<int>(permissions); //Mahan
|
return Tools.DeserializeFromBsonList<int>(permissions); //Mahan
|
||||||
}
|
}
|
||||||
|
|
||||||
public bool HasPermission(int permission)
|
|
||||||
{
|
|
||||||
return GetPermissions().Any(x => x == permission);
|
|
||||||
}
|
|
||||||
|
|
||||||
public long CurrentAccountId()
|
public long CurrentAccountId()
|
||||||
{
|
{
|
||||||
return IsAuthenticated()
|
return IsAuthenticated()
|
||||||
@@ -203,8 +198,7 @@ public class AuthHelper : IAuthHelper
|
|||||||
new("workshopList",workshopBson),
|
new("workshopList",workshopBson),
|
||||||
new("WorkshopSlug",slug),
|
new("WorkshopSlug",slug),
|
||||||
new("WorkshopId", account.WorkshopId.ToString()),
|
new("WorkshopId", account.WorkshopId.ToString()),
|
||||||
new("WorkshopName",account.WorkshopName??""),
|
new("WorkshopName",account.WorkshopName??"")
|
||||||
new("pm.userId", account.PmUserId.ToString()),
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -27,12 +27,10 @@ public class AuthViewModel
|
|||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
public long SubAccountId { get; set; }
|
public long SubAccountId { get; set; }
|
||||||
public long? PmUserId { get; set; }
|
|
||||||
|
|
||||||
|
|
||||||
public AuthViewModel(long id, long roleId, string fullname, string username, string mobile,string profilePhoto,
|
public AuthViewModel(long id, long roleId, string fullname, string username, string mobile,string profilePhoto,
|
||||||
List<int> permissions, string roleName, string adminAreaPermission, string clientAriaPermission, int? positionValue,
|
List<int> permissions, string roleName, string adminAreaPermission, string clientAriaPermission, int? positionValue, long subAccountId = 0)
|
||||||
long subAccountId = 0,long? pmUserId = null)
|
|
||||||
{
|
{
|
||||||
Id = id;
|
Id = id;
|
||||||
RoleId = roleId;
|
RoleId = roleId;
|
||||||
@@ -46,7 +44,6 @@ public class AuthViewModel
|
|||||||
ClientAriaPermission = clientAriaPermission;
|
ClientAriaPermission = clientAriaPermission;
|
||||||
PositionValue = positionValue;
|
PositionValue = positionValue;
|
||||||
SubAccountId = subAccountId;
|
SubAccountId = subAccountId;
|
||||||
PmUserId = pmUserId;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public AuthViewModel()
|
public AuthViewModel()
|
||||||
|
|||||||
@@ -1,22 +0,0 @@
|
|||||||
namespace _0_Framework.Application.Enums;
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// وضعیت تایید قرادا مالی
|
|
||||||
/// </summary>
|
|
||||||
public enum InstitutionContractVerificationStatus
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// در انتظار تایید
|
|
||||||
/// </summary>
|
|
||||||
PendingForVerify = 0,
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// در انتظار کارپوشه
|
|
||||||
/// </summary>
|
|
||||||
PendingWorkflow = 1,
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// تایید شده
|
|
||||||
/// </summary>
|
|
||||||
Verified = 2
|
|
||||||
}
|
|
||||||
@@ -1,15 +0,0 @@
|
|||||||
namespace _0_Framework.Application.Enums;
|
|
||||||
|
|
||||||
public enum TypeOfCheckoutWarning
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// هشدار های متفرقه
|
|
||||||
/// </summary>
|
|
||||||
OthersWarning,
|
|
||||||
/// <summary>
|
|
||||||
/// هشدار سهم بیمه کارگر
|
|
||||||
/// </summary>
|
|
||||||
InsuranceEmployeeShare,
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,41 +0,0 @@
|
|||||||
namespace _0_Framework.Application.Enums;
|
|
||||||
|
|
||||||
public enum TypeOfSmsSetting
|
|
||||||
{
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک
|
|
||||||
/// یادآور بدهی ماهیانه قرارداد مالی
|
|
||||||
/// </summary>
|
|
||||||
InstitutionContractDebtReminder,
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک
|
|
||||||
/// صورت حساب ماهانه قرارداد مالی
|
|
||||||
/// </summary>
|
|
||||||
MonthlyInstitutionContract,
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک
|
|
||||||
/// اعلام مسدودی طرف حساب
|
|
||||||
/// </summary>
|
|
||||||
BlockContractingParty,
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک
|
|
||||||
/// هشدار اول
|
|
||||||
/// </summary>
|
|
||||||
Warning,
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
///پیامک اقدام قضائی
|
|
||||||
/// </summary>
|
|
||||||
LegalAction,
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک تایید قراداد
|
|
||||||
/// </summary>
|
|
||||||
InstitutionContractConfirm,
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,25 +0,0 @@
|
|||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace _0_Framework.Application.FaceEmbedding;
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// سرویس اطلاعرسانی تغییرات Face Embedding
|
|
||||||
/// </summary>
|
|
||||||
public interface IFaceEmbeddingNotificationService
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// اطلاعرسانی ایجاد یا بهروزرسانی Embedding
|
|
||||||
/// </summary>
|
|
||||||
Task NotifyEmbeddingCreatedAsync(long workshopId, long employeeId, string employeeFullName);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// اطلاعرسانی حذف Embedding
|
|
||||||
/// </summary>
|
|
||||||
Task NotifyEmbeddingDeletedAsync(long workshopId, long employeeId);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// اطلاعرسانی بهبود Embedding
|
|
||||||
/// </summary>
|
|
||||||
Task NotifyEmbeddingRefinedAsync(long workshopId, long employeeId);
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -1,25 +0,0 @@
|
|||||||
using System.Collections.Generic;
|
|
||||||
using System.IO;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace _0_Framework.Application.FaceEmbedding;
|
|
||||||
|
|
||||||
public interface IFaceEmbeddingService
|
|
||||||
{
|
|
||||||
Task<OperationResult> GenerateEmbeddingsAsync(long employeeId, long workshopId, string employeeFullName, string picture1Path, string picture2Path);
|
|
||||||
Task<OperationResult> GenerateEmbeddingsFromStreamAsync(long employeeId, long workshopId, string employeeFullName, Stream picture1Stream, Stream picture2Stream);
|
|
||||||
Task<OperationResult> RefineEmbeddingAsync(long employeeId, long workshopId, float[] embedding, float confidence, Dictionary<string, object> metadata = null);
|
|
||||||
Task<OperationResult> DeleteEmbeddingAsync(long employeeId, long workshopId);
|
|
||||||
Task<OperationResult<FaceEmbeddingResponse>> GetEmbeddingAsync(long employeeId, long workshopId);
|
|
||||||
Task<OperationResult> UpdateEmbeddingFullNameAsync(long employeeId, long workshopId, string newFullName);
|
|
||||||
}
|
|
||||||
|
|
||||||
public class FaceEmbeddingResponse
|
|
||||||
{
|
|
||||||
public long EmployeeId { get; set; }
|
|
||||||
public long WorkshopId { get; set; }
|
|
||||||
public string EmployeeFullName { get; set; }
|
|
||||||
public float[] Embedding { get; set; }
|
|
||||||
public float Confidence { get; set; }
|
|
||||||
public Dictionary<string, object> Metadata { get; set; }
|
|
||||||
}
|
|
||||||
@@ -12,7 +12,6 @@ public interface IAuthHelper
|
|||||||
string CurrentAccountRole();
|
string CurrentAccountRole();
|
||||||
AuthViewModel CurrentAccountInfo();
|
AuthViewModel CurrentAccountInfo();
|
||||||
List<int> GetPermissions();
|
List<int> GetPermissions();
|
||||||
bool HasPermission(int permission);
|
|
||||||
long CurrentAccountId();
|
long CurrentAccountId();
|
||||||
string CurrentAccountMobile();
|
string CurrentAccountMobile();
|
||||||
|
|
||||||
|
|||||||
@@ -39,7 +39,7 @@ public class AqayePardakhtPaymentGateway:IPaymentGateway
|
|||||||
amount = command.Amount,
|
amount = command.Amount,
|
||||||
callback = command.CallBackUrl,
|
callback = command.CallBackUrl,
|
||||||
card_number = command.CardNumber,
|
card_number = command.CardNumber,
|
||||||
invoice_id = command.TransactionId,
|
invoice_id = command.InvoiceId,
|
||||||
mobile = command.Mobile,
|
mobile = command.Mobile,
|
||||||
email = command.Email??"",
|
email = command.Email??"",
|
||||||
description = command.Description,
|
description = command.Description,
|
||||||
@@ -73,7 +73,7 @@ public class AqayePardakhtPaymentGateway:IPaymentGateway
|
|||||||
amount = command.Amount,
|
amount = command.Amount,
|
||||||
callback = command.CallBackUrl,
|
callback = command.CallBackUrl,
|
||||||
card_number = command.Amount,
|
card_number = command.Amount,
|
||||||
invoice_id = command.TransactionId,
|
invoice_id = command.InvoiceId,
|
||||||
mobile = command.Mobile,
|
mobile = command.Mobile,
|
||||||
email = command.Email,
|
email = command.Email,
|
||||||
description = command.Email,
|
description = command.Email,
|
||||||
|
|||||||
@@ -29,11 +29,9 @@ public class PaymentGatewayResponse
|
|||||||
public int? ErrorCode { get; set; }
|
public int? ErrorCode { get; set; }
|
||||||
|
|
||||||
[JsonPropertyName("transid")]
|
[JsonPropertyName("transid")]
|
||||||
public string Token { get; set; }
|
public string TransactionId { get; set; }
|
||||||
|
|
||||||
public bool IsSuccess { get; set; }
|
public bool IsSuccess => Status == "success";
|
||||||
|
|
||||||
public string Message { get; set; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public class WalletAmountResponse
|
public class WalletAmountResponse
|
||||||
@@ -49,19 +47,16 @@ public class WalletAmountResponse
|
|||||||
public class CreatePaymentGatewayRequest
|
public class CreatePaymentGatewayRequest
|
||||||
{
|
{
|
||||||
public double Amount { get; set; }
|
public double Amount { get; set; }
|
||||||
public string TransactionId { get; set; }
|
|
||||||
public string CallBackUrl { get; set; }
|
public string CallBackUrl { get; set; }
|
||||||
|
public string InvoiceId { get; set; }
|
||||||
public string CardNumber { get; set; }
|
public string CardNumber { get; set; }
|
||||||
public string Mobile { get; set; }
|
public string Mobile { get; set; }
|
||||||
public string Email { get; set; }
|
public string Email { get; set; }
|
||||||
public string Description { get; set; }
|
public string Description { get; set; }
|
||||||
public long FinancialInvoiceId { get; set; }
|
|
||||||
public IDictionary<string, object> ExtraData { get; set; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public class VerifyPaymentGateWayRequest
|
public class VerifyPaymentGateWayRequest
|
||||||
{
|
{
|
||||||
public string DigitalReceipt { get; set; }
|
public string TransactionId { get; set; }
|
||||||
public string TransactionId { get; set; }
|
|
||||||
public double Amount { get; set; }
|
public double Amount { get; set; }
|
||||||
}
|
}
|
||||||
@@ -1,112 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Net.Http;
|
|
||||||
using System.Net.Http.Json;
|
|
||||||
using System.Threading;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using Microsoft.Extensions.Logging;
|
|
||||||
using Newtonsoft.Json;
|
|
||||||
|
|
||||||
namespace _0_Framework.Application.PaymentGateway;
|
|
||||||
|
|
||||||
public class SepehrPaymentGateway:IPaymentGateway
|
|
||||||
{
|
|
||||||
private readonly HttpClient _httpClient;
|
|
||||||
private const long TerminalId = 99213700;
|
|
||||||
private readonly ILogger<SepehrPaymentGateway> _logger;
|
|
||||||
|
|
||||||
public SepehrPaymentGateway(IHttpClientFactory httpClient, ILogger<SepehrPaymentGateway> logger)
|
|
||||||
{
|
|
||||||
_logger = logger;
|
|
||||||
_httpClient = httpClient.CreateClient();
|
|
||||||
_httpClient.BaseAddress = new Uri("https://sepehr.shaparak.ir/Rest/V1/PeymentApi/");
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<PaymentGatewayResponse> Create(CreatePaymentGatewayRequest command, CancellationToken cancellationToken = default)
|
|
||||||
{
|
|
||||||
_logger.LogInformation("Create payment started. TransactionId: {TransactionId}, Amount: {Amount}", command.TransactionId, command.Amount);
|
|
||||||
command.ExtraData ??= new Dictionary<string, object>();
|
|
||||||
_logger.LogInformation("Initializing extra data with FinancialInvoiceId: {FinancialInvoiceId}", command.FinancialInvoiceId);
|
|
||||||
command.ExtraData.Add("financialInvoiceId", command.FinancialInvoiceId);
|
|
||||||
var extraData = JsonConvert.SerializeObject(command.ExtraData);
|
|
||||||
_logger.LogInformation("Serialized extra data payload: {Payload}", extraData);
|
|
||||||
|
|
||||||
var res = await _httpClient.PostAsJsonAsync("GetToken", new
|
|
||||||
{
|
|
||||||
TerminalID = TerminalId,
|
|
||||||
Amount = command.Amount,
|
|
||||||
InvoiceID = command.TransactionId,
|
|
||||||
callbackURL = command.CallBackUrl,
|
|
||||||
payload = extraData
|
|
||||||
}, cancellationToken: cancellationToken);
|
|
||||||
_logger.LogInformation("Create payment request sent. StatusCode: {StatusCode}", res.StatusCode);
|
|
||||||
// خواندن محتوای پاسخ
|
|
||||||
var content = await res.Content.ReadAsStringAsync(cancellationToken);
|
|
||||||
_logger.LogInformation("Create payment response content: {Content}", content);
|
|
||||||
|
|
||||||
// تبدیل پاسخ JSON به آبجکت داتنت
|
|
||||||
var json = System.Text.Json.JsonDocument.Parse(content);
|
|
||||||
_logger.LogInformation("Create payment JSON parsed successfully.");
|
|
||||||
|
|
||||||
// گرفتن مقدار AccessToken
|
|
||||||
var accessToken = json.RootElement.GetProperty("Accesstoken").ToString();
|
|
||||||
var status = json.RootElement.GetProperty("Status").ToString();
|
|
||||||
_logger.LogInformation("Create payment parsed values. Status: {Status}, AccessToken: {AccessToken}", status, accessToken);
|
|
||||||
|
|
||||||
return new PaymentGatewayResponse
|
|
||||||
{
|
|
||||||
Status = status,
|
|
||||||
IsSuccess = status == "0",
|
|
||||||
Token = accessToken,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
public string GetStartPayUrl(string token)=>
|
|
||||||
$"https://sepehr.shaparak.ir/Payment/Pay?token={token}&terminalId={TerminalId}";
|
|
||||||
|
|
||||||
public async Task<PaymentGatewayResponse> Verify(VerifyPaymentGateWayRequest command, CancellationToken cancellationToken = default)
|
|
||||||
{
|
|
||||||
_logger.LogInformation("Verify payment started. DigitalReceipt: {DigitalReceipt}", command.DigitalReceipt);
|
|
||||||
var res = await _httpClient.PostAsJsonAsync("Advice", new
|
|
||||||
{
|
|
||||||
digitalreceipt = command.DigitalReceipt,
|
|
||||||
Tid = TerminalId,
|
|
||||||
}, cancellationToken: cancellationToken);
|
|
||||||
_logger.LogInformation("Verify payment request sent. StatusCode: {StatusCode}", res.StatusCode);
|
|
||||||
// خواندن محتوای پاسخ
|
|
||||||
var content = await res.Content.ReadAsStringAsync(cancellationToken);
|
|
||||||
_logger.LogInformation("Verify payment response content: {Content}", content);
|
|
||||||
|
|
||||||
// تبدیل پاسخ JSON به آبجکت داتنت
|
|
||||||
var json = System.Text.Json.JsonDocument.Parse(content);
|
|
||||||
_logger.LogInformation("Verify payment JSON parsed successfully.");
|
|
||||||
|
|
||||||
var message = json.RootElement.GetProperty("Message").GetString();
|
|
||||||
var status = json.RootElement.GetProperty("Status").GetString();
|
|
||||||
_logger.LogInformation("Verify payment parsed values. Status: {Status}, Message: {Message}", status, message);
|
|
||||||
return new PaymentGatewayResponse
|
|
||||||
{
|
|
||||||
Status = status,
|
|
||||||
IsSuccess = status.ToLower() == "ok",
|
|
||||||
Message = message
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public Task<PaymentGatewayResponse> CreateSandBox(CreatePaymentGatewayRequest command, CancellationToken cancellationToken = default)
|
|
||||||
{
|
|
||||||
throw new System.NotImplementedException();
|
|
||||||
}
|
|
||||||
|
|
||||||
public string GetStartPaySandBoxUrl(string transactionId)
|
|
||||||
{
|
|
||||||
throw new System.NotImplementedException();
|
|
||||||
}
|
|
||||||
|
|
||||||
public Task<WalletAmountResponse> GetWalletAmount(CancellationToken cancellationToken)
|
|
||||||
{
|
|
||||||
throw new System.NotImplementedException();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,13 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace _0_Framework.Application;
|
|
||||||
|
|
||||||
public static class SecretKeys
|
|
||||||
{
|
|
||||||
|
|
||||||
public static string ProgramManagerInternalApi => "JOb09$Ic3NJd0siLCJtYWMiOiI2%dmODJmNDV";
|
|
||||||
}
|
|
||||||
@@ -27,79 +27,11 @@ public interface ISmsService
|
|||||||
|
|
||||||
Task<double> GetCreditAmount();
|
Task<double> GetCreditAmount();
|
||||||
|
|
||||||
public Task<bool> SendInstitutionCreationVerificationLink(string number, string fullName, Guid institutionId, long contractingPartyId, long institutionContractId, string typeOfSms = null);
|
public Task<bool> SendInstitutionVerificationLink(string number, string fullName, Guid institutionId, long contractingPartyId, long institutionContractId);
|
||||||
|
|
||||||
public Task<bool> SendInstitutionVerificationCode(string number, string code, string contractingPartyFullName,
|
public Task<bool> SendInstitutionVerificationCode(string number, string code, string contractingPartyFullName,
|
||||||
long contractingPartyId, long institutionContractId);
|
long contractingPartyId, long institutionContractId);
|
||||||
|
|
||||||
SmsResult TaskReminderSms(string number, string taskCount);
|
|
||||||
|
|
||||||
#endregion
|
|
||||||
|
|
||||||
|
|
||||||
#region InstitutionContractSMS
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک اهانه جدید
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="number"></param>
|
|
||||||
/// <param name="tamplateId"></param>
|
|
||||||
/// <param name="fullname"></param>
|
|
||||||
/// <param name="amount"></param>
|
|
||||||
/// <param name="code1"></param>
|
|
||||||
/// <param name="code2"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<(byte status, string message, int messaeId, bool isSucceded)> MonthlyBillNew(string number, int tamplateId, string fullname, string amount, string code1,
|
|
||||||
string code2);
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک ماهانه قدیم
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="number"></param>
|
|
||||||
/// <param name="tamplateId"></param>
|
|
||||||
/// <param name="fullname"></param>
|
|
||||||
/// <param name="amount"></param>
|
|
||||||
/// <param name="id"></param>
|
|
||||||
/// <param name="aprove"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<(byte status, string message, int messaeId, bool isSucceded)> MonthlyBill(string number, int tamplateId, string fullname, string amount, string id, string aprove);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک مسدودی طرف حساب
|
|
||||||
/// قراردادهای قدیم
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="number"></param>
|
|
||||||
/// <param name="fullname"></param>
|
|
||||||
/// <param name="amount"></param>
|
|
||||||
/// <param name="accountType"></param>
|
|
||||||
/// <param name="id"></param>
|
|
||||||
/// <param name="aprove"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<(byte status, string message, int messaeId, bool isSucceded)> BlockMessage(string number, string fullname, string amount, string accountType, string id, string aprove);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیامک مسدودی طرف حساب
|
|
||||||
/// قرارداد های جدید
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="number"></param>
|
|
||||||
/// <param name="fullname"></param>
|
|
||||||
/// <param name="amount"></param>
|
|
||||||
/// <param name="code1"></param>
|
|
||||||
/// <param name="code2"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<(byte status, string message, int messaeId, bool isSucceded)> BlockMessageForElectronicContract(string number,
|
|
||||||
string fullname,
|
|
||||||
string amount, string code1, string code2);
|
|
||||||
#endregion
|
|
||||||
|
|
||||||
#region AlarmMessage
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ارسال پیامک های خطا یا اعمال ارسال
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="number"></param>
|
|
||||||
/// <param name="message"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<bool> Alarm(string number, string message);
|
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -1,32 +0,0 @@
|
|||||||
namespace _0_Framework.Application.Sms;
|
|
||||||
|
|
||||||
public class SmsResult
|
|
||||||
{
|
|
||||||
public SmsResult()
|
|
||||||
{
|
|
||||||
IsSuccedded = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public bool IsSuccedded { get; set; }
|
|
||||||
public string Message { get; set; }
|
|
||||||
public byte StatusCode { get; set; }
|
|
||||||
public int MessageId { get; set; }
|
|
||||||
|
|
||||||
public SmsResult Succedded(byte statusCode, string message, int messageId)
|
|
||||||
{
|
|
||||||
IsSuccedded = true;
|
|
||||||
Message = message;
|
|
||||||
StatusCode = statusCode;
|
|
||||||
MessageId = messageId;
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
public SmsResult Failed(byte statusCode, string message, int messageId)
|
|
||||||
{
|
|
||||||
IsSuccedded = false;
|
|
||||||
Message = message;
|
|
||||||
StatusCode = statusCode;
|
|
||||||
MessageId = messageId;
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -32,22 +32,11 @@ public static class StaticWorkshopAccounts
|
|||||||
/// 392 - عمار حسن دوست
|
/// 392 - عمار حسن دوست
|
||||||
/// 20 - سمیرا الهی نیا
|
/// 20 - سمیرا الهی نیا
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public static List<long> StaticAccountIds = [2, 3, 380, 381, 392, 20, 476];
|
public static List<long> StaticAccountIds = [2, 3, 380, 381, 392, 20];
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// این تاریخ در جدول اکانت لفت ورک به این معنیست
|
/// این تاریخ در جدول اکانت لفت ورک به این معنیست
|
||||||
/// که کاربر همچنان به کارگاه دسترسی دارد
|
/// که کاربر همچنان به کارگاه دسترسی دارد
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public static DateTime ContinuesWorkingDate = new DateTime(2150, 1, 1);
|
public static DateTime ContinuesWorkingDate = new DateTime(2150, 1, 1);
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// لیستی آی دی نقش هایی که مسئول بیمه کارگاه هستند
|
|
||||||
/// 7 : بیمه ارشد
|
|
||||||
/// 8 : بیمه ساده
|
|
||||||
/// </summary>
|
|
||||||
public static List<long> InsuranceAccountsRoleIds = [7, 8];
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -1,9 +0,0 @@
|
|||||||
namespace _0_Framework.Application.Enums
|
|
||||||
{
|
|
||||||
public class CheckoutDynamicDeductionItem
|
|
||||||
{
|
|
||||||
public string Name { get; set; }
|
|
||||||
public int Count { get; set; }
|
|
||||||
public string Amount { get; set; }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -17,7 +17,7 @@ public class ExcelGenerator
|
|||||||
{
|
{
|
||||||
public ExcelGenerator()
|
public ExcelGenerator()
|
||||||
{
|
{
|
||||||
OfficeOpenXml.ExcelPackage.License.SetNonCommercialOrganization("Gozareshgir Noncommercial organization");
|
ExcelPackage.LicenseContext = LicenseContext.NonCommercial;
|
||||||
}
|
}
|
||||||
public static byte[] GenerateExcel<T>(List<T> obj, string date = "") where T : class
|
public static byte[] GenerateExcel<T>(List<T> obj, string date = "") where T : class
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,10 +1,7 @@
|
|||||||
#nullable enable
|
using System;
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using FluentValidation;
|
|
||||||
using Microsoft.AspNetCore.Diagnostics;
|
using Microsoft.AspNetCore.Diagnostics;
|
||||||
using Microsoft.AspNetCore.Http;
|
using Microsoft.AspNetCore.Http;
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
@@ -24,24 +21,12 @@ public class CustomExceptionHandler : IExceptionHandler
|
|||||||
|
|
||||||
public async ValueTask<bool> TryHandleAsync(HttpContext context, Exception exception, CancellationToken cancellationToken)
|
public async ValueTask<bool> TryHandleAsync(HttpContext context, Exception exception, CancellationToken cancellationToken)
|
||||||
{
|
{
|
||||||
_logger.LogError(exception,
|
_logger.LogError(
|
||||||
"Error Message: {exceptionMessage}, Type: {exceptionType}, Time: {time}, Path: {path}, TraceId: {traceId}",
|
"Error Message: {exceptionMessage}, Time of occurrence {time}",
|
||||||
exception.Message,
|
exception.Message, DateTime.UtcNow);
|
||||||
exception.GetType().FullName,
|
|
||||||
DateTime.UtcNow,
|
|
||||||
context.Request.Path,
|
|
||||||
context.TraceIdentifier);
|
|
||||||
|
|
||||||
(string Detail, string Title, int StatusCode, Dictionary<string, object>? Extra) details = exception switch
|
(string Detail, string Title, int StatusCode, Dictionary<string, object>? Extra) details = exception switch
|
||||||
{
|
{
|
||||||
ValidationException validationException =>
|
|
||||||
(
|
|
||||||
validationException.Errors.FirstOrDefault()?.ErrorMessage ?? "One or more validation errors occurred.",
|
|
||||||
"Validation Error",
|
|
||||||
context.Response.StatusCode = StatusCodes.Status400BadRequest,
|
|
||||||
null
|
|
||||||
),
|
|
||||||
|
|
||||||
InternalServerException =>
|
InternalServerException =>
|
||||||
(
|
(
|
||||||
exception.Message,
|
exception.Message,
|
||||||
@@ -49,7 +34,6 @@ public class CustomExceptionHandler : IExceptionHandler
|
|||||||
context.Response.StatusCode = StatusCodes.Status500InternalServerError,
|
context.Response.StatusCode = StatusCodes.Status500InternalServerError,
|
||||||
null
|
null
|
||||||
),
|
),
|
||||||
|
|
||||||
BadRequestException bre =>
|
BadRequestException bre =>
|
||||||
(
|
(
|
||||||
exception.Message,
|
exception.Message,
|
||||||
@@ -57,7 +41,6 @@ public class CustomExceptionHandler : IExceptionHandler
|
|||||||
context.Response.StatusCode = StatusCodes.Status400BadRequest,
|
context.Response.StatusCode = StatusCodes.Status400BadRequest,
|
||||||
bre.Extra
|
bre.Extra
|
||||||
),
|
),
|
||||||
|
|
||||||
NotFoundException =>
|
NotFoundException =>
|
||||||
(
|
(
|
||||||
exception.Message,
|
exception.Message,
|
||||||
@@ -65,7 +48,6 @@ public class CustomExceptionHandler : IExceptionHandler
|
|||||||
context.Response.StatusCode = StatusCodes.Status404NotFound,
|
context.Response.StatusCode = StatusCodes.Status404NotFound,
|
||||||
null
|
null
|
||||||
),
|
),
|
||||||
|
|
||||||
UnAuthorizeException =>
|
UnAuthorizeException =>
|
||||||
(
|
(
|
||||||
exception.Message,
|
exception.Message,
|
||||||
@@ -73,7 +55,6 @@ public class CustomExceptionHandler : IExceptionHandler
|
|||||||
context.Response.StatusCode = StatusCodes.Status401Unauthorized,
|
context.Response.StatusCode = StatusCodes.Status401Unauthorized,
|
||||||
null
|
null
|
||||||
),
|
),
|
||||||
|
|
||||||
_ =>
|
_ =>
|
||||||
(
|
(
|
||||||
exception.Message,
|
exception.Message,
|
||||||
@@ -92,6 +73,8 @@ public class CustomExceptionHandler : IExceptionHandler
|
|||||||
Extensions = details.Extra ?? new Dictionary<string, object>()
|
Extensions = details.Extra ?? new Dictionary<string, object>()
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
problemDetails.Extensions.Add("traceId", context.TraceIdentifier);
|
problemDetails.Extensions.Add("traceId", context.TraceIdentifier);
|
||||||
|
|
||||||
await context.Response.WriteAsJsonAsync(problemDetails, cancellationToken: cancellationToken);
|
await context.Response.WriteAsJsonAsync(problemDetails, cancellationToken: cancellationToken);
|
||||||
|
|||||||
@@ -1,404 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.IO;
|
|
||||||
using System.Net.Http;
|
|
||||||
using System.Net.Http.Headers;
|
|
||||||
using System.Net.Http.Json;
|
|
||||||
using System.Text.Json;
|
|
||||||
using _0_Framework.Application;
|
|
||||||
using _0_Framework.Application.FaceEmbedding;
|
|
||||||
using Microsoft.Extensions.Logging;
|
|
||||||
using Microsoft.Extensions.Http;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace _0_Framework.Infrastructure;
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیادهسازی سرویس ارتباط با API پایتون برای مدیریت Embeddings چهره
|
|
||||||
/// </summary>
|
|
||||||
public class FaceEmbeddingService : IFaceEmbeddingService
|
|
||||||
{
|
|
||||||
private readonly IHttpClientFactory _httpClientFactory;
|
|
||||||
private readonly ILogger<FaceEmbeddingService> _logger;
|
|
||||||
private readonly IFaceEmbeddingNotificationService _notificationService;
|
|
||||||
private readonly string _apiBaseUrl;
|
|
||||||
|
|
||||||
public FaceEmbeddingService(IHttpClientFactory httpClientFactory, ILogger<FaceEmbeddingService> logger,
|
|
||||||
IFaceEmbeddingNotificationService notificationService = null)
|
|
||||||
{
|
|
||||||
_httpClientFactory = httpClientFactory;
|
|
||||||
_logger = logger;
|
|
||||||
_notificationService = notificationService;
|
|
||||||
_apiBaseUrl = "http://localhost:8000";
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<OperationResult> GenerateEmbeddingsAsync(long employeeId, long workshopId,
|
|
||||||
string employeeFullName, string picture1Path, string picture2Path)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var httpClient = _httpClientFactory.CreateClient();
|
|
||||||
httpClient.BaseAddress = new Uri(_apiBaseUrl);
|
|
||||||
httpClient.Timeout = TimeSpan.FromSeconds(30);
|
|
||||||
|
|
||||||
using var content = new MultipartFormDataContent();
|
|
||||||
|
|
||||||
// Add form fields
|
|
||||||
content.Add(new StringContent(employeeId.ToString()), "employee_id");
|
|
||||||
content.Add(new StringContent(workshopId.ToString()), "workshop_id");
|
|
||||||
content.Add(new StringContent(employeeFullName ?? ""), "employee_full_name");
|
|
||||||
|
|
||||||
// Add picture files
|
|
||||||
if (File.Exists(picture1Path))
|
|
||||||
{
|
|
||||||
var picture1Bytes = await File.ReadAllBytesAsync(picture1Path);
|
|
||||||
var picture1Content = new ByteArrayContent(picture1Bytes);
|
|
||||||
picture1Content.Headers.ContentType = new MediaTypeHeaderValue("image/jpeg");
|
|
||||||
content.Add(picture1Content, "picture1", "1.jpg");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
_logger.LogWarning("Picture1 not found at path: {Path}", picture1Path);
|
|
||||||
return new OperationResult { IsSuccedded = false, Message = "تصویر اول یافت نشد" };
|
|
||||||
}
|
|
||||||
|
|
||||||
if (File.Exists(picture2Path))
|
|
||||||
{
|
|
||||||
var picture2Bytes = await File.ReadAllBytesAsync(picture2Path);
|
|
||||||
var picture2Content = new ByteArrayContent(picture2Bytes);
|
|
||||||
picture2Content.Headers.ContentType = new MediaTypeHeaderValue("image/jpeg");
|
|
||||||
content.Add(picture2Content, "picture2", "2.jpg");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
_logger.LogWarning("Picture2 not found at path: {Path}", picture2Path);
|
|
||||||
return new OperationResult { IsSuccedded = false, Message = "تصویر دوم یافت نشد" };
|
|
||||||
}
|
|
||||||
|
|
||||||
// Send request to Python API
|
|
||||||
var response = await httpClient.PostAsync("embeddings", content);
|
|
||||||
|
|
||||||
if (response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
var responseContent = await response.Content.ReadAsStringAsync();
|
|
||||||
_logger.LogInformation(
|
|
||||||
"Embeddings generated successfully for Employee {EmployeeId}, Workshop {WorkshopId}",
|
|
||||||
employeeId, workshopId);
|
|
||||||
|
|
||||||
// ارسال اطلاعرسانی به سایر سیستمها
|
|
||||||
if (_notificationService != null)
|
|
||||||
{
|
|
||||||
await _notificationService.NotifyEmbeddingCreatedAsync(workshopId, employeeId, employeeFullName);
|
|
||||||
}
|
|
||||||
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = true,
|
|
||||||
Message = "Embedding با موفقیت ایجاد شد"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var errorContent = await response.Content.ReadAsStringAsync();
|
|
||||||
_logger.LogError("Failed to generate embeddings. Status: {StatusCode}, Error: {Error}",
|
|
||||||
response.StatusCode, errorContent);
|
|
||||||
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = $"خطا در تولید Embedding: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (HttpRequestException ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "HTTP error while calling embeddings API for Employee {EmployeeId}", employeeId);
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = "خطا در ارتباط با سرور Embedding"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "Error while calling embeddings API for Employee {EmployeeId}", employeeId);
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = "خطای غیرمنتظره در تولید Embedding"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<OperationResult> GenerateEmbeddingsFromStreamAsync(long employeeId, long workshopId,
|
|
||||||
string employeeFullName, Stream picture1Stream, Stream picture2Stream)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var httpClient = _httpClientFactory.CreateClient();
|
|
||||||
httpClient.BaseAddress = new Uri(_apiBaseUrl);
|
|
||||||
httpClient.Timeout = TimeSpan.FromSeconds(30);
|
|
||||||
|
|
||||||
using var content = new MultipartFormDataContent();
|
|
||||||
|
|
||||||
// Add form fields
|
|
||||||
content.Add(new StringContent(employeeId.ToString()), "employee_id");
|
|
||||||
content.Add(new StringContent(workshopId.ToString()), "workshop_id");
|
|
||||||
content.Add(new StringContent(employeeFullName ?? ""), "employee_full_name");
|
|
||||||
|
|
||||||
// Add picture streams
|
|
||||||
var picture1Content = new StreamContent(picture1Stream);
|
|
||||||
picture1Content.Headers.ContentType = new MediaTypeHeaderValue("image/jpeg");
|
|
||||||
content.Add(picture1Content, "picture1", "1.jpg");
|
|
||||||
|
|
||||||
var picture2Content = new StreamContent(picture2Stream);
|
|
||||||
picture2Content.Headers.ContentType = new MediaTypeHeaderValue("image/jpeg");
|
|
||||||
content.Add(picture2Content, "picture2", "2.jpg");
|
|
||||||
|
|
||||||
// Send request to Python API
|
|
||||||
var response = await httpClient.PostAsync("embeddings", content);
|
|
||||||
|
|
||||||
if (response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
_logger.LogInformation("Embeddings generated successfully from streams for Employee {EmployeeId}",
|
|
||||||
employeeId);
|
|
||||||
|
|
||||||
// ارسال اطلاعرسانی به سایر سیستمها
|
|
||||||
if (_notificationService != null)
|
|
||||||
{
|
|
||||||
await _notificationService.NotifyEmbeddingCreatedAsync(workshopId, employeeId, employeeFullName);
|
|
||||||
}
|
|
||||||
|
|
||||||
return new OperationResult { IsSuccedded = true, Message = "Embedding با موفقیت ایجاد شد" };
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var errorContent = await response.Content.ReadAsStringAsync();
|
|
||||||
_logger.LogError("Failed to generate embeddings from streams. Status: {StatusCode}, Error: {Error}",
|
|
||||||
response.StatusCode, errorContent);
|
|
||||||
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = $"خطا در تولید Embedding: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "Error while generating embeddings from streams for Employee {EmployeeId}",
|
|
||||||
employeeId);
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = "خطا در تولید Embedding"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<OperationResult> RefineEmbeddingAsync(long employeeId, long workshopId, float[] embedding,
|
|
||||||
float confidence, Dictionary<string, object> metadata = null)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var httpClient = _httpClientFactory.CreateClient();
|
|
||||||
httpClient.BaseAddress = new Uri(_apiBaseUrl);
|
|
||||||
httpClient.Timeout = TimeSpan.FromSeconds(30);
|
|
||||||
|
|
||||||
var requestBody = new
|
|
||||||
{
|
|
||||||
employeeId,
|
|
||||||
workshopId,
|
|
||||||
embedding,
|
|
||||||
confidence,
|
|
||||||
metadata = metadata ?? new Dictionary<string, object>()
|
|
||||||
};
|
|
||||||
|
|
||||||
var response = await httpClient.PostAsJsonAsync("embeddings/refine", requestBody);
|
|
||||||
|
|
||||||
if (response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
_logger.LogInformation("Embedding refined successfully for Employee {EmployeeId}", employeeId);
|
|
||||||
|
|
||||||
// ارسال اطلاعرسانی به سایر سیستمها
|
|
||||||
if (_notificationService != null)
|
|
||||||
{
|
|
||||||
await _notificationService.NotifyEmbeddingRefinedAsync(workshopId, employeeId);
|
|
||||||
}
|
|
||||||
|
|
||||||
return new OperationResult { IsSuccedded = true, Message = "Embedding بهبود یافت" };
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var errorContent = await response.Content.ReadAsStringAsync();
|
|
||||||
_logger.LogError("Failed to refine embedding. Status: {StatusCode}, Error: {Error}",
|
|
||||||
response.StatusCode, errorContent);
|
|
||||||
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = $"خطا در بهبود Embedding: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "Error while refining embedding for Employee {EmployeeId}", employeeId);
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = "خطا در بهبود Embedding"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<OperationResult> DeleteEmbeddingAsync(long employeeId, long workshopId)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var httpClient = _httpClientFactory.CreateClient();
|
|
||||||
httpClient.BaseAddress = new Uri(_apiBaseUrl);
|
|
||||||
httpClient.Timeout = TimeSpan.FromSeconds(30);
|
|
||||||
|
|
||||||
var response = await httpClient.DeleteAsync($"embeddings/{workshopId}/{employeeId}");
|
|
||||||
|
|
||||||
if (response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
_logger.LogInformation("Embedding deleted successfully for Employee {EmployeeId}", employeeId);
|
|
||||||
|
|
||||||
// ارسال اطلاعرسانی به سایر سیستمها
|
|
||||||
if (_notificationService != null)
|
|
||||||
{
|
|
||||||
await _notificationService.NotifyEmbeddingDeletedAsync(workshopId, employeeId);
|
|
||||||
}
|
|
||||||
|
|
||||||
return new OperationResult { IsSuccedded = true, Message = "Embedding حذف شد" };
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var errorContent = await response.Content.ReadAsStringAsync();
|
|
||||||
_logger.LogError("Failed to delete embedding. Status: {StatusCode}, Error: {Error}",
|
|
||||||
response.StatusCode, errorContent);
|
|
||||||
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = $"خطا در حذف Embedding: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "Error while deleting embedding for Employee {EmployeeId}", employeeId);
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = "خطا در حذف Embedding"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<OperationResult<FaceEmbeddingResponse>> GetEmbeddingAsync(long employeeId, long workshopId)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var httpClient = _httpClientFactory.CreateClient();
|
|
||||||
httpClient.BaseAddress = new Uri(_apiBaseUrl);
|
|
||||||
httpClient.Timeout = TimeSpan.FromSeconds(30);
|
|
||||||
|
|
||||||
var response = await httpClient.GetAsync($"embeddings/{workshopId}/{employeeId}");
|
|
||||||
|
|
||||||
if (response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
var content = await response.Content.ReadAsStringAsync();
|
|
||||||
var embeddingData = JsonSerializer.Deserialize<FaceEmbeddingResponse>(content,
|
|
||||||
new JsonSerializerOptions { PropertyNameCaseInsensitive = true });
|
|
||||||
|
|
||||||
_logger.LogInformation("Embedding retrieved successfully for Employee {EmployeeId}", employeeId);
|
|
||||||
|
|
||||||
return new OperationResult<FaceEmbeddingResponse>
|
|
||||||
{
|
|
||||||
IsSuccedded = true,
|
|
||||||
Message = "Embedding دریافت شد",
|
|
||||||
Data = embeddingData
|
|
||||||
};
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var errorContent = await response.Content.ReadAsStringAsync();
|
|
||||||
_logger.LogError("Failed to get embedding. Status: {StatusCode}, Error: {Error}",
|
|
||||||
response.StatusCode, errorContent);
|
|
||||||
|
|
||||||
return new OperationResult<FaceEmbeddingResponse>
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = $"خطا در دریافت Embedding: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "Error while getting embedding for Employee {EmployeeId}", employeeId);
|
|
||||||
return new OperationResult<FaceEmbeddingResponse>
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = "خطا در دریافت Embedding"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<OperationResult> UpdateEmbeddingFullNameAsync(long employeeId, long workshopId,
|
|
||||||
string newFullName)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var httpClient = _httpClientFactory.CreateClient();
|
|
||||||
httpClient.BaseAddress = new Uri(_apiBaseUrl);
|
|
||||||
httpClient.Timeout = TimeSpan.FromSeconds(30);
|
|
||||||
|
|
||||||
var requestBody = new
|
|
||||||
{
|
|
||||||
employee_id = employeeId,
|
|
||||||
workshop_id = workshopId,
|
|
||||||
employee_full_name = newFullName
|
|
||||||
};
|
|
||||||
|
|
||||||
var response = await httpClient.PutAsJsonAsync("embeddings/update-name", requestBody);
|
|
||||||
|
|
||||||
if (response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
_logger.LogInformation("Employee Name Changed For {EmployeeId} In workshop ={WorkshopId}", employeeId,
|
|
||||||
workshopId);
|
|
||||||
|
|
||||||
// ارسال اطلاعرسانی به سایر سیستمها
|
|
||||||
if (_notificationService != null)
|
|
||||||
{
|
|
||||||
//await _notificationService.NotifyEmbeddingRefinedAsync(workshopId, employeeId);
|
|
||||||
}
|
|
||||||
|
|
||||||
return new OperationResult { IsSuccedded = true, Message = "عملیات با موفقیت انجام شد" };
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var errorContent = await response.Content.ReadAsStringAsync();
|
|
||||||
_logger.LogError("Failed to refine embedding. Status: {StatusCode}, Error: {Error}",
|
|
||||||
response.StatusCode, errorContent);
|
|
||||||
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = $"خطا در بهبود Embedding: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "Error while Changing EmployeeFullName for Employee {EmployeeId}", employeeId);
|
|
||||||
return new OperationResult
|
|
||||||
{
|
|
||||||
IsSuccedded = false,
|
|
||||||
Message = "خطا در بهبود Embedding"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,29 +0,0 @@
|
|||||||
using System.Threading.Tasks;
|
|
||||||
using _0_Framework.Application.FaceEmbedding;
|
|
||||||
|
|
||||||
namespace _0_Framework.InfraStructure;
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیادهسازی پیشفرض (بدون عملیات) برای IFaceEmbeddingNotificationService
|
|
||||||
/// این کلاس زمانی استفاده میشود که SignalR در دسترس نباشد
|
|
||||||
/// </summary>
|
|
||||||
public class NullFaceEmbeddingNotificationService : IFaceEmbeddingNotificationService
|
|
||||||
{
|
|
||||||
public Task NotifyEmbeddingCreatedAsync(long workshopId, long employeeId, string employeeFullName)
|
|
||||||
{
|
|
||||||
// هیچ عملیاتی انجام نمیدهد
|
|
||||||
return Task.CompletedTask;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Task NotifyEmbeddingDeletedAsync(long workshopId, long employeeId)
|
|
||||||
{
|
|
||||||
// هیچ عملیاتی انجام نمیدهد
|
|
||||||
return Task.CompletedTask;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Task NotifyEmbeddingRefinedAsync(long workshopId, long employeeId)
|
|
||||||
{
|
|
||||||
// هیچ عملیاتی انجام نمیدهد
|
|
||||||
return Task.CompletedTask;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,624 +0,0 @@
|
|||||||
# راهنمای اتصال اپلیکیشن Android به SignalR برای Face Embedding
|
|
||||||
|
|
||||||
## 1. افزودن کتابخانه SignalR به پروژه Android
|
|
||||||
|
|
||||||
در فایل `build.gradle` (Module: app) خود، dependency زیر را اضافه کنید:
|
|
||||||
|
|
||||||
```gradle
|
|
||||||
dependencies {
|
|
||||||
// SignalR for Android
|
|
||||||
implementation 'com.microsoft.signalr:signalr:7.0.0'
|
|
||||||
|
|
||||||
// اگر از Kotlin استفاده میکنید:
|
|
||||||
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.7.1'
|
|
||||||
|
|
||||||
// برای JSON پردازش:
|
|
||||||
implementation 'com.google.code.gson:gson:2.10.1'
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
## 2. اضافه کردن Permission در AndroidManifest.xml
|
|
||||||
|
|
||||||
```xml
|
|
||||||
<uses-permission android:name="android.permission.INTERNET" />
|
|
||||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
|
|
||||||
```
|
|
||||||
|
|
||||||
## 3. کد Java/Kotlin برای اتصال به SignalR
|
|
||||||
|
|
||||||
### نسخه Java:
|
|
||||||
|
|
||||||
```java
|
|
||||||
import com.microsoft.signalr.HubConnection;
|
|
||||||
import com.microsoft.signalr.HubConnectionBuilder;
|
|
||||||
import com.microsoft.signalr.HubConnectionState;
|
|
||||||
import com.google.gson.JsonObject;
|
|
||||||
import android.util.Log;
|
|
||||||
|
|
||||||
public class FaceEmbeddingSignalRClient {
|
|
||||||
private static final String TAG = "FaceEmbeddingHub";
|
|
||||||
private HubConnection hubConnection;
|
|
||||||
private String serverUrl = "http://YOUR_SERVER_IP:PORT/trackingFaceEmbeddingHub"; // آدرس سرور خود را وارد کنید
|
|
||||||
private long workshopId;
|
|
||||||
|
|
||||||
public FaceEmbeddingSignalRClient(long workshopId) {
|
|
||||||
this.workshopId = workshopId;
|
|
||||||
initializeSignalR();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void initializeSignalR() {
|
|
||||||
// ایجاد اتصال SignalR
|
|
||||||
hubConnection = HubConnectionBuilder
|
|
||||||
.create(serverUrl)
|
|
||||||
.build();
|
|
||||||
|
|
||||||
// دریافت رویداد ایجاد Embedding
|
|
||||||
hubConnection.on("EmbeddingCreated", (data) -> {
|
|
||||||
JsonObject jsonData = (JsonObject) data;
|
|
||||||
long employeeId = jsonData.get("employeeId").getAsLong();
|
|
||||||
String employeeFullName = jsonData.get("employeeFullName").getAsString();
|
|
||||||
String timestamp = jsonData.get("timestamp").getAsString();
|
|
||||||
|
|
||||||
Log.d(TAG, "Embedding Created - Employee: " + employeeFullName + " (ID: " + employeeId + ")");
|
|
||||||
|
|
||||||
// اینجا میتوانید دادههای جدید را از سرور بگیرید یا UI را بروزرسانی کنید
|
|
||||||
onEmbeddingCreated(employeeId, employeeFullName, timestamp);
|
|
||||||
|
|
||||||
}, JsonObject.class);
|
|
||||||
|
|
||||||
// دریافت رویداد حذف Embedding
|
|
||||||
hubConnection.on("EmbeddingDeleted", (data) -> {
|
|
||||||
JsonObject jsonData = (JsonObject) data;
|
|
||||||
long employeeId = jsonData.get("employeeId").getAsLong();
|
|
||||||
String timestamp = jsonData.get("timestamp").getAsString();
|
|
||||||
|
|
||||||
Log.d(TAG, "Embedding Deleted - Employee ID: " + employeeId);
|
|
||||||
onEmbeddingDeleted(employeeId, timestamp);
|
|
||||||
|
|
||||||
}, JsonObject.class);
|
|
||||||
|
|
||||||
// دریافت رویداد بهبود Embedding
|
|
||||||
hubConnection.on("EmbeddingRefined", (data) -> {
|
|
||||||
JsonObject jsonData = (JsonObject) data;
|
|
||||||
long employeeId = jsonData.get("employeeId").getAsLong();
|
|
||||||
String timestamp = jsonData.get("timestamp").getAsString();
|
|
||||||
|
|
||||||
Log.d(TAG, "Embedding Refined - Employee ID: " + employeeId);
|
|
||||||
onEmbeddingRefined(employeeId, timestamp);
|
|
||||||
|
|
||||||
}, JsonObject.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void connect() {
|
|
||||||
if (hubConnection.getConnectionState() == HubConnectionState.DISCONNECTED) {
|
|
||||||
hubConnection.start()
|
|
||||||
.doOnComplete(() -> {
|
|
||||||
Log.d(TAG, "Connected to SignalR Hub");
|
|
||||||
joinWorkshopGroup();
|
|
||||||
})
|
|
||||||
.doOnError(error -> {
|
|
||||||
Log.e(TAG, "Error connecting to SignalR: " + error.getMessage());
|
|
||||||
})
|
|
||||||
.subscribe();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void joinWorkshopGroup() {
|
|
||||||
// عضویت در گروه مخصوص این کارگاه
|
|
||||||
hubConnection.send("JoinWorkshopGroup", workshopId);
|
|
||||||
Log.d(TAG, "Joined workshop group: " + workshopId);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void disconnect() {
|
|
||||||
if (hubConnection.getConnectionState() == HubConnectionState.CONNECTED) {
|
|
||||||
// خروج از گروه
|
|
||||||
hubConnection.send("LeaveWorkshopGroup", workshopId);
|
|
||||||
|
|
||||||
hubConnection.stop();
|
|
||||||
Log.d(TAG, "Disconnected from SignalR Hub");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// این متدها را در Activity/Fragment خود override کنید
|
|
||||||
protected void onEmbeddingCreated(long employeeId, String employeeFullName, String timestamp) {
|
|
||||||
// اینجا UI را بروزرسانی کنید یا داده جدید را بگیرید
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void onEmbeddingDeleted(long employeeId, String timestamp) {
|
|
||||||
// اینجا UI را بروزرسانی کنید
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void onEmbeddingRefined(long employeeId, String timestamp) {
|
|
||||||
// اینجا UI را بروزرسانی کنید
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
### نسخه Kotlin:
|
|
||||||
|
|
||||||
```kotlin
|
|
||||||
import com.microsoft.signalr.HubConnection
|
|
||||||
import com.microsoft.signalr.HubConnectionBuilder
|
|
||||||
import com.microsoft.signalr.HubConnectionState
|
|
||||||
import com.google.gson.JsonObject
|
|
||||||
import android.util.Log
|
|
||||||
import kotlinx.coroutines.CoroutineScope
|
|
||||||
import kotlinx.coroutines.Dispatchers
|
|
||||||
import kotlinx.coroutines.launch
|
|
||||||
|
|
||||||
class FaceEmbeddingSignalRClient(private val workshopId: Long) {
|
|
||||||
|
|
||||||
companion object {
|
|
||||||
private const val TAG = "FaceEmbeddingHub"
|
|
||||||
}
|
|
||||||
|
|
||||||
private lateinit var hubConnection: HubConnection
|
|
||||||
private val serverUrl = "http://YOUR_SERVER_IP:PORT/trackingFaceEmbeddingHub" // آدرس سرور خود را وارد کنید
|
|
||||||
|
|
||||||
init {
|
|
||||||
initializeSignalR()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun initializeSignalR() {
|
|
||||||
hubConnection = HubConnectionBuilder
|
|
||||||
.create(serverUrl)
|
|
||||||
.build()
|
|
||||||
|
|
||||||
// دریافت رویداد ایجاد Embedding
|
|
||||||
hubConnection.on("EmbeddingCreated", { data: JsonObject ->
|
|
||||||
val employeeId = data.get("employeeId").asLong
|
|
||||||
val employeeFullName = data.get("employeeFullName").asString
|
|
||||||
val timestamp = data.get("timestamp").asString
|
|
||||||
|
|
||||||
Log.d(TAG, "Embedding Created - Employee: $employeeFullName (ID: $employeeId)")
|
|
||||||
onEmbeddingCreated(employeeId, employeeFullName, timestamp)
|
|
||||||
}, JsonObject::class.java)
|
|
||||||
|
|
||||||
// دریافت رویداد حذف Embedding
|
|
||||||
hubConnection.on("EmbeddingDeleted", { data: JsonObject ->
|
|
||||||
val employeeId = data.get("employeeId").asLong
|
|
||||||
val timestamp = data.get("timestamp").asString
|
|
||||||
|
|
||||||
Log.d(TAG, "Embedding Deleted - Employee ID: $employeeId")
|
|
||||||
onEmbeddingDeleted(employeeId, timestamp)
|
|
||||||
}, JsonObject::class.java)
|
|
||||||
|
|
||||||
// دریافت رویداد بهبود Embedding
|
|
||||||
hubConnection.on("EmbeddingRefined", { data: JsonObject ->
|
|
||||||
val employeeId = data.get("employeeId").asLong
|
|
||||||
val timestamp = data.get("timestamp").asString
|
|
||||||
|
|
||||||
Log.d(TAG, "Embedding Refined - Employee ID: $employeeId")
|
|
||||||
onEmbeddingRefined(employeeId, timestamp)
|
|
||||||
}, JsonObject::class.java)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun connect() {
|
|
||||||
if (hubConnection.connectionState == HubConnectionState.DISCONNECTED) {
|
|
||||||
CoroutineScope(Dispatchers.IO).launch {
|
|
||||||
try {
|
|
||||||
hubConnection.start().blockingAwait()
|
|
||||||
Log.d(TAG, "Connected to SignalR Hub")
|
|
||||||
joinWorkshopGroup()
|
|
||||||
} catch (e: Exception) {
|
|
||||||
Log.e(TAG, "Error connecting to SignalR: ${e.message}")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun joinWorkshopGroup() {
|
|
||||||
hubConnection.send("JoinWorkshopGroup", workshopId)
|
|
||||||
Log.d(TAG, "Joined workshop group: $workshopId")
|
|
||||||
}
|
|
||||||
|
|
||||||
fun disconnect() {
|
|
||||||
if (hubConnection.connectionState == HubConnectionState.CONNECTED) {
|
|
||||||
hubConnection.send("LeaveWorkshopGroup", workshopId)
|
|
||||||
hubConnection.stop()
|
|
||||||
Log.d(TAG, "Disconnected from SignalR Hub")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// این متدها را override کنید
|
|
||||||
open fun onEmbeddingCreated(employeeId: Long, employeeFullName: String, timestamp: String) {
|
|
||||||
// اینجا UI را بروزرسانی کنید یا داده جدید را بگیرید
|
|
||||||
}
|
|
||||||
|
|
||||||
open fun onEmbeddingDeleted(employeeId: Long, timestamp: String) {
|
|
||||||
// اینجا UI را بروزرسانی کنید
|
|
||||||
}
|
|
||||||
|
|
||||||
open fun onEmbeddingRefined(employeeId: Long, timestamp: String) {
|
|
||||||
// اینجا UI را بروزرسانی کنید
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
## 4. استفاده در Activity یا Fragment
|
|
||||||
|
|
||||||
### مثال با Login و دریافت WorkshopId
|
|
||||||
|
|
||||||
#### Java:
|
|
||||||
```java
|
|
||||||
public class LoginActivity extends AppCompatActivity {
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onCreate(Bundle savedInstanceState) {
|
|
||||||
super.onCreate(savedInstanceState);
|
|
||||||
setContentView(R.layout.activity_login);
|
|
||||||
|
|
||||||
Button btnLogin = findViewById(R.id.btnLogin);
|
|
||||||
btnLogin.setOnClickListener(v -> performLogin());
|
|
||||||
}
|
|
||||||
|
|
||||||
private void performLogin() {
|
|
||||||
// فراخوانی API لاگین
|
|
||||||
// فرض کنید response شامل workshopId است
|
|
||||||
|
|
||||||
// مثال ساده (باید از Retrofit یا کتابخانه مشابه استفاده کنید):
|
|
||||||
// LoginResponse response = apiService.login(username, password);
|
|
||||||
// long workshopId = response.getWorkshopId();
|
|
||||||
|
|
||||||
long workshopId = 123; // این را از response دریافت کنید
|
|
||||||
|
|
||||||
// ذخیره workshopId
|
|
||||||
SharedPreferences prefs = getSharedPreferences("AppPrefs", MODE_PRIVATE);
|
|
||||||
prefs.edit().putLong("workshopId", workshopId).apply();
|
|
||||||
|
|
||||||
// رفتن به صفحه اصلی
|
|
||||||
Intent intent = new Intent(this, MainActivity.class);
|
|
||||||
startActivity(intent);
|
|
||||||
finish();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public class MainActivity extends AppCompatActivity {
|
|
||||||
private FaceEmbeddingSignalRClient signalRClient;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onCreate(Bundle savedInstanceState) {
|
|
||||||
super.onCreate(savedInstanceState);
|
|
||||||
setContentView(R.layout.activity_main);
|
|
||||||
|
|
||||||
// دریافت workshopId از SharedPreferences
|
|
||||||
SharedPreferences prefs = getSharedPreferences("AppPrefs", MODE_PRIVATE);
|
|
||||||
long workshopId = prefs.getLong("workshopId", 0);
|
|
||||||
|
|
||||||
if (workshopId == 0) {
|
|
||||||
// اگر workshopId وجود نداره، برگرد به صفحه لاگین
|
|
||||||
Intent intent = new Intent(this, LoginActivity.class);
|
|
||||||
startActivity(intent);
|
|
||||||
finish();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// ایجاد و اتصال SignalR
|
|
||||||
signalRClient = new FaceEmbeddingSignalRClient(workshopId) {
|
|
||||||
@Override
|
|
||||||
protected void onEmbeddingCreated(long employeeId, String employeeFullName, String timestamp) {
|
|
||||||
runOnUiThread(() -> {
|
|
||||||
// بروزرسانی UI
|
|
||||||
Toast.makeText(MainActivity.this,
|
|
||||||
"Embedding ایجاد شد برای: " + employeeFullName,
|
|
||||||
Toast.LENGTH_SHORT).show();
|
|
||||||
|
|
||||||
// دریافت دادههای جدید از API
|
|
||||||
refreshEmployeeList();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onEmbeddingDeleted(long employeeId, String timestamp) {
|
|
||||||
runOnUiThread(() -> {
|
|
||||||
// بروزرسانی UI
|
|
||||||
refreshEmployeeList();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onEmbeddingRefined(long employeeId, String timestamp) {
|
|
||||||
runOnUiThread(() -> {
|
|
||||||
// بروزرسانی UI
|
|
||||||
refreshEmployeeList();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
signalRClient.connect();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onDestroy() {
|
|
||||||
super.onDestroy();
|
|
||||||
if (signalRClient != null) {
|
|
||||||
signalRClient.disconnect();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void refreshEmployeeList() {
|
|
||||||
// دریافت لیست جدید کارمندان از API
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### Kotlin:
|
|
||||||
```kotlin
|
|
||||||
class LoginActivity : AppCompatActivity() {
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
setContentView(R.layout.activity_login)
|
|
||||||
|
|
||||||
val btnLogin = findViewById<Button>(R.id.btnLogin)
|
|
||||||
btnLogin.setOnClickListener { performLogin() }
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun performLogin() {
|
|
||||||
// فراخوانی API لاگین
|
|
||||||
// فرض کنید response شامل workshopId است
|
|
||||||
|
|
||||||
// مثال ساده (باید از Retrofit یا کتابخانه مشابه استفاده کنید):
|
|
||||||
// val response = apiService.login(username, password)
|
|
||||||
// val workshopId = response.workshopId
|
|
||||||
|
|
||||||
val workshopId = 123L // این را از response دریافت کنید
|
|
||||||
|
|
||||||
// ذخیره workshopId
|
|
||||||
val prefs = getSharedPreferences("AppPrefs", Context.MODE_PRIVATE)
|
|
||||||
prefs.edit().putLong("workshopId", workshopId).apply()
|
|
||||||
|
|
||||||
// رفتن به صفحه اصلی
|
|
||||||
val intent = Intent(this, MainActivity::class.java)
|
|
||||||
startActivity(intent)
|
|
||||||
finish()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class MainActivity : AppCompatActivity() {
|
|
||||||
private lateinit var signalRClient: FaceEmbeddingSignalRClient
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
setContentView(R.layout.activity_main)
|
|
||||||
|
|
||||||
// دریافت workshopId از SharedPreferences
|
|
||||||
val prefs = getSharedPreferences("AppPrefs", Context.MODE_PRIVATE)
|
|
||||||
val workshopId = prefs.getLong("workshopId", 0L)
|
|
||||||
|
|
||||||
if (workshopId == 0L) {
|
|
||||||
// اگر workshopId وجود نداره، برگرد به صفحه لاگین
|
|
||||||
val intent = Intent(this, LoginActivity::class.java)
|
|
||||||
startActivity(intent)
|
|
||||||
finish()
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
// ایجاد و اتصال SignalR
|
|
||||||
signalRClient = object : FaceEmbeddingSignalRClient(workshopId) {
|
|
||||||
override fun onEmbeddingCreated(employeeId: Long, employeeFullName: String, timestamp: String) {
|
|
||||||
runOnUiThread {
|
|
||||||
// بروزرسانی UI
|
|
||||||
Toast.makeText(this@MainActivity,
|
|
||||||
"Embedding ایجاد شد برای: $employeeFullName",
|
|
||||||
Toast.LENGTH_SHORT).show()
|
|
||||||
|
|
||||||
// دریافت دادههای جدید از API
|
|
||||||
refreshEmployeeList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onEmbeddingDeleted(employeeId: Long, timestamp: String) {
|
|
||||||
runOnUiThread {
|
|
||||||
// بروزرسانی UI
|
|
||||||
refreshEmployeeList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onEmbeddingRefined(employeeId: Long, timestamp: String) {
|
|
||||||
runOnUiThread {
|
|
||||||
// بروزرسانی UI
|
|
||||||
refreshEmployeeList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
signalRClient.connect()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onDestroy() {
|
|
||||||
super.onDestroy()
|
|
||||||
signalRClient.disconnect()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun refreshEmployeeList() {
|
|
||||||
// دریافت لیست جدید کارمندان از API
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
### مثال ساده بدون Login:
|
|
||||||
اگر workshopId را از قبل میدانید:
|
|
||||||
|
|
||||||
#### Java:
|
|
||||||
```java
|
|
||||||
public class MainActivity extends AppCompatActivity {
|
|
||||||
private FaceEmbeddingSignalRClient signalRClient;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onCreate(Bundle savedInstanceState) {
|
|
||||||
super.onCreate(savedInstanceState);
|
|
||||||
setContentView(R.layout.activity_main);
|
|
||||||
|
|
||||||
long workshopId = 123; // شناسه کارگاه خود را وارد کنید
|
|
||||||
|
|
||||||
signalRClient = new FaceEmbeddingSignalRClient(workshopId) {
|
|
||||||
@Override
|
|
||||||
protected void onEmbeddingCreated(long employeeId, String employeeFullName, String timestamp) {
|
|
||||||
runOnUiThread(() -> {
|
|
||||||
// بروزرسانی UI
|
|
||||||
Toast.makeText(MainActivity.this,
|
|
||||||
"Embedding ایجاد شد برای: " + employeeFullName,
|
|
||||||
Toast.LENGTH_SHORT).show();
|
|
||||||
|
|
||||||
// دریافت دادههای جدید از API
|
|
||||||
refreshEmployeeList();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onEmbeddingDeleted(long employeeId, String timestamp) {
|
|
||||||
runOnUiThread(() -> {
|
|
||||||
// بروزرسانی UI
|
|
||||||
refreshEmployeeList();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
signalRClient.connect();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onDestroy() {
|
|
||||||
super.onDestroy();
|
|
||||||
if (signalRClient != null) {
|
|
||||||
signalRClient.disconnect();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void refreshEmployeeList() {
|
|
||||||
// دریافت لیست جدید کارمندان از API
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### Kotlin:
|
|
||||||
```kotlin
|
|
||||||
class MainActivity : AppCompatActivity() {
|
|
||||||
private lateinit var signalRClient: FaceEmbeddingSignalRClient
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
setContentView(R.layout.activity_main)
|
|
||||||
|
|
||||||
val workshopId = 123L // شناسه کارگاه خود را وارد کنید
|
|
||||||
|
|
||||||
signalRClient = object : FaceEmbeddingSignalRClient(workshopId) {
|
|
||||||
override fun onEmbeddingCreated(employeeId: Long, employeeFullName: String, timestamp: String) {
|
|
||||||
runOnUiThread {
|
|
||||||
// بروزرسانی UI
|
|
||||||
Toast.makeText(this@MainActivity,
|
|
||||||
"Embedding ایجاد شد برای: $employeeFullName",
|
|
||||||
Toast.LENGTH_SHORT).show()
|
|
||||||
|
|
||||||
// دریافت دادههای جدید از API
|
|
||||||
refreshEmployeeList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onEmbeddingDeleted(employeeId: Long, timestamp: String) {
|
|
||||||
runOnUiThread {
|
|
||||||
// بروزرسانی UI
|
|
||||||
refreshEmployeeList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
signalRClient.connect()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onDestroy() {
|
|
||||||
super.onDestroy()
|
|
||||||
signalRClient.disconnect()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun refreshEmployeeList() {
|
|
||||||
// دریافت لیست جدید کارمندان از API
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
## 5. نکات مهم
|
|
||||||
|
|
||||||
### آدرس سرور
|
|
||||||
- اگر روی شبیهساز اندروید تست میکنید و سرور روی localhost اجرا میشود، از آدرس `http://10.0.2.2:PORT` استفاده کنید
|
|
||||||
- اگر روی دستگاه فیزیکی تست میکنید، از آدرس IP شبکه محلی سرور استفاده کنید (مثل `http://192.168.1.100:PORT`)
|
|
||||||
- PORT پیشفرض معمولاً 5000 یا 5001 است (بسته به کانفیگ پروژه شما)
|
|
||||||
|
|
||||||
### دریافت WorkshopId از Login
|
|
||||||
بعد از login موفق، workshopId را از سرور دریافت کنید و در SharedPreferences یا یک Singleton ذخیره کنید:
|
|
||||||
|
|
||||||
```java
|
|
||||||
// بعد از login موفق
|
|
||||||
SharedPreferences prefs = getSharedPreferences("AppPrefs", MODE_PRIVATE);
|
|
||||||
prefs.edit().putLong("workshopId", workshopId).apply();
|
|
||||||
|
|
||||||
// استفاده در Activity
|
|
||||||
long workshopId = prefs.getLong("workshopId", 0);
|
|
||||||
```
|
|
||||||
|
|
||||||
یا در Kotlin:
|
|
||||||
|
|
||||||
```kotlin
|
|
||||||
// بعد از login موفق
|
|
||||||
val prefs = getSharedPreferences("AppPrefs", Context.MODE_PRIVATE)
|
|
||||||
prefs.edit().putLong("workshopId", workshopId).apply()
|
|
||||||
|
|
||||||
// استفاده در Activity
|
|
||||||
val workshopId = prefs.getLong("workshopId", 0L)
|
|
||||||
```
|
|
||||||
|
|
||||||
### مدیریت اتصال
|
|
||||||
برای reconnection خودکار:
|
|
||||||
|
|
||||||
```java
|
|
||||||
hubConnection.onClosed(exception -> {
|
|
||||||
Log.e(TAG, "Connection closed. Attempting to reconnect...");
|
|
||||||
new Handler().postDelayed(() -> connect(), 5000); // تلاش مجدد بعد از 5 ثانیه
|
|
||||||
});
|
|
||||||
```
|
|
||||||
|
|
||||||
### Thread Safety
|
|
||||||
همیشه UI updates را در main thread انجام دهید:
|
|
||||||
|
|
||||||
```java
|
|
||||||
runOnUiThread(() -> {
|
|
||||||
// UI updates here
|
|
||||||
});
|
|
||||||
```
|
|
||||||
|
|
||||||
## 6. تست اتصال
|
|
||||||
|
|
||||||
برای تست میتوانید:
|
|
||||||
1. اپلیکیشن را اجرا کنید
|
|
||||||
2. از طریق Postman یا Swagger یک Embedding ایجاد کنید
|
|
||||||
3. باید در Logcat پیام "Embedding Created" را ببینید
|
|
||||||
|
|
||||||
## 7. خطایابی (Debugging)
|
|
||||||
|
|
||||||
برای دیدن جزئیات بیشتر:
|
|
||||||
|
|
||||||
```java
|
|
||||||
hubConnection = HubConnectionBuilder
|
|
||||||
.create(serverUrl)
|
|
||||||
.withHttpConnectionOptions(options -> {
|
|
||||||
options.setLogging(LogLevel.TRACE);
|
|
||||||
})
|
|
||||||
.build();
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## خلاصه Endpoints
|
|
||||||
|
|
||||||
| نوع رویداد | متد SignalR | پارامترهای دریافتی |
|
|
||||||
|-----------|-------------|---------------------|
|
|
||||||
| ایجاد Embedding | `EmbeddingCreated` | workshopId, employeeId, employeeFullName, timestamp |
|
|
||||||
| حذف Embedding | `EmbeddingDeleted` | workshopId, employeeId, timestamp |
|
|
||||||
| بهبود Embedding | `EmbeddingRefined` | workshopId, employeeId, timestamp |
|
|
||||||
|
|
||||||
| متد ارسالی | پارامتر | توضیحات |
|
|
||||||
|-----------|---------|---------|
|
|
||||||
| `JoinWorkshopGroup` | workshopId | عضویت در گروه کارگاه |
|
|
||||||
| `LeaveWorkshopGroup` | workshopId | خروج از گروه کارگاه |
|
|
||||||
|
|
||||||
@@ -4,7 +4,6 @@ using System.Collections.Generic;
|
|||||||
using System.ComponentModel.DataAnnotations;
|
using System.ComponentModel.DataAnnotations;
|
||||||
using AccountManagement.Application.Contracts.Role;
|
using AccountManagement.Application.Contracts.Role;
|
||||||
using Microsoft.AspNetCore.Http;
|
using Microsoft.AspNetCore.Http;
|
||||||
using Microsoft.AspNetCore.Mvc.Rendering;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.Account;
|
namespace AccountManagement.Application.Contracts.Account;
|
||||||
|
|
||||||
@@ -36,20 +35,4 @@ public class CreateAccount
|
|||||||
public string Email { get; set; }
|
public string Email { get; set; }
|
||||||
public string VerifyCode { get; set; }
|
public string VerifyCode { get; set; }
|
||||||
public string IsActiveString { get; set; }
|
public string IsActiveString { get; set; }
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// آیا کاربر در پروگرام منیجر فعالیت مبکند؟
|
|
||||||
/// </summary>
|
|
||||||
public bool IsProgramManagerUser { get; set; }
|
|
||||||
/// <summary>
|
|
||||||
/// لیست نقش های پروگرام منیجر
|
|
||||||
/// </summary>
|
|
||||||
public List<long> UserRoles { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// لیست نقشهای موجود در پروگرام منیجر
|
|
||||||
/// </summary>
|
|
||||||
public SelectList RoleList { get; set; }
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -3,5 +3,4 @@
|
|||||||
public class EditAccount : CreateAccount
|
public class EditAccount : CreateAccount
|
||||||
{
|
{
|
||||||
public long Id { get; set; }
|
public long Id { get; set; }
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -1,4 +1,10 @@
|
|||||||
namespace AccountManagement.Application.Contracts.Account;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace AccountManagement.Application.Contracts.Account;
|
||||||
|
|
||||||
public class EditClientAccount : RegisterAccount
|
public class EditClientAccount : RegisterAccount
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -2,21 +2,15 @@
|
|||||||
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using Shared.Contracts.PmUser.Queries;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.Account;
|
namespace AccountManagement.Application.Contracts.Account;
|
||||||
|
|
||||||
public interface IAccountApplication
|
public interface IAccountApplication
|
||||||
{
|
{
|
||||||
AccountViewModel GetAccountBy(long id);
|
AccountViewModel GetAccountBy(long id);
|
||||||
/// <summary>
|
OperationResult Create(CreateAccount command);
|
||||||
/// ایجاد کاربر گزارشگیر و پروگرام منیجر
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="command"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<OperationResult> Create(CreateAccount command);
|
|
||||||
OperationResult RegisterClient(RegisterAccount command);
|
OperationResult RegisterClient(RegisterAccount command);
|
||||||
Task<OperationResult> Edit(EditAccount command);
|
OperationResult Edit(EditAccount command);
|
||||||
OperationResult EditClient(EditClientAccount command);
|
OperationResult EditClient(EditClientAccount command);
|
||||||
OperationResult ChangePassword(ChangePassword command);
|
OperationResult ChangePassword(ChangePassword command);
|
||||||
OperationResult Login(Login command);
|
OperationResult Login(Login command);
|
||||||
@@ -34,7 +28,7 @@ public interface IAccountApplication
|
|||||||
OperationResult DeActive(long id);
|
OperationResult DeActive(long id);
|
||||||
OperationResult DirectLogin(long id);
|
OperationResult DirectLogin(long id);
|
||||||
|
|
||||||
// AccountLeftWorkViewModel WorkshopList(long accountId);
|
AccountLeftWorkViewModel WorkshopList(long accountId);
|
||||||
OperationResult SaveWorkshopAccount(
|
OperationResult SaveWorkshopAccount(
|
||||||
List<WorkshopAccountlistViewModel> workshopAccountList,
|
List<WorkshopAccountlistViewModel> workshopAccountList,
|
||||||
string startDate,
|
string startDate,
|
||||||
@@ -72,13 +66,4 @@ public interface IAccountApplication
|
|||||||
public bool CheckExistClientAccount(string userName);
|
public bool CheckExistClientAccount(string userName);
|
||||||
List<AccountViewModel> GetAdminAccountsNew();
|
List<AccountViewModel> GetAdminAccountsNew();
|
||||||
|
|
||||||
void CameraLogin(CameraLoginRequest request);
|
|
||||||
|
|
||||||
Task<GetPmUserDto> GetPmUserAsync(long accountId);
|
|
||||||
}
|
|
||||||
|
|
||||||
public class CameraLoginRequest
|
|
||||||
{
|
|
||||||
public string UserName { get; set; }
|
|
||||||
public string Password { get; set; }
|
|
||||||
}
|
}
|
||||||
@@ -1,4 +1,10 @@
|
|||||||
using System.ComponentModel.DataAnnotations;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using _0_Framework.Application;
|
||||||
using Microsoft.AspNetCore.Http;
|
using Microsoft.AspNetCore.Http;
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.Account;
|
namespace AccountManagement.Application.Contracts.Account;
|
||||||
|
|||||||
@@ -1,4 +1,10 @@
|
|||||||
namespace AccountManagement.Application.Contracts.Account;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace AccountManagement.Application.Contracts.Account;
|
||||||
|
|
||||||
public class WorkshopSelectList
|
public class WorkshopSelectList
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,20 +1,15 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http" Version="2.3.0" />
|
<PackageReference Include="Microsoft.AspNetCore.Mvc.ViewFeatures" Version="2.2.0" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.3.0" />
|
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Mvc.ViewFeatures" Version="2.3.0" />
|
|
||||||
<PackageReference Include="Microsoft.Extensions.Caching.Memory" Version="10.0.1" />
|
|
||||||
<PackageReference Include="System.Security.Cryptography.Xml" Version="10.0.1" />
|
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ProjectReference Include="..\0_Framework\0_Framework.csproj" />
|
<ProjectReference Include="..\0_Framework\0_Framework.csproj" />
|
||||||
<ProjectReference Include="..\Shared.Contracts\Shared.Contracts.csproj" />
|
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
|||||||
@@ -1,11 +0,0 @@
|
|||||||
namespace AccountManagement.Application.Contracts.ProgramManagerApiResult;
|
|
||||||
|
|
||||||
public record ApiResponse
|
|
||||||
{
|
|
||||||
public bool isSuccess { get; set; }
|
|
||||||
public string errorMessage { get; set; }
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public ErrorType ErrorType { get; set; }
|
|
||||||
}
|
|
||||||
@@ -1,22 +0,0 @@
|
|||||||
using System.Collections.Generic;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.ProgramManagerApiResult;
|
|
||||||
|
|
||||||
|
|
||||||
public record CreateProgramManagerRole
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// نام نقش
|
|
||||||
/// </summary>
|
|
||||||
public string RoleName { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// کدهای دسترسی
|
|
||||||
/// </summary>
|
|
||||||
public List<int> Permissions { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// آی دی اکانت گزارشگیر
|
|
||||||
/// </summary>
|
|
||||||
public long? GozareshgirRoleId { get; set; }
|
|
||||||
};
|
|
||||||
@@ -1,7 +0,0 @@
|
|||||||
using System.Collections.Generic;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.ProgramManagerApiResult;
|
|
||||||
|
|
||||||
public record CreateProgramManagerUser(string FullName, string UserName, string Password, string Mobile, string Email, long? AccountId, List<long> Roles);
|
|
||||||
|
|
||||||
public record EditUserCommand(string FullName, string UserName, string Mobile, long AccountId, List<long> Roles, bool IsActive);
|
|
||||||
@@ -1,11 +0,0 @@
|
|||||||
namespace AccountManagement.Application.Contracts.ProgramManagerApiResult;
|
|
||||||
|
|
||||||
public enum ErrorType
|
|
||||||
{
|
|
||||||
None,
|
|
||||||
BadRequest,
|
|
||||||
NotFound,
|
|
||||||
Unauthorized,
|
|
||||||
Validation,
|
|
||||||
InternalServerError
|
|
||||||
}
|
|
||||||
@@ -1,22 +0,0 @@
|
|||||||
using System.Collections.Generic;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.ProgramManagerApiResult;
|
|
||||||
|
|
||||||
public class RoleResponse
|
|
||||||
{
|
|
||||||
public bool isSuccess { get; set; }
|
|
||||||
public RolesData data { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class RolesData
|
|
||||||
{
|
|
||||||
public List<RoleList> role { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class RoleList
|
|
||||||
{
|
|
||||||
public int id { get; set; }
|
|
||||||
public string roleName { get; set; }
|
|
||||||
public int gozareshgirRoleId { get; set; }
|
|
||||||
public List<int> permissions { get; set; }
|
|
||||||
}
|
|
||||||
@@ -1,55 +0,0 @@
|
|||||||
using System.Collections.Generic;
|
|
||||||
using static System.Runtime.InteropServices.JavaScript.JSType;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.ProgramManagerApiResult;
|
|
||||||
|
|
||||||
public record SingleUserResponseResult
|
|
||||||
{
|
|
||||||
public bool isSuccess { get; set; }
|
|
||||||
public SingleUserData Data { get; set; }
|
|
||||||
};
|
|
||||||
|
|
||||||
public record SingleUserData
|
|
||||||
|
|
||||||
{
|
|
||||||
public long id { get; set; }
|
|
||||||
/// <summary>
|
|
||||||
/// نام و نام خانوادگی
|
|
||||||
/// </summary>
|
|
||||||
public string fullName { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// نام کاربری
|
|
||||||
/// </summary>
|
|
||||||
public string userName { get; set; }
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// مسیر عکس پروفایل
|
|
||||||
/// </summary>
|
|
||||||
public string profilePhotoPath { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// شماره موبایل
|
|
||||||
/// </summary>
|
|
||||||
public string mobile { get; set; }
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// فعال/غیر فعال بودن یوزر
|
|
||||||
/// </summary>
|
|
||||||
public bool isActive { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// گذرواژه
|
|
||||||
/// </summary>
|
|
||||||
public string password { get; set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ای دی اکانت کاربر در گزارشگیر
|
|
||||||
/// </summary>
|
|
||||||
public long? accountId { get; set; }
|
|
||||||
|
|
||||||
public List<long> Roles { get; set; }
|
|
||||||
}
|
|
||||||
@@ -9,10 +9,6 @@ namespace AccountManagement.Application.Contracts.Role
|
|||||||
[Required(ErrorMessage = ValidationMessages.IsRequired)]
|
[Required(ErrorMessage = ValidationMessages.IsRequired)]
|
||||||
public string Name { get; set; }
|
public string Name { get; set; }
|
||||||
public List<int> Permissions { get; set; }
|
public List<int> Permissions { get; set; }
|
||||||
/// <summary>
|
|
||||||
/// لیست پرمیشن های پروگرام منیجر
|
|
||||||
/// </summary>
|
|
||||||
public List<int> PmPermissions { get; set; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,26 +1,13 @@
|
|||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
|
|
||||||
using Microsoft.AspNetCore.Mvc.Rendering;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Threading.Tasks;
|
|
||||||
using Shared.Contracts.PmRole.Queries;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application.Contracts.Role
|
namespace AccountManagement.Application.Contracts.Role
|
||||||
{
|
{
|
||||||
public interface IRoleApplication
|
public interface IRoleApplication
|
||||||
{
|
{
|
||||||
Task<OperationResult> Create(CreateRole command);
|
OperationResult Create(CreateRole command);
|
||||||
Task<OperationResult> Edit(EditRole command);
|
OperationResult Edit(EditRole command);
|
||||||
List<RoleViewModel> List();
|
List<RoleViewModel> List();
|
||||||
EditRole GetDetails(long id);
|
EditRole GetDetails(long id);
|
||||||
|
|
||||||
#region ProgramManager
|
|
||||||
|
|
||||||
Task<SelectList> GetPmRoleList(long? gozareshgirRoleId);
|
|
||||||
Task<List<GetPmRolesDto>> GetPmRoleListToEdit(long? gozareshgirRoleId);
|
|
||||||
|
|
||||||
|
|
||||||
#endregion
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,25 +1,28 @@
|
|||||||
using _0_Framework.Application;
|
using System;
|
||||||
using _0_Framework.Application.Sms;
|
using System.Collections;
|
||||||
using _0_Framework.Exceptions;
|
using _0_Framework.Application;
|
||||||
using AccountManagement.Application.Contracts.Account;
|
using AccountManagement.Application.Contracts.Account;
|
||||||
using AccountManagement.Domain.AccountAgg;
|
using AccountManagement.Domain.AccountAgg;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Runtime.InteropServices;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using _0_Framework.Application.Sms;
|
||||||
using AccountManagement.Domain.AccountLeftWorkAgg;
|
using AccountManagement.Domain.AccountLeftWorkAgg;
|
||||||
using AccountManagement.Domain.CameraAccountAgg;
|
using AccountManagement.Domain.CameraAccountAgg;
|
||||||
using AccountManagement.Domain.PositionAgg;
|
|
||||||
using AccountManagement.Domain.RoleAgg;
|
using AccountManagement.Domain.RoleAgg;
|
||||||
|
using CompanyManagment.App.Contracts.Workshop;
|
||||||
|
using Microsoft.AspNetCore.Http;
|
||||||
|
using Microsoft.AspNetCore.Mvc.Rendering;
|
||||||
|
using static Microsoft.EntityFrameworkCore.DbLoggerCategory.Database;
|
||||||
|
using Company.Domain.WorkshopAgg;
|
||||||
|
using System.Security.Claims;
|
||||||
|
using AccountManagement.Domain.PositionAgg;
|
||||||
using AccountManagement.Domain.SubAccountAgg;
|
using AccountManagement.Domain.SubAccountAgg;
|
||||||
using AccountManagement.Domain.SubAccountPermissionSubtitle1Agg;
|
using AccountManagement.Domain.SubAccountPermissionSubtitle1Agg;
|
||||||
using AccountManagement.Domain.SubAccountRoleAgg;
|
using AccountManagement.Domain.SubAccountRoleAgg;
|
||||||
using Company.Domain._common;
|
|
||||||
using Company.Domain.WorkshopAgg;
|
|
||||||
using Company.Domain.WorkshopSubAccountAgg;
|
using Company.Domain.WorkshopSubAccountAgg;
|
||||||
using Microsoft.AspNetCore.Mvc.Rendering;
|
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using Shared.Contracts.PmUser.Commands;
|
|
||||||
using Shared.Contracts.PmUser.Queries;
|
|
||||||
|
|
||||||
//using AccountManagement.Domain.RoleAgg;
|
//using AccountManagement.Domain.RoleAgg;
|
||||||
|
|
||||||
@@ -35,25 +38,15 @@ public class AccountApplication : IAccountApplication
|
|||||||
private readonly ISmsService _smsService;
|
private readonly ISmsService _smsService;
|
||||||
private readonly ICameraAccountRepository _cameraAccountRepository;
|
private readonly ICameraAccountRepository _cameraAccountRepository;
|
||||||
private readonly IPositionRepository _positionRepository;
|
private readonly IPositionRepository _positionRepository;
|
||||||
private readonly IAccountLeftworkRepository _accountLeftworkRepository;
|
private readonly IAccountLeftworkRepository _accountLeftworkRepository;
|
||||||
private readonly IWorkshopRepository _workshopRepository;
|
private readonly IWorkshopRepository _workshopRepository;
|
||||||
private readonly ISubAccountRepository _subAccountRepository;
|
private readonly ISubAccountRepository _subAccountRepository;
|
||||||
private readonly ISubAccountRoleRepository _subAccountRoleRepository;
|
private readonly ISubAccountRoleRepository _subAccountRoleRepository;
|
||||||
private readonly IWorkshopSubAccountRepository _workshopSubAccountRepository;
|
private readonly IWorkshopSubAccountRepository _workshopSubAccountRepository;
|
||||||
private readonly ISubAccountPermissionSubtitle1Repository _accountPermissionSubtitle1Repository;
|
private readonly ISubAccountPermissionSubtitle1Repository _accountPermissionSubtitle1Repository;
|
||||||
|
|
||||||
private readonly IUnitOfWork _unitOfWork;
|
public AccountApplication(IAccountRepository accountRepository, IPasswordHasher passwordHasher,
|
||||||
private readonly IPmUserQueryService _pmUserQueryService;
|
IFileUploader fileUploader, IAuthHelper authHelper, IRoleRepository roleRepository, IWorker worker, ISmsService smsService, ICameraAccountRepository cameraAccountRepository, IPositionRepository positionRepository, IAccountLeftworkRepository accountLeftworkRepository, IWorkshopRepository workshopRepository, ISubAccountRepository subAccountRepository, ISubAccountRoleRepository subAccountRoleRepository, IWorkshopSubAccountRepository workshopSubAccountRepository, ISubAccountPermissionSubtitle1Repository accountPermissionSubtitle1Repository)
|
||||||
private readonly IPmUserCommandService _pmUserCommandService;
|
|
||||||
|
|
||||||
public AccountApplication(IAccountRepository accountRepository, IPasswordHasher passwordHasher,
|
|
||||||
IFileUploader fileUploader, IAuthHelper authHelper, IRoleRepository roleRepository, IWorker worker,
|
|
||||||
ISmsService smsService, ICameraAccountRepository cameraAccountRepository,
|
|
||||||
IPositionRepository positionRepository, IAccountLeftworkRepository accountLeftworkRepository,
|
|
||||||
IWorkshopRepository workshopRepository, ISubAccountRepository subAccountRepository,
|
|
||||||
ISubAccountRoleRepository subAccountRoleRepository, IWorkshopSubAccountRepository workshopSubAccountRepository,
|
|
||||||
ISubAccountPermissionSubtitle1Repository accountPermissionSubtitle1Repository, IUnitOfWork unitOfWork,
|
|
||||||
IPmUserQueryService pmUserQueryService, IPmUserCommandService pmUserCommandService)
|
|
||||||
{
|
{
|
||||||
_authHelper = authHelper;
|
_authHelper = authHelper;
|
||||||
_roleRepository = roleRepository;
|
_roleRepository = roleRepository;
|
||||||
@@ -66,13 +59,10 @@ public class AccountApplication : IAccountApplication
|
|||||||
_subAccountRoleRepository = subAccountRoleRepository;
|
_subAccountRoleRepository = subAccountRoleRepository;
|
||||||
_workshopSubAccountRepository = workshopSubAccountRepository;
|
_workshopSubAccountRepository = workshopSubAccountRepository;
|
||||||
_accountPermissionSubtitle1Repository = accountPermissionSubtitle1Repository;
|
_accountPermissionSubtitle1Repository = accountPermissionSubtitle1Repository;
|
||||||
_unitOfWork = unitOfWork;
|
|
||||||
|
|
||||||
_pmUserQueryService = pmUserQueryService;
|
|
||||||
_pmUserCommandService = pmUserCommandService;
|
|
||||||
_fileUploader = fileUploader;
|
_fileUploader = fileUploader;
|
||||||
_passwordHasher = passwordHasher;
|
_passwordHasher = passwordHasher;
|
||||||
_accountRepository = accountRepository;
|
_accountRepository = accountRepository;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public OperationResult EditClient(EditClientAccount command)
|
public OperationResult EditClient(EditClientAccount command)
|
||||||
@@ -93,8 +83,7 @@ public class AccountApplication : IAccountApplication
|
|||||||
(x.Mobile == command.Mobile && x.id != command.Id)))
|
(x.Mobile == command.Mobile && x.id != command.Id)))
|
||||||
return opreation.Failed("شماره موبایل تکراری است");
|
return opreation.Failed("شماره موبایل تکراری است");
|
||||||
if (_accountRepository.Exists(x =>
|
if (_accountRepository.Exists(x =>
|
||||||
(x.NationalCode == command.NationalCode && !string.IsNullOrWhiteSpace(x.NationalCode) &&
|
(x.NationalCode == command.NationalCode && !string.IsNullOrWhiteSpace(x.NationalCode) && x.id != command.Id)))
|
||||||
x.id != command.Id)))
|
|
||||||
return opreation.Failed("کد ملی تکراری است");
|
return opreation.Failed("کد ملی تکراری است");
|
||||||
if (_accountRepository.Exists(x =>
|
if (_accountRepository.Exists(x =>
|
||||||
(x.Email == command.Email && !string.IsNullOrWhiteSpace(x.Email) && x.id != command.Id)))
|
(x.Email == command.Email && !string.IsNullOrWhiteSpace(x.Email) && x.id != command.Id)))
|
||||||
@@ -102,8 +91,7 @@ public class AccountApplication : IAccountApplication
|
|||||||
|
|
||||||
var path = $"profilePhotos";
|
var path = $"profilePhotos";
|
||||||
var picturePath = _fileUploader.Upload(command.ProfilePhoto, path);
|
var picturePath = _fileUploader.Upload(command.ProfilePhoto, path);
|
||||||
editAccount.EditClient(command.Fullname, command.Username, command.Mobile, picturePath, command.Email,
|
editAccount.EditClient(command.Fullname,command.Username,command.Mobile,picturePath,command.Email,command.NationalCode);
|
||||||
command.NationalCode);
|
|
||||||
_accountRepository.SaveChanges();
|
_accountRepository.SaveChanges();
|
||||||
return opreation.Succcedded();
|
return opreation.Succcedded();
|
||||||
}
|
}
|
||||||
@@ -134,7 +122,7 @@ public class AccountApplication : IAccountApplication
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<OperationResult> Create(CreateAccount command)
|
public OperationResult Create(CreateAccount command)
|
||||||
{
|
{
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
|
|
||||||
@@ -144,59 +132,15 @@ public class AccountApplication : IAccountApplication
|
|||||||
var password = _passwordHasher.Hash(command.Password);
|
var password = _passwordHasher.Hash(command.Password);
|
||||||
var roleName = _roleRepository.GetDetails(command.RoleId);
|
var roleName = _roleRepository.GetDetails(command.RoleId);
|
||||||
var path = $"profilePhotos";
|
var path = $"profilePhotos";
|
||||||
var picturePath = "";
|
|
||||||
if (_fileUploader != null)
|
if (_fileUploader != null)
|
||||||
{
|
{
|
||||||
picturePath = _fileUploader.Upload(command.ProfilePhoto, path);
|
var picturePath = _fileUploader.Upload(command.ProfilePhoto, path);
|
||||||
|
var account = new Account(command.Fullname, command.Username, password, command.Mobile, command.RoleId,
|
||||||
|
picturePath, roleName.Name,"true","false");
|
||||||
|
_accountRepository.Create(account);
|
||||||
}
|
}
|
||||||
|
|
||||||
var account = new Account(command.Fullname, command.Username, password, command.Mobile, command.RoleId,
|
|
||||||
picturePath, roleName.Name, "true", "false");
|
|
||||||
|
|
||||||
_unitOfWork.BeginAccountContext();
|
|
||||||
|
|
||||||
|
|
||||||
_accountRepository.Create(account);
|
|
||||||
_accountRepository.SaveChanges();
|
_accountRepository.SaveChanges();
|
||||||
|
|
||||||
if (command.IsProgramManagerUser)
|
|
||||||
{
|
|
||||||
if (command.UserRoles == null)
|
|
||||||
return operation.Failed("حداقل یک نقش برای کاربر مدیریت پروژه لازم است");
|
|
||||||
var pmUserRoles = command.UserRoles.Where(x => x > 0).ToList();
|
|
||||||
var createPm = await _pmUserCommandService.Create(new CreatePmUserDto(command.Fullname, command.Username,
|
|
||||||
account.Password, command.Mobile,
|
|
||||||
null, account.id, pmUserRoles));
|
|
||||||
if (!createPm.isSuccess)
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("خطا در ویرایش کاربر پروگرام منیجر");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//var url = "api/user/create";
|
|
||||||
//var key = SecretKeys.ProgramManagerInternalApi;
|
|
||||||
|
|
||||||
//var response = InternalApiCaller.PostAsync<CreateProgramManagerUser, ApiResponse>(
|
|
||||||
// url,
|
|
||||||
// key,
|
|
||||||
// parameters
|
|
||||||
//);
|
|
||||||
|
|
||||||
//if (!response.Success)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Error);
|
|
||||||
//}
|
|
||||||
|
|
||||||
//if (!response.Result.isSuccess)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Result.errorMessage);
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
|
|
||||||
_unitOfWork.CommitAccountContext();
|
|
||||||
return operation.Succcedded();
|
return operation.Succcedded();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -210,8 +154,8 @@ public class AccountApplication : IAccountApplication
|
|||||||
return opreation.Failed("پر کردن تمامی فیلدها الزامی است");
|
return opreation.Failed("پر کردن تمامی فیلدها الزامی است");
|
||||||
if (_accountRepository.Exists(x => x.Username == command.Username))
|
if (_accountRepository.Exists(x => x.Username == command.Username))
|
||||||
return opreation.Failed("نام کاربری تکراری است");
|
return opreation.Failed("نام کاربری تکراری است");
|
||||||
if (_accountRepository.Exists(x => x.Mobile == command.Mobile && x.IsActiveString == "true"))
|
if (_accountRepository.Exists(x => x.Mobile == command.Mobile && x.IsActiveString =="true"))
|
||||||
|
|
||||||
return opreation.Failed("مقادیر وارد شده تکراری است");
|
return opreation.Failed("مقادیر وارد شده تکراری است");
|
||||||
|
|
||||||
//var nationalCodeValidation = command.NationalCode.NationalCodeValid();
|
//var nationalCodeValidation = command.NationalCode.NationalCodeValid();
|
||||||
@@ -228,14 +172,14 @@ public class AccountApplication : IAccountApplication
|
|||||||
// break;
|
// break;
|
||||||
//}
|
//}
|
||||||
var password = _passwordHasher.Hash(command.Password);
|
var password = _passwordHasher.Hash(command.Password);
|
||||||
var register = new Account(command.Fullname, command.Username, password, command.Mobile, command.NationalCode);
|
var register =new Account(command.Fullname,command.Username, password, command.Mobile, command.NationalCode);
|
||||||
_accountRepository.Create(register);
|
_accountRepository.Create(register);
|
||||||
_accountRepository.SaveChanges();
|
_accountRepository.SaveChanges();
|
||||||
|
|
||||||
return opreation.Succcedded(register.id, message: "ثبت نام شما با موفقیت انجام شد");
|
return opreation.Succcedded(register.id,message: "ثبت نام شما با موفقیت انجام شد");
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<OperationResult> Edit(EditAccount command)
|
public OperationResult Edit(EditAccount command)
|
||||||
{
|
{
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
var account = _accountRepository.Get(command.Id);
|
var account = _accountRepository.Get(command.Id);
|
||||||
@@ -249,124 +193,8 @@ public class AccountApplication : IAccountApplication
|
|||||||
var roleName = _roleRepository.GetDetails(command.RoleId);
|
var roleName = _roleRepository.GetDetails(command.RoleId);
|
||||||
var path = $"profilePhotos";
|
var path = $"profilePhotos";
|
||||||
var picturePath = _fileUploader.Upload(command.ProfilePhoto, path);
|
var picturePath = _fileUploader.Upload(command.ProfilePhoto, path);
|
||||||
_unitOfWork.BeginAccountContext();
|
|
||||||
account.Edit(command.Fullname, command.Username, command.Mobile, command.RoleId, picturePath, roleName.Name);
|
account.Edit(command.Fullname, command.Username, command.Mobile, command.RoleId, picturePath, roleName.Name);
|
||||||
_accountRepository.SaveChanges();
|
_accountRepository.SaveChanges();
|
||||||
var key = SecretKeys.ProgramManagerInternalApi;
|
|
||||||
|
|
||||||
//var apiResult = InternalApiCaller.GetAsync<SingleUserResponseResult>(
|
|
||||||
// $"api/user/{account.id}",
|
|
||||||
// key
|
|
||||||
//);
|
|
||||||
var userResult = await _pmUserQueryService.GetPmUserDataByAccountId(account.id);
|
|
||||||
|
|
||||||
if (command.UserRoles == null)
|
|
||||||
return operation.Failed("حداقل یک نقش برای کاربر مدیریت پروژه لازم است");
|
|
||||||
var pmUserRoles = command.UserRoles.Where(x => x > 0).ToList();
|
|
||||||
|
|
||||||
//اگر کاربر در پروگرام منیجر قبلا ایجاد شده
|
|
||||||
if (userResult.Id > 0)
|
|
||||||
{
|
|
||||||
if (!command.UserRoles.Any())
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("حداقل یک نقش باید انتخاب شود");
|
|
||||||
}
|
|
||||||
|
|
||||||
var editPm = await _pmUserCommandService.Edit(new EditPmUserDto(command.Fullname, command.Username,
|
|
||||||
command.Mobile, account.id, pmUserRoles,
|
|
||||||
command.IsProgramManagerUser));
|
|
||||||
if (!editPm.isSuccess)
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("خطا در ویرایش کاربر پروگرام منیجر");
|
|
||||||
}
|
|
||||||
|
|
||||||
//var parameters = new EditUserCommand(
|
|
||||||
// command.Fullname,
|
|
||||||
// command.Username,
|
|
||||||
// command.Mobile,
|
|
||||||
// account.id,
|
|
||||||
// command.UserRoles,
|
|
||||||
// command.IsProgramManagerUser
|
|
||||||
//);
|
|
||||||
//var url = "api/user/edit";
|
|
||||||
//var response = InternalApiCaller.PostAsync<EditUserCommand, ApiResponse>(
|
|
||||||
// url,
|
|
||||||
// key,
|
|
||||||
// parameters
|
|
||||||
//);
|
|
||||||
|
|
||||||
//if (!response.Success)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Error);
|
|
||||||
|
|
||||||
//}
|
|
||||||
|
|
||||||
//if (!response.Result.isSuccess)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Error);
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
else //اگر کاربر قبلا ایجاد نشده
|
|
||||||
{
|
|
||||||
//اگر تیک فعالیت در پروگرام منیجر روشن بود
|
|
||||||
if (command.IsProgramManagerUser)
|
|
||||||
{
|
|
||||||
if (!command.UserRoles.Any())
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("حداقل یک نقش باید انتخاب شود");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
var createPm = await _pmUserCommandService.Create(new CreatePmUserDto(command.Fullname,
|
|
||||||
command.Username, account.Password, command.Mobile,
|
|
||||||
null, account.id, pmUserRoles));
|
|
||||||
if (!createPm.isSuccess)
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("خطا در ویرایش کاربر پروگرام منیجر");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//var parameters = new CreateProgramManagerUser(
|
|
||||||
// command.Fullname,
|
|
||||||
// command.Username,
|
|
||||||
// account.Password,
|
|
||||||
// command.Mobile,
|
|
||||||
// command.Email,
|
|
||||||
// account.id,
|
|
||||||
// command.UserRoles
|
|
||||||
//);
|
|
||||||
|
|
||||||
//var url = "api/user/Create";
|
|
||||||
|
|
||||||
|
|
||||||
//var response = InternalApiCaller.PostAsync<CreateProgramManagerUser, ApiResponse>(
|
|
||||||
// url,
|
|
||||||
// key,
|
|
||||||
// parameters
|
|
||||||
//);
|
|
||||||
|
|
||||||
//if (!response.Success)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Error);
|
|
||||||
|
|
||||||
//}
|
|
||||||
|
|
||||||
//if (!response.Result.isSuccess)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Error);
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_unitOfWork.CommitAccountContext();
|
|
||||||
return operation.Succcedded();
|
return operation.Succcedded();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -377,21 +205,22 @@ public class AccountApplication : IAccountApplication
|
|||||||
|
|
||||||
public OperationResult Login(Login command)
|
public OperationResult Login(Login command)
|
||||||
{
|
{
|
||||||
|
|
||||||
long idAutoriz = 0;
|
long idAutoriz = 0;
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
if (string.IsNullOrWhiteSpace(command.Password))
|
if (string.IsNullOrWhiteSpace(command.Password))
|
||||||
return operation.Failed(ApplicationMessages.EmptyPassword);
|
return operation.Failed(ApplicationMessages.EmptyPassword);
|
||||||
|
|
||||||
if (string.IsNullOrWhiteSpace(command.Username))
|
if (string.IsNullOrWhiteSpace(command.Username))
|
||||||
return operation.Failed(ApplicationMessages.EmptyUsername);
|
return operation.Failed(ApplicationMessages.EmptyUsername);
|
||||||
|
|
||||||
var account = _accountRepository.GetBy(command.Username);
|
var account = _accountRepository.GetBy(command.Username);
|
||||||
var cameraAccount = _cameraAccountRepository.GetBy(command.Username);
|
var cameraAccount = _cameraAccountRepository.GetBy(command.Username);
|
||||||
SubAccount subAccount = _subAccountRepository.GetBy(command.Username);
|
SubAccount subAccount = _subAccountRepository.GetBy(command.Username);
|
||||||
if (account == null && cameraAccount == null && subAccount == null)
|
if (account == null && cameraAccount == null && subAccount == null)
|
||||||
return operation.Failed(ApplicationMessages.WrongUserPass);
|
return operation.Failed(ApplicationMessages.WrongUserPass);
|
||||||
|
|
||||||
if (account != null)
|
if (account != null)
|
||||||
{
|
{
|
||||||
(bool Verified, bool NeedUpgrade) result = _passwordHasher.Check(account.Password, command.Password);
|
(bool Verified, bool NeedUpgrade) result = _passwordHasher.Check(account.Password, command.Password);
|
||||||
if (!result.Verified)
|
if (!result.Verified)
|
||||||
@@ -400,29 +229,6 @@ public class AccountApplication : IAccountApplication
|
|||||||
.Permissions
|
.Permissions
|
||||||
.Select(x => x.Code)
|
.Select(x => x.Code)
|
||||||
.ToList();
|
.ToList();
|
||||||
//PmPermission
|
|
||||||
var PmUserData = _pmUserQueryService.GetPmUserDataByAccountId(account.id)
|
|
||||||
.GetAwaiter().GetResult();
|
|
||||||
long? pmUserId = null;
|
|
||||||
if (PmUserData != null)
|
|
||||||
{
|
|
||||||
if (PmUserData.AccountId > 0 && PmUserData.IsActive)
|
|
||||||
{
|
|
||||||
var pmUserPermissions =
|
|
||||||
PmUserData.RoleListDto != null
|
|
||||||
? PmUserData.RoleListDto
|
|
||||||
.SelectMany(x => x.Permissions)
|
|
||||||
.Where(p => p != 99)
|
|
||||||
.Distinct()
|
|
||||||
.ToList()
|
|
||||||
: new List<int>();
|
|
||||||
permissions.AddRange(pmUserPermissions);
|
|
||||||
}
|
|
||||||
|
|
||||||
pmUserId = PmUserData.Id > 0 ? PmUserData.Id : null;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int? positionValue;
|
int? positionValue;
|
||||||
if (account.PositionId != null)
|
if (account.PositionId != null)
|
||||||
{
|
{
|
||||||
@@ -432,45 +238,37 @@ public class AccountApplication : IAccountApplication
|
|||||||
{
|
{
|
||||||
positionValue = null;
|
positionValue = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
||||||
, account.Username, account.Mobile, account.ProfilePhoto,
|
, account.Username, account.Mobile, account.ProfilePhoto, permissions, account.RoleName, account.AdminAreaPermission, account.ClientAriaPermission, positionValue);
|
||||||
permissions, account.RoleName, account.AdminAreaPermission,
|
|
||||||
account.ClientAriaPermission, positionValue, 0, pmUserId);
|
|
||||||
|
|
||||||
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false" &&
|
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false" &&
|
||||||
account.IsActiveString == "true")
|
account.IsActiveString == "true")
|
||||||
{
|
{
|
||||||
var clientPermissions = _accountPermissionSubtitle1Repository.GetAllPermissionCodes();
|
var clientPermissions = _accountPermissionSubtitle1Repository.GetAllPermissionCodes();
|
||||||
authViewModel.Permissions = clientPermissions;
|
authViewModel.Permissions = clientPermissions;
|
||||||
var workshopList = _workshopRepository.GetWorkshopsByClientAccountId(account.id).Select(x =>
|
var workshopList = _workshopRepository.GetWorkshopsByClientAccountId(account.id).Select(x => new WorkshopClaim
|
||||||
new WorkshopClaim
|
|
||||||
{
|
|
||||||
PersonnelCount = x.PersonnelCount,
|
|
||||||
Id = x.Id,
|
|
||||||
Name = x.WorkshopFullName,
|
|
||||||
Slug = _passwordHasher.SlugHasher(x.Id)
|
|
||||||
}).OrderByDescending(x => x.PersonnelCount).ToList();
|
|
||||||
authViewModel.WorkshopList = workshopList;
|
|
||||||
if (workshopList.Any())
|
|
||||||
{
|
{
|
||||||
var workshop = workshopList.First();
|
PersonnelCount = x.PersonnelCount,
|
||||||
authViewModel.WorkshopName = workshop.Name;
|
Id = x.Id,
|
||||||
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.Id);
|
Name = x.WorkshopFullName,
|
||||||
|
Slug = _passwordHasher.SlugHasher(x.Id)
|
||||||
|
}).OrderByDescending(x => x.PersonnelCount).ToList();
|
||||||
|
authViewModel.WorkshopList = workshopList;
|
||||||
|
if (workshopList.Any())
|
||||||
|
{
|
||||||
|
var workshop = workshopList.First();
|
||||||
|
authViewModel.WorkshopName = workshop.Name;
|
||||||
|
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.Id);
|
||||||
authViewModel.WorkshopId = workshop.Id;
|
authViewModel.WorkshopId = workshop.Id;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
_authHelper.Signin(authViewModel);
|
_authHelper.Signin(authViewModel);
|
||||||
|
|
||||||
if ((account.AdminAreaPermission == "true" && account.ClientAriaPermission == "true" &&
|
if ((account.AdminAreaPermission == "true" && account.ClientAriaPermission == "true" && account.IsActiveString == "true") || (account.AdminAreaPermission == "true" && account.ClientAriaPermission == "false" && account.IsActiveString == "true"))
|
||||||
account.IsActiveString == "true") || (account.AdminAreaPermission == "true" &&
|
|
||||||
account.ClientAriaPermission == "false" &&
|
|
||||||
account.IsActiveString == "true"))
|
|
||||||
idAutoriz = 1;
|
idAutoriz = 1;
|
||||||
|
|
||||||
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false" &&
|
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false" && account.IsActiveString == "true")
|
||||||
account.IsActiveString == "true")
|
|
||||||
idAutoriz = 2;
|
idAutoriz = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -482,8 +280,7 @@ public class AccountApplication : IAccountApplication
|
|||||||
|
|
||||||
var mobile = string.IsNullOrWhiteSpace(cameraAccount.Mobile) ? " " : cameraAccount.Mobile;
|
var mobile = string.IsNullOrWhiteSpace(cameraAccount.Mobile) ? " " : cameraAccount.Mobile;
|
||||||
var authViewModel = new CameraAuthViewModel(cameraAccount.id, cameraAccount.WorkshopId,
|
var authViewModel = new CameraAuthViewModel(cameraAccount.id, cameraAccount.WorkshopId,
|
||||||
cameraAccount.Username, mobile, cameraAccount.WorkshopName, cameraAccount.AccountId,
|
cameraAccount.Username, mobile, cameraAccount.WorkshopName, cameraAccount.AccountId,cameraAccount.IsActiveSting);
|
||||||
cameraAccount.IsActiveSting);
|
|
||||||
if (cameraAccount.IsActiveSting == "true")
|
if (cameraAccount.IsActiveSting == "true")
|
||||||
{
|
{
|
||||||
_authHelper.CameraSignIn(authViewModel);
|
_authHelper.CameraSignIn(authViewModel);
|
||||||
@@ -493,43 +290,42 @@ public class AccountApplication : IAccountApplication
|
|||||||
{
|
{
|
||||||
idAutoriz = 0;
|
idAutoriz = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (subAccount != null)
|
if (subAccount != null)
|
||||||
{
|
{
|
||||||
(bool Verified, bool NeedUpgrade) result = _passwordHasher.Check(subAccount.Password, command.Password);
|
(bool Verified, bool NeedUpgrade) result = _passwordHasher.Check(subAccount.Password, command.Password);
|
||||||
if (!result.Verified)
|
if (!result.Verified)
|
||||||
return operation.Failed(ApplicationMessages.WrongUserPass);
|
return operation.Failed(ApplicationMessages.WrongUserPass);
|
||||||
var role = _subAccountRoleRepository.Get(subAccount.SubAccountRoleId);
|
var role = _subAccountRoleRepository.Get(subAccount.SubAccountRoleId);
|
||||||
|
|
||||||
var permissions = role.RolePermissions.Select(x => x.PermissionCode).ToList();
|
var permissions = role.RolePermissions.Select(x => x.PermissionCode).ToList();
|
||||||
var authViewModel = new AuthViewModel(subAccount.AccountId, subAccount.SubAccountRoleId, subAccount.FullName
|
var authViewModel = new AuthViewModel(subAccount.AccountId, subAccount.SubAccountRoleId, subAccount.FullName
|
||||||
, subAccount.Username, subAccount.PhoneNumber, "", permissions, role.Title, "false",
|
, subAccount.Username, subAccount.PhoneNumber, "", permissions, role.Title, "false",
|
||||||
"true", 0, subAccount.id);
|
"true", 0, subAccount.id);
|
||||||
var workshopList = _workshopSubAccountRepository.GetWorkshopsBySubAccountId(subAccount.id);
|
var workshopList = _workshopSubAccountRepository.GetWorkshopsBySubAccountId(subAccount.id);
|
||||||
authViewModel.WorkshopList = workshopList.Select(x => new WorkshopClaim()
|
authViewModel.WorkshopList = workshopList.Select(x => new WorkshopClaim()
|
||||||
{
|
{
|
||||||
Slug = _passwordHasher.SlugHasher(x.WorkshopId),
|
Slug = _passwordHasher.SlugHasher(x.WorkshopId),
|
||||||
Name = x.WorkshopName,
|
Name = x.WorkshopName,
|
||||||
PersonnelCount = x.PersonnelCount,
|
PersonnelCount = x.PersonnelCount,
|
||||||
Id = x.WorkshopId
|
Id = x.WorkshopId
|
||||||
}).ToList();
|
}).ToList();
|
||||||
|
|
||||||
if (workshopList.Any())
|
if (workshopList.Any())
|
||||||
{
|
{
|
||||||
var workshop = workshopList.First();
|
var workshop = workshopList.First();
|
||||||
authViewModel.WorkshopName = workshop.WorkshopName;
|
authViewModel.WorkshopName = workshop.WorkshopName;
|
||||||
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.WorkshopId);
|
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.WorkshopId);
|
||||||
authViewModel.WorkshopId = workshop.WorkshopId;
|
authViewModel.WorkshopId = workshop.WorkshopId;
|
||||||
}
|
}
|
||||||
|
_authHelper.Signin(authViewModel);
|
||||||
|
idAutoriz = 2;
|
||||||
|
}
|
||||||
|
|
||||||
_authHelper.Signin(authViewModel);
|
return operation.Succcedded(idAutoriz);
|
||||||
idAutoriz = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
return operation.Succcedded(idAutoriz);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public OperationResult LoginWithMobile(long id)
|
public OperationResult LoginWithMobile(long id)
|
||||||
{
|
{
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
@@ -538,6 +334,7 @@ public class AccountApplication : IAccountApplication
|
|||||||
return operation.Failed(ApplicationMessages.WrongUserPass);
|
return operation.Failed(ApplicationMessages.WrongUserPass);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
var permissions = _roleRepository.Get(account.RoleId)
|
var permissions = _roleRepository.Get(account.RoleId)
|
||||||
.Permissions
|
.Permissions
|
||||||
.Select(x => x.Code)
|
.Select(x => x.Code)
|
||||||
@@ -553,43 +350,39 @@ public class AccountApplication : IAccountApplication
|
|||||||
}
|
}
|
||||||
|
|
||||||
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
||||||
, account.Username, account.Mobile, account.ProfilePhoto, permissions, account.RoleName,
|
, account.Username, account.Mobile, account.ProfilePhoto, permissions, account.RoleName, account.AdminAreaPermission, account.ClientAriaPermission, positionValue);
|
||||||
account.AdminAreaPermission, account.ClientAriaPermission, positionValue);
|
|
||||||
|
|
||||||
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false" &&
|
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false" &&
|
||||||
account.IsActiveString == "true")
|
account.IsActiveString == "true")
|
||||||
{
|
{
|
||||||
var clientPermissions = _accountPermissionSubtitle1Repository.GetAllPermissionCodes();
|
var clientPermissions = _accountPermissionSubtitle1Repository.GetAllPermissionCodes();
|
||||||
authViewModel.Permissions = clientPermissions;
|
authViewModel.Permissions = clientPermissions;
|
||||||
var workshopList = _workshopRepository.GetWorkshopsByClientAccountId(account.id).Select(x =>
|
var workshopList = _workshopRepository.GetWorkshopsByClientAccountId(account.id).Select(x => new WorkshopClaim
|
||||||
new WorkshopClaim
|
{
|
||||||
{
|
PersonnelCount = x.PersonnelCount,
|
||||||
PersonnelCount = x.PersonnelCount,
|
Id = x.Id,
|
||||||
Id = x.Id,
|
Name = x.WorkshopFullName,
|
||||||
Name = x.WorkshopFullName,
|
Slug = _passwordHasher.SlugHasher(x.Id)
|
||||||
Slug = _passwordHasher.SlugHasher(x.Id)
|
}).OrderByDescending(x => x.PersonnelCount).ToList();
|
||||||
}).OrderByDescending(x => x.PersonnelCount).ToList();
|
authViewModel.WorkshopList = workshopList;
|
||||||
authViewModel.WorkshopList = workshopList;
|
if (workshopList.Any())
|
||||||
if (workshopList.Any())
|
{
|
||||||
{
|
var workshop = workshopList.First();
|
||||||
var workshop = workshopList.First();
|
authViewModel.WorkshopName = workshop.Name;
|
||||||
authViewModel.WorkshopName = workshop.Name;
|
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.Id);
|
||||||
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.Id);
|
|
||||||
authViewModel.WorkshopId = workshop.Id;
|
authViewModel.WorkshopId = workshop.Id;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
_authHelper.Signin(authViewModel);
|
_authHelper.Signin(authViewModel);
|
||||||
long idAutoriz = 0;
|
long idAutoriz = 0;
|
||||||
if (account.AdminAreaPermission == "true" && account.ClientAriaPermission == "true" ||
|
if (account.AdminAreaPermission == "true" && account.ClientAriaPermission == "true" || account.AdminAreaPermission == "true" && account.ClientAriaPermission == "false")
|
||||||
account.AdminAreaPermission == "true" && account.ClientAriaPermission == "false")
|
|
||||||
idAutoriz = 1;
|
idAutoriz = 1;
|
||||||
|
|
||||||
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false")
|
if (account.ClientAriaPermission == "true" && account.AdminAreaPermission == "false")
|
||||||
idAutoriz = 2;
|
idAutoriz = 2;
|
||||||
return operation.Succcedded(idAutoriz);
|
return operation.Succcedded(idAutoriz);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Logout()
|
public void Logout()
|
||||||
{
|
{
|
||||||
_authHelper.SignOut();
|
_authHelper.SignOut();
|
||||||
@@ -625,7 +418,6 @@ public class AccountApplication : IAccountApplication
|
|||||||
_accountRepository.SaveChanges();
|
_accountRepository.SaveChanges();
|
||||||
return operation.Succcedded();
|
return operation.Succcedded();
|
||||||
}
|
}
|
||||||
|
|
||||||
public EditAccount GetByVerifyCode(string code, string phone)
|
public EditAccount GetByVerifyCode(string code, string phone)
|
||||||
{
|
{
|
||||||
return _accountRepository.GetByVerifyCode(code, phone);
|
return _accountRepository.GetByVerifyCode(code, phone);
|
||||||
@@ -636,7 +428,7 @@ public class AccountApplication : IAccountApplication
|
|||||||
return _accountRepository.GetByUserNameAndId(id, username);
|
return _accountRepository.GetByUserNameAndId(id, username);
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<OperationResult> SetVerifyCode(string phone, long id)
|
public async Task <OperationResult> SetVerifyCode(string phone, long id)
|
||||||
{
|
{
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
var account = _accountRepository.Get(id);
|
var account = _accountRepository.Get(id);
|
||||||
@@ -650,10 +442,11 @@ public class AccountApplication : IAccountApplication
|
|||||||
_smsService.LoginSend(phone, r);
|
_smsService.LoginSend(phone, r);
|
||||||
|
|
||||||
//TimeSpan delay = TimeSpan.FromSeconds(30);
|
//TimeSpan delay = TimeSpan.FromSeconds(30);
|
||||||
|
|
||||||
await _accountRepository.RemoveCode(id);
|
await _accountRepository.RemoveCode(id);
|
||||||
|
|
||||||
return operation.Succcedded();
|
return operation.Succcedded();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -698,88 +491,88 @@ public class AccountApplication : IAccountApplication
|
|||||||
return operation.Failed("این اکانت وجود ندارد");
|
return operation.Failed("این اکانت وجود ندارد");
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
var permissions = _roleRepository.Get(account.RoleId)
|
var permissions = _roleRepository.Get(account.RoleId)
|
||||||
.Permissions
|
.Permissions
|
||||||
.Select(x => x.Code)
|
.Select(x => x.Code)
|
||||||
.ToList();
|
.ToList();
|
||||||
|
|
||||||
|
|
||||||
_authHelper.SignOut();
|
_authHelper.SignOut();
|
||||||
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
||||||
, account.Username, account.Mobile, account.ProfilePhoto, permissions, account.RoleName, "false", "true",
|
, account.Username, account.Mobile, account.ProfilePhoto, permissions, account.RoleName, "false", "true",null);
|
||||||
null);
|
var workshopList = _workshopRepository.GetWorkshopsByClientAccountId(account.id).Select(x => new WorkshopClaim
|
||||||
var workshopList = _workshopRepository.GetWorkshopsByClientAccountId(account.id).Select(x => new WorkshopClaim
|
{
|
||||||
{
|
PersonnelCount = x.PersonnelCount,
|
||||||
PersonnelCount = x.PersonnelCount,
|
Id = x.Id,
|
||||||
Id = x.Id,
|
Name = x.WorkshopFullName,
|
||||||
Name = x.WorkshopFullName,
|
Slug = _passwordHasher.SlugHasher(x.Id)
|
||||||
Slug = _passwordHasher.SlugHasher(x.Id)
|
}).OrderByDescending(x => x.PersonnelCount).ToList();
|
||||||
}).OrderByDescending(x => x.PersonnelCount).ToList();
|
|
||||||
|
|
||||||
authViewModel.WorkshopList = workshopList;
|
authViewModel.WorkshopList = workshopList;
|
||||||
|
|
||||||
var clientPermissions = _accountPermissionSubtitle1Repository.GetAllPermissionCodes();
|
var clientPermissions = _accountPermissionSubtitle1Repository.GetAllPermissionCodes();
|
||||||
authViewModel.Permissions = clientPermissions;
|
authViewModel.Permissions = clientPermissions;
|
||||||
if (authViewModel.WorkshopList.Any())
|
if (authViewModel.WorkshopList.Any())
|
||||||
{
|
{
|
||||||
var workshop = authViewModel.WorkshopList.First();
|
var workshop = authViewModel.WorkshopList.First();
|
||||||
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.Id);
|
authViewModel.WorkshopSlug = _passwordHasher.SlugHasher(workshop.Id);
|
||||||
authViewModel.WorkshopName = workshop.Name;
|
authViewModel.WorkshopName = workshop.Name;
|
||||||
authViewModel.WorkshopId = workshop.Id;
|
authViewModel.WorkshopId = workshop.Id;
|
||||||
}
|
}
|
||||||
|
_authHelper.Signin(authViewModel);
|
||||||
_authHelper.Signin(authViewModel);
|
|
||||||
return operation.Succcedded(2);
|
return operation.Succcedded(2);
|
||||||
}
|
}
|
||||||
|
|
||||||
public OperationResult DirectCameraLogin(long cameraAccountId)
|
public OperationResult DirectCameraLogin(long cameraAccountId)
|
||||||
{
|
{
|
||||||
var prAcc = _authHelper.CurrentAccountInfo();
|
var prAcc = _authHelper.CurrentAccountInfo();
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
var cameraAccount = _cameraAccountRepository.GetById(cameraAccountId);
|
var cameraAccount = _cameraAccountRepository.GetById(cameraAccountId);
|
||||||
if (cameraAccount == null)
|
if (cameraAccount == null)
|
||||||
return operation.Failed("این اکانت وجود ندارد");
|
return operation.Failed("این اکانت وجود ندارد");
|
||||||
|
|
||||||
|
|
||||||
_authHelper.SignOut();
|
|
||||||
|
|
||||||
|
|
||||||
var mobile = string.IsNullOrWhiteSpace(cameraAccount.Mobile) ? " " : cameraAccount.Mobile;
|
|
||||||
var authViewModel = new CameraAuthViewModel(cameraAccount.id, cameraAccount.WorkshopId,
|
|
||||||
cameraAccount.Username, mobile, cameraAccount.WorkshopName, cameraAccount.AccountId,
|
|
||||||
cameraAccount.IsActiveSting);
|
|
||||||
if (cameraAccount.IsActiveSting == "true")
|
|
||||||
{
|
|
||||||
_authHelper.CameraSignIn(authViewModel);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return operation.Failed("این اکانت غیر فعال شده است");
|
|
||||||
}
|
|
||||||
|
|
||||||
return operation.Succcedded(2);
|
_authHelper.SignOut();
|
||||||
|
|
||||||
|
|
||||||
|
var mobile = string.IsNullOrWhiteSpace(cameraAccount.Mobile) ? " " : cameraAccount.Mobile;
|
||||||
|
var authViewModel = new CameraAuthViewModel(cameraAccount.id, cameraAccount.WorkshopId,
|
||||||
|
cameraAccount.Username, mobile, cameraAccount.WorkshopName, cameraAccount.AccountId, cameraAccount.IsActiveSting);
|
||||||
|
if (cameraAccount.IsActiveSting == "true")
|
||||||
|
{
|
||||||
|
_authHelper.CameraSignIn(authViewModel);
|
||||||
|
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return operation.Failed("این اکانت غیر فعال شده است");
|
||||||
|
}
|
||||||
|
return operation.Succcedded(2);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// public AccountLeftWorkViewModel WorkshopList(long accountId)
|
public AccountLeftWorkViewModel WorkshopList(long accountId)
|
||||||
// {
|
{
|
||||||
// string fullname = this._accountRepository.GetById(accountId).Fullname;
|
string fullname = this._accountRepository.GetById(accountId).Fullname;
|
||||||
// List<WorkshopAccountlistViewModel> source = _accountLeftworkRepository.WorkshopList(accountId);
|
List<WorkshopAccountlistViewModel> source =_accountLeftworkRepository.WorkshopList(accountId);
|
||||||
// List<long> userWorkshopIds = source.Select(x => x.WorkshopId).ToList();
|
List<long> userWorkshopIds = source.Select(x => x.WorkshopId).ToList();
|
||||||
// List<WorkshopSelectList> allWorkshops = this._accountLeftworkRepository.GetAllWorkshops();
|
List<WorkshopSelectList> allWorkshops = this._accountLeftworkRepository.GetAllWorkshops();
|
||||||
// List<AccountViewModel> accountSelectList = this._accountRepository.GetAdminAccountSelectList();
|
List<AccountViewModel> accountSelectList = this._accountRepository.GetAdminAccountSelectList();
|
||||||
// (string StartWorkFa, string LeftWorkFa) byAccountId = this._accountLeftworkRepository.GetByAccountId(accountId);
|
(string StartWorkFa, string LeftWorkFa) byAccountId = this._accountLeftworkRepository.GetByAccountId(accountId);
|
||||||
// return new AccountLeftWorkViewModel()
|
return new AccountLeftWorkViewModel()
|
||||||
// {
|
{
|
||||||
// AccountId = accountId,
|
AccountId = accountId,
|
||||||
// AccountFullName = fullname,
|
AccountFullName = fullname,
|
||||||
// StartDateFa = byAccountId.StartWorkFa,
|
StartDateFa = byAccountId.StartWorkFa,
|
||||||
// LeftDateFa = byAccountId.LeftWorkFa,
|
LeftDateFa = byAccountId.LeftWorkFa,
|
||||||
// WorkshopAccountlist = source,
|
WorkshopAccountlist = source,
|
||||||
// WorkshopSelectList = new SelectList(allWorkshops.Where(x => !userWorkshopIds.Contains(x.Id)), "Id", "WorkshopFullName"),
|
WorkshopSelectList = new SelectList(allWorkshops.Where(x => !userWorkshopIds.Contains(x.Id)), "Id", "WorkshopFullName"),
|
||||||
// AccountSelectList = new SelectList(accountSelectList, "Id", "Fullname")
|
AccountSelectList = new SelectList(accountSelectList, "Id", "Fullname")
|
||||||
// };
|
};
|
||||||
// }
|
}
|
||||||
|
|
||||||
public OperationResult SaveWorkshopAccount(
|
public OperationResult SaveWorkshopAccount(
|
||||||
List<WorkshopAccountlistViewModel> workshopAccountList,
|
List<WorkshopAccountlistViewModel> workshopAccountList,
|
||||||
@@ -789,12 +582,10 @@ public class AccountApplication : IAccountApplication
|
|||||||
{
|
{
|
||||||
return this._accountLeftworkRepository.SaveWorkshopAccount(workshopAccountList, startDate, leftDate, accountId);
|
return this._accountLeftworkRepository.SaveWorkshopAccount(workshopAccountList, startDate, leftDate, accountId);
|
||||||
}
|
}
|
||||||
|
|
||||||
public OperationResult CreateNewWorkshopAccount(long currentAccountId, long newAccountId)
|
public OperationResult CreateNewWorkshopAccount(long currentAccountId, long newAccountId)
|
||||||
{
|
{
|
||||||
return this._accountLeftworkRepository.CopyWorkshopToNewAccount(currentAccountId, newAccountId);
|
return this._accountLeftworkRepository.CopyWorkshopToNewAccount(currentAccountId, newAccountId);
|
||||||
}
|
}
|
||||||
|
|
||||||
#region Mahan
|
#region Mahan
|
||||||
|
|
||||||
public List<AccountViewModel> AccountsForAssign(long taskId)
|
public List<AccountViewModel> AccountsForAssign(long taskId)
|
||||||
@@ -808,7 +599,6 @@ public class AccountApplication : IAccountApplication
|
|||||||
{
|
{
|
||||||
return new List<AccountViewModel>();
|
return new List<AccountViewModel>();
|
||||||
}
|
}
|
||||||
|
|
||||||
return _accountRepository.GetAccountsByPositionId(positionId);
|
return _accountRepository.GetAccountsByPositionId(positionId);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -826,6 +616,7 @@ public class AccountApplication : IAccountApplication
|
|||||||
return operation.Failed("این اکانت وجود ندارد");
|
return operation.Failed("این اکانت وجود ندارد");
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
var permissions = _roleRepository.Get(account.RoleId)
|
var permissions = _roleRepository.Get(account.RoleId)
|
||||||
.Permissions
|
.Permissions
|
||||||
.Select(x => x.Code)
|
.Select(x => x.Code)
|
||||||
@@ -834,10 +625,10 @@ public class AccountApplication : IAccountApplication
|
|||||||
|
|
||||||
_authHelper.SignOut();
|
_authHelper.SignOut();
|
||||||
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
var authViewModel = new AuthViewModel(account.id, account.RoleId, account.Fullname
|
||||||
, account.Username, account.Mobile, account.ProfilePhoto, permissions, account.RoleName,
|
, account.Username, account.Mobile, account.ProfilePhoto, permissions, account.RoleName, account.AdminAreaPermission, account.ClientAriaPermission, account.Position.PositionValue);
|
||||||
account.AdminAreaPermission, account.ClientAriaPermission, account.Position.PositionValue);
|
|
||||||
_authHelper.Signin(authViewModel);
|
_authHelper.Signin(authViewModel);
|
||||||
return operation.Succcedded(2);
|
return operation.Succcedded(2);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<List<AccountSelectListViewModel>> GetAdminSelectList()
|
public async Task<List<AccountSelectListViewModel>> GetAdminSelectList()
|
||||||
@@ -846,74 +637,68 @@ public class AccountApplication : IAccountApplication
|
|||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
#region Pooya
|
#region Pooya
|
||||||
|
public OperationResult IsPhoneNumberAndPasswordValid(long accountId, string phoneNumber, string password, string rePassword)
|
||||||
public OperationResult IsPhoneNumberAndPasswordValid(long accountId, string phoneNumber, string password,
|
|
||||||
string rePassword)
|
|
||||||
{
|
{
|
||||||
OperationResult op = new();
|
OperationResult op = new();
|
||||||
|
|
||||||
var entity = _accountRepository.Get(accountId);
|
var entity = _accountRepository.Get(accountId);
|
||||||
|
|
||||||
if (entity == null)
|
if (entity == null)
|
||||||
return op.Failed(ApplicationMessages.RecordNotFound);
|
return op.Failed(ApplicationMessages.RecordNotFound);
|
||||||
|
|
||||||
if (!string.IsNullOrWhiteSpace(rePassword) || !string.IsNullOrWhiteSpace(password))
|
if (!string.IsNullOrWhiteSpace(rePassword) || !string.IsNullOrWhiteSpace(password))
|
||||||
{
|
{
|
||||||
if (rePassword != password)
|
if (rePassword != password)
|
||||||
return op.Failed("تکرار رمز عبور با رمز عبور مطابقت ندارد");
|
return op.Failed("تکرار رمز عبور با رمز عبور مطابقت ندارد");
|
||||||
|
|
||||||
if (password.Length < 8)
|
if (password.Length < 8)
|
||||||
return op.Failed("رمز عبور نمی تواند کمتر از 8 کاراکتر باشد");
|
return op.Failed("رمز عبور نمی تواند کمتر از 8 کاراکتر باشد");
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((string.IsNullOrWhiteSpace(phoneNumber) || entity.Mobile == phoneNumber) &&
|
if ((string.IsNullOrWhiteSpace(phoneNumber) || entity.Mobile == phoneNumber) && string.IsNullOrWhiteSpace(rePassword))
|
||||||
string.IsNullOrWhiteSpace(rePassword))
|
return op.Failed("چیزی برای تغییر وجود ندارد");
|
||||||
return op.Failed("چیزی برای تغییر وجود ندارد");
|
|
||||||
|
|
||||||
|
|
||||||
if (!string.IsNullOrWhiteSpace(phoneNumber) && entity.Mobile != phoneNumber)
|
if (!string.IsNullOrWhiteSpace(phoneNumber) && entity.Mobile != phoneNumber)
|
||||||
{
|
{
|
||||||
phoneNumber = phoneNumber.Trim();
|
phoneNumber = phoneNumber.Trim();
|
||||||
if (phoneNumber.Length != 11)
|
if (phoneNumber.Length != 11)
|
||||||
return op.Failed("شماره تلفن همراه به درستی وارد نشده است");
|
return op.Failed("شماره تلفن همراه به درستی وارد نشده است");
|
||||||
if (_accountRepository.Exists(x => x.Mobile == phoneNumber && x.id != accountId) ||
|
if (_accountRepository.Exists(x => x.Mobile == phoneNumber && x.id != accountId) ||
|
||||||
_subAccountRepository.Exists(x => x.PhoneNumber == phoneNumber) ||
|
_subAccountRepository.Exists(x => x.PhoneNumber == phoneNumber) ||
|
||||||
_cameraAccountRepository.Exists(x => x.Mobile == phoneNumber))
|
_cameraAccountRepository.Exists(x => x.Mobile == phoneNumber))
|
||||||
return op.Failed("قبلا یک حساب با این شماره ثبت شده است");
|
return op.Failed("قبلا یک حساب با این شماره ثبت شده است");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return op.Succcedded();
|
return op.Succcedded();
|
||||||
}
|
}
|
||||||
|
|
||||||
public OperationResult ChangePasswordAndPhoneNumber(AccountChangePasswordAndPhoneNumber command)
|
public OperationResult ChangePasswordAndPhoneNumber(AccountChangePasswordAndPhoneNumber command)
|
||||||
{
|
{
|
||||||
OperationResult op = new();
|
OperationResult op = new();
|
||||||
command.PhoneNumber = command.PhoneNumber.Trim();
|
command.PhoneNumber = command.PhoneNumber.Trim();
|
||||||
var entity = _accountRepository.Get(command.AccountId);
|
var entity = _accountRepository.Get(command.AccountId);
|
||||||
if (entity == null)
|
if (entity == null)
|
||||||
return op.Failed(ApplicationMessages.RecordNotFound);
|
return op.Failed(ApplicationMessages.RecordNotFound);
|
||||||
var validationResult = IsPhoneNumberAndPasswordValid(command.AccountId, command.PhoneNumber, command.Password,
|
var validationResult = IsPhoneNumberAndPasswordValid(command.AccountId, command.PhoneNumber, command.Password, command.RePassword);
|
||||||
command.RePassword);
|
if (validationResult.IsSuccedded == false)
|
||||||
if (validationResult.IsSuccedded == false)
|
return validationResult;
|
||||||
return validationResult;
|
|
||||||
|
|
||||||
if (!string.IsNullOrWhiteSpace(command.RePassword))
|
if (!string.IsNullOrWhiteSpace(command.RePassword))
|
||||||
{
|
{
|
||||||
entity.ChangePassword(_passwordHasher.Hash(command.Password));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!string.IsNullOrWhiteSpace(command.PhoneNumber))
|
entity.ChangePassword(_passwordHasher.Hash(command.Password));
|
||||||
{
|
}
|
||||||
entity.Edit(entity.Fullname, entity.Username, command.PhoneNumber, entity.RoleId, entity.ProfilePhoto,
|
|
||||||
entity.RoleName);
|
|
||||||
}
|
|
||||||
|
|
||||||
_accountRepository.SaveChanges();
|
if (!string.IsNullOrWhiteSpace(command.PhoneNumber))
|
||||||
return op.Succcedded();
|
{
|
||||||
}
|
entity.Edit(entity.Fullname, entity.Username, command.PhoneNumber, entity.RoleId, entity.ProfilePhoto, entity.RoleName);
|
||||||
|
}
|
||||||
|
_accountRepository.SaveChanges();
|
||||||
|
return op.Succcedded();
|
||||||
|
}
|
||||||
//public UserClaimsResponseDTO GetClaimsForSignIn(Login command)
|
//public UserClaimsResponseDTO GetClaimsForSignIn(Login command)
|
||||||
//{
|
//{
|
||||||
// var operation = new OperationResult();
|
// var operation = new OperationResult();
|
||||||
@@ -1006,7 +791,6 @@ public class AccountApplication : IAccountApplication
|
|||||||
|
|
||||||
// return claimsResponse.Failed(ApplicationMessages.WrongUserPass);
|
// return claimsResponse.Failed(ApplicationMessages.WrongUserPass);
|
||||||
//}
|
//}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
|
||||||
@@ -1019,34 +803,4 @@ public class AccountApplication : IAccountApplication
|
|||||||
{
|
{
|
||||||
return _accountRepository.GetAdminAccountsNew();
|
return _accountRepository.GetAdminAccountsNew();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void CameraLogin(CameraLoginRequest request)
|
|
||||||
{
|
|
||||||
var cameraAccount = _cameraAccountRepository.GetBy(request.UserName);
|
|
||||||
|
|
||||||
if (cameraAccount == null)
|
|
||||||
{
|
|
||||||
throw new BadRequestException(ApplicationMessages.WrongUserPass);
|
|
||||||
}
|
|
||||||
|
|
||||||
(bool Verified, bool NeedUpgrade) result = _passwordHasher.Check(cameraAccount.Password, request.Password);
|
|
||||||
|
|
||||||
if (!result.Verified)
|
|
||||||
throw new BadRequestException(ApplicationMessages.WrongUserPass);
|
|
||||||
|
|
||||||
var mobile = string.IsNullOrWhiteSpace(cameraAccount.Mobile) ? " " : cameraAccount.Mobile;
|
|
||||||
|
|
||||||
var authViewModel = new CameraAuthViewModel(cameraAccount.id, cameraAccount.WorkshopId,
|
|
||||||
cameraAccount.Username, mobile, cameraAccount.WorkshopName, cameraAccount.AccountId,
|
|
||||||
cameraAccount.IsActiveSting);
|
|
||||||
if (cameraAccount.IsActiveSting != "true")
|
|
||||||
throw new BadRequestException(ApplicationMessages.WrongUserPass);
|
|
||||||
|
|
||||||
_authHelper.CameraSignIn(authViewModel);
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<GetPmUserDto> GetPmUserAsync(long accountId)
|
|
||||||
{
|
|
||||||
return await _pmUserQueryService.GetPmUserDataByAccountId(accountId);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
@@ -1,14 +1,13 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ProjectReference Include="..\AccountManagement.Application.Contracts\AccountManagement.Application.Contracts.csproj" />
|
<ProjectReference Include="..\AccountManagement.Application.Contracts\AccountManagement.Application.Contracts.csproj" />
|
||||||
<ProjectReference Include="..\AccountManagement.Domain\AccountManagement.Domain.csproj" />
|
<ProjectReference Include="..\AccountManagement.Domain\AccountManagement.Domain.csproj" />
|
||||||
<ProjectReference Include="..\Company.Domain\Company.Domain.csproj" />
|
<ProjectReference Include="..\Company.Domain\Company.Domain.csproj" />
|
||||||
<ProjectReference Include="..\Shared.Contracts\Shared.Contracts.csproj" />
|
|
||||||
|
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,8 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading.Tasks;
|
||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
using AccountManagement.Application.Contracts.Account;
|
using AccountManagement.Application.Contracts.Account;
|
||||||
using AccountManagement.Application.Contracts.CameraAccount;
|
using AccountManagement.Application.Contracts.CameraAccount;
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
using System.Collections.Generic;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
|
|||||||
@@ -2,14 +2,6 @@
|
|||||||
using AccountManagement.Application.Contracts.Role;
|
using AccountManagement.Application.Contracts.Role;
|
||||||
using AccountManagement.Domain.RoleAgg;
|
using AccountManagement.Domain.RoleAgg;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using Company.Domain._common;
|
|
||||||
using Microsoft.AspNetCore.Mvc.Rendering;
|
|
||||||
using Shared.Contracts.PmRole.Commands;
|
|
||||||
using GetPmRolesDto = Shared.Contracts.PmRole.Queries.GetPmRolesDto;
|
|
||||||
using Role = AccountManagement.Domain.RoleAgg.Role;
|
|
||||||
using Shared.Contracts.PmRole.Queries;
|
|
||||||
|
|
||||||
namespace AccountManagement.Application;
|
namespace AccountManagement.Application;
|
||||||
|
|
||||||
@@ -17,82 +9,32 @@ public class RoleApplication : IRoleApplication
|
|||||||
{
|
{
|
||||||
private readonly IRoleRepository _roleRepository;
|
private readonly IRoleRepository _roleRepository;
|
||||||
|
|
||||||
private readonly IPmRoleQueryService _pmRoleQueryService;
|
public RoleApplication(IRoleRepository roleRepository)
|
||||||
private readonly IPmRoleCommandService _pmRoleCommandService;
|
|
||||||
private readonly IUnitOfWork _unitOfWork;
|
|
||||||
|
|
||||||
public RoleApplication(IRoleRepository roleRepository, IUnitOfWork unitOfWork, IPmRoleQueryService pmRoleQueryService, IPmRoleCommandService pmRoleCommandService)
|
|
||||||
{
|
{
|
||||||
_roleRepository = roleRepository;
|
_roleRepository = roleRepository;
|
||||||
_unitOfWork = unitOfWork;
|
|
||||||
_pmRoleQueryService = pmRoleQueryService;
|
|
||||||
_pmRoleCommandService = pmRoleCommandService;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<OperationResult> Create(CreateRole command)
|
public OperationResult Create(CreateRole command)
|
||||||
{
|
{
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
if (_roleRepository.Exists(x => x.Name == command.Name))
|
if (_roleRepository.Exists(x => x.Name == command.Name))
|
||||||
return operation.Failed(ApplicationMessages.DuplicatedRecord);
|
return operation.Failed(ApplicationMessages.DuplicatedRecord);
|
||||||
var permissions = command.Permissions.Where(x => x > 0).Select(x => new Permission(x)).ToList();
|
var permissions = new List<Permission>();
|
||||||
|
foreach (var code in command.Permissions)
|
||||||
|
{
|
||||||
|
if (code > 0)
|
||||||
|
{
|
||||||
|
permissions.Add(new Permission(code));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
//command.Permissions.ForEach(code => permissions.Add(new Permission(code)));
|
||||||
var role = new Role(command.Name, permissions);
|
var role = new Role(command.Name, permissions);
|
||||||
_unitOfWork.BeginAccountContext();
|
|
||||||
|
|
||||||
_roleRepository.Create(role);
|
_roleRepository.Create(role);
|
||||||
_roleRepository.SaveChanges();
|
_roleRepository.SaveChanges();
|
||||||
|
|
||||||
var pmPermissions = command.PmPermissions.Where(x => x > 0).ToList();
|
|
||||||
if (pmPermissions.Any())
|
|
||||||
{
|
|
||||||
|
|
||||||
var pmRole = new CreatePmRoleDto{ RoleName = command.Name, Permissions = pmPermissions, GozareshgirRoleId = role.id};
|
|
||||||
var res =await _pmRoleCommandService.Create(pmRole);
|
|
||||||
if (!res.Item1)
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("خطا در ویرایش دسترسی ها در پروگرام منیجر");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//var parameters = new CreateProgramManagerRole
|
|
||||||
//{
|
|
||||||
// RoleName = command.Name,
|
|
||||||
// Permissions = pmPermissions,
|
|
||||||
// GozareshgirRoleId = role.id
|
|
||||||
|
|
||||||
//};
|
|
||||||
|
|
||||||
//var url = "api/role";
|
|
||||||
//var key = SecretKeys.ProgramManagerInternalApi;
|
|
||||||
|
|
||||||
//var response = InternalApiCaller.PostAsync<CreateProgramManagerRole, ApiResponse>(
|
|
||||||
// url,
|
|
||||||
// key,
|
|
||||||
// parameters
|
|
||||||
//);
|
|
||||||
|
|
||||||
|
|
||||||
//if (!response.Success)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed("ارتباط با اپلیکیش پروگرام منیجر برقرار نشد");
|
|
||||||
//}
|
|
||||||
|
|
||||||
//if (!response.Result.isSuccess)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Result.errorMessage);
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
//command.Permissions.ForEach(code => permissions.Add(new Permission(code)));
|
|
||||||
_unitOfWork.CommitAccountContext();
|
|
||||||
return operation.Succcedded();
|
return operation.Succcedded();
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<OperationResult> Edit(EditRole command)
|
public OperationResult Edit(EditRole command)
|
||||||
{
|
{
|
||||||
var operation = new OperationResult();
|
var operation = new OperationResult();
|
||||||
var role = _roleRepository.Get(command.Id);
|
var role = _roleRepository.Get(command.Id);
|
||||||
@@ -105,134 +47,17 @@ public class RoleApplication : IRoleApplication
|
|||||||
//var permissions = new List<Permission>();
|
//var permissions = new List<Permission>();
|
||||||
//command.Permissions.ForEach(code => permissions.Add(new Permission(code)));
|
//command.Permissions.ForEach(code => permissions.Add(new Permission(code)));
|
||||||
|
|
||||||
var permissions = command.Permissions.Where(x => x > 0).Select(x => new Permission(x)).ToList();
|
var permissions = new List<Permission>();
|
||||||
|
foreach (var code in command.Permissions)
|
||||||
|
{
|
||||||
|
if (code > 0)
|
||||||
|
{
|
||||||
|
permissions.Add(new Permission(code));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
_unitOfWork.BeginAccountContext();
|
|
||||||
role.Edit(command.Name, permissions);
|
role.Edit(command.Name, permissions);
|
||||||
_roleRepository.SaveChanges();
|
_roleRepository.SaveChanges();
|
||||||
var key = SecretKeys.ProgramManagerInternalApi;
|
|
||||||
var pmPermissions = command.PmPermissions.Where(x => x > 0).ToList();
|
|
||||||
|
|
||||||
|
|
||||||
//یافتن نقش در پروگرام منیجر
|
|
||||||
//var apiResult = InternalApiCaller.GetAsync<RoleResponse>(
|
|
||||||
// "api/role",
|
|
||||||
// key,
|
|
||||||
// new Dictionary<string, object>
|
|
||||||
// {
|
|
||||||
// { "RoleName", "" },
|
|
||||||
|
|
||||||
// { "GozareshgirRoleId", command.Id}
|
|
||||||
// }
|
|
||||||
//);
|
|
||||||
|
|
||||||
|
|
||||||
var pmRoleListResult = await _pmRoleQueryService.GetPmRoleList(command.Id);
|
|
||||||
var pmRoleResult = pmRoleListResult.FirstOrDefault();
|
|
||||||
|
|
||||||
//اگر این نقش در پروگرام منیجر وجود داشت ویرایش کن
|
|
||||||
if (pmRoleResult != null)
|
|
||||||
{
|
|
||||||
var edit = new CreatePmRoleDto { RoleName = command.Name, Permissions = pmPermissions, GozareshgirRoleId = role.id };
|
|
||||||
var res = await _pmRoleCommandService.Edit(edit);
|
|
||||||
if (!res.Item1)
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("خطا در ویرایش دسترسی ها در پروگرام منیجر");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
//var parameters = new CreateProgramManagerRole
|
|
||||||
//{
|
|
||||||
// RoleName = command.Name,
|
|
||||||
// Permissions = pmPermissions,
|
|
||||||
// GozareshgirRoleId = role.id
|
|
||||||
|
|
||||||
//};
|
|
||||||
//var url = "api/role/edit";
|
|
||||||
//var response = InternalApiCaller.PostAsync<CreateProgramManagerRole, ApiResponse>(
|
|
||||||
// url,
|
|
||||||
// key,
|
|
||||||
// parameters
|
|
||||||
//);
|
|
||||||
|
|
||||||
|
|
||||||
//if (!response.Success)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed("ارتباط با اپلیکیش پروگرام منیجر برقرار نشد");
|
|
||||||
//}
|
|
||||||
|
|
||||||
//if (!response.Result.isSuccess)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Result.errorMessage);
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
else //اگر نقش در پروگرام منیجر وجود نداشت
|
|
||||||
{
|
|
||||||
|
|
||||||
//اگر تیک پرمیشن های پروگرام منیجر زده شده
|
|
||||||
//این نقش را سمت پروگرام منیجر بساز
|
|
||||||
if (pmPermissions.Any())
|
|
||||||
{
|
|
||||||
var pmRole = new CreatePmRoleDto { RoleName = command.Name, Permissions = pmPermissions, GozareshgirRoleId = role.id };
|
|
||||||
var res = await _pmRoleCommandService.Create(pmRole);
|
|
||||||
if (!res.Item1)
|
|
||||||
{
|
|
||||||
_unitOfWork.RollbackAccountContext();
|
|
||||||
return operation.Failed("خطا در ویرایش دسترسی ها در پروگرام منیجر");
|
|
||||||
}
|
|
||||||
|
|
||||||
//try
|
|
||||||
//{
|
|
||||||
// var pmPermissionsData = pmPermissions.Where(x => x > 0).Select(x => new PmPermission(x)).ToList();
|
|
||||||
// var pmRole = new PmRole(command.Name, command.Id, pmPermissionsData);
|
|
||||||
// await _pmRoleRepository.CreateAsync(pmRole);
|
|
||||||
// await _pmRoleRepository.SaveChangesAsync();
|
|
||||||
|
|
||||||
//}
|
|
||||||
//catch (System.Exception)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed("خطا در ویرایش دسترسی ها در پروگرام منیجر");
|
|
||||||
//}
|
|
||||||
|
|
||||||
//var parameters = new CreateProgramManagerRole
|
|
||||||
//{
|
|
||||||
// RoleName = command.Name,
|
|
||||||
// Permissions = pmPermissions,
|
|
||||||
// GozareshgirRoleId = role.id
|
|
||||||
|
|
||||||
//};
|
|
||||||
|
|
||||||
//var url = "api/role";
|
|
||||||
|
|
||||||
|
|
||||||
//var response = InternalApiCaller.PostAsync<CreateProgramManagerRole, ApiResponse>(
|
|
||||||
// url,
|
|
||||||
// key,
|
|
||||||
// parameters
|
|
||||||
//);
|
|
||||||
|
|
||||||
|
|
||||||
//if (!response.Success)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed("ارتباط با اپلیکیش پروگرام منیجر برقرار نشد");
|
|
||||||
//}
|
|
||||||
|
|
||||||
//if (!response.Result.isSuccess)
|
|
||||||
//{
|
|
||||||
// _unitOfWork.RollbackAccountContext();
|
|
||||||
// return operation.Failed(response.Result.errorMessage);
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
_unitOfWork.CommitAccountContext();
|
|
||||||
return operation.Succcedded();
|
return operation.Succcedded();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -245,23 +70,4 @@ public class RoleApplication : IRoleApplication
|
|||||||
{
|
{
|
||||||
return _roleRepository.List();
|
return _roleRepository.List();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public async Task<SelectList> GetPmRoleList(long? gozareshgirRoleId)
|
|
||||||
{
|
|
||||||
var rolse = await _pmRoleQueryService.GetPmRoleList(gozareshgirRoleId);
|
|
||||||
return new SelectList(rolse, "Id", "RoleName");
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<List<GetPmRolesDto>> GetPmRoleListToEdit(long? gozareshgirRoleId)
|
|
||||||
{
|
|
||||||
return await _pmRoleQueryService.GetPmRoleList(gozareshgirRoleId);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -5,11 +5,14 @@ using AccountManagement.Domain.AccountAgg;
|
|||||||
using AccountManagement.Domain.CameraAccountAgg;
|
using AccountManagement.Domain.CameraAccountAgg;
|
||||||
using AccountManagement.Domain.SubAccountAgg;
|
using AccountManagement.Domain.SubAccountAgg;
|
||||||
using AccountManagement.Domain.SubAccountRoleAgg;
|
using AccountManagement.Domain.SubAccountRoleAgg;
|
||||||
|
using Company.Domain.WorkshopAccountAgg;
|
||||||
using Company.Domain.WorkshopSubAccountAgg;
|
using Company.Domain.WorkshopSubAccountAgg;
|
||||||
|
using CompanyManagment.App.Contracts.Workshop;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
using static Microsoft.EntityFrameworkCore.DbLoggerCategory.Database;
|
||||||
|
|
||||||
|
|
||||||
namespace AccountManagement.Application
|
namespace AccountManagement.Application
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using System.Collections.Generic;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
using AccountManagement.Application.Contracts.TaskSubject;
|
using AccountManagement.Application.Contracts.TaskSubject;
|
||||||
using AccountManagement.Domain.TaskSubjectAgg;
|
using AccountManagement.Domain.TaskSubjectAgg;
|
||||||
|
using static Microsoft.EntityFrameworkCore.DbLoggerCategory.Database;
|
||||||
|
|
||||||
namespace AccountManagement.Application;
|
namespace AccountManagement.Application;
|
||||||
|
|
||||||
|
|||||||
@@ -1,13 +1,13 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="10.0.1" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="8.0.4" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="10.0.1" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="8.0.4" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="10.0.1">
|
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="8.0.4">
|
||||||
<PrivateAssets>all</PrivateAssets>
|
<PrivateAssets>all</PrivateAssets>
|
||||||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||||
</PackageReference>
|
</PackageReference>
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ public interface IAccountLeftworkRepository : IRepository<long, AccountLeftWork>
|
|||||||
{
|
{
|
||||||
(string StartWorkFa, string LeftWorkFa) GetByAccountId(long accountId);
|
(string StartWorkFa, string LeftWorkFa) GetByAccountId(long accountId);
|
||||||
List<WorkshopAccountlistViewModel> WorkshopList(long accountId);
|
List<WorkshopAccountlistViewModel> WorkshopList(long accountId);
|
||||||
// List<WorkshopSelectList> GetAllWorkshops();
|
List<WorkshopSelectList> GetAllWorkshops();
|
||||||
|
|
||||||
OperationResult CopyWorkshopToNewAccount(long currentAccountId, long newAccountId);
|
OperationResult CopyWorkshopToNewAccount(long currentAccountId, long newAccountId);
|
||||||
|
|
||||||
|
|||||||
@@ -1,16 +1,9 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http" Version="2.3.0" />
|
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.3.0" />
|
|
||||||
<PackageReference Include="Microsoft.Extensions.Caching.Memory" Version="10.0.1" />
|
|
||||||
<PackageReference Include="System.Security.Cryptography.Xml" Version="10.0.1" />
|
|
||||||
</ItemGroup>
|
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ProjectReference Include="..\0_Framework\0_Framework.csproj" />
|
<ProjectReference Include="..\0_Framework\0_Framework.csproj" />
|
||||||
<ProjectReference Include="..\AccountManagement.Application.Contracts\AccountManagement.Application.Contracts.csproj" />
|
<ProjectReference Include="..\AccountManagement.Application.Contracts\AccountManagement.Application.Contracts.csproj" />
|
||||||
|
|||||||
@@ -1,155 +0,0 @@
|
|||||||
using Newtonsoft.Json;
|
|
||||||
using System.Net.Http;
|
|
||||||
using System.Text;
|
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using Microsoft.Extensions.Configuration;
|
|
||||||
|
|
||||||
namespace AccountManagement.Domain.InternalApiCaller;
|
|
||||||
|
|
||||||
public class ApiResult<T>
|
|
||||||
{
|
|
||||||
public bool Success { get; set; }
|
|
||||||
public T Result { get; set; }
|
|
||||||
public string Error { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class InternalApiCaller
|
|
||||||
{
|
|
||||||
private static string _baseUrl = "";
|
|
||||||
|
|
||||||
public static void SetBaseUrl(string baseUrl)
|
|
||||||
{
|
|
||||||
_baseUrl = baseUrl.TrimEnd('/'); // حذف / اضافی
|
|
||||||
}
|
|
||||||
/// <summary>
|
|
||||||
///api post متد
|
|
||||||
/// </summary>
|
|
||||||
/// <typeparam name="TRequest"></typeparam>
|
|
||||||
/// <typeparam name="TResponse"></typeparam>
|
|
||||||
/// <param name="url"></param>
|
|
||||||
/// <param name="internalKey"></param>
|
|
||||||
/// <param name="body"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
public static ApiResult<TResponse> PostAsync<TRequest, TResponse>(
|
|
||||||
string url,
|
|
||||||
string internalKey,
|
|
||||||
TRequest body
|
|
||||||
)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var client = new HttpClient();
|
|
||||||
|
|
||||||
// ساخت URL نهایی
|
|
||||||
var finalUrl = $"{_baseUrl}/{url.TrimStart('/')}";
|
|
||||||
|
|
||||||
var request = new HttpRequestMessage(HttpMethod.Post, finalUrl);
|
|
||||||
|
|
||||||
request.Headers.Add("X-INTERNAL-KEY", internalKey);
|
|
||||||
|
|
||||||
var json = JsonConvert.SerializeObject(body);
|
|
||||||
request.Content = new StringContent(json, Encoding.UTF8, "application/json");
|
|
||||||
|
|
||||||
var response = client.SendAsync(request).GetAwaiter().GetResult();
|
|
||||||
|
|
||||||
if (!response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
return new ApiResult<TResponse>
|
|
||||||
{
|
|
||||||
Success = false,
|
|
||||||
Error = $"HTTP Error: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
var text = response.Content.ReadAsStringAsync().GetAwaiter().GetResult();
|
|
||||||
var deserialized = JsonConvert.DeserializeObject<TResponse>(text);
|
|
||||||
|
|
||||||
return new ApiResult<TResponse>
|
|
||||||
{
|
|
||||||
Success = true,
|
|
||||||
Result = deserialized
|
|
||||||
};
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
return new ApiResult<TResponse>
|
|
||||||
{
|
|
||||||
Success = false,
|
|
||||||
Error = ex.Message
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Api Get متد
|
|
||||||
/// </summary>
|
|
||||||
/// <typeparam name="TResponse"></typeparam>
|
|
||||||
/// <param name="url"></param>
|
|
||||||
/// <param name="internalKey"></param>
|
|
||||||
/// <param name="parameters"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
public static ApiResult<TResponse> GetAsync<TResponse>(
|
|
||||||
string url,
|
|
||||||
string internalKey,
|
|
||||||
Dictionary<string, object> parameters = null
|
|
||||||
)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (parameters != null && parameters.Any())
|
|
||||||
{
|
|
||||||
var query = string.Join("&",
|
|
||||||
parameters
|
|
||||||
.Where(p => p.Value != null)
|
|
||||||
.Select(p => $"{p.Key}={p.Value}")
|
|
||||||
);
|
|
||||||
|
|
||||||
url += url.Contains("?") ? "&" + query : "?" + query;
|
|
||||||
}
|
|
||||||
|
|
||||||
// ساخت URL نهایی
|
|
||||||
var finalUrl = $"{_baseUrl}/{url.TrimStart('/')}";
|
|
||||||
|
|
||||||
var client = new HttpClient();
|
|
||||||
var request = new HttpRequestMessage(HttpMethod.Get, finalUrl);
|
|
||||||
|
|
||||||
request.Headers.Add("X-INTERNAL-KEY", internalKey);
|
|
||||||
|
|
||||||
var response = client.SendAsync(request).GetAwaiter().GetResult();
|
|
||||||
|
|
||||||
if (!response.IsSuccessStatusCode)
|
|
||||||
{
|
|
||||||
return new ApiResult<TResponse>
|
|
||||||
{
|
|
||||||
Success = false,
|
|
||||||
Error = $"HTTP Error: {response.StatusCode}"
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
var text = response.Content.ReadAsStringAsync().GetAwaiter().GetResult();
|
|
||||||
var deserialized = JsonConvert.DeserializeObject<TResponse>(text);
|
|
||||||
|
|
||||||
return new ApiResult<TResponse>
|
|
||||||
{
|
|
||||||
Success = true,
|
|
||||||
Result = deserialized
|
|
||||||
};
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
return new ApiResult<TResponse>
|
|
||||||
{
|
|
||||||
Success = false,
|
|
||||||
Error = ex.Message
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
using AccountManagement.Domain.AccountAgg;
|
using AccountManagement.Domain.AccountAgg;
|
||||||
using AccountMangement.Infrastructure.EFCore.Mappings;
|
using AccountMangement.Infrastructure.EFCore.Mappings;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System;
|
using System;
|
||||||
@@ -26,6 +26,7 @@ using AccountManagement.Domain.SubAccountPermissionSubtitle2Agg;
|
|||||||
using AccountManagement.Domain.SubAccountPermissionSubtitle3Agg;
|
using AccountManagement.Domain.SubAccountPermissionSubtitle3Agg;
|
||||||
using AccountManagement.Domain.SubAccountPermissionSubtitle4Agg;
|
using AccountManagement.Domain.SubAccountPermissionSubtitle4Agg;
|
||||||
using AccountManagement.Domain.SubAccountRoleAgg;
|
using AccountManagement.Domain.SubAccountRoleAgg;
|
||||||
|
using AccountMangement.Infrastructure.EFCore.Seed;
|
||||||
using AccountManagement.Domain.TaskScheduleAgg;
|
using AccountManagement.Domain.TaskScheduleAgg;
|
||||||
|
|
||||||
namespace AccountMangement.Infrastructure.EFCore
|
namespace AccountMangement.Infrastructure.EFCore
|
||||||
@@ -59,10 +60,9 @@ namespace AccountMangement.Infrastructure.EFCore
|
|||||||
|
|
||||||
public DbSet<TaskSchedule> TaskSchedules { get; set; }
|
public DbSet<TaskSchedule> TaskSchedules { get; set; }
|
||||||
|
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#region Pooya
|
#region Pooya
|
||||||
public DbSet<SubAccount> SubAccounts { get; set; }
|
public DbSet<SubAccount> SubAccounts { get; set; }
|
||||||
public DbSet<SubAccountRole> SubAccountRoles { get; set; }
|
public DbSet<SubAccountRole> SubAccountRoles { get; set; }
|
||||||
|
|||||||
@@ -1,15 +1,13 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Azure.Identity" Version="1.17.1" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="8.0.4" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http" Version="2.3.0" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="8.0.4" />
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="10.0.1" />
|
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="8.0.4">
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="10.0.1" />
|
|
||||||
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="10.0.1">
|
|
||||||
<PrivateAssets>all</PrivateAssets>
|
<PrivateAssets>all</PrivateAssets>
|
||||||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||||
</PackageReference>
|
</PackageReference>
|
||||||
@@ -20,12 +18,4 @@
|
|||||||
<ProjectReference Include="..\Company.Domain\Company.Domain.csproj" />
|
<ProjectReference Include="..\Company.Domain\Company.Domain.csproj" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
|
||||||
<Folder Include="Services\" />
|
|
||||||
</ItemGroup>
|
|
||||||
|
|
||||||
<ItemGroup>
|
|
||||||
<Compile Remove="Mappings\BugReportMapping.cs" />
|
|
||||||
</ItemGroup>
|
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -1,31 +0,0 @@
|
|||||||
using System;
|
|
||||||
using Microsoft.EntityFrameworkCore.Migrations;
|
|
||||||
|
|
||||||
#nullable disable
|
|
||||||
|
|
||||||
namespace AccountMangement.Infrastructure.EFCore.Migrations
|
|
||||||
{
|
|
||||||
/// <inheritdoc />
|
|
||||||
public partial class addprogrammangerbooinaccount : Migration
|
|
||||||
{
|
|
||||||
/// <inheritdoc />
|
|
||||||
protected override void Up(MigrationBuilder migrationBuilder)
|
|
||||||
{
|
|
||||||
migrationBuilder.AddColumn<bool>(
|
|
||||||
name: "IsProgramManagerUser",
|
|
||||||
table: "Accounts",
|
|
||||||
type: "bit",
|
|
||||||
nullable: false,
|
|
||||||
defaultValue: false);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <inheritdoc />
|
|
||||||
protected override void Down(MigrationBuilder migrationBuilder)
|
|
||||||
{
|
|
||||||
migrationBuilder.DropColumn(
|
|
||||||
name: "IsProgramManagerUser",
|
|
||||||
table: "Accounts");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
File diff suppressed because it is too large
Load Diff
@@ -1,29 +0,0 @@
|
|||||||
using Microsoft.EntityFrameworkCore.Migrations;
|
|
||||||
|
|
||||||
#nullable disable
|
|
||||||
|
|
||||||
namespace AccountMangement.Infrastructure.EFCore.Migrations
|
|
||||||
{
|
|
||||||
/// <inheritdoc />
|
|
||||||
public partial class romoveIsProgramManagerUserFromAccount : Migration
|
|
||||||
{
|
|
||||||
/// <inheritdoc />
|
|
||||||
protected override void Up(MigrationBuilder migrationBuilder)
|
|
||||||
{
|
|
||||||
migrationBuilder.DropColumn(
|
|
||||||
name: "IsProgramManagerUser",
|
|
||||||
table: "Accounts");
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <inheritdoc />
|
|
||||||
protected override void Down(MigrationBuilder migrationBuilder)
|
|
||||||
{
|
|
||||||
migrationBuilder.AddColumn<bool>(
|
|
||||||
name: "IsProgramManagerUser",
|
|
||||||
table: "Accounts",
|
|
||||||
type: "bit",
|
|
||||||
nullable: false,
|
|
||||||
defaultValue: false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -17,7 +17,7 @@ namespace AccountMangement.Infrastructure.EFCore.Migrations
|
|||||||
{
|
{
|
||||||
#pragma warning disable 612, 618
|
#pragma warning disable 612, 618
|
||||||
modelBuilder
|
modelBuilder
|
||||||
.HasAnnotation("ProductVersion", "10.0.1")
|
.HasAnnotation("ProductVersion", "8.0.10")
|
||||||
.HasAnnotation("Relational:MaxIdentifierLength", 128);
|
.HasAnnotation("Relational:MaxIdentifierLength", 128);
|
||||||
|
|
||||||
SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder);
|
SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder);
|
||||||
@@ -377,87 +377,6 @@ namespace AccountMangement.Infrastructure.EFCore.Migrations
|
|||||||
b.ToTable("Medias", (string)null);
|
b.ToTable("Medias", (string)null);
|
||||||
});
|
});
|
||||||
|
|
||||||
modelBuilder.Entity("AccountManagement.Domain.PmDomains.PmRoleAgg.PmRole", b =>
|
|
||||||
{
|
|
||||||
b.Property<long>("id")
|
|
||||||
.ValueGeneratedOnAdd()
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<long>("id"));
|
|
||||||
|
|
||||||
b.Property<DateTime>("CreationDate")
|
|
||||||
.HasColumnType("datetime2");
|
|
||||||
|
|
||||||
b.Property<long?>("GozareshgirRoleId")
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
b.Property<string>("RoleName")
|
|
||||||
.IsRequired()
|
|
||||||
.HasMaxLength(100)
|
|
||||||
.HasColumnType("nvarchar(100)");
|
|
||||||
|
|
||||||
b.HasKey("id");
|
|
||||||
|
|
||||||
b.ToTable("PmRoles", null, t =>
|
|
||||||
{
|
|
||||||
t.ExcludeFromMigrations();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
modelBuilder.Entity("AccountManagement.Domain.PmDomains.PmUserAgg.PmUser", b =>
|
|
||||||
{
|
|
||||||
b.Property<long>("id")
|
|
||||||
.ValueGeneratedOnAdd()
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<long>("id"));
|
|
||||||
|
|
||||||
b.Property<long?>("AccountId")
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
b.Property<DateTime>("CreationDate")
|
|
||||||
.HasColumnType("datetime2");
|
|
||||||
|
|
||||||
b.Property<string>("Email")
|
|
||||||
.HasMaxLength(150)
|
|
||||||
.HasColumnType("nvarchar(150)");
|
|
||||||
|
|
||||||
b.Property<string>("FullName")
|
|
||||||
.IsRequired()
|
|
||||||
.HasMaxLength(100)
|
|
||||||
.HasColumnType("nvarchar(100)");
|
|
||||||
|
|
||||||
b.Property<bool>("IsActive")
|
|
||||||
.HasColumnType("bit");
|
|
||||||
|
|
||||||
b.Property<string>("Mobile")
|
|
||||||
.IsRequired()
|
|
||||||
.HasMaxLength(20)
|
|
||||||
.HasColumnType("nvarchar(20)");
|
|
||||||
|
|
||||||
b.Property<string>("Password")
|
|
||||||
.IsRequired()
|
|
||||||
.HasMaxLength(1000)
|
|
||||||
.HasColumnType("nvarchar(1000)");
|
|
||||||
|
|
||||||
b.Property<string>("ProfilePhotoPath")
|
|
||||||
.HasMaxLength(500)
|
|
||||||
.HasColumnType("nvarchar(500)");
|
|
||||||
|
|
||||||
b.Property<string>("UserName")
|
|
||||||
.IsRequired()
|
|
||||||
.HasMaxLength(100)
|
|
||||||
.HasColumnType("nvarchar(100)");
|
|
||||||
|
|
||||||
b.Property<string>("VerifyCode")
|
|
||||||
.HasMaxLength(10)
|
|
||||||
.HasColumnType("nvarchar(10)");
|
|
||||||
|
|
||||||
b.HasKey("id");
|
|
||||||
|
|
||||||
b.ToTable("Users", (string)null);
|
|
||||||
});
|
|
||||||
|
|
||||||
modelBuilder.Entity("AccountManagement.Domain.PositionAgg.Position", b =>
|
modelBuilder.Entity("AccountManagement.Domain.PositionAgg.Position", b =>
|
||||||
{
|
{
|
||||||
b.Property<long>("id")
|
b.Property<long>("id")
|
||||||
@@ -1082,71 +1001,6 @@ namespace AccountMangement.Infrastructure.EFCore.Migrations
|
|||||||
b.Navigation("Media");
|
b.Navigation("Media");
|
||||||
});
|
});
|
||||||
|
|
||||||
modelBuilder.Entity("AccountManagement.Domain.PmDomains.PmRoleAgg.PmRole", b =>
|
|
||||||
{
|
|
||||||
b.OwnsMany("AccountManagement.Domain.PmDomains.PmPermissionAgg.PmPermission", "PmPermission", b1 =>
|
|
||||||
{
|
|
||||||
b1.Property<long>("Id")
|
|
||||||
.ValueGeneratedOnAdd()
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
SqlServerPropertyBuilderExtensions.UseIdentityColumn(b1.Property<long>("Id"));
|
|
||||||
|
|
||||||
b1.Property<int>("Code")
|
|
||||||
.HasColumnType("int");
|
|
||||||
|
|
||||||
b1.Property<long>("Roleid")
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
b1.HasKey("Id");
|
|
||||||
|
|
||||||
b1.HasIndex("Roleid");
|
|
||||||
|
|
||||||
b1.ToTable("PmRolePermissions", null, t =>
|
|
||||||
{
|
|
||||||
t.ExcludeFromMigrations();
|
|
||||||
});
|
|
||||||
|
|
||||||
b1.WithOwner("Role")
|
|
||||||
.HasForeignKey("Roleid");
|
|
||||||
|
|
||||||
b1.Navigation("Role");
|
|
||||||
});
|
|
||||||
|
|
||||||
b.Navigation("PmPermission");
|
|
||||||
});
|
|
||||||
|
|
||||||
modelBuilder.Entity("AccountManagement.Domain.PmDomains.PmUserAgg.PmUser", b =>
|
|
||||||
{
|
|
||||||
b.OwnsMany("AccountManagement.Domain.PmDomains.PmRoleUserAgg.PmRoleUser", "RoleUser", b1 =>
|
|
||||||
{
|
|
||||||
b1.Property<long>("Id")
|
|
||||||
.ValueGeneratedOnAdd()
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
SqlServerPropertyBuilderExtensions.UseIdentityColumn(b1.Property<long>("Id"));
|
|
||||||
|
|
||||||
b1.Property<long>("RoleId")
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
b1.Property<long>("Userid")
|
|
||||||
.HasColumnType("bigint");
|
|
||||||
|
|
||||||
b1.HasKey("Id");
|
|
||||||
|
|
||||||
b1.HasIndex("Userid");
|
|
||||||
|
|
||||||
b1.ToTable("RoleUsers", (string)null);
|
|
||||||
|
|
||||||
b1.WithOwner("User")
|
|
||||||
.HasForeignKey("Userid");
|
|
||||||
|
|
||||||
b1.Navigation("User");
|
|
||||||
});
|
|
||||||
|
|
||||||
b.Navigation("RoleUser");
|
|
||||||
});
|
|
||||||
|
|
||||||
modelBuilder.Entity("AccountManagement.Domain.RoleAgg.Role", b =>
|
modelBuilder.Entity("AccountManagement.Domain.RoleAgg.Role", b =>
|
||||||
{
|
{
|
||||||
b.OwnsMany("AccountManagement.Domain.RoleAgg.Permission", "Permissions", b1 =>
|
b.OwnsMany("AccountManagement.Domain.RoleAgg.Permission", "Permissions", b1 =>
|
||||||
|
|||||||
@@ -18,13 +18,14 @@ public class AccountLeftworkRepository : RepositoryBase<long, AccountLeftWork>,
|
|||||||
{
|
{
|
||||||
private readonly AccountContext _accountContext;
|
private readonly AccountContext _accountContext;
|
||||||
private readonly IWorkshopAccountRepository _workshopAccountRepository;
|
private readonly IWorkshopAccountRepository _workshopAccountRepository;
|
||||||
|
private readonly IWorkshopApplication _workshopApplication;
|
||||||
|
|
||||||
public AccountLeftworkRepository(AccountContext accountContext,
|
public AccountLeftworkRepository(AccountContext accountContext, IWorkshopAccountRepository workshopAccountRepository, IWorkshopApplication workshopApplication) : base(accountContext)
|
||||||
IWorkshopAccountRepository workshopAccountRepository) : base(accountContext)
|
|
||||||
{
|
{
|
||||||
_accountContext = accountContext;
|
_accountContext = accountContext;
|
||||||
_workshopAccountRepository = workshopAccountRepository;
|
_workshopAccountRepository = workshopAccountRepository;
|
||||||
}
|
_workshopApplication = workshopApplication;
|
||||||
|
}
|
||||||
|
|
||||||
public (string StartWorkFa, string LeftWorkFa) GetByAccountId(long accountId)
|
public (string StartWorkFa, string LeftWorkFa) GetByAccountId(long accountId)
|
||||||
{
|
{
|
||||||
@@ -57,14 +58,14 @@ public class AccountLeftworkRepository : RepositoryBase<long, AccountLeftWork>,
|
|||||||
}).ToList();
|
}).ToList();
|
||||||
}
|
}
|
||||||
|
|
||||||
// public List<WorkshopSelectList> GetAllWorkshops()
|
public List<WorkshopSelectList> GetAllWorkshops()
|
||||||
// {
|
{
|
||||||
// return this._workshopApplication.GetWorkshopAll().Select(x => new WorkshopSelectList()
|
return this._workshopApplication.GetWorkshopAll().Select(x => new WorkshopSelectList()
|
||||||
// {
|
{
|
||||||
// Id = x.Id,
|
Id = x.Id,
|
||||||
// WorkshopFullName = x.WorkshopFullName
|
WorkshopFullName = x.WorkshopFullName
|
||||||
// }).ToList();
|
}).ToList();
|
||||||
// }
|
}
|
||||||
|
|
||||||
public OperationResult CopyWorkshopToNewAccount(long currentAccountId, long newAccountId)
|
public OperationResult CopyWorkshopToNewAccount(long currentAccountId, long newAccountId)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,175 +0,0 @@
|
|||||||
# سیستم گزارش خرابی (Bug Report System)
|
|
||||||
|
|
||||||
## نمای کلی
|
|
||||||
|
|
||||||
این سیستم برای جمعآوری، ذخیره و مدیریت گزارشهای خرابی از تطبیق موبایلی طراحی شده است.
|
|
||||||
|
|
||||||
## ساختار فایلها
|
|
||||||
|
|
||||||
### Domain Layer
|
|
||||||
- `AccountManagement.Domain/BugReportAgg/`
|
|
||||||
- `BugReport.cs` - موجودیت اصلی
|
|
||||||
- `BugReportLog.cs` - لاگهای گزارش
|
|
||||||
- `BugReportScreenshot.cs` - تصاویر ضمیمه شده
|
|
||||||
|
|
||||||
### Application Contracts
|
|
||||||
- `AccountManagement.Application.Contracts/BugReport/`
|
|
||||||
- `IBugReportApplication.cs` - اینترفیس سرویس
|
|
||||||
- `CreateBugReportCommand.cs` - درخواست ایجاد
|
|
||||||
- `EditBugReportCommand.cs` - درخواست ویرایش
|
|
||||||
- `BugReportViewModel.cs` - نمایش لیست
|
|
||||||
- `BugReportDetailViewModel.cs` - نمایش جزئیات
|
|
||||||
- `IBugReportRepository.cs` - اینترفیس Repository
|
|
||||||
|
|
||||||
### Application Service
|
|
||||||
- `AccountManagement.Application/BugReportApplication.cs` - پیادهسازی سرویس
|
|
||||||
|
|
||||||
### Infrastructure
|
|
||||||
- `AccountMangement.Infrastructure.EFCore/`
|
|
||||||
- `Mappings/BugReportMapping.cs`
|
|
||||||
- `Mappings/BugReportLogMapping.cs`
|
|
||||||
- `Mappings/BugReportScreenshotMapping.cs`
|
|
||||||
- `Repository/BugReportRepository.cs`
|
|
||||||
|
|
||||||
### API Controller
|
|
||||||
- `ServiceHost/Controllers/BugReportController.cs`
|
|
||||||
|
|
||||||
### Admin Pages
|
|
||||||
- `ServiceHost/Areas/AdminNew/Pages/BugReport/`
|
|
||||||
- `BugReportPageModel.cs` - base model
|
|
||||||
- `Index.cshtml.cs / Index.cshtml` - لیست گزارشها
|
|
||||||
- `Details.cshtml.cs / Details.cshtml` - جزئیات کامل
|
|
||||||
- `Edit.cshtml.cs / Edit.cshtml` - ویرایش وضعیت/اولویت
|
|
||||||
- `Delete.cshtml.cs / Delete.cshtml` - حذف
|
|
||||||
|
|
||||||
## روش استفاده
|
|
||||||
|
|
||||||
### 1. ثبت گزارش از موبایل
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
POST /api/bugreport/submit
|
|
||||||
|
|
||||||
{
|
|
||||||
"title": "برنامه هنگام ورود خراب میشود",
|
|
||||||
"description": "هنگام وارد کردن نام کاربری، برنامه کرش میکند",
|
|
||||||
"userEmail": "user@example.com",
|
|
||||||
"deviceModel": "Samsung Galaxy S21",
|
|
||||||
"osVersion": "Android 12",
|
|
||||||
"platform": "Android",
|
|
||||||
"manufacturer": "Samsung",
|
|
||||||
"deviceId": "device-unique-id",
|
|
||||||
"screenResolution": "1440x3200",
|
|
||||||
"memoryInMB": 8000,
|
|
||||||
"storageInMB": 256000,
|
|
||||||
"batteryLevel": 75,
|
|
||||||
"isCharging": false,
|
|
||||||
"networkType": "4G",
|
|
||||||
"appVersion": "1.0.0",
|
|
||||||
"buildNumber": "100",
|
|
||||||
"packageName": "com.example.app",
|
|
||||||
"installTime": "2024-01-01T10:00:00Z",
|
|
||||||
"lastUpdateTime": "2024-12-01T14:30:00Z",
|
|
||||||
"flavor": "production",
|
|
||||||
"type": 1, // Crash = 1
|
|
||||||
"priority": 2, // High = 2
|
|
||||||
"stackTrace": "...",
|
|
||||||
"logs": ["log1", "log2"],
|
|
||||||
"screenshots": ["base64-encoded-image-1"]
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2. دسترسی به Admin Panel
|
|
||||||
|
|
||||||
```
|
|
||||||
https://yourdomain.com/AdminNew/BugReport
|
|
||||||
```
|
|
||||||
|
|
||||||
**صفحات موجود:**
|
|
||||||
- **Index** - لیست تمام گزارشها با فیلترها
|
|
||||||
- **Details** - نمایش جزئیات کامل شامل:
|
|
||||||
- معلومات کاربر و گزارش
|
|
||||||
- معلومات دستگاه
|
|
||||||
- معلومات برنامه
|
|
||||||
- لاگها
|
|
||||||
- تصاویر
|
|
||||||
- Stack Trace
|
|
||||||
- **Edit** - تغییر وضعیت و اولویت
|
|
||||||
- **Delete** - حذف گزارش
|
|
||||||
|
|
||||||
### 3. درخواستهای API
|
|
||||||
|
|
||||||
#### دریافت لیست
|
|
||||||
```
|
|
||||||
GET /api/bugreport/list?type=1&priority=2&status=1&searchTerm=crash&pageNumber=1&pageSize=10
|
|
||||||
```
|
|
||||||
|
|
||||||
#### دریافت جزئیات
|
|
||||||
```
|
|
||||||
GET /api/bugreport/{id}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### ویرایش
|
|
||||||
```
|
|
||||||
PUT /api/bugreport/{id}
|
|
||||||
|
|
||||||
{
|
|
||||||
"id": 1,
|
|
||||||
"priority": 2,
|
|
||||||
"status": 3
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
#### حذف
|
|
||||||
```
|
|
||||||
DELETE /api/bugreport/{id}
|
|
||||||
```
|
|
||||||
|
|
||||||
## انواع (Enums)
|
|
||||||
|
|
||||||
### BugReportType
|
|
||||||
- `1` - Crash (کرش)
|
|
||||||
- `2` - UI (مشکل رابط)
|
|
||||||
- `3` - Performance (عملکرد)
|
|
||||||
- `4` - Feature (فیچر)
|
|
||||||
- `5` - Network (شبکه)
|
|
||||||
- `6` - Camera (دوربین)
|
|
||||||
- `7` - FaceRecognition (تشخیص چهره)
|
|
||||||
- `8` - Database (دیتابیس)
|
|
||||||
- `9` - Login (ورود)
|
|
||||||
- `10` - Other (سایر)
|
|
||||||
|
|
||||||
### BugPriority
|
|
||||||
- `1` - Critical (بحرانی)
|
|
||||||
- `2` - High (بالا)
|
|
||||||
- `3` - Medium (متوسط)
|
|
||||||
- `4` - Low (پایین)
|
|
||||||
|
|
||||||
### BugReportStatus
|
|
||||||
- `1` - Open (باز)
|
|
||||||
- `2` - InProgress (در حال بررسی)
|
|
||||||
- `3` - Fixed (رفع شده)
|
|
||||||
- `4` - Closed (بسته شده)
|
|
||||||
- `5` - Reopened (مجدداً باز)
|
|
||||||
|
|
||||||
## Migration
|
|
||||||
|
|
||||||
برای اعمال تغییرات دیتابیس:
|
|
||||||
|
|
||||||
```powershell
|
|
||||||
Add-Migration AddBugReportTables
|
|
||||||
Update-Database
|
|
||||||
```
|
|
||||||
|
|
||||||
## نکات مهم
|
|
||||||
|
|
||||||
1. **تصاویر**: تصاویر به صورت Base64 encoded ذخیره میشوند
|
|
||||||
2. **لاگها**: تمام لاگها به صورت جدا ذخیره میشوند
|
|
||||||
3. **وضعیت پیشفرض**: وقتی گزارش ثبت میشود، وضعیت آن "Open" است
|
|
||||||
4. **تاریخ**: تاریخ ایجاد و بروزرسانی خودکار ثبت میشود
|
|
||||||
|
|
||||||
## Security
|
|
||||||
|
|
||||||
- API endpoints از `authentication` محافظت میشوند
|
|
||||||
- Admin pages تنها برای کاربرانی با دسترسی AdminArea قابل دسترس هستند
|
|
||||||
- حذف و ویرایش نیاز به تأیید دارد
|
|
||||||
|
|
||||||
@@ -1,25 +0,0 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
|
||||||
|
|
||||||
<PropertyGroup>
|
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
|
||||||
<Nullable>enable</Nullable>
|
|
||||||
<ImplicitUsings>enable</ImplicitUsings>
|
|
||||||
<AssemblyName>BackgroundInstitutionContract.Task</AssemblyName>
|
|
||||||
<RootNamespace>BackgroundInstitutionContract.Task</RootNamespace>
|
|
||||||
</PropertyGroup>
|
|
||||||
|
|
||||||
<ItemGroup>
|
|
||||||
<ProjectReference Include="..\..\0_Framework\0_Framework.csproj" />
|
|
||||||
<ProjectReference Include="..\..\AccountManagement.Configuration\AccountManagement.Configuration.csproj" />
|
|
||||||
<ProjectReference Include="..\..\PersonalContractingParty.Config\PersonalContractingParty.Config.csproj" />
|
|
||||||
<ProjectReference Include="..\..\ProgramManager\src\Infrastructure\GozareshgirProgramManager.Infrastructure\GozareshgirProgramManager.Infrastructure.csproj" />
|
|
||||||
<ProjectReference Include="..\..\Query.Bootstrapper\Query.Bootstrapper.csproj" />
|
|
||||||
<ProjectReference Include="..\..\WorkFlow\Infrastructure\WorkFlow.Infrastructure.Config\WorkFlow.Infrastructure.Config.csproj" />
|
|
||||||
</ItemGroup>
|
|
||||||
|
|
||||||
<ItemGroup>
|
|
||||||
<PackageReference Include="Serilog.AspNetCore" Version="10.0.0" />
|
|
||||||
<PackageReference Include="Serilog.Sinks.File" Version="7.0.0" />
|
|
||||||
</ItemGroup>
|
|
||||||
|
|
||||||
</Project>
|
|
||||||
@@ -1,32 +0,0 @@
|
|||||||
using _0_Framework.Application;
|
|
||||||
|
|
||||||
namespace BackgroundInstitutionContract.Task
|
|
||||||
{
|
|
||||||
public class FileUploader : IFileUploader
|
|
||||||
{
|
|
||||||
private readonly IWebHostEnvironment _webHostEnvironment;
|
|
||||||
|
|
||||||
public FileUploader(IWebHostEnvironment webHostEnvironment)
|
|
||||||
{
|
|
||||||
_webHostEnvironment = webHostEnvironment;
|
|
||||||
}
|
|
||||||
|
|
||||||
public string Upload(IFormFile file, string path)
|
|
||||||
{
|
|
||||||
if (file == null) return "";
|
|
||||||
|
|
||||||
var directoryPath = $"{_webHostEnvironment.WebRootPath}\\ProductPictures\\{path}";
|
|
||||||
|
|
||||||
if (!Directory.Exists(directoryPath))
|
|
||||||
Directory.CreateDirectory(directoryPath);
|
|
||||||
|
|
||||||
var fileName = $"{DateTime.Now.ToFileName()}-{file.FileName}";
|
|
||||||
var filePath = $"{directoryPath}\\{fileName}";
|
|
||||||
var output = System.IO.File.Create(filePath);
|
|
||||||
file.CopyTo(output);
|
|
||||||
return $"{path}/{fileName}";
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,203 +0,0 @@
|
|||||||
|
|
||||||
using _0_Framework.Application;
|
|
||||||
using _0_Framework.Application.Sms;
|
|
||||||
using Company.Domain.ContarctingPartyAgg;
|
|
||||||
using Company.Domain.InstitutionContractAgg;
|
|
||||||
using Hangfire;
|
|
||||||
|
|
||||||
namespace BackgroundInstitutionContract.Task.Jobs;
|
|
||||||
|
|
||||||
public class JobSchedulerRegistrator
|
|
||||||
{
|
|
||||||
private readonly IBackgroundJobClient _backgroundJobClient;
|
|
||||||
private readonly SmsReminder _smsReminder;
|
|
||||||
private readonly IInstitutionContractRepository _institutionContractRepository;
|
|
||||||
private static DateTime? _lastRunCreateTransaction;
|
|
||||||
private static DateTime? _lastRunSendMonthlySms;
|
|
||||||
private readonly ISmsService _smsService;
|
|
||||||
private readonly ILogger<JobSchedulerRegistrator> _logger;
|
|
||||||
|
|
||||||
|
|
||||||
public JobSchedulerRegistrator(SmsReminder smsReminder, IBackgroundJobClient backgroundJobClient, IInstitutionContractRepository institutionContractRepository, ISmsService smsService, ILogger<JobSchedulerRegistrator> logger)
|
|
||||||
{
|
|
||||||
_smsReminder = smsReminder;
|
|
||||||
_backgroundJobClient = backgroundJobClient;
|
|
||||||
_institutionContractRepository = institutionContractRepository;
|
|
||||||
_smsService = smsService;
|
|
||||||
_logger = logger;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Register()
|
|
||||||
{
|
|
||||||
_logger.LogInformation("hangfire Started");
|
|
||||||
RecurringJob.AddOrUpdate(
|
|
||||||
"InstitutionContract.CreateFinancialTransaction",
|
|
||||||
() => CreateFinancialTransaction(),
|
|
||||||
"*/30 * * * *" // هر 30 دقیقه یکبار چک کن
|
|
||||||
);
|
|
||||||
|
|
||||||
RecurringJob.AddOrUpdate(
|
|
||||||
"InstitutionContract.SendMonthlySms",
|
|
||||||
() => SendFirstDayOfMonthSms(),
|
|
||||||
"*/20 * * * *" // هر 30 دقیقه یکبار چک کن
|
|
||||||
);
|
|
||||||
|
|
||||||
RecurringJob.AddOrUpdate(
|
|
||||||
"InstitutionContract.SendReminderSms",
|
|
||||||
() => SendReminderSms(),
|
|
||||||
"*/1 * * * *" // هر 1 دقیقه یکبار چک کن
|
|
||||||
);
|
|
||||||
RecurringJob.AddOrUpdate(
|
|
||||||
"InstitutionContract.SendBlockSms",
|
|
||||||
() => SendBlockSms(),
|
|
||||||
"*/1 * * * *" // هر 1 دقیقه یکبار چک کن
|
|
||||||
);
|
|
||||||
RecurringJob.AddOrUpdate(
|
|
||||||
"InstitutionContract.SendInstitutionContractConfirmSms",
|
|
||||||
() => SendInstitutionContractConfirmSms(),
|
|
||||||
"*/1 * * * *" // هر 1 دقیقه یکبار چک کن
|
|
||||||
);
|
|
||||||
|
|
||||||
//RecurringJob.AddOrUpdate(
|
|
||||||
// "InstitutionContract.SendWarningSms",
|
|
||||||
// () => SendWarningSms(),
|
|
||||||
// "*/1 * * * *" // هر 1 دقیقه یکبار چک کن
|
|
||||||
//);
|
|
||||||
|
|
||||||
//RecurringJob.AddOrUpdate(
|
|
||||||
// "InstitutionContract.SendLegalActionSms",
|
|
||||||
// () => SendLegalActionSms(),
|
|
||||||
// "*/1 * * * *" // هر 1 دقیقه یکبار چک کن
|
|
||||||
//);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ایجاد سند بدهی ماهیانه برای قراداد مالی
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
[DisableConcurrentExecution(timeoutInSeconds: 1200)]
|
|
||||||
public async System.Threading.Tasks.Task CreateFinancialTransaction()
|
|
||||||
{
|
|
||||||
var now =DateTime.Now;
|
|
||||||
var endOfMonth = now.ToFarsi().FindeEndOfMonth();
|
|
||||||
var endOfMonthGr = endOfMonth.ToGeorgianDateTime();
|
|
||||||
_logger.LogInformation("CreateFinancialTransaction job run");
|
|
||||||
if (now.Date == endOfMonthGr.Date && now.Hour >= 2 && now.Hour < 4 &&
|
|
||||||
now.Date != _lastRunCreateTransaction?.Date)
|
|
||||||
{
|
|
||||||
|
|
||||||
var month = endOfMonth.Substring(5, 2);
|
|
||||||
var year = endOfMonth.Substring(0, 4);
|
|
||||||
var monthName = month.ToFarsiMonthByNumber();
|
|
||||||
var description = $"{monthName} {year}";
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
var endnew = ($"{endOfMonth.Substring(0, 8)}01").FindeEndOfMonth();
|
|
||||||
|
|
||||||
var endNewGr = endnew.ToGeorgianDateTime();
|
|
||||||
var endNewFa = endNewGr.ToFarsi();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
await _institutionContractRepository.CreateTransactionForInstitutionContracts(endNewGr, endNewFa, description);
|
|
||||||
_lastRunCreateTransaction = now;
|
|
||||||
Console.WriteLine("CreateTransAction executed");
|
|
||||||
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
await _smsService.Alarm("09114221321", "خطا-ایجاد سند مالی");
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ارسال پیامک صورت حساب ماهانه
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
[DisableConcurrentExecution(timeoutInSeconds: 600)]
|
|
||||||
public async System.Threading.Tasks.Task SendFirstDayOfMonthSms()
|
|
||||||
{
|
|
||||||
//var now = new DateTime(2025,11,21, 10,30,0);
|
|
||||||
var now = DateTime.Now;
|
|
||||||
var endOfMonth = now.ToFarsi().FindeEndOfMonth();
|
|
||||||
var endOfMonthGr = endOfMonth.ToGeorgianDateTime();
|
|
||||||
_logger.LogInformation("SendFirstDayOfMonthSms job run");
|
|
||||||
if (now.Date == endOfMonthGr.Date && now.Hour >= 10 && now.Hour < 11 &&
|
|
||||||
now.Date != _lastRunSendMonthlySms?.Date)
|
|
||||||
{
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
await _institutionContractRepository.SendMonthlySms(now);
|
|
||||||
_lastRunSendMonthlySms = now;
|
|
||||||
Console.WriteLine("Send Monthly sms executed");
|
|
||||||
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
//_smsService.Alarm("09114221321", "خطا-ایجاد سند مالی");
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ارسال پیامک یاد آور بدهی
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
[DisableConcurrentExecution(timeoutInSeconds: 1200)]
|
|
||||||
public async System.Threading.Tasks.Task SendReminderSms()
|
|
||||||
{
|
|
||||||
_logger.LogInformation("SendReminderSms job run");
|
|
||||||
await _institutionContractRepository.SendReminderSmsForBackgroundTask();
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ارسال پیامک مسدودی
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
[DisableConcurrentExecution(timeoutInSeconds: 100)]
|
|
||||||
public async System.Threading.Tasks.Task SendBlockSms()
|
|
||||||
{
|
|
||||||
_logger.LogInformation("SendBlockSms job run");
|
|
||||||
await _institutionContractRepository.SendBlockSmsForBackgroundTask();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ارسال پیامک یادآور تایید قراداد مالی
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
[DisableConcurrentExecution(timeoutInSeconds: 100)]
|
|
||||||
public async System.Threading.Tasks.Task SendInstitutionContractConfirmSms()
|
|
||||||
{
|
|
||||||
_logger.LogInformation("SendInstitutionContractConfirmSms job run");
|
|
||||||
await _institutionContractRepository.SendInstitutionContractConfirmSmsTask();
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// ارسال پیامک هشدار
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
[DisableConcurrentExecution(timeoutInSeconds: 100)]
|
|
||||||
public async System.Threading.Tasks.Task SendWarningSms()
|
|
||||||
{
|
|
||||||
_logger.LogInformation("SendWarningSms job run");
|
|
||||||
await _institutionContractRepository.SendWarningSmsTask();
|
|
||||||
}
|
|
||||||
|
|
||||||
[DisableConcurrentExecution(timeoutInSeconds: 100)]
|
|
||||||
public async System.Threading.Tasks.Task SendLegalActionSms()
|
|
||||||
{
|
|
||||||
_logger.LogInformation("SendWarningSms job run");
|
|
||||||
await _institutionContractRepository.SendLegalActionSmsTask();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,116 +0,0 @@
|
|||||||
using _0_Framework.Application.Sms;
|
|
||||||
using AccountManagement.Application.Contracts.Account;
|
|
||||||
using AccountMangement.Infrastructure.EFCore;
|
|
||||||
using Company.Domain.SmsResultAgg;
|
|
||||||
using Microsoft.EntityFrameworkCore;
|
|
||||||
using SmsResult = Company.Domain.SmsResultAgg.SmsResult;
|
|
||||||
|
|
||||||
namespace BackgroundInstitutionContract.Task.Jobs;
|
|
||||||
public class SmsReminder
|
|
||||||
{
|
|
||||||
private readonly AccountContext _accountContext;
|
|
||||||
private readonly ISmsService _smsService;
|
|
||||||
private readonly ISmsResultRepository _smsResultRepository;
|
|
||||||
|
|
||||||
public SmsReminder(ISmsService smsService, AccountContext accountContext, ISmsResultRepository smsResultRepository)
|
|
||||||
{
|
|
||||||
_smsService = smsService;
|
|
||||||
_accountContext = accountContext;
|
|
||||||
_smsResultRepository = smsResultRepository;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Execute()
|
|
||||||
{
|
|
||||||
//var accounts = _accountContext.Accounts.Where(x => x.PositionId > 0 && x.IsActiveString == "true").Select(x => new AccountViewModel() { Id = x.id, Mobile = x.Mobile, Fullname = x.Fullname }).ToList();
|
|
||||||
//Thread.Sleep(300);
|
|
||||||
//var accounts = new List<AccountViewModel>() { new AccountViewModel() { Mobile = "09114221321", Id = 2 } };
|
|
||||||
var accounts= _accountContext.Accounts.Where(x => x.Username.ToLower()=="mahan").Select(x => new AccountViewModel() { Id = x.id, Mobile = x.Mobile, Fullname = x.Fullname }).ToList();
|
|
||||||
var smsVM = accounts.Select(x => new AccountSmsTaskViewModel()
|
|
||||||
{
|
|
||||||
Mobile = x.Mobile,
|
|
||||||
AccountId = x.Id,
|
|
||||||
FullName = x.Fullname,
|
|
||||||
TaskCount = GetLateTasksCount(x.Id)
|
|
||||||
}).Where(x => x.TaskCount > 0 && !string.IsNullOrEmpty(x.Mobile) && x.Mobile.Length == 11).ToList();
|
|
||||||
Thread.Sleep(300);
|
|
||||||
|
|
||||||
|
|
||||||
foreach (var viewmodel in smsVM)
|
|
||||||
{
|
|
||||||
var smsResult = _smsService.TaskReminderSms(viewmodel.Mobile, $"{viewmodel.TaskCount}");
|
|
||||||
Thread.Sleep(1000);
|
|
||||||
var createSmsResult = new SmsResult(smsResult.MessageId, smsResult.Message, "یادآور وظایف",
|
|
||||||
viewmodel.FullName, viewmodel.Mobile, viewmodel.AccountId, viewmodel.AccountId);
|
|
||||||
_smsResultRepository.Create(createSmsResult);
|
|
||||||
_smsResultRepository.SaveChanges();
|
|
||||||
Thread.Sleep(1000);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
private int GetLateTasksCount(long accountId)
|
|
||||||
{
|
|
||||||
var positionValue = _accountContext.Accounts
|
|
||||||
.Where(x => x.id == accountId)
|
|
||||||
.Include(p => p.Position)
|
|
||||||
.Select(x => x.Position.PositionValue)
|
|
||||||
.FirstOrDefault();
|
|
||||||
|
|
||||||
if (positionValue == 0)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
|
|
||||||
DateTime now = DateTime.Now;
|
|
||||||
int overdueTasksCount;
|
|
||||||
|
|
||||||
if (positionValue == 1)
|
|
||||||
{
|
|
||||||
overdueTasksCount = _accountContext.Assigns.Include(x => x.Task).Where(x => x.AssignedId == accountId &&
|
|
||||||
x.AssignerId == accountId && x.Task.Assigns.Count == 1 &&
|
|
||||||
!x.IsCancel && !x.IsCanceledRequest &&
|
|
||||||
!x.IsDone && !x.TimeRequest && !x.IsDoneRequest && x.EndTaskDate.Date <= DateTime.Now.Date && x.Task.IsActiveString == "true")
|
|
||||||
.GroupBy(x => x.TaskId).Select(x => x.First()).Count();
|
|
||||||
|
|
||||||
//overdueTasksCount = _accountContext.Tasks.Include(x =>
|
|
||||||
// x.Assigns).Count(x => !x.Assigns.Any(a => a.IsCancel) && !x.Assigns.Any(a => a.IsCanceledRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.IsDone) && !x.Assigns.Any(a => a.IsDoneRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.TimeRequest)
|
|
||||||
// && x.Assigns.Any(a => a.AssignedId == accountId && a.AssignerId == accountId) &&
|
|
||||||
// (x.Assigns.First(a => a.AssignedId == accountId && a.AssignerId == accountId)
|
|
||||||
// .EndTaskDate.Date <= DateTime.Now.Date) && x.Assigns.Count == 1);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
|
|
||||||
overdueTasksCount = _accountContext.Assigns
|
|
||||||
.Include(x => x.Task)
|
|
||||||
.Where(x => x.AssignedId == accountId &&
|
|
||||||
!x.IsCancel && !x.IsCanceledRequest &&
|
|
||||||
!x.IsDone && !x.TimeRequest && !x.IsDoneRequest && x.EndTaskDate.Date <= DateTime.Now.Date && x.Task.IsActiveString == "true")
|
|
||||||
.GroupBy(x => x.TaskId).Select(x => x.First()).Count();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//overdueTasksCount = _accountContext.Tasks.Include(x =>
|
|
||||||
// x.Assigns).Count(x => !x.Assigns.Any(a => a.IsCancel) && !x.Assigns.Any(a => a.IsCanceledRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.IsDone) && !x.Assigns.Any(a => a.IsDoneRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.TimeRequest)
|
|
||||||
// && x.Assigns.Any(a => a.AssignedId == accountId) &&
|
|
||||||
// (x.Assigns.First(a => a.AssignedId == accountId).EndTaskDate.Date <= DateTime.Now.Date));
|
|
||||||
|
|
||||||
|
|
||||||
var overdueRequestsCount = _accountContext.Assigns.Include(x => x.Task)
|
|
||||||
.Where(x => (x.IsCanceledRequest
|
|
||||||
|| x.IsDoneRequest || x.TimeRequest) && !x.IsCancel && !x.IsDone &&
|
|
||||||
x.Task.IsActiveString == "true" &&
|
|
||||||
x.Task.SenderId == accountId).GroupBy(x => x.TaskId).Select(x => x.First()).Count();
|
|
||||||
|
|
||||||
return overdueTasksCount + overdueRequestsCount;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
public class AccountSmsTaskViewModel
|
|
||||||
{
|
|
||||||
public int TaskCount { get; set; }
|
|
||||||
public long AccountId { get; set; }
|
|
||||||
public string Mobile { get; set; }
|
|
||||||
public string FullName { get; set; }
|
|
||||||
}
|
|
||||||
@@ -1,25 +0,0 @@
|
|||||||
using BackgroundInstitutionContract.Task.Jobs;
|
|
||||||
|
|
||||||
|
|
||||||
namespace BackgroundInstitutionContract.Task;
|
|
||||||
|
|
||||||
public class JobsBootstrapper
|
|
||||||
{
|
|
||||||
public static void Configure(IServiceCollection services)
|
|
||||||
{
|
|
||||||
var currentNamespace = typeof(JobSchedulerRegistrator).Namespace; // همون namespace کلاس
|
|
||||||
|
|
||||||
var assembly = typeof(JobSchedulerRegistrator).Assembly;
|
|
||||||
|
|
||||||
var jobTypes = assembly.GetTypes()
|
|
||||||
.Where(t =>
|
|
||||||
t is { IsClass: true, IsAbstract: false, Namespace: not null } &&
|
|
||||||
t.Namespace.StartsWith(currentNamespace, StringComparison.Ordinal))
|
|
||||||
.ToList();
|
|
||||||
|
|
||||||
foreach (var jobType in jobTypes)
|
|
||||||
{
|
|
||||||
services.AddTransient(jobType);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,10 +0,0 @@
|
|||||||
using GozareshgirProgramManager.Application.Interfaces;
|
|
||||||
using GozareshgirProgramManager.Domain.ProjectAgg.Enums;
|
|
||||||
|
|
||||||
public class NullBoardNotificationPublisher:IBoardNotificationPublisher
|
|
||||||
{
|
|
||||||
public Task SendProjectStatusChanged(long userId, TaskSectionStatus oldStatus, TaskSectionStatus newStatus, Guid sectionId)
|
|
||||||
{
|
|
||||||
throw new NotImplementedException();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,108 +0,0 @@
|
|||||||
using _0_Framework.Application;
|
|
||||||
using _0_Framework.Application.Sms;
|
|
||||||
using _0_Framework.Application.UID;
|
|
||||||
using _0_Framework.InfraStructure.Mongo;
|
|
||||||
using AccountManagement.Configuration;
|
|
||||||
using BackgroundInstitutionContract.Task;
|
|
||||||
using BackgroundInstitutionContract.Task.Jobs;
|
|
||||||
using CompanyManagment.App.Contracts.Hubs;
|
|
||||||
using CompanyManagment.EFCore.Services;
|
|
||||||
using GozareshgirProgramManager.Application._Bootstrapper;
|
|
||||||
using GozareshgirProgramManager.Application.Interfaces;
|
|
||||||
using GozareshgirProgramManager.Application.Modules.Users.Commands.CreateUser;
|
|
||||||
using GozareshgirProgramManager.Infrastructure;
|
|
||||||
using GozareshgirProgramManager.Infrastructure.Persistence.Seed;
|
|
||||||
using Hangfire;
|
|
||||||
using Microsoft.AspNetCore.Identity;
|
|
||||||
using MongoDB.Driver;
|
|
||||||
using PersonalContractingParty.Config;
|
|
||||||
using Query.Bootstrapper;
|
|
||||||
using Serilog;
|
|
||||||
using Serilog.Events;
|
|
||||||
using Shared.Contracts.PmUser.Queries;
|
|
||||||
using WorkFlow.Infrastructure.Config;
|
|
||||||
|
|
||||||
var logDirectory = @"C:\Logs\Hangfire\BackgroundInstitutionContract\";
|
|
||||||
|
|
||||||
if (!Directory.Exists(logDirectory))
|
|
||||||
{
|
|
||||||
Directory.CreateDirectory(logDirectory);
|
|
||||||
}
|
|
||||||
|
|
||||||
Log.Logger = new LoggerConfiguration()
|
|
||||||
//NO EF Core log
|
|
||||||
.MinimumLevel.Override("Microsoft.EntityFrameworkCore", LogEventLevel.Warning)
|
|
||||||
|
|
||||||
//NO DbCommand log
|
|
||||||
.MinimumLevel.Override("Microsoft.EntityFrameworkCore.Database.Command", LogEventLevel.Warning)
|
|
||||||
|
|
||||||
//NO Microsoft Public log
|
|
||||||
.MinimumLevel.Override("Microsoft", LogEventLevel.Warning)
|
|
||||||
//.MinimumLevel.Information()
|
|
||||||
.WriteTo.File(
|
|
||||||
path: Path.Combine(logDirectory, "institution-contract-log-.txt"),
|
|
||||||
rollingInterval: RollingInterval.Day,
|
|
||||||
retainedFileCountLimit: 30,
|
|
||||||
shared: true,
|
|
||||||
outputTemplate:
|
|
||||||
"{Timestamp:yyyy-MM-dd HH:mm:ss} [{Level}] {Message}{NewLine}{Exception}"
|
|
||||||
).CreateLogger();
|
|
||||||
|
|
||||||
var builder = WebApplication.CreateBuilder(args);
|
|
||||||
var hangfireConnectionString = builder.Configuration.GetConnectionString("HangfireDb");
|
|
||||||
builder.Services.AddHangfire(x => x.UseSqlServerStorage(hangfireConnectionString));
|
|
||||||
builder.Services.AddHangfireServer();
|
|
||||||
var connectionString = builder.Configuration.GetConnectionString("MesbahDb");
|
|
||||||
var connectionStringTestDb = builder.Configuration.GetConnectionString("TestDb");
|
|
||||||
builder.Services.AddSingleton<IPasswordHasher, PasswordHasher>();
|
|
||||||
builder.Services.AddTransient<IAuthHelper, AuthHelper>();
|
|
||||||
builder.Services.AddTransient<ISmsService, SmsService>();
|
|
||||||
builder.Services.AddTransient<IUidService, UidService>();
|
|
||||||
builder.Services.AddTransient<IFileUploader, FileUploader>();
|
|
||||||
builder.Services.Configure<AppSettingConfiguration>(builder.Configuration);
|
|
||||||
builder.Services.AddScoped<IBoardNotificationPublisher, NullBoardNotificationPublisher>();
|
|
||||||
#region MongoDb
|
|
||||||
|
|
||||||
var mongoConnectionSection = builder.Configuration.GetSection("MongoDb");
|
|
||||||
var mongoDbSettings = mongoConnectionSection.Get<MongoDbConfig>();
|
|
||||||
var mongoClient = new MongoClient(mongoDbSettings.ConnectionString);
|
|
||||||
var mongoDatabase = mongoClient.GetDatabase(mongoDbSettings.DatabaseName);
|
|
||||||
|
|
||||||
builder.Services.AddSingleton<IMongoDatabase>(mongoDatabase);
|
|
||||||
|
|
||||||
#endregion
|
|
||||||
|
|
||||||
builder.Services.AddProgramManagerApplication();
|
|
||||||
builder.Services.AddProgramManagerInfrastructure(builder.Configuration);
|
|
||||||
|
|
||||||
|
|
||||||
PersonalBootstrapper.Configure(builder.Services, connectionString);
|
|
||||||
TestDbBootStrapper.Configure(builder.Services, connectionStringTestDb);
|
|
||||||
AccountManagementBootstrapper.Configure(builder.Services, connectionString);
|
|
||||||
WorkFlowBootstrapper.Configure(builder.Services, connectionString);
|
|
||||||
|
|
||||||
QueryBootstrapper.Configure(builder.Services);
|
|
||||||
JobsBootstrapper.Configure(builder.Services);
|
|
||||||
builder.Services.AddHttpClient();
|
|
||||||
builder.Services.AddHttpContextAccessor();
|
|
||||||
builder.Services.AddSignalR();
|
|
||||||
|
|
||||||
|
|
||||||
builder.Host.UseSerilog();
|
|
||||||
Log.Information("SERILOG STARTED SUCCESSFULLY");
|
|
||||||
|
|
||||||
|
|
||||||
var app = builder.Build();
|
|
||||||
|
|
||||||
app.MapHub<SendSmsHub>("/sendSmsHub");
|
|
||||||
|
|
||||||
app.MapHangfireDashboard();
|
|
||||||
app.MapGet("/", () => "Hello World!");
|
|
||||||
|
|
||||||
using (var scope = app.Services.CreateScope())
|
|
||||||
{
|
|
||||||
var jobScheduler = scope.ServiceProvider.GetRequiredService<JobSchedulerRegistrator>();
|
|
||||||
jobScheduler.Register();
|
|
||||||
}
|
|
||||||
|
|
||||||
app.Run();
|
|
||||||
@@ -1,38 +0,0 @@
|
|||||||
{
|
|
||||||
"$schema": "http://json.schemastore.org/launchsettings.json",
|
|
||||||
"iisSettings": {
|
|
||||||
"windowsAuthentication": false,
|
|
||||||
"anonymousAuthentication": true,
|
|
||||||
"iisExpress": {
|
|
||||||
"applicationUrl": "http://localhost:56492",
|
|
||||||
"sslPort": 44378
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"profiles": {
|
|
||||||
"http": {
|
|
||||||
"commandName": "Project",
|
|
||||||
"dotnetRunMessages": true,
|
|
||||||
"launchBrowser": true,
|
|
||||||
"applicationUrl": "http://localhost:5216",
|
|
||||||
"environmentVariables": {
|
|
||||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"https": {
|
|
||||||
"commandName": "Project",
|
|
||||||
"dotnetRunMessages": true,
|
|
||||||
"launchBrowser": true,
|
|
||||||
"applicationUrl": "https://localhost:7223;http://localhost:5217",
|
|
||||||
"environmentVariables": {
|
|
||||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"IIS Express": {
|
|
||||||
"commandName": "IISExpress",
|
|
||||||
"launchBrowser": true,
|
|
||||||
"environmentVariables": {
|
|
||||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,47 +0,0 @@
|
|||||||
{
|
|
||||||
"DetailedErrors": true,
|
|
||||||
"Logging": {
|
|
||||||
"LogLevel": {
|
|
||||||
"Default": "Information",
|
|
||||||
"Microsoft": "Warning",
|
|
||||||
"Microsoft.Hosting.Lifetime": "Information"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"ConnectionStrings": {
|
|
||||||
//تست
|
|
||||||
//"MesbahDb": "Data Source=DESKTOP-NUE119G\\MSNEW;Initial Catalog=Mesbah_db;Integrated Security=True"
|
|
||||||
|
|
||||||
//server
|
|
||||||
//"MesbahDb": "Data Source=171.22.24.15;Initial Catalog=mesbah_db;Persist Security Info=False;User ID=ir_db;Password=R2rNp[170]18[3019]#@ATt;TrustServerCertificate=true;",
|
|
||||||
|
|
||||||
|
|
||||||
//local
|
|
||||||
"MesbahDb": "Data Source=.;Initial Catalog=mesbah_db;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
|
|
||||||
//dad-mehr
|
|
||||||
//"MesbahDb": "Data Source=.;Initial Catalog=teamWork;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
|
|
||||||
"TestDb": "Data Source=.;Initial Catalog=TestDb;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
|
|
||||||
//mahan Docker
|
|
||||||
//"MesbahDb": "Data Source=localhost,5069;Initial Catalog=mesbah_db;User ID=sa;Password=YourPassword123;TrustServerCertificate=True;",
|
|
||||||
"HangfireDb": "Data Source=.;Initial Catalog=hangfire_db;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
//"HangfireDb": "Data Source=185.208.175.186;Initial Catalog=hangfire_db;Persist Security Info=False;User ID=ir_db;Password=R2rNp[170]18[3019]#@ATt;TrustServerCertificate=true;"
|
|
||||||
},
|
|
||||||
|
|
||||||
"GoogleRecaptchaV3": {
|
|
||||||
"SiteKey": "6Lfhp_AnAAAAAB79WkrMoHd1k8ir4m8VvfjE7FTH",
|
|
||||||
"SecretKey": "6Lfhp_AnAAAAANjDDY6DPrbbUQS7k6ZCRmrVP5Lb"
|
|
||||||
},
|
|
||||||
"SmsSecrets": {
|
|
||||||
"ApiKey": "Og5M562igmzJRhQPnq0GdtieYdLgtfikjzxOmeQBPxJjZtyge5Klc046Lfw1mxSa",
|
|
||||||
"SecretKey": "dadmehr"
|
|
||||||
},
|
|
||||||
"Domain": ".gozareshgir.ir",
|
|
||||||
"MongoDb": {
|
|
||||||
"ConnectionString": "mongodb://localhost:27017",
|
|
||||||
"DatabaseName": "Gozareshgir"
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,28 +0,0 @@
|
|||||||
{
|
|
||||||
"Logging": {
|
|
||||||
"LogLevel": {
|
|
||||||
"Default": "Information",
|
|
||||||
"Microsoft": "Warning",
|
|
||||||
"Microsoft.Hosting.Lifetime": "Information"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"ConnectionStrings": {
|
|
||||||
|
|
||||||
//local
|
|
||||||
//"MesbahDb": "Data Source=.;Initial Catalog=mesbah_db;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
"MesbahDb": "Data Source=185.208.175.186;Initial Catalog=mesbah_db;Persist Security Info=False;User ID=ir_db;Password=R2rNp[170]18[3019]#@ATt;TrustServerCertificate=true;",
|
|
||||||
//dad-mehr
|
|
||||||
//"MesbahDb": "Data Source=.;Initial Catalog=teamWork;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
|
|
||||||
//"TestDb": "Data Source=.;Initial Catalog=TestDb;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
"TestDb": "Data Source=185.208.175.186;Initial Catalog=TestDb;Persist Security Info=False;User ID=ir_db;Password=R2rNp[170]18[3019]#@ATt;TrustServerCertificate=true;",
|
|
||||||
//"MesbahDb": "Data Source=.\\MSSQLSERVER2019;Initial Catalog=mesbah_db;Persist Security Info=False;User ID=mesbah_db;Password=sa142857$@;"
|
|
||||||
//"HangfireDb": "Data Source=.;Initial Catalog=hangfire_db;Integrated Security=True;TrustServerCertificate=true;",
|
|
||||||
"HangfireDb": "Data Source=185.208.175.186;Initial Catalog=hangfire_db;Persist Security Info=False;User ID=ir_db;Password=R2rNp[170]18[3019]#@ATt;TrustServerCertificate=true;"
|
|
||||||
},
|
|
||||||
"MongoDb": {
|
|
||||||
"ConnectionString": "mongodb://localhost:27017",
|
|
||||||
"DatabaseName": "Gozareshgir"
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,17 +0,0 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
|
||||||
|
|
||||||
<PropertyGroup>
|
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
|
||||||
<Nullable>enable</Nullable>
|
|
||||||
<ImplicitUsings>enable</ImplicitUsings>
|
|
||||||
</PropertyGroup>
|
|
||||||
|
|
||||||
<ItemGroup>
|
|
||||||
<ProjectReference Include="..\..\0_Framework\0_Framework.csproj" />
|
|
||||||
<ProjectReference Include="..\..\AccountManagement.Configuration\AccountManagement.Configuration.csproj" />
|
|
||||||
<ProjectReference Include="..\..\PersonalContractingParty.Config\PersonalContractingParty.Config.csproj" />
|
|
||||||
<ProjectReference Include="..\..\Query.Bootstrapper\Query.Bootstrapper.csproj" />
|
|
||||||
<ProjectReference Include="..\..\WorkFlow\Infrastructure\WorkFlow.Infrastructure.Config\WorkFlow.Infrastructure.Config.csproj" />
|
|
||||||
</ItemGroup>
|
|
||||||
|
|
||||||
</Project>
|
|
||||||
@@ -1,32 +0,0 @@
|
|||||||
using _0_Framework.Application;
|
|
||||||
|
|
||||||
namespace BackgroundJobs.Task
|
|
||||||
{
|
|
||||||
public class FileUploader : IFileUploader
|
|
||||||
{
|
|
||||||
private readonly IWebHostEnvironment _webHostEnvironment;
|
|
||||||
|
|
||||||
public FileUploader(IWebHostEnvironment webHostEnvironment)
|
|
||||||
{
|
|
||||||
_webHostEnvironment = webHostEnvironment;
|
|
||||||
}
|
|
||||||
|
|
||||||
public string Upload(IFormFile file, string path)
|
|
||||||
{
|
|
||||||
if (file == null) return "";
|
|
||||||
|
|
||||||
var directoryPath = $"{_webHostEnvironment.WebRootPath}\\ProductPictures\\{path}";
|
|
||||||
|
|
||||||
if (!Directory.Exists(directoryPath))
|
|
||||||
Directory.CreateDirectory(directoryPath);
|
|
||||||
|
|
||||||
var fileName = $"{DateTime.Now.ToFileName()}-{file.FileName}";
|
|
||||||
var filePath = $"{directoryPath}\\{fileName}";
|
|
||||||
var output = System.IO.File.Create(filePath);
|
|
||||||
file.CopyTo(output);
|
|
||||||
return $"{path}/{fileName}";
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,62 +0,0 @@
|
|||||||
using Hangfire;
|
|
||||||
|
|
||||||
namespace BackgroundJobs.Task.Jobs;
|
|
||||||
|
|
||||||
public class JobSchedulerRegistrator
|
|
||||||
{
|
|
||||||
private readonly IBackgroundJobClient _backgroundJobClient;
|
|
||||||
private readonly SmsReminder _smsReminder;
|
|
||||||
private static DateTime? _lastRunDateMorning;
|
|
||||||
private static DateTime? _lastRunDateEvening;
|
|
||||||
|
|
||||||
public JobSchedulerRegistrator(SmsReminder smsReminder, IBackgroundJobClient backgroundJobClient)
|
|
||||||
{
|
|
||||||
_smsReminder = smsReminder;
|
|
||||||
_backgroundJobClient = backgroundJobClient;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Register()
|
|
||||||
{
|
|
||||||
RecurringJob.AddOrUpdate(
|
|
||||||
"Task.SmsReminderChecker",
|
|
||||||
() => SmsReminderCheckAndSchedule(),
|
|
||||||
"*/5 * * * *" // هر 5 دقیقه یکبار چک کن
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SmsReminderCheckAndSchedule()
|
|
||||||
{
|
|
||||||
var now = DateTime.Now;
|
|
||||||
|
|
||||||
var startMorning = new TimeSpan(9, 0, 0);
|
|
||||||
var endMorning = new TimeSpan(9, 40, 0);
|
|
||||||
|
|
||||||
var startEvening = new TimeSpan(15, 30, 0);
|
|
||||||
var endEvening = new TimeSpan(15, 40, 0);
|
|
||||||
|
|
||||||
// صبح
|
|
||||||
if (now.DayOfWeek != DayOfWeek.Friday &&
|
|
||||||
now.TimeOfDay >= startMorning &&
|
|
||||||
now.TimeOfDay < endMorning)
|
|
||||||
{
|
|
||||||
if (_lastRunDateMorning?.Date != now.Date)
|
|
||||||
{
|
|
||||||
_backgroundJobClient.Enqueue(() => _smsReminder.Execute());
|
|
||||||
_lastRunDateMorning = now;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// عصر - پنجشنبه و جمعه تعطیل است
|
|
||||||
if (now.DayOfWeek != DayOfWeek.Friday &&
|
|
||||||
now.DayOfWeek != DayOfWeek.Thursday &&
|
|
||||||
now.TimeOfDay >= startEvening &&
|
|
||||||
now.TimeOfDay < endEvening)
|
|
||||||
{
|
|
||||||
if (_lastRunDateEvening?.Date != now.Date)
|
|
||||||
{
|
|
||||||
_backgroundJobClient.Enqueue(() => _smsReminder.Execute());
|
|
||||||
_lastRunDateEvening = now;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,116 +0,0 @@
|
|||||||
using _0_Framework.Application.Sms;
|
|
||||||
using AccountManagement.Application.Contracts.Account;
|
|
||||||
using AccountMangement.Infrastructure.EFCore;
|
|
||||||
using Company.Domain.SmsResultAgg;
|
|
||||||
using Microsoft.EntityFrameworkCore;
|
|
||||||
using SmsResult = Company.Domain.SmsResultAgg.SmsResult;
|
|
||||||
|
|
||||||
namespace BackgroundJobs.Task.Jobs;
|
|
||||||
public class SmsReminder
|
|
||||||
{
|
|
||||||
private readonly AccountContext _accountContext;
|
|
||||||
private readonly ISmsService _smsService;
|
|
||||||
private readonly ISmsResultRepository _smsResultRepository;
|
|
||||||
|
|
||||||
public SmsReminder(ISmsService smsService, AccountContext accountContext, ISmsResultRepository smsResultRepository)
|
|
||||||
{
|
|
||||||
_smsService = smsService;
|
|
||||||
_accountContext = accountContext;
|
|
||||||
_smsResultRepository = smsResultRepository;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Execute()
|
|
||||||
{
|
|
||||||
//var accounts = _accountContext.Accounts.Where(x => x.PositionId > 0 && x.IsActiveString == "true").Select(x => new AccountViewModel() { Id = x.id, Mobile = x.Mobile, Fullname = x.Fullname }).ToList();
|
|
||||||
//Thread.Sleep(300);
|
|
||||||
//var accounts = new List<AccountViewModel>() { new AccountViewModel() { Mobile = "09114221321", Id = 2 } };
|
|
||||||
var accounts= _accountContext.Accounts.Where(x => x.Username.ToLower()=="mahan").Select(x => new AccountViewModel() { Id = x.id, Mobile = x.Mobile, Fullname = x.Fullname }).ToList();
|
|
||||||
var smsVM = accounts.Select(x => new AccountSmsTaskViewModel()
|
|
||||||
{
|
|
||||||
Mobile = x.Mobile,
|
|
||||||
AccountId = x.Id,
|
|
||||||
FullName = x.Fullname,
|
|
||||||
TaskCount = GetLateTasksCount(x.Id)
|
|
||||||
}).Where(x => x.TaskCount > 0 && !string.IsNullOrEmpty(x.Mobile) && x.Mobile.Length == 11).ToList();
|
|
||||||
Thread.Sleep(300);
|
|
||||||
|
|
||||||
|
|
||||||
foreach (var viewmodel in smsVM)
|
|
||||||
{
|
|
||||||
var smsResult = _smsService.TaskReminderSms(viewmodel.Mobile, $"{viewmodel.TaskCount}");
|
|
||||||
Thread.Sleep(1000);
|
|
||||||
var createSmsResult = new SmsResult(smsResult.MessageId, smsResult.Message, "یادآور وظایف",
|
|
||||||
viewmodel.FullName, viewmodel.Mobile, viewmodel.AccountId, viewmodel.AccountId);
|
|
||||||
_smsResultRepository.Create(createSmsResult);
|
|
||||||
_smsResultRepository.SaveChanges();
|
|
||||||
Thread.Sleep(1000);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
private int GetLateTasksCount(long accountId)
|
|
||||||
{
|
|
||||||
var positionValue = _accountContext.Accounts
|
|
||||||
.Where(x => x.id == accountId)
|
|
||||||
.Include(p => p.Position)
|
|
||||||
.Select(x => x.Position.PositionValue)
|
|
||||||
.FirstOrDefault();
|
|
||||||
|
|
||||||
if (positionValue == 0)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
|
|
||||||
DateTime now = DateTime.Now;
|
|
||||||
int overdueTasksCount;
|
|
||||||
|
|
||||||
if (positionValue == 1)
|
|
||||||
{
|
|
||||||
overdueTasksCount = _accountContext.Assigns.Include(x => x.Task).Where(x => x.AssignedId == accountId &&
|
|
||||||
x.AssignerId == accountId && x.Task.Assigns.Count == 1 &&
|
|
||||||
!x.IsCancel && !x.IsCanceledRequest &&
|
|
||||||
!x.IsDone && !x.TimeRequest && !x.IsDoneRequest && x.EndTaskDate.Date <= DateTime.Now.Date && x.Task.IsActiveString == "true")
|
|
||||||
.GroupBy(x => x.TaskId).Select(x => x.First()).Count();
|
|
||||||
|
|
||||||
//overdueTasksCount = _accountContext.Tasks.Include(x =>
|
|
||||||
// x.Assigns).Count(x => !x.Assigns.Any(a => a.IsCancel) && !x.Assigns.Any(a => a.IsCanceledRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.IsDone) && !x.Assigns.Any(a => a.IsDoneRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.TimeRequest)
|
|
||||||
// && x.Assigns.Any(a => a.AssignedId == accountId && a.AssignerId == accountId) &&
|
|
||||||
// (x.Assigns.First(a => a.AssignedId == accountId && a.AssignerId == accountId)
|
|
||||||
// .EndTaskDate.Date <= DateTime.Now.Date) && x.Assigns.Count == 1);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
|
|
||||||
overdueTasksCount = _accountContext.Assigns
|
|
||||||
.Include(x => x.Task)
|
|
||||||
.Where(x => x.AssignedId == accountId &&
|
|
||||||
!x.IsCancel && !x.IsCanceledRequest &&
|
|
||||||
!x.IsDone && !x.TimeRequest && !x.IsDoneRequest && x.EndTaskDate.Date <= DateTime.Now.Date && x.Task.IsActiveString == "true")
|
|
||||||
.GroupBy(x => x.TaskId).Select(x => x.First()).Count();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
//overdueTasksCount = _accountContext.Tasks.Include(x =>
|
|
||||||
// x.Assigns).Count(x => !x.Assigns.Any(a => a.IsCancel) && !x.Assigns.Any(a => a.IsCanceledRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.IsDone) && !x.Assigns.Any(a => a.IsDoneRequest) &&
|
|
||||||
// !x.Assigns.Any(a => a.TimeRequest)
|
|
||||||
// && x.Assigns.Any(a => a.AssignedId == accountId) &&
|
|
||||||
// (x.Assigns.First(a => a.AssignedId == accountId).EndTaskDate.Date <= DateTime.Now.Date));
|
|
||||||
|
|
||||||
|
|
||||||
var overdueRequestsCount = _accountContext.Assigns.Include(x => x.Task)
|
|
||||||
.Where(x => (x.IsCanceledRequest
|
|
||||||
|| x.IsDoneRequest || x.TimeRequest) && !x.IsCancel && !x.IsDone &&
|
|
||||||
x.Task.IsActiveString == "true" &&
|
|
||||||
x.Task.SenderId == accountId).GroupBy(x => x.TaskId).Select(x => x.First()).Count();
|
|
||||||
|
|
||||||
return overdueTasksCount + overdueRequestsCount;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
public class AccountSmsTaskViewModel
|
|
||||||
{
|
|
||||||
public int TaskCount { get; set; }
|
|
||||||
public long AccountId { get; set; }
|
|
||||||
public string Mobile { get; set; }
|
|
||||||
public string FullName { get; set; }
|
|
||||||
}
|
|
||||||
@@ -1,24 +0,0 @@
|
|||||||
using BackgroundJobs.Task.Jobs;
|
|
||||||
|
|
||||||
namespace BackgroundJobs.Task;
|
|
||||||
|
|
||||||
public class JobsBootstrapper
|
|
||||||
{
|
|
||||||
public static void Configure(IServiceCollection services)
|
|
||||||
{
|
|
||||||
var currentNamespace = typeof(JobSchedulerRegistrator).Namespace; // همون namespace کلاس
|
|
||||||
|
|
||||||
var assembly = typeof(JobSchedulerRegistrator).Assembly;
|
|
||||||
|
|
||||||
var jobTypes = assembly.GetTypes()
|
|
||||||
.Where(t =>
|
|
||||||
t is { IsClass: true, IsAbstract: false, Namespace: not null } &&
|
|
||||||
t.Namespace.StartsWith(currentNamespace, StringComparison.Ordinal))
|
|
||||||
.ToList();
|
|
||||||
|
|
||||||
foreach (var jobType in jobTypes)
|
|
||||||
{
|
|
||||||
services.AddTransient(jobType);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,59 +0,0 @@
|
|||||||
using _0_Framework.Application;
|
|
||||||
using _0_Framework.Application.Sms;
|
|
||||||
using _0_Framework.Application.UID;
|
|
||||||
using _0_Framework.InfraStructure.Mongo;
|
|
||||||
using AccountManagement.Configuration;
|
|
||||||
using BackgroundJobs.Task;
|
|
||||||
using BackgroundJobs.Task.Jobs;
|
|
||||||
using CompanyManagment.EFCore.Services;
|
|
||||||
using Hangfire;
|
|
||||||
using Microsoft.AspNetCore.Identity;
|
|
||||||
using MongoDB.Driver;
|
|
||||||
using PersonalContractingParty.Config;
|
|
||||||
using Query.Bootstrapper;
|
|
||||||
using WorkFlow.Infrastructure.Config;
|
|
||||||
|
|
||||||
var builder = WebApplication.CreateBuilder(args);
|
|
||||||
var hangfireConnectionString = builder.Configuration.GetConnectionString("HangfireDb");
|
|
||||||
builder.Services.AddHangfire(x => x.UseSqlServerStorage(hangfireConnectionString));
|
|
||||||
builder.Services.AddHangfireServer();
|
|
||||||
var connectionString = builder.Configuration.GetConnectionString("MesbahDb");
|
|
||||||
var connectionStringTestDb = builder.Configuration.GetConnectionString("TestDb");
|
|
||||||
builder.Services.AddSingleton<IPasswordHasher, PasswordHasher>();
|
|
||||||
builder.Services.AddTransient<IAuthHelper, AuthHelper>();
|
|
||||||
builder.Services.AddTransient<ISmsService, SmsService>();
|
|
||||||
builder.Services.AddTransient<IUidService, UidService>();
|
|
||||||
builder.Services.AddTransient<IFileUploader, FileUploader>();
|
|
||||||
builder.Services.Configure<AppSettingConfiguration>(builder.Configuration);
|
|
||||||
|
|
||||||
#region MongoDb
|
|
||||||
|
|
||||||
var mongoConnectionSection = builder.Configuration.GetSection("MongoDb");
|
|
||||||
var mongoDbSettings = mongoConnectionSection.Get<MongoDbConfig>();
|
|
||||||
var mongoClient = new MongoClient(mongoDbSettings.ConnectionString);
|
|
||||||
var mongoDatabase = mongoClient.GetDatabase(mongoDbSettings.DatabaseName);
|
|
||||||
|
|
||||||
builder.Services.AddSingleton<IMongoDatabase>(mongoDatabase);
|
|
||||||
|
|
||||||
#endregion
|
|
||||||
|
|
||||||
PersonalBootstrapper.Configure(builder.Services, connectionString);
|
|
||||||
TestDbBootStrapper.Configure(builder.Services, connectionStringTestDb);
|
|
||||||
AccountManagementBootstrapper.Configure(builder.Services, connectionString);
|
|
||||||
WorkFlowBootstrapper.Configure(builder.Services, connectionString);
|
|
||||||
QueryBootstrapper.Configure(builder.Services);
|
|
||||||
JobsBootstrapper.Configure(builder.Services);
|
|
||||||
builder.Services.AddHttpClient();
|
|
||||||
builder.Services.AddHttpContextAccessor();
|
|
||||||
var app = builder.Build();
|
|
||||||
|
|
||||||
app.MapHangfireDashboard();
|
|
||||||
app.MapGet("/", () => "Hello World!");
|
|
||||||
|
|
||||||
using (var scope = app.Services.CreateScope())
|
|
||||||
{
|
|
||||||
var jobScheduler = scope.ServiceProvider.GetRequiredService<JobSchedulerRegistrator>();
|
|
||||||
jobScheduler.Register();
|
|
||||||
}
|
|
||||||
|
|
||||||
app.Run();
|
|
||||||
@@ -1,38 +0,0 @@
|
|||||||
{
|
|
||||||
"$schema": "http://json.schemastore.org/launchsettings.json",
|
|
||||||
"iisSettings": {
|
|
||||||
"windowsAuthentication": false,
|
|
||||||
"anonymousAuthentication": true,
|
|
||||||
"iisExpress": {
|
|
||||||
"applicationUrl": "http://localhost:56492",
|
|
||||||
"sslPort": 44378
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"profiles": {
|
|
||||||
"http": {
|
|
||||||
"commandName": "Project",
|
|
||||||
"dotnetRunMessages": true,
|
|
||||||
"launchBrowser": true,
|
|
||||||
"applicationUrl": "http://localhost:5216",
|
|
||||||
"environmentVariables": {
|
|
||||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"https": {
|
|
||||||
"commandName": "Project",
|
|
||||||
"dotnetRunMessages": true,
|
|
||||||
"launchBrowser": true,
|
|
||||||
"applicationUrl": "https://localhost:7222;http://localhost:5216",
|
|
||||||
"environmentVariables": {
|
|
||||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"IIS Express": {
|
|
||||||
"commandName": "IISExpress",
|
|
||||||
"launchBrowser": true,
|
|
||||||
"environmentVariables": {
|
|
||||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,9 +0,0 @@
|
|||||||
{
|
|
||||||
"Logging": {
|
|
||||||
"LogLevel": {
|
|
||||||
"Default": "Information",
|
|
||||||
"Microsoft.AspNetCore": "Warning"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"AllowedHosts": "*"
|
|
||||||
}
|
|
||||||
314
CHANGELOG.md
314
CHANGELOG.md
@@ -1,314 +0,0 @@
|
|||||||
# خلاصه تغییرات سیستم گزارش خرابی
|
|
||||||
|
|
||||||
## 📝 فایلهای اضافه شده (23 فایل)
|
|
||||||
|
|
||||||
### 1️⃣ Domain Layer (3 فایل)
|
|
||||||
```
|
|
||||||
✓ AccountManagement.Domain/BugReportAgg/
|
|
||||||
├── BugReport.cs
|
|
||||||
├── BugReportLog.cs
|
|
||||||
└── BugReportScreenshot.cs
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2️⃣ Application Contracts (6 فایل)
|
|
||||||
```
|
|
||||||
✓ AccountManagement.Application.Contracts/BugReport/
|
|
||||||
├── IBugReportRepository.cs
|
|
||||||
├── IBugReportApplication.cs
|
|
||||||
├── CreateBugReportCommand.cs
|
|
||||||
├── EditBugReportCommand.cs
|
|
||||||
├── BugReportViewModel.cs
|
|
||||||
└── BugReportDetailViewModel.cs
|
|
||||||
```
|
|
||||||
|
|
||||||
### 3️⃣ Application Service (1 فایل)
|
|
||||||
```
|
|
||||||
✓ AccountManagement.Application/
|
|
||||||
└── BugReportApplication.cs
|
|
||||||
```
|
|
||||||
|
|
||||||
### 4️⃣ Infrastructure EFCore (4 فایل)
|
|
||||||
```
|
|
||||||
✓ AccountMangement.Infrastructure.EFCore/
|
|
||||||
├── Mappings/
|
|
||||||
│ ├── BugReportMapping.cs
|
|
||||||
│ ├── BugReportLogMapping.cs
|
|
||||||
│ └── BugReportScreenshotMapping.cs
|
|
||||||
└── Repository/
|
|
||||||
└── BugReportRepository.cs
|
|
||||||
```
|
|
||||||
|
|
||||||
### 5️⃣ API Controller (1 فایل)
|
|
||||||
```
|
|
||||||
✓ ServiceHost/Controllers/
|
|
||||||
└── BugReportController.cs
|
|
||||||
```
|
|
||||||
|
|
||||||
### 6️⃣ Admin Pages (8 فایل)
|
|
||||||
```
|
|
||||||
✓ ServiceHost/Areas/AdminNew/Pages/BugReport/
|
|
||||||
├── BugReportPageModel.cs
|
|
||||||
├── Index.cshtml.cs
|
|
||||||
├── Index.cshtml
|
|
||||||
├── Details.cshtml.cs
|
|
||||||
├── Details.cshtml
|
|
||||||
├── Edit.cshtml.cs
|
|
||||||
├── Edit.cshtml
|
|
||||||
├── Delete.cshtml.cs
|
|
||||||
└── Delete.cshtml
|
|
||||||
```
|
|
||||||
|
|
||||||
### 7️⃣ Documentation (2 فایل)
|
|
||||||
```
|
|
||||||
✓ BUG_REPORT_SYSTEM.md
|
|
||||||
✓ FLUTTER_BUG_REPORT_EXAMPLE.dart
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ✏️ فایلهای اصلاح شده (2 فایل)
|
|
||||||
|
|
||||||
### 1. AccountManagement.Configuration/AccountManagementBootstrapper.cs
|
|
||||||
**تغییر:** اضافه کردن using برای BugReport
|
|
||||||
```csharp
|
|
||||||
using AccountManagement.Application.Contracts.BugReport;
|
|
||||||
```
|
|
||||||
|
|
||||||
**تغییر:** رجیستریشن سرویسها
|
|
||||||
```csharp
|
|
||||||
services.AddTransient<IBugReportApplication, BugReportApplication>();
|
|
||||||
services.AddTransient<IBugReportRepository, BugReportRepository>();
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2. AccountMangement.Infrastructure.EFCore/AccountContext.cs
|
|
||||||
**تغییر:** اضافه کردن using
|
|
||||||
```csharp
|
|
||||||
using AccountManagement.Domain.BugReportAgg;
|
|
||||||
```
|
|
||||||
|
|
||||||
**تغییر:** اضافه کردن DbSets
|
|
||||||
```csharp
|
|
||||||
#region BugReport
|
|
||||||
public DbSet<BugReport> BugReports { get; set; }
|
|
||||||
public DbSet<BugReportLog> BugReportLogs { get; set; }
|
|
||||||
public DbSet<BugReportScreenshot> BugReportScreenshots { get; set; }
|
|
||||||
#endregion
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔧 موارد مورد نیاز قبل از استفاده
|
|
||||||
|
|
||||||
### 1. Database Migration
|
|
||||||
```powershell
|
|
||||||
# در Package Manager Console
|
|
||||||
cd AccountMangement.Infrastructure.EFCore
|
|
||||||
|
|
||||||
Add-Migration AddBugReportSystem
|
|
||||||
Update-Database
|
|
||||||
```
|
|
||||||
|
|
||||||
### 2. الگوی Enum برای Flutter
|
|
||||||
```dart
|
|
||||||
enum BugReportType {
|
|
||||||
crash, // 1
|
|
||||||
ui, // 2
|
|
||||||
performance, // 3
|
|
||||||
feature, // 4
|
|
||||||
network, // 5
|
|
||||||
camera, // 6
|
|
||||||
faceRecognition, // 7
|
|
||||||
database, // 8
|
|
||||||
login, // 9
|
|
||||||
other, // 10
|
|
||||||
}
|
|
||||||
|
|
||||||
enum BugPriority {
|
|
||||||
critical, // 1
|
|
||||||
high, // 2
|
|
||||||
medium, // 3
|
|
||||||
low, // 4
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🚀 نقاط ورود
|
|
||||||
|
|
||||||
### API Endpoints
|
|
||||||
```
|
|
||||||
POST /api/bugreport/submit - ثبت گزارش جدید
|
|
||||||
GET /api/bugreport/list - دریافت لیست
|
|
||||||
GET /api/bugreport/{id} - دریافت جزئیات
|
|
||||||
PUT /api/bugreport/{id} - ویرایش وضعیت/اولویت
|
|
||||||
DELETE /api/bugreport/{id} - حذف گزارش
|
|
||||||
```
|
|
||||||
|
|
||||||
### Admin Pages
|
|
||||||
```
|
|
||||||
/AdminNew/BugReport - لیست گزارشها
|
|
||||||
/AdminNew/BugReport/Details/{id} - جزئیات کامل
|
|
||||||
/AdminNew/BugReport/Edit/{id} - ویرایش
|
|
||||||
/AdminNew/BugReport/Delete/{id} - حذف
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📊 Database Schema
|
|
||||||
|
|
||||||
### BugReports جدول
|
|
||||||
```sql
|
|
||||||
- id (bigint, PK)
|
|
||||||
- Title (nvarchar(200))
|
|
||||||
- Description (ntext)
|
|
||||||
- UserEmail (nvarchar(150))
|
|
||||||
- AccountId (bigint, nullable)
|
|
||||||
- DeviceModel (nvarchar(100))
|
|
||||||
- OsVersion (nvarchar(50))
|
|
||||||
- Platform (nvarchar(50))
|
|
||||||
- Manufacturer (nvarchar(100))
|
|
||||||
- DeviceId (nvarchar(200))
|
|
||||||
- ScreenResolution (nvarchar(50))
|
|
||||||
- MemoryInMB (int)
|
|
||||||
- StorageInMB (int)
|
|
||||||
- BatteryLevel (int)
|
|
||||||
- IsCharging (bit)
|
|
||||||
- NetworkType (nvarchar(50))
|
|
||||||
- AppVersion (nvarchar(50))
|
|
||||||
- BuildNumber (nvarchar(50))
|
|
||||||
- PackageName (nvarchar(150))
|
|
||||||
- InstallTime (datetime2)
|
|
||||||
- LastUpdateTime (datetime2)
|
|
||||||
- Flavor (nvarchar(50))
|
|
||||||
- Type (int)
|
|
||||||
- Priority (int)
|
|
||||||
- Status (int)
|
|
||||||
- StackTrace (ntext, nullable)
|
|
||||||
- CreationDate (datetime2)
|
|
||||||
- UpdateDate (datetime2, nullable)
|
|
||||||
```
|
|
||||||
|
|
||||||
### BugReportLogs جدول
|
|
||||||
```sql
|
|
||||||
- id (bigint, PK)
|
|
||||||
- BugReportId (bigint, FK)
|
|
||||||
- Message (ntext)
|
|
||||||
- Timestamp (datetime2)
|
|
||||||
```
|
|
||||||
|
|
||||||
### BugReportScreenshots جدول
|
|
||||||
```sql
|
|
||||||
- id (bigint, PK)
|
|
||||||
- BugReportId (bigint, FK)
|
|
||||||
- Base64Data (ntext)
|
|
||||||
- FileName (nvarchar(255))
|
|
||||||
- UploadDate (datetime2)
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ✨ مثال درخواست API
|
|
||||||
|
|
||||||
```json
|
|
||||||
POST /api/bugreport/submit
|
|
||||||
Content-Type: application/json
|
|
||||||
|
|
||||||
{
|
|
||||||
"title": "برنامه هنگام ورود خراب میشود",
|
|
||||||
"description": "هنگام فشار دادن دکمه ورود، برنامه کرش میکند",
|
|
||||||
"userEmail": "user@example.com",
|
|
||||||
"accountId": 123,
|
|
||||||
"deviceModel": "Samsung Galaxy S21",
|
|
||||||
"osVersion": "Android 12",
|
|
||||||
"platform": "Android",
|
|
||||||
"manufacturer": "Samsung",
|
|
||||||
"deviceId": "device-12345",
|
|
||||||
"screenResolution": "1440x3200",
|
|
||||||
"memoryInMB": 8000,
|
|
||||||
"storageInMB": 256000,
|
|
||||||
"batteryLevel": 75,
|
|
||||||
"isCharging": false,
|
|
||||||
"networkType": "4G",
|
|
||||||
"appVersion": "1.0.0",
|
|
||||||
"buildNumber": "100",
|
|
||||||
"packageName": "com.example.app",
|
|
||||||
"installTime": "2024-01-01T10:00:00Z",
|
|
||||||
"lastUpdateTime": "2024-12-07T14:30:00Z",
|
|
||||||
"flavor": "production",
|
|
||||||
"type": 1,
|
|
||||||
"priority": 2,
|
|
||||||
"stackTrace": "...",
|
|
||||||
"logs": ["log line 1", "log line 2"],
|
|
||||||
"screenshots": ["base64-string"]
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🔐 Security Features
|
|
||||||
|
|
||||||
- ✅ Authorization برای Admin Pages (AdminAreaPermission required)
|
|
||||||
- ✅ API Authentication
|
|
||||||
- ✅ XSS Protection (Html.Raw محدود)
|
|
||||||
- ✅ CSRF Protection (ASP.NET Core default)
|
|
||||||
- ✅ Input Validation
|
|
||||||
- ✅ Safe Delete with Confirmation
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📚 Documentation Files
|
|
||||||
|
|
||||||
1. **BUG_REPORT_SYSTEM.md** - راهنمای کامل سیستم
|
|
||||||
2. **FLUTTER_BUG_REPORT_EXAMPLE.dart** - مثال پیادهسازی Flutter
|
|
||||||
3. **CHANGELOG.md** (این فایل) - خلاصه تغییرات
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## ✅ Checklist پیادهسازی
|
|
||||||
|
|
||||||
- [x] Domain Models
|
|
||||||
- [x] Database Mappings
|
|
||||||
- [x] Repository Pattern
|
|
||||||
- [x] Application Services
|
|
||||||
- [x] API Endpoints
|
|
||||||
- [x] Admin UI Pages
|
|
||||||
- [x] Dependency Injection
|
|
||||||
- [x] Error Handling
|
|
||||||
- [x] Documentation
|
|
||||||
- [x] Flutter Example
|
|
||||||
- [ ] Database Migration (باید دستی اجرا شود)
|
|
||||||
- [ ] Testing
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 🎯 مراحل بعدی
|
|
||||||
|
|
||||||
1. **اجرای Migration:**
|
|
||||||
```powershell
|
|
||||||
Add-Migration AddBugReportSystem
|
|
||||||
Update-Database
|
|
||||||
```
|
|
||||||
|
|
||||||
2. **تست API:**
|
|
||||||
- استفاده از Postman/Thunder Client
|
|
||||||
- تست تمام endpoints
|
|
||||||
|
|
||||||
3. **تست Admin Panel:**
|
|
||||||
- دسترسی به /AdminNew/BugReport
|
|
||||||
- تست فیلترها و جستجو
|
|
||||||
- تست ویرایش و حذف
|
|
||||||
|
|
||||||
4. **Integration Flutter:**
|
|
||||||
- کپی کردن `FLUTTER_BUG_REPORT_EXAMPLE.dart`
|
|
||||||
- سازگار کردن با پروژه Flutter
|
|
||||||
- تست ثبت گزارشها
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
## 📞 پشتیبانی
|
|
||||||
|
|
||||||
برای هر سوال یا مشکل:
|
|
||||||
1. بررسی کنید `BUG_REPORT_SYSTEM.md`
|
|
||||||
2. بررسی کنید logs و error messages
|
|
||||||
3. مطمئن شوید Migration اجرا شده است
|
|
||||||
|
|
||||||
@@ -1,7 +1,6 @@
|
|||||||
using System;
|
using System;
|
||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
using _0_Framework.Domain;
|
using _0_Framework.Domain;
|
||||||
using CompanyManagment.App.Contracts.AndroidApkVersion;
|
|
||||||
|
|
||||||
namespace Company.Domain.AndroidApkVersionAgg;
|
namespace Company.Domain.AndroidApkVersionAgg;
|
||||||
|
|
||||||
@@ -9,17 +8,14 @@ public class AndroidApkVersion:EntityBase
|
|||||||
{
|
{
|
||||||
private AndroidApkVersion () { }
|
private AndroidApkVersion () { }
|
||||||
|
|
||||||
public AndroidApkVersion( string versionName,string versionCode, IsActive isActive, string path, ApkType apkType, bool isForce = false)
|
public AndroidApkVersion( string versionName,string versionCode, IsActive isActive, string path)
|
||||||
{
|
{
|
||||||
|
|
||||||
VersionName = versionName;
|
VersionName = versionName;
|
||||||
VersionCode = versionCode;
|
VersionCode = versionCode;
|
||||||
IsActive = isActive;
|
IsActive = isActive;
|
||||||
Path = path;
|
Path = path;
|
||||||
ApkType = apkType;
|
Title = $"Gozareshgir-{versionName}-{CreationDate:g}";
|
||||||
IsForce = isForce;
|
|
||||||
var appName = apkType == ApkType.WebView ? "Gozareshgir-WebView" : "Gozareshgir-FaceDetection";
|
|
||||||
Title = $"{appName}-{versionName}-{CreationDate:g}";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public string Title { get; private set; }
|
public string Title { get; private set; }
|
||||||
@@ -27,9 +23,6 @@ public class AndroidApkVersion:EntityBase
|
|||||||
public string VersionCode{ get; private set; }
|
public string VersionCode{ get; private set; }
|
||||||
public IsActive IsActive { get; private set; }
|
public IsActive IsActive { get; private set; }
|
||||||
public string Path { get; set; }
|
public string Path { get; set; }
|
||||||
public ApkType ApkType { get; private set; }
|
|
||||||
public bool IsForce { get; private set; }
|
|
||||||
|
|
||||||
|
|
||||||
public void Active()
|
public void Active()
|
||||||
{
|
{
|
||||||
@@ -40,4 +33,4 @@ public class AndroidApkVersion:EntityBase
|
|||||||
{
|
{
|
||||||
IsActive = IsActive.False;
|
IsActive = IsActive.False;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,14 +1,12 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using _0_Framework_b.Domain;
|
using _0_Framework_b.Domain;
|
||||||
using CompanyManagment.App.Contracts.AndroidApkVersion;
|
|
||||||
|
|
||||||
namespace Company.Domain.AndroidApkVersionAgg;
|
namespace Company.Domain.AndroidApkVersionAgg;
|
||||||
|
|
||||||
public interface IAndroidApkVersionRepository:IRepository<long,AndroidApkVersion>
|
public interface IAndroidApkVersionRepository:IRepository<long,AndroidApkVersion>
|
||||||
{
|
{
|
||||||
IQueryable<AndroidApkVersion> GetActives(ApkType apkType);
|
IQueryable<AndroidApkVersion> GetActives();
|
||||||
AndroidApkVersion GetLatestActive(ApkType apkType);
|
|
||||||
void Remove(AndroidApkVersion entity);
|
void Remove(AndroidApkVersion entity);
|
||||||
System.Threading.Tasks.Task<string> GetLatestActiveVersionPath(ApkType apkType);
|
System.Threading.Tasks.Task<string> GetLatestActiveVersionPath();
|
||||||
}
|
}
|
||||||
@@ -1,195 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using _0_Framework.Domain;
|
|
||||||
using MongoDB.Bson.Serialization.Attributes;
|
|
||||||
|
|
||||||
namespace Company.Domain.CameraBugReportAgg;
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// مدل دامنه برای گزارش خرابی دوربین
|
|
||||||
/// </summary>
|
|
||||||
public class CameraBugReport
|
|
||||||
{
|
|
||||||
[BsonId]
|
|
||||||
[BsonRepresentation(MongoDB.Bson.BsonType.String)]
|
|
||||||
public Guid Id { get; set; }
|
|
||||||
|
|
||||||
public CameraBugReport()
|
|
||||||
{
|
|
||||||
Id = Guid.NewGuid();
|
|
||||||
CreationDate = DateTime.Now;
|
|
||||||
Status = CameraBugReportStatus.Open;
|
|
||||||
Screenshots = new List<CameraBugReportScreenshot>();
|
|
||||||
Logs = new List<CameraBugReportLog>();
|
|
||||||
}
|
|
||||||
|
|
||||||
public CameraBugReport(
|
|
||||||
string title,
|
|
||||||
string description,
|
|
||||||
string userEmail,
|
|
||||||
string deviceModel,
|
|
||||||
string osVersion,
|
|
||||||
string manufacturer,
|
|
||||||
string buildNumber,
|
|
||||||
string appVersion,
|
|
||||||
string screenResolution,
|
|
||||||
bool isCharging,
|
|
||||||
int batteryLevel,
|
|
||||||
int storageInMB,
|
|
||||||
int memoryInMB,
|
|
||||||
string networkType,
|
|
||||||
string platform,
|
|
||||||
string deviceId,
|
|
||||||
string packageName,
|
|
||||||
DateTime installTime,
|
|
||||||
DateTime lastUpdateTime,
|
|
||||||
string flavor,
|
|
||||||
CameraBugReportType type,
|
|
||||||
CameraBugPriority priority,
|
|
||||||
long? accountId = null,
|
|
||||||
string stackTrace = null) : this()
|
|
||||||
|
|
||||||
{
|
|
||||||
Priority = priority;
|
|
||||||
Type = type;
|
|
||||||
Flavor = flavor;
|
|
||||||
LastUpdateTime = lastUpdateTime;
|
|
||||||
InstallTime = installTime;
|
|
||||||
PackageName = packageName;
|
|
||||||
BuildNumber = buildNumber;
|
|
||||||
AppVersion = appVersion;
|
|
||||||
NetworkType = networkType;
|
|
||||||
IsCharging = isCharging;
|
|
||||||
BatteryLevel = batteryLevel;
|
|
||||||
StorageInMB = storageInMB;
|
|
||||||
MemoryInMB = memoryInMB;
|
|
||||||
ScreenResolution = screenResolution;
|
|
||||||
DeviceId = deviceId;
|
|
||||||
Manufacturer = manufacturer;
|
|
||||||
Platform = platform;
|
|
||||||
OsVersion = osVersion;
|
|
||||||
DeviceModel = deviceModel;
|
|
||||||
AccountId = accountId;
|
|
||||||
UserEmail = userEmail;
|
|
||||||
Description = description;
|
|
||||||
Title = title;
|
|
||||||
StackTrace = stackTrace;
|
|
||||||
}
|
|
||||||
|
|
||||||
[BsonElement("screenshots")]
|
|
||||||
public List<CameraBugReportScreenshot> Screenshots { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("logs")]
|
|
||||||
public List<CameraBugReportLog> Logs { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("updateDate")]
|
|
||||||
public DateTime? UpdateDate { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("creationDate")]
|
|
||||||
public DateTime CreationDate { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("stackTrace")]
|
|
||||||
public string StackTrace { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("status")]
|
|
||||||
[BsonRepresentation(MongoDB.Bson.BsonType.String)]
|
|
||||||
public CameraBugReportStatus Status { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("priority")]
|
|
||||||
[BsonRepresentation(MongoDB.Bson.BsonType.String)]
|
|
||||||
|
|
||||||
public CameraBugPriority Priority { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("type")]
|
|
||||||
[BsonRepresentation(MongoDB.Bson.BsonType.String)]
|
|
||||||
|
|
||||||
public CameraBugReportType Type { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("flavor")]
|
|
||||||
public string Flavor { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("lastUpdateTime")]
|
|
||||||
public DateTime LastUpdateTime { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("installTime")]
|
|
||||||
public DateTime InstallTime { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("packageName")]
|
|
||||||
public string PackageName { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("buildNumber")]
|
|
||||||
public string BuildNumber { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("appVersion")]
|
|
||||||
public string AppVersion { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("networkType")]
|
|
||||||
public string NetworkType { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("isCharging")]
|
|
||||||
public bool IsCharging { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("batteryLevel")]
|
|
||||||
public int BatteryLevel { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("storageInMB")]
|
|
||||||
public int StorageInMB { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("memoryInMB")]
|
|
||||||
public int MemoryInMB { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("screenResolution")]
|
|
||||||
public string ScreenResolution { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("deviceId")]
|
|
||||||
public string DeviceId { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("manufacturer")]
|
|
||||||
public string Manufacturer { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("platform")]
|
|
||||||
public string Platform { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("osVersion")]
|
|
||||||
public string OsVersion { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("deviceModel")]
|
|
||||||
public string DeviceModel { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("accountId")]
|
|
||||||
public long? AccountId { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("userEmail")]
|
|
||||||
public string UserEmail { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("description")]
|
|
||||||
public string Description { get; private set; }
|
|
||||||
|
|
||||||
[BsonElement("title")]
|
|
||||||
public string Title { get; private set; }
|
|
||||||
|
|
||||||
|
|
||||||
public void ChangeStatus(CameraBugReportStatus newStatus)
|
|
||||||
{
|
|
||||||
UpdateDate = DateTime.Now;
|
|
||||||
Status = newStatus;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ChangePriority(CameraBugPriority newPriority)
|
|
||||||
{
|
|
||||||
Priority = newPriority;
|
|
||||||
UpdateDate = DateTime.Now;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void AddScreenshot(string base64Data, string fileName)
|
|
||||||
{
|
|
||||||
Screenshots.Add(new CameraBugReportScreenshot
|
|
||||||
{ Base64Data = base64Data, FileName = fileName, UploadDate = DateTime.Now });
|
|
||||||
}
|
|
||||||
|
|
||||||
public void AddLog(string logMessage)
|
|
||||||
{
|
|
||||||
Logs.Add(new CameraBugReportLog { Message = logMessage, Timestamp = DateTime.Now });
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -1,20 +0,0 @@
|
|||||||
using System;
|
|
||||||
using _0_Framework.Domain;
|
|
||||||
using MongoDB.Bson.Serialization.Attributes;
|
|
||||||
|
|
||||||
namespace Company.Domain.CameraBugReportAgg
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// لاگهای گزارش خرابی دوربین
|
|
||||||
/// </summary>
|
|
||||||
public class CameraBugReportLog : EntityBase
|
|
||||||
{
|
|
||||||
// FK و navigation property حذف شد برای MongoDB
|
|
||||||
[BsonElement("message")]
|
|
||||||
public string Message { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("timestamp")]
|
|
||||||
public DateTime Timestamp { get; set; }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -1,23 +0,0 @@
|
|||||||
using System;
|
|
||||||
using _0_Framework.Domain;
|
|
||||||
using MongoDB.Bson.Serialization.Attributes;
|
|
||||||
|
|
||||||
namespace Company.Domain.CameraBugReportAgg
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// عکسهای ضمیمه شده به گزارش خرابی دوربین (Base64 encoded)
|
|
||||||
/// </summary>
|
|
||||||
public class CameraBugReportScreenshot : EntityBase
|
|
||||||
{
|
|
||||||
// FK و navigation property حذف شد برای MongoDB
|
|
||||||
[BsonElement("base64Data")]
|
|
||||||
public string Base64Data { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("fileName")]
|
|
||||||
public string FileName { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("uploadDate")]
|
|
||||||
public DateTime UploadDate { get; set; }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -1,34 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using _0_Framework.InfraStructure;
|
|
||||||
|
|
||||||
namespace Company.Domain.CameraBugReportAgg;
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// رابط انبار گزارش خرابی دوربین برای MongoDB
|
|
||||||
/// </summary>
|
|
||||||
public interface ICameraBugReportRepository
|
|
||||||
{
|
|
||||||
// Async methods for MongoDB operations
|
|
||||||
Task CreateAsync(CameraBugReport bugReport);
|
|
||||||
Task UpdateAsync(CameraBugReport bugReport);
|
|
||||||
Task<CameraBugReport> GetByIdAsync(Guid id);
|
|
||||||
Task<List<CameraBugReport>> GetAllAsync();
|
|
||||||
Task<List<CameraBugReport>> GetAllAsync(int skip, int take);
|
|
||||||
Task DeleteAsync(Guid id);
|
|
||||||
Task<bool> IsExistAsync(Guid id);
|
|
||||||
Task<List<CameraBugReport>> FilterAsync(
|
|
||||||
CameraBugReportType? type = null,
|
|
||||||
CameraBugPriority? priority = null,
|
|
||||||
CameraBugReportStatus? status = null,
|
|
||||||
string searchTerm = null,
|
|
||||||
int skip = 0,
|
|
||||||
int take = 10);
|
|
||||||
Task<int> CountAsync(
|
|
||||||
CameraBugReportType? type = null,
|
|
||||||
CameraBugPriority? priority = null,
|
|
||||||
CameraBugReportStatus? status = null,
|
|
||||||
string searchTerm = null);
|
|
||||||
}
|
|
||||||
@@ -1,7 +1,6 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections;
|
using System.Collections;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Security.AccessControl;
|
|
||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
using _0_Framework.Domain;
|
using _0_Framework.Domain;
|
||||||
using _0_Framework.Domain.CustomizeCheckoutShared.Enums;
|
using _0_Framework.Domain.CustomizeCheckoutShared.Enums;
|
||||||
@@ -13,25 +12,25 @@ namespace Company.Domain.CheckoutAgg;
|
|||||||
|
|
||||||
public class Checkout : EntityBase
|
public class Checkout : EntityBase
|
||||||
{
|
{
|
||||||
public Checkout()
|
private Checkout()
|
||||||
{
|
{
|
||||||
}
|
|
||||||
|
}
|
||||||
public Checkout(string employeeFullName, string fathersName, string nationalCode, string dateOfBirth,
|
public Checkout(string employeeFullName, string fathersName, string nationalCode, string dateOfBirth,
|
||||||
long employeeId, string workshopName, long workshopId, string contractNo, DateTime contractStart,
|
long employeeId, string workshopName, long workshopId, string contractNo, DateTime contractStart,
|
||||||
DateTime contractEnd, string month, string year, long contractId, long workingHoursId,
|
DateTime contractEnd, string month, string year, long contractId, long workingHoursId,
|
||||||
double monthlySalary, double baseYearsPay, double consumableItems, double housingAllowance,
|
double monthlySalary, double baseYearsPay, double consumableItems, double housingAllowance,
|
||||||
double overtimePay, double nightworkPay, double fridayPay, double missionPay, double shiftPay,
|
double overtimePay, double nightworkPay, double fridayPay, double missionPay, double shiftPay,
|
||||||
double familyAllowance, double bonusesPay, double yearsPay, double leavePay,
|
double familyAllowance, double bonusesPay, double yearsPay, double leavePay,
|
||||||
double insuranceDeduction, double taxDeducation, double installmentDeduction,
|
double insuranceDeduction, double taxDeducation, double installmentDeduction,
|
||||||
double salaryAidDeduction, double absenceDeduction, string sumOfWorkingDays
|
double salaryAidDeduction, double absenceDeduction, string sumOfWorkingDays
|
||||||
, string archiveCode, string personnelCode,
|
, string archiveCode, string personnelCode,
|
||||||
string totalClaims, string totalDeductions, double totalPayment, string signature, double marriedAllowance, bool leaveCheckout,
|
string totalClaims, string totalDeductions, double totalPayment, string signature, double marriedAllowance, bool leaveCheckout,
|
||||||
double creditLeaves, double absencePeriod, double averageHoursPerDay, bool hasRollCall, string overTimeWorkvalue,
|
double creditLeaves, double absencePeriod, double averageHoursPerDay, bool hasRollCall, string overTimeWorkvalue,
|
||||||
string overNightWorkValue, string fridayWorkValue, string rotatingShifValue, string absenceValue,
|
string overNightWorkValue, string fridayWorkValue, string rotatingShifValue, string absenceValue,
|
||||||
string totalDayOfLeaveCompute, string totalDayOfYearsCompute, string totalDayOfBunosesCompute,
|
string totalDayOfLeaveCompute, string totalDayOfYearsCompute, string totalDayOfBunosesCompute,
|
||||||
ICollection<CheckoutLoanInstallment> loanInstallments,
|
ICollection<CheckoutLoanInstallment> loanInstallments,
|
||||||
ICollection<CheckoutSalaryAid> salaryAids, CheckoutRollCall checkoutRollCall, TimeSpan employeeMandatoryHours, bool hasInsuranceShareTheSameAsList)
|
ICollection<CheckoutSalaryAid> salaryAids,CheckoutRollCall checkoutRollCall,TimeSpan employeeMandatoryHours)
|
||||||
{
|
{
|
||||||
EmployeeFullName = employeeFullName;
|
EmployeeFullName = employeeFullName;
|
||||||
FathersName = fathersName;
|
FathersName = fathersName;
|
||||||
@@ -92,7 +91,6 @@ public class Checkout : EntityBase
|
|||||||
SalaryAids = salaryAids;
|
SalaryAids = salaryAids;
|
||||||
CheckoutRollCall = checkoutRollCall;
|
CheckoutRollCall = checkoutRollCall;
|
||||||
EmployeeMandatoryHours = employeeMandatoryHours;
|
EmployeeMandatoryHours = employeeMandatoryHours;
|
||||||
HasInsuranceShareTheSameAsList = hasInsuranceShareTheSameAsList;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -101,7 +99,7 @@ public class Checkout : EntityBase
|
|||||||
public string Signature { get; private set; }
|
public string Signature { get; private set; }
|
||||||
public string FathersName { get; private set; }
|
public string FathersName { get; private set; }
|
||||||
public string NationalCode { get; private set; }
|
public string NationalCode { get; private set; }
|
||||||
public string DateOfBirth { get; private set; }
|
public string DateOfBirth { get; private set; }
|
||||||
public long EmployeeId { get; private set; }
|
public long EmployeeId { get; private set; }
|
||||||
|
|
||||||
public string WorkshopName { get; private set; }
|
public string WorkshopName { get; private set; }
|
||||||
@@ -137,7 +135,7 @@ public class Checkout : EntityBase
|
|||||||
public double SalaryAidDeduction { get; private set; }
|
public double SalaryAidDeduction { get; private set; }
|
||||||
|
|
||||||
public double AbsenceDeduction { get; private set; }
|
public double AbsenceDeduction { get; private set; }
|
||||||
|
|
||||||
public string SumOfWorkingDays { get; private set; }
|
public string SumOfWorkingDays { get; private set; }
|
||||||
public string ArchiveCode { get; private set; }
|
public string ArchiveCode { get; private set; }
|
||||||
public string PersonnelCode { get; private set; }
|
public string PersonnelCode { get; private set; }
|
||||||
@@ -159,70 +157,58 @@ public class Checkout : EntityBase
|
|||||||
//میانگین ساعت کار در یک روز
|
//میانگین ساعت کار در یک روز
|
||||||
public double AverageHoursPerDay { get; private set; }
|
public double AverageHoursPerDay { get; private set; }
|
||||||
public bool HasRollCall { get; private set; }
|
public bool HasRollCall { get; private set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// مقدار اضافه کار
|
/// مقدار اضافه کار
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string OverTimeWorkValue { get; private set; }
|
public string OverTimeWorkValue { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// مقدار شبکاری
|
/// مقدار شبکاری
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string OverNightWorkValue { get; private set; }
|
public string OverNightWorkValue { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// مقدار جمعه کاری
|
/// مقدار جمعه کاری
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string FridayWorkValue { get; private set; }
|
public string FridayWorkValue { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// درصد نوبت کاری
|
/// درصد نوبت کاری
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string RotatingShiftValue { get; private set; }
|
public string RotatingShiftValue { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// مقدار غیبت
|
/// مقدار غیبت
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string AbsenceValue { get; private set; }
|
public string AbsenceValue { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// تعداد روزهای محاسبه شده برای مزد مرخصی
|
/// تعداد روزهای محاسبه شده برای مزد مرخصی
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string TotalDayOfLeaveCompute { get; private set; }
|
public string TotalDayOfLeaveCompute { get; private set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// تعداد روزهای محاسبه شده برای سنوات
|
/// تعداد روزهای محاسبه شده برای سنوات
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string TotalDayOfYearsCompute { get; private set; }
|
public string TotalDayOfYearsCompute { get; private set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// تعداد روزهای محاسبه شده برای عیدی و پاداش
|
/// تعداد روزهای محاسبه شده برای عیدی و پاداش
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string TotalDayOfBunosesCompute { get; private set; }
|
public string TotalDayOfBunosesCompute { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// دارای تداخل مبلغ است. این در زمانی اتفاق می افتد که فیش مبلغ آن تغییر کرده ولی به دلیل مسائل قانونی امکان صدور دوباره آن وجود ندارد
|
/// دارای تداخل مبلغ است. این در زمانی اتفاق می افتد که فیش مبلغ آن تغییر کرده ولی به دلیل مسائل قانونی امکان صدور دوباره آن وجود ندارد
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool HasAmountConflict { get; private set; }
|
public bool HasAmountConflict { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// ساعت موظفی پرسنل در ماه
|
/// ساعت موظفی پرسنل در ماه
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public TimeSpan EmployeeMandatoryHours { get; set; }
|
public TimeSpan EmployeeMandatoryHours { get; set; }
|
||||||
|
|
||||||
|
#region valueObjects
|
||||||
|
|
||||||
/// <summary>
|
public ICollection<CheckoutLoanInstallment> LoanInstallments { get; set; } = [];
|
||||||
/// آیا حق بیمه مشابه لیست بیمه حساب شده؟
|
public ICollection<CheckoutSalaryAid> SalaryAids { get; set; } = [];
|
||||||
/// </summary>
|
|
||||||
public bool HasInsuranceShareTheSameAsList { get; private set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// آیا فیش نیاز به بروزرسانی دارد
|
|
||||||
/// </summary>
|
|
||||||
public bool IsUpdateNeeded { get; private set; }
|
|
||||||
|
|
||||||
public List<CheckoutWarningMessage> CheckoutWarningMessageList { get; set; }
|
|
||||||
|
|
||||||
#region valueObjects
|
|
||||||
|
|
||||||
public ICollection<CheckoutLoanInstallment> LoanInstallments { get; set; } = [];
|
|
||||||
public ICollection<CheckoutSalaryAid> SalaryAids { get; set; } = [];
|
|
||||||
public CheckoutRollCall CheckoutRollCall { get; private set; }
|
public CheckoutRollCall CheckoutRollCall { get; private set; }
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
@@ -291,7 +277,7 @@ public class Checkout : EntityBase
|
|||||||
var year = contarctStart.ToFarsiYear();
|
var year = contarctStart.ToFarsiYear();
|
||||||
var sumYear = year.Substring(Math.Max(0, year.Length - 2));
|
var sumYear = year.Substring(Math.Max(0, year.Length - 2));
|
||||||
|
|
||||||
|
|
||||||
ContractNo = archiveCode + "/" + personnelCode + "/" + sumYear + "/" + month;
|
ContractNo = archiveCode + "/" + personnelCode + "/" + sumYear + "/" + month;
|
||||||
}
|
}
|
||||||
public void Active()
|
public void Active()
|
||||||
@@ -326,7 +312,7 @@ public class Checkout : EntityBase
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public void SetSalaryAid(ICollection<CheckoutSalaryAid> salaryAids, double salaryAidAmount)
|
public void SetSalaryAid(ICollection<CheckoutSalaryAid> salaryAids,double salaryAidAmount)
|
||||||
{
|
{
|
||||||
SalaryAids = salaryAids;
|
SalaryAids = salaryAids;
|
||||||
SalaryAidDeduction = salaryAidAmount;
|
SalaryAidDeduction = salaryAidAmount;
|
||||||
@@ -344,45 +330,30 @@ public class Checkout : EntityBase
|
|||||||
|
|
||||||
public void SetAmountConflict(bool hasAmountConflict)
|
public void SetAmountConflict(bool hasAmountConflict)
|
||||||
{
|
{
|
||||||
HasAmountConflict = hasAmountConflict;
|
HasAmountConflict = hasAmountConflict;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void SetEmployeeMandatoryHours(TimeSpan employeeMandatoryHours)
|
public void SetEmployeeMandatoryHours(TimeSpan employeeMandatoryHours)
|
||||||
{
|
{
|
||||||
EmployeeMandatoryHours = employeeMandatoryHours;
|
EmployeeMandatoryHours = employeeMandatoryHours;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void SetInsuranceShare()
|
|
||||||
{
|
|
||||||
HasInsuranceShareTheSameAsList = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// نیاز به آپدیت
|
|
||||||
/// </summary>
|
|
||||||
public void SetUpdateNeeded()
|
|
||||||
{
|
|
||||||
IsUpdateNeeded = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public class CheckoutRollCall
|
public class CheckoutRollCall
|
||||||
{
|
{
|
||||||
private CheckoutRollCall() { }
|
private CheckoutRollCall(){}
|
||||||
public CheckoutRollCall(TimeSpan totalMandatoryTimeSpan, TimeSpan totalPresentTimeSpan, TimeSpan totalBreakTimeSpan,
|
public CheckoutRollCall(TimeSpan totalMandatoryTimeSpan, TimeSpan totalPresentTimeSpan, TimeSpan totalBreakTimeSpan,
|
||||||
TimeSpan totalWorkingTimeSpan, TimeSpan totalPaidLeaveTmeSpan, TimeSpan totalSickLeaveTimeSpan,
|
TimeSpan totalWorkingTimeSpan, TimeSpan totalPaidLeaveTmeSpan, TimeSpan totalSickLeaveTimeSpan,
|
||||||
ICollection<CheckoutRollCallDay> rollCallDaysCollection)
|
ICollection<CheckoutRollCallDay> rollCallDaysCollection)
|
||||||
{
|
{
|
||||||
TotalMandatoryTimeSpan = totalMandatoryTimeSpan;
|
TotalMandatoryTimeSpan = totalMandatoryTimeSpan;
|
||||||
TotalPresentTimeSpan = totalPresentTimeSpan;
|
TotalPresentTimeSpan = totalPresentTimeSpan;
|
||||||
TotalBreakTimeSpan = totalBreakTimeSpan;
|
TotalBreakTimeSpan = totalBreakTimeSpan;
|
||||||
TotalWorkingTimeSpan = totalWorkingTimeSpan;
|
TotalWorkingTimeSpan = totalWorkingTimeSpan;
|
||||||
TotalPaidLeaveTmeSpan = totalPaidLeaveTmeSpan;
|
TotalPaidLeaveTmeSpan = totalPaidLeaveTmeSpan;
|
||||||
TotalSickLeaveTimeSpan = totalSickLeaveTimeSpan;
|
TotalSickLeaveTimeSpan = totalSickLeaveTimeSpan;
|
||||||
RollCallDaysCollection = rollCallDaysCollection;
|
RollCallDaysCollection = rollCallDaysCollection;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -423,27 +394,27 @@ public class CheckoutRollCall
|
|||||||
|
|
||||||
public class CheckoutRollCallDay
|
public class CheckoutRollCallDay
|
||||||
{
|
{
|
||||||
private CheckoutRollCallDay() { }
|
private CheckoutRollCallDay(){}
|
||||||
public CheckoutRollCallDay(DateTime date, string firstStartDate, string firstEndDate,
|
public CheckoutRollCallDay(DateTime date, string firstStartDate, string firstEndDate,
|
||||||
string secondStartDate, string secondEndDate, TimeSpan breakTimeSpan,
|
string secondStartDate, string secondEndDate, TimeSpan breakTimeSpan,
|
||||||
bool isSliced, TimeSpan workingTimeSpan, bool isAbsent, bool isFriday,
|
bool isSliced, TimeSpan workingTimeSpan, bool isAbsent, bool isFriday,
|
||||||
bool isHoliday, string leaveType)
|
bool isHoliday, string leaveType)
|
||||||
{
|
{
|
||||||
Date = date;
|
Date = date;
|
||||||
FirstStartDate = firstStartDate;
|
FirstStartDate = firstStartDate;
|
||||||
FirstEndDate = firstEndDate;
|
FirstEndDate = firstEndDate;
|
||||||
SecondStartDate = secondStartDate;
|
SecondStartDate = secondStartDate;
|
||||||
SecondEndDate = secondEndDate;
|
SecondEndDate = secondEndDate;
|
||||||
BreakTimeSpan = breakTimeSpan;
|
BreakTimeSpan = breakTimeSpan;
|
||||||
IsSliced = isSliced;
|
IsSliced = isSliced;
|
||||||
WorkingTimeSpan = workingTimeSpan;
|
WorkingTimeSpan = workingTimeSpan;
|
||||||
IsAbsent = isAbsent;
|
IsAbsent = isAbsent;
|
||||||
IsFriday = isFriday;
|
IsFriday = isFriday;
|
||||||
IsHoliday = isHoliday;
|
IsHoliday = isHoliday;
|
||||||
LeaveType = leaveType;
|
LeaveType = leaveType;
|
||||||
}
|
}
|
||||||
|
|
||||||
public long Id { get; set; }
|
public long Id { get; set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// تاریخ
|
/// تاریخ
|
||||||
@@ -487,12 +458,12 @@ public class CheckoutRollCallDay
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// آیا غیبت است
|
/// آیا غیبت است
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool IsAbsent { get; private set; }
|
public bool IsAbsent { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// آیا جمعه است
|
/// آیا جمعه است
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool IsFriday { get; private set; }
|
public bool IsFriday { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// آیا تعطیل رسمی است
|
/// آیا تعطیل رسمی است
|
||||||
@@ -504,6 +475,6 @@ public class CheckoutRollCallDay
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public string LeaveType { get; private set; }
|
public string LeaveType { get; private set; }
|
||||||
|
|
||||||
public long CheckoutId { get; set; }
|
public long CheckoutId { get; set; }
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -1,32 +0,0 @@
|
|||||||
using _0_Framework.Application.Enums;
|
|
||||||
using _0_Framework.Domain;
|
|
||||||
|
|
||||||
namespace Company.Domain.CheckoutAgg;
|
|
||||||
|
|
||||||
public class CheckoutWarningMessage : EntityBaseWithoutCreationDate
|
|
||||||
{
|
|
||||||
public CheckoutWarningMessage(string warningMessage, long checkoutId, TypeOfCheckoutWarning typeOfCheckoutWarning)
|
|
||||||
{
|
|
||||||
WarningMessage = warningMessage;
|
|
||||||
CheckoutId = checkoutId;
|
|
||||||
TypeOfCheckoutWarning = typeOfCheckoutWarning;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// پیام هشدار
|
|
||||||
/// </summary>
|
|
||||||
public string WarningMessage { get; private set; }
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// آی دی فیش حقوقی
|
|
||||||
/// </summary>
|
|
||||||
public long CheckoutId { get; private set; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// نوع هشدار فیش حقوقی
|
|
||||||
/// </summary>
|
|
||||||
public TypeOfCheckoutWarning TypeOfCheckoutWarning { get; private set; }
|
|
||||||
|
|
||||||
public Checkout Checkout { get; set; }
|
|
||||||
}
|
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net10.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
@@ -16,15 +16,10 @@
|
|||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Folder Include="CheckoutAgg\ValueObjects\" />
|
<Folder Include="CheckoutAgg\ValueObjects\" />
|
||||||
<Folder Include="_common\" />
|
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http" Version="2.3.0" />
|
<PackageReference Include="MongoDB.Bson" Version="3.5.0" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.3.0" />
|
|
||||||
<PackageReference Include="Microsoft.Extensions.Caching.Memory" Version="10.0.1" />
|
|
||||||
<PackageReference Include="MongoDB.Bson" Version="3.5.2" />
|
|
||||||
<PackageReference Include="System.Security.Cryptography.Xml" Version="10.0.1" />
|
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
using System;
|
using CompanyManagment.App.Contracts.PersonalContractingParty;
|
||||||
using CompanyManagment.App.Contracts.PersonalContractingParty;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
using _0_Framework.Domain;
|
using _0_Framework.Domain;
|
||||||
@@ -33,9 +32,7 @@ public interface IPersonalContractingPartyRepository :IRepository<long, Personal
|
|||||||
List<PersonalContractingPartyViewModel> SearchForMain(PersonalContractingPartySearchModel searchModel2);
|
List<PersonalContractingPartyViewModel> SearchForMain(PersonalContractingPartySearchModel searchModel2);
|
||||||
OperationResult DeletePersonalContractingParties(long id);
|
OperationResult DeletePersonalContractingParties(long id);
|
||||||
bool GetHasContract(long id);
|
bool GetHasContract(long id);
|
||||||
[Obsolete("از متدهای async استفاده کنید")]
|
|
||||||
OperationResult DeActiveAll(long id);
|
OperationResult DeActiveAll(long id);
|
||||||
[Obsolete("از متدهای async استفاده کنید")]
|
|
||||||
OperationResult ActiveAll(long id);
|
OperationResult ActiveAll(long id);
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
@@ -78,10 +75,5 @@ public interface IPersonalContractingPartyRepository :IRepository<long, Personal
|
|||||||
Task<GetLegalContractingPartyDetailsViewModel> GetLegalDetails(long id);
|
Task<GetLegalContractingPartyDetailsViewModel> GetLegalDetails(long id);
|
||||||
|
|
||||||
Task<PersonalContractingParty> GetByNationalCode(string nationalCode);
|
Task<PersonalContractingParty> GetByNationalCode(string nationalCode);
|
||||||
Task<PersonalContractingParty> GetByNationalId(string registerId);
|
Task<PersonalContractingParty> GetByRegisterId(string registerId);
|
||||||
|
|
||||||
Task<OperationResult> DeActiveAllAsync(long id);
|
|
||||||
Task<OperationResult> ActiveAllAsync(long id);
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -251,35 +251,6 @@ public class PersonalContractingParty : EntityBase
|
|||||||
this.IsAuthenticated = true;
|
this.IsAuthenticated = true;
|
||||||
Phone = phone;
|
Phone = phone;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void UnAuthenticateRealEdit(string fName, string lName, string fatherName,string idNumber,
|
|
||||||
string idNumberSeri, string idNumberSerial, string dateOfBirth, Gender gender,string phone)
|
|
||||||
{
|
|
||||||
this.FName = fName;
|
|
||||||
this.LName = lName;
|
|
||||||
this.FatherName = fatherName;
|
|
||||||
this.IdNumberSeri = idNumberSeri;
|
|
||||||
this.IdNumberSerial = idNumberSerial;
|
|
||||||
this.DateOfBirth = !string.IsNullOrWhiteSpace(dateOfBirth) ? dateOfBirth.ToGeorgianDateTime() : null;
|
|
||||||
this.IdNumber = idNumber;
|
|
||||||
this.Gender = gender;
|
|
||||||
Phone = phone;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void UnAuthenticateLegalEdit(string fName, string lName, string fatherName, string idNumber,
|
|
||||||
string idNumberSeri,
|
|
||||||
string idNumberSerial, string dateOfBirth, Gender gender, string phone)
|
|
||||||
{
|
|
||||||
CeoFName = fName;
|
|
||||||
CeoLName = lName;
|
|
||||||
this.FatherName = fatherName;
|
|
||||||
this.IdNumberSeri = idNumberSeri;
|
|
||||||
this.IdNumberSerial = idNumberSerial;
|
|
||||||
this.DateOfBirth = !string.IsNullOrWhiteSpace(dateOfBirth) ? dateOfBirth.ToGeorgianDateTime() : null;
|
|
||||||
this.IdNumber = idNumber;
|
|
||||||
this.Gender = gender;
|
|
||||||
Phone = phone;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void RegisterComplete(string fatherName, string idNumberSeri, string idNumberSerial, DateTime dateOfBirth, Gender gender)
|
public void RegisterComplete(string fatherName, string idNumberSeri, string idNumberSerial, DateTime dateOfBirth, Gender gender)
|
||||||
{
|
{
|
||||||
@@ -290,13 +261,4 @@ public class PersonalContractingParty : EntityBase
|
|||||||
this.Gender = gender;
|
this.Gender = gender;
|
||||||
this.IsAuthenticated = true;
|
this.IsAuthenticated = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void EditLegalPartyFromInstitution(string legalPosition, string companyName,
|
|
||||||
string registerId,string nationalId)
|
|
||||||
{
|
|
||||||
LegalPosition = legalPosition;
|
|
||||||
LName = companyName;
|
|
||||||
RegisterId = registerId;
|
|
||||||
NationalId = nationalId;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
@@ -48,10 +48,6 @@ public interface IContractRepository : IRepository<long, Contract>
|
|||||||
bool Remove(long id);
|
bool Remove(long id);
|
||||||
|
|
||||||
List<ContractViweModel> SearchForClient(ContractSearchModel searchModel);
|
List<ContractViweModel> SearchForClient(ContractSearchModel searchModel);
|
||||||
|
|
||||||
Task<PagedResult<GetContractListForClientResponse>> GetContractListForClient(GetContractListForClientRequest searchModel);
|
|
||||||
|
|
||||||
Task<List<ContractPrintViewModel>> PrintAllAsync(List<long> ids);
|
|
||||||
#endregion
|
#endregion
|
||||||
#region NewChangeByHeydari
|
#region NewChangeByHeydari
|
||||||
|
|
||||||
@@ -67,8 +63,4 @@ public interface IContractRepository : IRepository<long, Contract>
|
|||||||
ContractViweModel GetByWorkshopIdEmployeeIdInDates(long workshopId, long employeeId, DateTime startOfMonth, DateTime endOfMonth);
|
ContractViweModel GetByWorkshopIdEmployeeIdInDates(long workshopId, long employeeId, DateTime startOfMonth, DateTime endOfMonth);
|
||||||
List<ContractViweModel> GetByWorkshopIdInDates(long workshopId, DateTime contractStart, DateTime contractEnd);
|
List<ContractViweModel> GetByWorkshopIdInDates(long workshopId, DateTime contractStart, DateTime contractEnd);
|
||||||
#endregion
|
#endregion
|
||||||
|
}
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@@ -2,7 +2,6 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using _0_Framework.Application;
|
using _0_Framework.Application;
|
||||||
using _0_Framework.Application.Enums;
|
|
||||||
using _0_Framework.Domain;
|
using _0_Framework.Domain;
|
||||||
using _0_Framework.Domain.CustomizeCheckoutShared.Enums;
|
using _0_Framework.Domain.CustomizeCheckoutShared.Enums;
|
||||||
using _0_Framework.Domain.CustomizeCheckoutShared.ValueObjects;
|
using _0_Framework.Domain.CustomizeCheckoutShared.ValueObjects;
|
||||||
@@ -34,8 +33,7 @@ public class CustomizeCheckout : EntityBase
|
|||||||
ICollection<CustomizeCheckoutSalaryAid> customizeCheckoutSalaryAids,
|
ICollection<CustomizeCheckoutSalaryAid> customizeCheckoutSalaryAids,
|
||||||
ICollection<CustomizeCheckoutReward> customizeCheckoutRewards, TimeSpan lateToWorkValue, double settingSalary,
|
ICollection<CustomizeCheckoutReward> customizeCheckoutRewards, TimeSpan lateToWorkValue, double settingSalary,
|
||||||
double dailyWage, WorkshopShiftStatus shiftStatus, IrregularShift irregularShift,
|
double dailyWage, WorkshopShiftStatus shiftStatus, IrregularShift irregularShift,
|
||||||
ICollection<CustomizeRotatingShift> customizeRotatingShifts, ICollection<CustomizeCheckoutRegularShift> employeeSettingsShifts,
|
ICollection<CustomizeRotatingShift> customizeRotatingShifts, ICollection<CustomizeCheckoutRegularShift> employeeSettingsShifts)
|
||||||
ICollection<CheckoutDynamicDeductionItem> checkoutDynamicDeductions)
|
|
||||||
{
|
{
|
||||||
YearInt = Convert.ToInt32(contractStart.ToFarsi().Substring(0, 4));
|
YearInt = Convert.ToInt32(contractStart.ToFarsi().Substring(0, 4));
|
||||||
MonthInt = Convert.ToInt32(contractStart.ToFarsi().Substring(5, 2));
|
MonthInt = Convert.ToInt32(contractStart.ToFarsi().Substring(5, 2));
|
||||||
@@ -85,7 +83,6 @@ public class CustomizeCheckout : EntityBase
|
|||||||
IrregularShift = irregularShift;
|
IrregularShift = irregularShift;
|
||||||
CustomizeRotatingShifts = customizeRotatingShifts;
|
CustomizeRotatingShifts = customizeRotatingShifts;
|
||||||
RegularShifts = employeeSettingsShifts;
|
RegularShifts = employeeSettingsShifts;
|
||||||
CheckoutDynamicDeductions = checkoutDynamicDeductions;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -289,7 +286,6 @@ public class CustomizeCheckout : EntityBase
|
|||||||
public ICollection<CustomizeCheckoutLoanInstallments> CustomizeCheckoutLoanInstallments { get; set; }
|
public ICollection<CustomizeCheckoutLoanInstallments> CustomizeCheckoutLoanInstallments { get; set; }
|
||||||
public ICollection<CustomizeCheckoutSalaryAid> CustomizeCheckoutSalaryAids { get; set; }
|
public ICollection<CustomizeCheckoutSalaryAid> CustomizeCheckoutSalaryAids { get; set; }
|
||||||
public ICollection<CustomizeCheckoutReward> CustomizeCheckoutRewards { get; set; }
|
public ICollection<CustomizeCheckoutReward> CustomizeCheckoutRewards { get; set; }
|
||||||
public ICollection<CheckoutDynamicDeductionItem> CheckoutDynamicDeductions { get; private set; }
|
|
||||||
|
|
||||||
public IrregularShift IrregularShift { get; set; }
|
public IrregularShift IrregularShift { get; set; }
|
||||||
public ICollection<CustomizeRotatingShift> CustomizeRotatingShifts { get; set; }
|
public ICollection<CustomizeRotatingShift> CustomizeRotatingShifts { get; set; }
|
||||||
|
|||||||
@@ -9,7 +9,6 @@ using Company.Domain.CustomizeCheckoutTempAgg.ValueObjects;
|
|||||||
using _0_Framework.Domain.CustomizeCheckoutShared.Enums;
|
using _0_Framework.Domain.CustomizeCheckoutShared.Enums;
|
||||||
using _0_Framework.Domain.CustomizeCheckoutShared.ValueObjects;
|
using _0_Framework.Domain.CustomizeCheckoutShared.ValueObjects;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using _0_Framework.Application.Enums;
|
|
||||||
|
|
||||||
|
|
||||||
namespace Company.Domain.CustomizeCheckoutTempAgg;
|
namespace Company.Domain.CustomizeCheckoutTempAgg;
|
||||||
@@ -22,8 +21,7 @@ public class CustomizeCheckoutTemp : EntityBase
|
|||||||
{
|
{
|
||||||
LateToWorkValue = lateToWorkValue;
|
LateToWorkValue = lateToWorkValue;
|
||||||
}
|
}
|
||||||
public CustomizeCheckoutTemp(
|
public CustomizeCheckoutTemp(DateTime contractStart, DateTime contractEnd, long employeeId, string employeeFName,
|
||||||
DateTime contractStart, DateTime contractEnd, long employeeId, string employeeFName,
|
|
||||||
string employeeLName, DateTime employeeDateOfBirth,
|
string employeeLName, DateTime employeeDateOfBirth,
|
||||||
string employeeNationalCode, string workshopFullName, long workshopId, long? contractId,
|
string employeeNationalCode, string workshopFullName, long workshopId, long? contractId,
|
||||||
double monthlySalary, double fridayPay, double overTimePay, double baseYearsPay, double bonusesPay,
|
double monthlySalary, double fridayPay, double overTimePay, double baseYearsPay, double bonusesPay,
|
||||||
@@ -39,8 +37,7 @@ public class CustomizeCheckoutTemp : EntityBase
|
|||||||
ICollection<CustomizeCheckoutTempSalaryAid> customizeCheckoutSalaryAids,
|
ICollection<CustomizeCheckoutTempSalaryAid> customizeCheckoutSalaryAids,
|
||||||
ICollection<CustomizeCheckoutTempReward> customizeCheckoutRewards,
|
ICollection<CustomizeCheckoutTempReward> customizeCheckoutRewards,
|
||||||
TimeSpan lateToWorkValue, double settingSalary, double dailyWage, WorkshopShiftStatus shiftStatus, IrregularShift irregularShift,
|
TimeSpan lateToWorkValue, double settingSalary, double dailyWage, WorkshopShiftStatus shiftStatus, IrregularShift irregularShift,
|
||||||
ICollection<CustomizeRotatingShift> customizeRotatingShifts, ICollection<CustomizeCheckoutRegularShift> employeeSettingsShifts,
|
ICollection<CustomizeRotatingShift> customizeRotatingShifts, ICollection<CustomizeCheckoutRegularShift> employeeSettingsShifts)
|
||||||
ICollection<CheckoutDynamicDeductionItem> checkoutDynamicDeductions)
|
|
||||||
{
|
{
|
||||||
YearInt = Convert.ToInt32(contractStart.ToFarsi().Substring(0, 4));
|
YearInt = Convert.ToInt32(contractStart.ToFarsi().Substring(0, 4));
|
||||||
MonthInt = Convert.ToInt32(contractStart.ToFarsi().Substring(5, 2));
|
MonthInt = Convert.ToInt32(contractStart.ToFarsi().Substring(5, 2));
|
||||||
@@ -90,7 +87,6 @@ public class CustomizeCheckoutTemp : EntityBase
|
|||||||
IrregularShift = irregularShift;
|
IrregularShift = irregularShift;
|
||||||
CustomizeRotatingShifts = customizeRotatingShifts;
|
CustomizeRotatingShifts = customizeRotatingShifts;
|
||||||
RegularShifts = employeeSettingsShifts;
|
RegularShifts = employeeSettingsShifts;
|
||||||
CheckoutDynamicDeductions = checkoutDynamicDeductions;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#region Getters
|
#region Getters
|
||||||
@@ -127,7 +123,6 @@ public class CustomizeCheckoutTemp : EntityBase
|
|||||||
public IrregularShift IrregularShift { get; set; }
|
public IrregularShift IrregularShift { get; set; }
|
||||||
public ICollection<CustomizeRotatingShift> CustomizeRotatingShifts { get; set; }
|
public ICollection<CustomizeRotatingShift> CustomizeRotatingShifts { get; set; }
|
||||||
public ICollection<CustomizeCheckoutRegularShift> RegularShifts { get; set; }
|
public ICollection<CustomizeCheckoutRegularShift> RegularShifts { get; set; }
|
||||||
public ICollection<CheckoutDynamicDeductionItem> CheckoutDynamicDeductions { get; private set; }
|
|
||||||
|
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
@@ -394,4 +389,4 @@ public class CustomizeCheckoutTemp : EntityBase
|
|||||||
{
|
{
|
||||||
HasAmountConflict = hasConflict;
|
HasAmountConflict = hasConflict;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -76,8 +76,8 @@ public interface IEmployeeRepository : IRepository<long, Employee>
|
|||||||
#region Api
|
#region Api
|
||||||
Task<List<EmployeeSelectListViewModel>> GetSelectList(string searchText,long id);
|
Task<List<EmployeeSelectListViewModel>> GetSelectList(string searchText,long id);
|
||||||
Task<List<GetEmployeeListViewModel>> GetList(GetEmployeeListSearchModel searchModel);
|
Task<List<GetEmployeeListViewModel>> GetList(GetEmployeeListSearchModel searchModel);
|
||||||
Task<List<GetClientEmployeeListViewModel>> GetClientEmployeeList(GetClientEmployeeListSearchModel searchModel, long workshopId);
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
|
||||||
|
Task<List<EmployeeSelectListViewModel>> GetWorkingEmployeesSelectList(long workshopId);
|
||||||
}
|
}
|
||||||
@@ -37,7 +37,7 @@ namespace Company.Domain.EmployeeDocumentsAgg
|
|||||||
{
|
{
|
||||||
WorkshopId = workshopId;
|
WorkshopId = workshopId;
|
||||||
EmployeeId = employeeId;
|
EmployeeId = employeeId;
|
||||||
Gender = gender??string.Empty;
|
Gender = gender;
|
||||||
}
|
}
|
||||||
|
|
||||||
private EmployeeDocuments()
|
private EmployeeDocuments()
|
||||||
|
|||||||
@@ -1,189 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using MongoDB.Bson;
|
|
||||||
using MongoDB.Bson.Serialization.Attributes;
|
|
||||||
|
|
||||||
namespace Company.Domain.EmployeeFaceEmbeddingAgg;
|
|
||||||
|
|
||||||
public class EmployeeFaceEmbedding
|
|
||||||
{
|
|
||||||
public EmployeeFaceEmbedding()
|
|
||||||
{
|
|
||||||
EmbeddingHistory = new List<EmbeddingHistoryItem>();
|
|
||||||
MetadataHistory = new List<MetadataHistoryItem>();
|
|
||||||
}
|
|
||||||
|
|
||||||
public EmployeeFaceEmbedding(string employeeFullName, long employeeId, long workshopId,
|
|
||||||
List<double> embeddings, EmployeeFaceEmbeddingMetadata metadata)
|
|
||||||
{
|
|
||||||
Id = Guid.NewGuid().ToString();
|
|
||||||
EmployeeFullName = employeeFullName;
|
|
||||||
EmployeeId = employeeId;
|
|
||||||
WorkshopId = workshopId;
|
|
||||||
Embeddings = embeddings;
|
|
||||||
Metadata = metadata;
|
|
||||||
EmbeddingHistory = new List<EmbeddingHistoryItem>();
|
|
||||||
MetadataHistory = new List<MetadataHistoryItem>();
|
|
||||||
CreatedAt = DateTime.UtcNow;
|
|
||||||
UpdatedAt = DateTime.UtcNow;
|
|
||||||
}
|
|
||||||
|
|
||||||
[BsonId]
|
|
||||||
[BsonRepresentation(BsonType.String)]
|
|
||||||
public string Id { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("employeeFullName")]
|
|
||||||
public string EmployeeFullName { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("employeeId")]
|
|
||||||
public long EmployeeId { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("workshopId")]
|
|
||||||
public long WorkshopId { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("embeddings")]
|
|
||||||
public List<double> Embeddings { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("metadata")]
|
|
||||||
public EmployeeFaceEmbeddingMetadata Metadata { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("embeddingHistory")]
|
|
||||||
public List<EmbeddingHistoryItem> EmbeddingHistory { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("metadataHistory")]
|
|
||||||
public List<MetadataHistoryItem> MetadataHistory { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("createdAt")]
|
|
||||||
public DateTime CreatedAt { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("updatedAt")]
|
|
||||||
public DateTime UpdatedAt { get; set; }
|
|
||||||
|
|
||||||
public void UpdateEmbedding(List<double> newEmbedding, double confidence, double refinementPercentage)
|
|
||||||
{
|
|
||||||
if (Embeddings != null)
|
|
||||||
{
|
|
||||||
EmbeddingHistory.Add(new EmbeddingHistoryItem
|
|
||||||
{
|
|
||||||
Embedding = new List<double>(Embeddings),
|
|
||||||
Timestamp = DateTime.UtcNow,
|
|
||||||
Confidence = confidence,
|
|
||||||
RefinementPercentage = refinementPercentage
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
Embeddings = newEmbedding;
|
|
||||||
UpdatedAt = DateTime.UtcNow;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void UpdateMetadata(EmployeeFaceEmbeddingMetadata newMetadata, double confidence, double refinementPercentage)
|
|
||||||
{
|
|
||||||
if (Metadata != null)
|
|
||||||
{
|
|
||||||
MetadataHistory.Add(new MetadataHistoryItem
|
|
||||||
{
|
|
||||||
Metadata = Metadata,
|
|
||||||
Timestamp = DateTime.UtcNow,
|
|
||||||
Confidence = confidence,
|
|
||||||
RefinementPercentage = refinementPercentage
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
Metadata = newMetadata;
|
|
||||||
UpdatedAt = DateTime.UtcNow;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void UpdateEmployeeInfo(string employeeFullName, long workshopId)
|
|
||||||
{
|
|
||||||
EmployeeFullName = employeeFullName;
|
|
||||||
WorkshopId = workshopId;
|
|
||||||
UpdatedAt = DateTime.UtcNow;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public class EmployeeFaceEmbeddingMetadata
|
|
||||||
{
|
|
||||||
[BsonElement("avg_eye_distance_normalized")]
|
|
||||||
public double AvgEyeDistanceNormalized { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("avg_eye_to_face_ratio")]
|
|
||||||
public double AvgEyeToFaceRatio { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("avg_face_aspect_ratio")]
|
|
||||||
public double AvgFaceAspectRatio { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("avg_detection_confidence")]
|
|
||||||
public double AvgDetectionConfidence { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("avg_keypoints_normalized")]
|
|
||||||
public EmployeeFaceEmbeddingKeypoints AvgKeypointsNormalized { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("per_image_metadata")]
|
|
||||||
public List<ImageMetadata> PerImageMetadata { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class EmployeeFaceEmbeddingKeypoints
|
|
||||||
{
|
|
||||||
[BsonElement("left_eye")]
|
|
||||||
public double[] LeftEye { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("right_eye")]
|
|
||||||
public double[] RightEye { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("nose")]
|
|
||||||
public double[] Nose { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("mouth_left")]
|
|
||||||
public double[] MouthLeft { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("mouth_right")]
|
|
||||||
public double[] MouthRight { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class ImageMetadata
|
|
||||||
{
|
|
||||||
[BsonElement("face_aspect_ratio")]
|
|
||||||
public double FaceAspectRatio { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("eye_distance_normalized")]
|
|
||||||
public double EyeDistanceNormalized { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("eye_to_face_ratio")]
|
|
||||||
public double EyeToFaceRatio { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("detection_confidence")]
|
|
||||||
public double DetectionConfidence { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("keypoints_normalized")]
|
|
||||||
public EmployeeFaceEmbeddingKeypoints KeypointsNormalized { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class EmbeddingHistoryItem
|
|
||||||
{
|
|
||||||
[BsonElement("embedding")]
|
|
||||||
public List<double> Embedding { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("timestamp")]
|
|
||||||
public DateTime Timestamp { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("confidence")]
|
|
||||||
public double Confidence { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("refinementPercentage")]
|
|
||||||
public double RefinementPercentage { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class MetadataHistoryItem
|
|
||||||
{
|
|
||||||
[BsonElement("metadata")]
|
|
||||||
public EmployeeFaceEmbeddingMetadata Metadata { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("timestamp")]
|
|
||||||
public DateTime Timestamp { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("confidence")]
|
|
||||||
public double Confidence { get; set; }
|
|
||||||
|
|
||||||
[BsonElement("refinementPercentage")]
|
|
||||||
public double RefinementPercentage { get; set; }
|
|
||||||
}
|
|
||||||
@@ -1,15 +0,0 @@
|
|||||||
using System.Collections.Generic;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace Company.Domain.EmployeeFaceEmbeddingAgg;
|
|
||||||
|
|
||||||
public interface IEmployeeFaceEmbeddingRepository
|
|
||||||
{
|
|
||||||
Task CreateAsync(EmployeeFaceEmbedding employeeFaceEmbedding);
|
|
||||||
Task UpdateAsync(EmployeeFaceEmbedding employeeFaceEmbedding);
|
|
||||||
Task<EmployeeFaceEmbedding> GetByIdAsync(string id);
|
|
||||||
Task<EmployeeFaceEmbedding> GetByEmployeeIdAsync(long employeeId);
|
|
||||||
Task<List<EmployeeFaceEmbedding>> GetByWorkshopIdAsync(long workshopId);
|
|
||||||
Task<List<EmployeeFaceEmbedding>> GetByWorkshopIdsAsync(List<long> workshopIds);
|
|
||||||
Task DeleteAsync(string id);
|
|
||||||
}
|
|
||||||
@@ -1,108 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using _0_Framework.Domain;
|
|
||||||
using Company.Domain.PaymentTransactionAgg;
|
|
||||||
using CompanyManagment.App.Contracts.FinancialInvoice;
|
|
||||||
|
|
||||||
namespace Company.Domain.FinancialInvoiceAgg;
|
|
||||||
|
|
||||||
public class FinancialInvoice : EntityBase
|
|
||||||
{
|
|
||||||
|
|
||||||
public string InvoiceNumber { get; private set; }
|
|
||||||
public string Description { get; set; }
|
|
||||||
public FinancialInvoiceStatus Status { get; private set; }
|
|
||||||
public DateTime? PaidAt { get; private set; }
|
|
||||||
public double Amount { get; private set; }
|
|
||||||
public Guid PublicId { get; private set; }
|
|
||||||
public bool IsActive { get; set; }
|
|
||||||
|
|
||||||
public List<PaymentTransaction> PaymentTransactions { get; private set; }
|
|
||||||
public long ContractingPartyId { get; private set; }
|
|
||||||
|
|
||||||
public List<FinancialInvoiceItem> Items { get; private set; }
|
|
||||||
|
|
||||||
public FinancialInvoice(double amount, long contractingPartyId, string description)
|
|
||||||
{
|
|
||||||
InvoiceNumber = GenerateInvoiceNumber();
|
|
||||||
Status = FinancialInvoiceStatus.Unpaid;
|
|
||||||
Amount = amount;
|
|
||||||
PublicId = Guid.NewGuid();
|
|
||||||
ContractingPartyId = contractingPartyId;
|
|
||||||
Description = description;
|
|
||||||
IsActive = true;
|
|
||||||
Items = [];
|
|
||||||
PaymentTransactions = [];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void AddItem(FinancialInvoiceItem item)
|
|
||||||
{
|
|
||||||
Items ??= [];
|
|
||||||
|
|
||||||
Items.Add(item);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetItems(List<FinancialInvoiceItem> items)
|
|
||||||
{
|
|
||||||
Items = items;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetPaid(DateTime paidAt)
|
|
||||||
{
|
|
||||||
Status = FinancialInvoiceStatus.Paid;
|
|
||||||
PaidAt = paidAt;
|
|
||||||
}
|
|
||||||
public void SetUnpaid()
|
|
||||||
{
|
|
||||||
Status = FinancialInvoiceStatus.Unpaid;
|
|
||||||
PaidAt = null;
|
|
||||||
}
|
|
||||||
public void SetCancelled()
|
|
||||||
{
|
|
||||||
Status = FinancialInvoiceStatus.Cancelled;
|
|
||||||
PaidAt = null;
|
|
||||||
}
|
|
||||||
public void SetRefunded()
|
|
||||||
{
|
|
||||||
Status = FinancialInvoiceStatus.Refunded;
|
|
||||||
PaidAt = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void DeActivate()
|
|
||||||
{
|
|
||||||
IsActive = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetInvoiceNumber(string invoiceNumber)
|
|
||||||
{
|
|
||||||
InvoiceNumber = invoiceNumber;
|
|
||||||
}
|
|
||||||
|
|
||||||
private string GenerateInvoiceNumber()
|
|
||||||
{
|
|
||||||
var timestamp = DateTime.Now.ToString("yyyyMMddHHmmss");
|
|
||||||
var random = new Random().Next(1000, 9999);
|
|
||||||
return $"GZ_{timestamp}{random}";
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public class FinancialInvoiceItem : EntityBase
|
|
||||||
{
|
|
||||||
public string Description { get; private set; }
|
|
||||||
public double Amount { get; private set; }
|
|
||||||
public FinancialInvoiceItemType Type { get; set; }
|
|
||||||
public long EntityId { get; set; }
|
|
||||||
public FinancialInvoice FinancialInvoice { get; set; }
|
|
||||||
public long FinancialInvoiceId { get; set; }
|
|
||||||
public FinancialInvoiceItem(string description, double amount,
|
|
||||||
long financialInvoiceId, FinancialInvoiceItemType type, long entityId)
|
|
||||||
{
|
|
||||||
Description = description;
|
|
||||||
Amount = amount;
|
|
||||||
FinancialInvoiceId = financialInvoiceId;
|
|
||||||
Type = type;
|
|
||||||
EntityId = entityId;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -1,15 +0,0 @@
|
|||||||
using System.Collections.Generic;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using _0_Framework.Domain;
|
|
||||||
using CompanyManagment.App.Contracts.FinancialInvoice;
|
|
||||||
|
|
||||||
namespace Company.Domain.FinancialInvoiceAgg;
|
|
||||||
|
|
||||||
public interface IFinancialInvoiceRepository : IRepository<long, FinancialInvoice>
|
|
||||||
{
|
|
||||||
EditFinancialInvoice GetDetails(long id);
|
|
||||||
List<FinancialInvoiceViewModel> Search(FinancialInvoiceSearchModel searchModel);
|
|
||||||
Task<FinancialInvoice> GetUnPaidByEntityId(long entityId, FinancialInvoiceItemType financialInvoiceItemType);
|
|
||||||
Task<FinancialInvoice> GetUnPaidFinancialInvoiceByContractingPartyIdAndAmount(long contractingPartyId,
|
|
||||||
double amount);
|
|
||||||
}
|
|
||||||
@@ -5,7 +5,6 @@ using System.Linq;
|
|||||||
using System.Text;
|
using System.Text;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using _0_Framework.Domain;
|
using _0_Framework.Domain;
|
||||||
using Company.Domain.FinancialInvoiceAgg;
|
|
||||||
using Company.Domain.FinancialTransactionAgg;
|
using Company.Domain.FinancialTransactionAgg;
|
||||||
|
|
||||||
namespace Company.Domain.FinancialStatmentAgg;
|
namespace Company.Domain.FinancialStatmentAgg;
|
||||||
|
|||||||
@@ -22,8 +22,6 @@ public interface IFinancialStatmentRepository : IRepository<long, FinancialStatm
|
|||||||
Task<OperationResult<ClientFinancialStatementViewModel>> GetDetailsByPublicId(string publicId);
|
Task<OperationResult<ClientFinancialStatementViewModel>> GetDetailsByPublicId(string publicId);
|
||||||
Task<GetFinancialStatementBalanceAmount> GetBalanceAmount(long id);
|
Task<GetFinancialStatementBalanceAmount> GetBalanceAmount(long id);
|
||||||
Task<double> GetClientDebtAmount(long accountId);
|
Task<double> GetClientDebtAmount(long accountId);
|
||||||
Task<double> GetClientDebtAmountByContractingPartyId(long contractingPartyId);
|
Task<FinancialStatmentDetailsByContractingPartyViewModel> GetDetailsByContractingParty(long contractingPartyId,FinancialStatementSearchModel searchModel);
|
||||||
|
|
||||||
Task<FinancialStatmentDetailsByContractingPartyViewModel> GetDetailsByContractingParty(long contractingPartyId,FinancialStatementSearchModel searchModel);
|
|
||||||
Task<FinancialStatment> GetByContractingPartyId(long contractingPartyId);
|
Task<FinancialStatment> GetByContractingPartyId(long contractingPartyId);
|
||||||
}
|
}
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user