Hr Payroll

This commit is contained in:
Sedat ÖZTÜRK 2025-10-23 15:05:16 +03:00
parent a83c5e83f5
commit c74c357c36
19 changed files with 1505 additions and 252 deletions

View file

@ -12100,8 +12100,8 @@
{
"resourceName": "Platform",
"key": "App.Hr.Payroll",
"tr": "Bordro",
"en": "Payroll"
"tr": "Bordro İşlemleri",
"en": "Payroll Management"
},
{
"resourceName": "Platform",
@ -15038,7 +15038,7 @@
"Code": "App.Hr.Payroll",
"DisplayName": "App.Hr.Payroll",
"Order": 10,
"Url": "/admin/hr/payroll",
"Url": "/admin/list/list-payroll",
"Icon": "FcMoneyTransfer",
"RequiredPermissionName": "App.Hr.Payroll",
"IsDisabled": false

File diff suppressed because it is too large Load diff

View file

@ -112,5 +112,7 @@ public enum TableNameEnum
CostCenter,
Employee,
Leave,
Overtime
Overtime,
Payroll,
PayrollItem
}

View file

@ -24,6 +24,8 @@ public static class PlatformConsts
public static string HtmlEditorOptions = "{\"toolbar\": {\"multiline\": true, \"items\": [{\"name\": \"undo\"},{\"name\": \"redo\"},{\"name\": \"separator\"},{\"name\": \"size\",\"acceptedValues\": [\"8pt\",\"10pt\",\"12pt\",\"14pt\",\"18pt\",\"24pt\",\"36pt\"],\"options\": {\"inputAttr\": {\"aria-label\": \"Font size\"}}},{\"name\": \"font\",\"acceptedValues\": [\"Arial\",\"Courier New\",\"Georgia\",\"Impact\",\"Lucida Console\",\"Tahoma\",\"Times New Roman\",\"Verdana\"],\"options\": {\"inputAttr\": {\"aria-label\": \"Font family\"}}},{\"name\": \"separator\"},{\"name\": \"bold\"},{\"name\": \"italic\"},{\"name\": \"strike\"},{\"name\": \"underline\"},{\"name\": \"separator\"},{\"name\": \"alignLeft\"},{\"name\": \"alignCenter\"},{\"name\": \"alignRight\"},{\"name\": \"alignJustify\"},{\"name\": \"separator\"},{\"name\": \"orderedList\"},{\"name\": \"bulletList\"},{\"name\": \"separator\"},{\"name\": \"header\",\"acceptedValues\": [false,1,2,3,4,5],\"options\": {\"inputAttr\": {\"aria-label\": \"Font family\"}}},{\"name\": \"separator\"},{\"name\": \"color\"},{\"name\": \"background\"},{\"name\": \"separator\"},{\"name\": \"link\"},{\"name\": \"image\"},{\"name\": \"separator\"},{\"name\": \"clear\"},{\"name\": \"codeBlock\"},{\"name\": \"blockquote\"},{\"name\": \"separator\"},{\"name\": \"insertTable\"},{\"name\": \"deleteTable\"},{\"name\": \"insertRowAbove\"},{\"name\": \"insertRowBelow\"},{\"name\": \"deleteRow\"},{\"name\": \"insertColumnLeft\"},{\"name\": \"insertColumnRight\"},{\"name\": \"deleteColumn\"}]}}";
public static string PhoneEditorOptions = "{\"format\": \"phoneGlobal\", \"mask\":\"(000) 000-0000\", \"maskInvalidMessage\":\"Lütfen geçerli bir telefon numarası girin\", \"useMaskedValue\":false, \"maskRules\": { \"X\": \"[1-9]\" }, \"placeholder\": \"(555) 123-4567\" }";
public static string TimeSpanOptions = "{\"type\":\"time\",\"pickerType\":\"list\",\"displayFormat\":\"HH:mm\",\"dateSerializationFormat\":\"yyyy-MM-ddTHH:mm:ss\",\"interval\":30,\"width\":\"100%\"}";
public static string NumberStandartFormat = "{ \"format\": \",##0.###\" }";
public static string NumberPercentFormat = "{ \"format\": \"#0.##'%'\" }";
}
public static class EditorScriptValues
@ -515,6 +517,7 @@ public static class PlatformConsts
public const string Employee = "list-employee";
public const string Leave = "list-leave";
public const string Overtime = "list-overtime";
public const string Payroll = "list-payroll";
}
}
@ -1317,6 +1320,9 @@ public static class PlatformConsts
public const string UserName = "@USERNAME";
public const string Roles = "@ROLES";
public const string Now = "@NOW";
public const string Year = "@YEAR";
public const string Month = "@MONTH";
public const string Day = "@DAY";
public const string Id = "@ID";
public const string Selected_Ids = "@SELECTED_IDS";
public const string TenantId = "@TENANTID";

View file

@ -130,6 +130,8 @@ public static class TableNameResolver
{ nameof(TableNameEnum.Employee), (PlatformConsts.TablePrefix.TenantByName, MenuPrefix.Hr) },
{ nameof(TableNameEnum.Leave), (PlatformConsts.TablePrefix.TenantByName, MenuPrefix.Hr) },
{ nameof(TableNameEnum.Overtime), (PlatformConsts.TablePrefix.TenantByName, MenuPrefix.Hr) },
{ nameof(TableNameEnum.Payroll), (PlatformConsts.TablePrefix.TenantByName, MenuPrefix.Hr) },
{ nameof(TableNameEnum.PayrollItem), (PlatformConsts.TablePrefix.TenantByName, MenuPrefix.Hr) },
// 🔹 ACCOUNTING
{ nameof(TableNameEnum.Bank), (PlatformConsts.TablePrefix.TenantByName, MenuPrefix.Accounting) },

View file

@ -459,7 +459,7 @@ public static class SeedConsts
public const string CostCenter = Default + ".CostCenter";
public const string Leave = Default + ".Leave";
public const string Overtime = Default + ".Overtime";
public const string Payrool = Default + ".Payrool";
public const string Payroll = Default + ".Payroll";
public const string Template360 = Default + ".Template360";
public const string Evulation360 = Default + ".Evulation360";
}

View file

@ -0,0 +1,32 @@
using System;
using System.Collections.Generic;
using Volo.Abp.Domain.Entities.Auditing;
using Volo.Abp.MultiTenancy;
namespace Kurs.Platform.Entities;
public class Payroll : FullAuditedEntity<Guid>, IMultiTenant
{
public Guid? TenantId { get; set; }
public Guid EmployeeId { get; set; }
public string PeriodYear { get; set; }
public string PeriodMonth { get; set; }
public decimal? BaseSalary { get; set; }
public decimal? Overtime { get; set; }
public decimal? Bonus { get; set; }
public decimal? GrossSalary { get; set; }
public decimal? NetSalary { get; set; }
public decimal? Tax { get; set; }
public decimal? SocialSecurity { get; set; }
public string Status { get; set; }
public DateTime? PaymentDate { get; set; }
// Navigation placeholders (allowances & deductions)
public ICollection<PayrollItem> Items { get; set; }
public Payroll()
{
Items = [];
}
}

View file

@ -0,0 +1,19 @@
using System;
using Volo.Abp.Domain.Entities.Auditing;
using Volo.Abp.MultiTenancy;
namespace Kurs.Platform.Entities;
public class PayrollItem : FullAuditedEntity<Guid>, IMultiTenant
{
public Guid? TenantId { get; set; }
public Guid PayrollItemId { get; set; }
public Payroll Payroll { get; set; }
public string Name { get; set; }
public decimal Amount { get; set; }
public string ItemType { get; set; } // "Allowance" or "Deduction"
public bool? Taxable { get; set; }
public bool? Mandatory { get; set; }
}

View file

@ -3,32 +3,41 @@ using System.Globalization;
using Kurs.Platform;
using Volo.Abp.DependencyInjection;
using Volo.Abp.MultiTenancy;
using Volo.Abp.Timing;
using Volo.Abp.Users;
public class DefaultValueHelper : ITransientDependency
{
private readonly ICurrentUser _currentUser;
private readonly ICurrentTenant _currentTenant;
private readonly IClock _clock;
public DefaultValueHelper(
ICurrentUser currentUser,
ICurrentTenant currentTenant
ICurrentTenant currentTenant,
IClock clock
)
{
_currentUser = currentUser;
_currentTenant = currentTenant;
_clock = clock;
}
public string GetDefaultValue(string strValue)
{
{
if (string.IsNullOrEmpty(strValue))
return strValue;
var now = _clock.Now;
var result = strValue
.Replace(PlatformConsts.DefaultValues.UserId, _currentUser.Id?.ToString() ?? Guid.Empty.ToString())
.Replace(PlatformConsts.DefaultValues.UserName, _currentUser.UserName ?? string.Empty)
.Replace(PlatformConsts.DefaultValues.Roles, string.Join("','", _currentUser.Roles ?? Array.Empty<string>()))
.Replace(PlatformConsts.DefaultValues.Now, DateTime.UtcNow.ToString("o", CultureInfo.InvariantCulture));
.Replace(PlatformConsts.DefaultValues.Now, now.ToString("O", CultureInfo.InvariantCulture))
.Replace(PlatformConsts.DefaultValues.Day, now.Day.ToString(CultureInfo.InvariantCulture))
.Replace(PlatformConsts.DefaultValues.Month, now.Month.ToString(CultureInfo.InvariantCulture))
.Replace(PlatformConsts.DefaultValues.Year, now.Year.ToString(CultureInfo.InvariantCulture));
// 🔹 TenantId özel durumu: NULL => IS NULL, varsa => = 'GUID'
if (_currentTenant?.Id.HasValue == true)

View file

@ -74,7 +74,13 @@ public class DefaultValueManager : PlatformDomainService, IDefaultValueManager
else if (field.Value == PlatformConsts.DefaultValues.Roles)
value = CurrentUser.Roles; //.JoinAsString("','");
else if (field.Value == PlatformConsts.DefaultValues.Now)
value = Clock.Now; // DateTime.UtcNow.ToString("o", CultureInfo.InvariantCulture);
value = Clock.Now;
else if (field.Value == PlatformConsts.DefaultValues.Day)
value = Clock.Now.Day;
else if (field.Value == PlatformConsts.DefaultValues.Month)
value = Clock.Now.Month;
else if (field.Value == PlatformConsts.DefaultValues.Year)
value = Clock.Now.Year;
else if (field.Value == PlatformConsts.DefaultValues.Id)
value = keys?.FirstOrDefault();
else if (field.Value == PlatformConsts.DefaultValues.Selected_Ids)

View file

@ -1818,5 +1818,39 @@ public class PlatformDbContext :
.HasPrincipalKey(e => e.Id)
.OnDelete(DeleteBehavior.Restrict);
});
builder.Entity<Payroll>(b =>
{
b.ToTable(TableNameResolver.GetFullTableName(nameof(TableNameEnum.Payroll)), Prefix.DbSchema);
b.ConfigureByConvention();
b.Property(x => x.EmployeeId).IsRequired();
b.Property(x => x.PeriodMonth).IsRequired().HasMaxLength(20);
b.Property(x => x.BaseSalary).HasPrecision(18, 2);
b.Property(x => x.Overtime).HasPrecision(18, 2);
b.Property(x => x.Bonus).HasPrecision(18, 2);
b.Property(x => x.GrossSalary).HasPrecision(18, 2);
b.Property(x => x.NetSalary).HasPrecision(18, 2);
b.Property(x => x.Tax).HasPrecision(18, 2);
b.Property(x => x.SocialSecurity).HasPrecision(18, 2);
});
builder.Entity<PayrollItem>(b =>
{
b.ToTable(TableNameResolver.GetFullTableName(nameof(TableNameEnum.PayrollItem)), Prefix.DbSchema);
b.ConfigureByConvention();
b.Property(x => x.Name).IsRequired().HasMaxLength(100);
b.Property(x => x.Amount).HasPrecision(18, 2);
b.Property(x => x.ItemType).IsRequired().HasMaxLength(20);
b.Property(x => x.Taxable).HasDefaultValue(false);
b.Property(x => x.Mandatory).HasDefaultValue(false);
b.HasOne(x => x.Payroll)
.WithMany(e => e.Items)
.HasForeignKey(x => x.PayrollItemId)
.HasPrincipalKey(e => e.Id)
.OnDelete(DeleteBehavior.Cascade);
});
}
}

View file

@ -13,7 +13,7 @@ using Volo.Abp.EntityFrameworkCore;
namespace Kurs.Platform.Migrations
{
[DbContext(typeof(PlatformDbContext))]
[Migration("20251023082453_Initial")]
[Migration("20251023112727_Initial")]
partial class Initial
{
/// <inheritdoc />
@ -5666,6 +5666,7 @@ namespace Kurs.Platform.Migrations
.HasColumnType("uniqueidentifier");
b.Property<decimal?>("Amount")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<Guid?>("ApprovedById")
@ -5715,6 +5716,7 @@ namespace Kurs.Platform.Migrations
.HasColumnName("LastModifierId");
b.Property<decimal>("Rate")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<string>("Reason")
@ -5804,6 +5806,170 @@ namespace Kurs.Platform.Migrations
b.ToTable("T_Adm_PaymentMethod", (string)null);
});
modelBuilder.Entity("Kurs.Platform.Entities.Payroll", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<decimal?>("BaseSalary")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<decimal?>("Bonus")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<DateTime>("CreationTime")
.HasColumnType("datetime2")
.HasColumnName("CreationTime");
b.Property<Guid?>("CreatorId")
.HasColumnType("uniqueidentifier")
.HasColumnName("CreatorId");
b.Property<Guid?>("DeleterId")
.HasColumnType("uniqueidentifier")
.HasColumnName("DeleterId");
b.Property<DateTime?>("DeletionTime")
.HasColumnType("datetime2")
.HasColumnName("DeletionTime");
b.Property<Guid>("EmployeeId")
.HasColumnType("uniqueidentifier");
b.Property<decimal?>("GrossSalary")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<bool>("IsDeleted")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false)
.HasColumnName("IsDeleted");
b.Property<DateTime?>("LastModificationTime")
.HasColumnType("datetime2")
.HasColumnName("LastModificationTime");
b.Property<Guid?>("LastModifierId")
.HasColumnType("uniqueidentifier")
.HasColumnName("LastModifierId");
b.Property<decimal?>("NetSalary")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<decimal?>("Overtime")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<DateTime?>("PaymentDate")
.HasColumnType("datetime2");
b.Property<string>("PeriodMonth")
.IsRequired()
.HasMaxLength(20)
.HasColumnType("nvarchar(20)");
b.Property<string>("PeriodYear")
.HasColumnType("nvarchar(max)");
b.Property<decimal?>("SocialSecurity")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<string>("Status")
.HasColumnType("nvarchar(max)");
b.Property<decimal?>("Tax")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<Guid?>("TenantId")
.HasColumnType("uniqueidentifier")
.HasColumnName("TenantId");
b.HasKey("Id");
b.ToTable("T_Hr_Payroll", (string)null);
});
modelBuilder.Entity("Kurs.Platform.Entities.PayrollItem", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<decimal>("Amount")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<DateTime>("CreationTime")
.HasColumnType("datetime2")
.HasColumnName("CreationTime");
b.Property<Guid?>("CreatorId")
.HasColumnType("uniqueidentifier")
.HasColumnName("CreatorId");
b.Property<Guid?>("DeleterId")
.HasColumnType("uniqueidentifier")
.HasColumnName("DeleterId");
b.Property<DateTime?>("DeletionTime")
.HasColumnType("datetime2")
.HasColumnName("DeletionTime");
b.Property<bool>("IsDeleted")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false)
.HasColumnName("IsDeleted");
b.Property<string>("ItemType")
.IsRequired()
.HasMaxLength(20)
.HasColumnType("nvarchar(20)");
b.Property<DateTime?>("LastModificationTime")
.HasColumnType("datetime2")
.HasColumnName("LastModificationTime");
b.Property<Guid?>("LastModifierId")
.HasColumnType("uniqueidentifier")
.HasColumnName("LastModifierId");
b.Property<bool?>("Mandatory")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false);
b.Property<string>("Name")
.IsRequired()
.HasMaxLength(100)
.HasColumnType("nvarchar(100)");
b.Property<Guid>("PayrollItemId")
.HasColumnType("uniqueidentifier");
b.Property<bool?>("Taxable")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false);
b.Property<Guid?>("TenantId")
.HasColumnType("uniqueidentifier")
.HasColumnName("TenantId");
b.HasKey("Id");
b.HasIndex("PayrollItemId");
b.ToTable("T_Hr_PayrollItem", (string)null);
});
modelBuilder.Entity("Kurs.Platform.Entities.Product", b =>
{
b.Property<Guid>("Id")
@ -10226,6 +10392,17 @@ namespace Kurs.Platform.Migrations
b.Navigation("Employee");
});
modelBuilder.Entity("Kurs.Platform.Entities.PayrollItem", b =>
{
b.HasOne("Kurs.Platform.Entities.Payroll", "Payroll")
.WithMany("Items")
.HasForeignKey("PayrollItemId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
b.Navigation("Payroll");
});
modelBuilder.Entity("Kurs.Platform.Entities.Question", b =>
{
b.HasOne("Kurs.Platform.Entities.QuestionPool", "QuestionPool")
@ -10601,6 +10778,11 @@ namespace Kurs.Platform.Migrations
b.Navigation("Items");
});
modelBuilder.Entity("Kurs.Platform.Entities.Payroll", b =>
{
b.Navigation("Items");
});
modelBuilder.Entity("Kurs.Platform.Entities.Question", b =>
{
b.Navigation("Options");

View file

@ -1798,6 +1798,37 @@ namespace Kurs.Platform.Migrations
table.PrimaryKey("PK_T_Hr_EmploymentType", x => x.Id);
});
migrationBuilder.CreateTable(
name: "T_Hr_Payroll",
columns: table => new
{
Id = table.Column<Guid>(type: "uniqueidentifier", nullable: false),
TenantId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
EmployeeId = table.Column<Guid>(type: "uniqueidentifier", nullable: false),
PeriodYear = table.Column<string>(type: "nvarchar(max)", nullable: true),
PeriodMonth = table.Column<string>(type: "nvarchar(20)", maxLength: 20, nullable: false),
BaseSalary = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
Overtime = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
Bonus = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
GrossSalary = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
NetSalary = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
Tax = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
SocialSecurity = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
Status = table.Column<string>(type: "nvarchar(max)", nullable: true),
PaymentDate = table.Column<DateTime>(type: "datetime2", nullable: true),
CreationTime = table.Column<DateTime>(type: "datetime2", nullable: false),
CreatorId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
LastModificationTime = table.Column<DateTime>(type: "datetime2", nullable: true),
LastModifierId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
IsDeleted = table.Column<bool>(type: "bit", nullable: false, defaultValue: false),
DeleterId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
DeletionTime = table.Column<DateTime>(type: "datetime2", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("PK_T_Hr_Payroll", x => x.Id);
});
migrationBuilder.CreateTable(
name: "T_Prt_Interesting",
columns: table => new
@ -3180,6 +3211,37 @@ namespace Kurs.Platform.Migrations
onDelete: ReferentialAction.Cascade);
});
migrationBuilder.CreateTable(
name: "T_Hr_PayrollItem",
columns: table => new
{
Id = table.Column<Guid>(type: "uniqueidentifier", nullable: false),
TenantId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
PayrollItemId = table.Column<Guid>(type: "uniqueidentifier", nullable: false),
Name = table.Column<string>(type: "nvarchar(100)", maxLength: 100, nullable: false),
Amount = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: false),
ItemType = table.Column<string>(type: "nvarchar(20)", maxLength: 20, nullable: false),
Taxable = table.Column<bool>(type: "bit", nullable: true, defaultValue: false),
Mandatory = table.Column<bool>(type: "bit", nullable: true, defaultValue: false),
CreationTime = table.Column<DateTime>(type: "datetime2", nullable: false),
CreatorId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
LastModificationTime = table.Column<DateTime>(type: "datetime2", nullable: true),
LastModifierId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
IsDeleted = table.Column<bool>(type: "bit", nullable: false, defaultValue: false),
DeleterId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
DeletionTime = table.Column<DateTime>(type: "datetime2", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("PK_T_Hr_PayrollItem", x => x.Id);
table.ForeignKey(
name: "FK_T_Hr_PayrollItem_T_Hr_Payroll_PayrollItemId",
column: x => x.PayrollItemId,
principalTable: "T_Hr_Payroll",
principalColumn: "Id",
onDelete: ReferentialAction.Cascade);
});
migrationBuilder.CreateTable(
name: "T_Sas_ApiEndpoint",
columns: table => new
@ -3990,8 +4052,8 @@ namespace Kurs.Platform.Migrations
ApprovedById = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
ApprovedDate = table.Column<DateTime>(type: "datetime2", nullable: true),
RejectionReason = table.Column<string>(type: "nvarchar(max)", nullable: true),
Rate = table.Column<decimal>(type: "decimal(18,2)", nullable: false),
Amount = table.Column<decimal>(type: "decimal(18,2)", nullable: true),
Rate = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: false),
Amount = table.Column<decimal>(type: "decimal(18,2)", precision: 18, scale: 2, nullable: true),
CreationTime = table.Column<DateTime>(type: "datetime2", nullable: false),
CreatorId = table.Column<Guid>(type: "uniqueidentifier", nullable: true),
LastModificationTime = table.Column<DateTime>(type: "datetime2", nullable: true),
@ -4650,6 +4712,11 @@ namespace Kurs.Platform.Migrations
table: "T_Hr_Overtime",
column: "EmployeeId");
migrationBuilder.CreateIndex(
name: "IX_T_Hr_PayrollItem_PayrollItemId",
table: "T_Hr_PayrollItem",
column: "PayrollItemId");
migrationBuilder.CreateIndex(
name: "IX_T_Sas_ApiEndpoint_EntityId",
table: "T_Sas_ApiEndpoint",
@ -4978,6 +5045,9 @@ namespace Kurs.Platform.Migrations
migrationBuilder.DropTable(
name: "T_Hr_Overtime");
migrationBuilder.DropTable(
name: "T_Hr_PayrollItem");
migrationBuilder.DropTable(
name: "T_Prt_Interesting");
@ -5101,6 +5171,9 @@ namespace Kurs.Platform.Migrations
migrationBuilder.DropTable(
name: "T_Crd_Question");
migrationBuilder.DropTable(
name: "T_Hr_Payroll");
migrationBuilder.DropTable(
name: "T_Sas_CustomEntity");

View file

@ -5663,6 +5663,7 @@ namespace Kurs.Platform.Migrations
.HasColumnType("uniqueidentifier");
b.Property<decimal?>("Amount")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<Guid?>("ApprovedById")
@ -5712,6 +5713,7 @@ namespace Kurs.Platform.Migrations
.HasColumnName("LastModifierId");
b.Property<decimal>("Rate")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<string>("Reason")
@ -5801,6 +5803,170 @@ namespace Kurs.Platform.Migrations
b.ToTable("T_Adm_PaymentMethod", (string)null);
});
modelBuilder.Entity("Kurs.Platform.Entities.Payroll", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<decimal?>("BaseSalary")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<decimal?>("Bonus")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<DateTime>("CreationTime")
.HasColumnType("datetime2")
.HasColumnName("CreationTime");
b.Property<Guid?>("CreatorId")
.HasColumnType("uniqueidentifier")
.HasColumnName("CreatorId");
b.Property<Guid?>("DeleterId")
.HasColumnType("uniqueidentifier")
.HasColumnName("DeleterId");
b.Property<DateTime?>("DeletionTime")
.HasColumnType("datetime2")
.HasColumnName("DeletionTime");
b.Property<Guid>("EmployeeId")
.HasColumnType("uniqueidentifier");
b.Property<decimal?>("GrossSalary")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<bool>("IsDeleted")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false)
.HasColumnName("IsDeleted");
b.Property<DateTime?>("LastModificationTime")
.HasColumnType("datetime2")
.HasColumnName("LastModificationTime");
b.Property<Guid?>("LastModifierId")
.HasColumnType("uniqueidentifier")
.HasColumnName("LastModifierId");
b.Property<decimal?>("NetSalary")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<decimal?>("Overtime")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<DateTime?>("PaymentDate")
.HasColumnType("datetime2");
b.Property<string>("PeriodMonth")
.IsRequired()
.HasMaxLength(20)
.HasColumnType("nvarchar(20)");
b.Property<string>("PeriodYear")
.HasColumnType("nvarchar(max)");
b.Property<decimal?>("SocialSecurity")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<string>("Status")
.HasColumnType("nvarchar(max)");
b.Property<decimal?>("Tax")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<Guid?>("TenantId")
.HasColumnType("uniqueidentifier")
.HasColumnName("TenantId");
b.HasKey("Id");
b.ToTable("T_Hr_Payroll", (string)null);
});
modelBuilder.Entity("Kurs.Platform.Entities.PayrollItem", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uniqueidentifier");
b.Property<decimal>("Amount")
.HasPrecision(18, 2)
.HasColumnType("decimal(18,2)");
b.Property<DateTime>("CreationTime")
.HasColumnType("datetime2")
.HasColumnName("CreationTime");
b.Property<Guid?>("CreatorId")
.HasColumnType("uniqueidentifier")
.HasColumnName("CreatorId");
b.Property<Guid?>("DeleterId")
.HasColumnType("uniqueidentifier")
.HasColumnName("DeleterId");
b.Property<DateTime?>("DeletionTime")
.HasColumnType("datetime2")
.HasColumnName("DeletionTime");
b.Property<bool>("IsDeleted")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false)
.HasColumnName("IsDeleted");
b.Property<string>("ItemType")
.IsRequired()
.HasMaxLength(20)
.HasColumnType("nvarchar(20)");
b.Property<DateTime?>("LastModificationTime")
.HasColumnType("datetime2")
.HasColumnName("LastModificationTime");
b.Property<Guid?>("LastModifierId")
.HasColumnType("uniqueidentifier")
.HasColumnName("LastModifierId");
b.Property<bool?>("Mandatory")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false);
b.Property<string>("Name")
.IsRequired()
.HasMaxLength(100)
.HasColumnType("nvarchar(100)");
b.Property<Guid>("PayrollItemId")
.HasColumnType("uniqueidentifier");
b.Property<bool?>("Taxable")
.ValueGeneratedOnAdd()
.HasColumnType("bit")
.HasDefaultValue(false);
b.Property<Guid?>("TenantId")
.HasColumnType("uniqueidentifier")
.HasColumnName("TenantId");
b.HasKey("Id");
b.HasIndex("PayrollItemId");
b.ToTable("T_Hr_PayrollItem", (string)null);
});
modelBuilder.Entity("Kurs.Platform.Entities.Product", b =>
{
b.Property<Guid>("Id")
@ -10223,6 +10389,17 @@ namespace Kurs.Platform.Migrations
b.Navigation("Employee");
});
modelBuilder.Entity("Kurs.Platform.Entities.PayrollItem", b =>
{
b.HasOne("Kurs.Platform.Entities.Payroll", "Payroll")
.WithMany("Items")
.HasForeignKey("PayrollItemId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
b.Navigation("Payroll");
});
modelBuilder.Entity("Kurs.Platform.Entities.Question", b =>
{
b.HasOne("Kurs.Platform.Entities.QuestionPool", "QuestionPool")
@ -10598,6 +10775,11 @@ namespace Kurs.Platform.Migrations
b.Navigation("Items");
});
modelBuilder.Entity("Kurs.Platform.Entities.Payroll", b =>
{
b.Navigation("Items");
});
modelBuilder.Entity("Kurs.Platform.Entities.Question", b =>
{
b.Navigation("Options");

View file

@ -2711,14 +2711,14 @@
"fullName": "Ali Öztürk",
"avatar": "https://i.pravatar.cc/150?img=12",
"nationalId": "12345678901",
"birthDate": "20.10.1988",
"birthDate": "10-10-1988",
"gender": "Male",
"maritalStatus": "Married",
"country": "Türkiye",
"city": "Ankara",
"district": "Ankara",
"street": "Kızılay Cd. No:12",
"postalCode": "06050",
"country": "TR",
"city": "TR.34",
"district": "Ümraniye",
"street": "Fatih sultan mehmet mah.",
"postalCode": "34771",
"phone": "2125550100",
"personalPhone": "5325550101",
"email": "ali.ozturk@company.com",
@ -2727,8 +2727,8 @@
"emergencyContactname": "Ayşe Öztürk",
"emergencyContactrelationship": "Eşi",
"emergencyContactphone": "5325550100",
"hireDate": "15-01-2020",
"terminationDate": "15-01-2020",
"hireDate": "09-01-2020",
"terminationDate": "09-01-2020",
"employmentTypeName": "FullTime",
"jobPositionCode": "1",
"departmentCode": "1",
@ -2736,8 +2736,8 @@
"baseSalary": 65000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "1",
"payrollGroup": "Monthly",
"bankAccountNumber": "1",
"badgeCode": "B001",
"employeeStatus": "Active",
"isActive": true,
@ -2751,14 +2751,14 @@
"fullName": "Ayşe Kaya",
"avatar": "https://i.pravatar.cc/150?img=5",
"nationalId": "12345678902",
"birthDate": "22.08.1990",
"birthDate": "02-08-1990",
"gender": "Female",
"maritalStatus": "Single",
"country": "Türkiye",
"city": "Ankara",
"district": "Ankara",
"street": "İnönü Bulvarı No:456",
"postalCode": "06000",
"country": "TR",
"city": "TR.06",
"district": "Güdül",
"street": "Özköy mah.",
"postalCode": "6840",
"phone": "2125550102",
"personalPhone": "5325550103",
"email": "ayse.kaya@company.com",
@ -2768,7 +2768,7 @@
"emergencyContactrelationship": "Anne",
"emergencyContactphone": "5325550104",
"hireDate": "01-06-2021",
"terminationDate": "",
"terminationDate": null,
"employmentTypeName": "FullTime",
"jobPositionCode": "2",
"departmentCode": "1",
@ -2776,8 +2776,8 @@
"baseSalary": 72000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "2",
"payrollGroup": "Monthly",
"bankAccountNumber": "2",
"badgeCode": "B002",
"employeeStatus": "Active",
"isActive": true,
@ -2791,24 +2791,24 @@
"fullName": "Mehmet Yılmaz",
"avatar": "https://i.pravatar.cc/150?img=8",
"nationalId": "12345678903",
"birthDate": "12.03.1987",
"birthDate": "12-03-1987",
"gender": "Male",
"maritalStatus": "Married",
"country": "Türkiye",
"city": "İstanbul",
"district": "İstanbul",
"street": "Cumhuriyet Cad. No:123",
"country": "TR",
"city": "TR.11",
"district": "Merkez",
"street": "Kızıldamlar köyü",
"postalCode": "34000",
"phone": "+90 212 555 0105",
"personalPhone": "+90 532 555 0106",
"phone": "2125550105",
"personalPhone": "5325550106",
"email": "mehmet.yilmaz@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Zeynep Yılmaz",
"emergencyContactrelationship": "Eşi",
"emergencyContactphone": "+90 532 555 0107",
"hireDate": "15-02-2020",
"terminationDate": "",
"emergencyContactphone": "5325550107",
"hireDate": "10-02-2020",
"terminationDate": null,
"employmentTypeName": "FullTime",
"jobPositionCode": "3",
"departmentCode": "1",
@ -2816,8 +2816,8 @@
"baseSalary": 85000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "2",
"payrollGroup": "Monthly",
"bankAccountNumber": "2",
"badgeCode": "B003",
"employeeStatus": "Active",
"isActive": true,
@ -2831,24 +2831,24 @@
"fullName": "Selin Demir",
"avatar": "https://i.pravatar.cc/150?img=9",
"nationalId": "12345678904",
"birthDate": "25.05.1993",
"birthDate": "05-05-1993",
"gender": "Female",
"maritalStatus": "Single",
"country": "Türkiye",
"city": "Ankara",
"district": "Ankara",
"street": "Atatürk Bulvarı No:78",
"country": "TR",
"city": "",
"district": "",
"street": "",
"postalCode": "06100",
"phone": "+90 312 555 0108",
"personalPhone": "+90 542 555 0109",
"phone": "3125550108",
"personalPhone": "5425550109",
"email": "selin.demir@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Ali Demir",
"emergencyContactrelationship": "Baba",
"emergencyContactphone": "+90 532 555 0110",
"emergencyContactphone": "5325550110",
"hireDate": "10-01-2022",
"terminationDate": "",
"terminationDate": null,
"employmentTypeName": "PartTime",
"jobPositionCode": "4",
"departmentCode": "1",
@ -2856,8 +2856,8 @@
"baseSalary": 60000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "3",
"payrollGroup": "Monthly",
"bankAccountNumber": "3",
"badgeCode": "B004",
"employeeStatus": "Active",
"isActive": true,
@ -2871,24 +2871,24 @@
"fullName": "Ahmet Çelik",
"avatar": "https://i.pravatar.cc/150?img=33",
"nationalId": "12345678905",
"birthDate": "10.09.1985",
"birthDate": "10-09-1985",
"gender": "Male",
"maritalStatus": "Married",
"country": "Türkiye",
"city": "İstanbul",
"district": "İstanbul",
"street": "Bağdat Cad. No:25",
"country": "TR",
"city": "TR.34",
"district": "Kadıköy",
"street": "Bağdat Cad.",
"postalCode": "34728",
"phone": "+90 212 555 0111",
"personalPhone": "+90 532 555 0112",
"phone": "2125550111",
"personalPhone": "5325550112",
"email": "ahmet.celik@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Emine Çelik",
"emergencyContactrelationship": "Eşi",
"emergencyContactphone": "+90 532 555 0113",
"emergencyContactphone": "5325550113",
"hireDate": "01-04-2019",
"terminationDate": "",
"terminationDate": null,
"employmentTypeName": "FullTime",
"jobPositionCode": "5",
"departmentCode": "1",
@ -2896,8 +2896,8 @@
"baseSalary": 95000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "4",
"payrollGroup": "Monthly",
"bankAccountNumber": "4",
"badgeCode": "B005",
"employeeStatus": "Active",
"isActive": true,
@ -2911,24 +2911,24 @@
"fullName": "Zeynep Arslan",
"avatar": "https://i.pravatar.cc/150?img=10",
"nationalId": "12345678906",
"birthDate": "30.01.1995",
"birthDate": "01-01-1995",
"gender": "Female",
"maritalStatus": "Single",
"country": "Türkiye",
"city": "İzmir",
"country": "TR",
"city": "TR.35",
"district": "İzmir",
"street": "Yıldız Mah. No:19",
"street": "Yıldız Mah.",
"postalCode": "35000",
"phone": "+90 216 555 0114",
"personalPhone": "+90 532 555 0115",
"phone": "2165550114",
"personalPhone": "5325550115",
"email": "zeynep.arslan@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Hasan Arslan",
"emergencyContactrelationship": "Baba",
"emergencyContactphone": "+90 532 555 0116",
"hireDate": "20-03-2023",
"terminationDate": "",
"emergencyContactphone": "5325550116",
"hireDate": "02-03-2023",
"terminationDate": null,
"employmentTypeName": "Intern",
"jobPositionCode": "6",
"departmentCode": "1",
@ -2936,8 +2936,8 @@
"baseSalary": 15000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "1",
"payrollGroup": "Monthly",
"bankAccountNumber": "1",
"badgeCode": "B006",
"employeeStatus": "Active",
"isActive": true,
@ -2951,24 +2951,24 @@
"fullName": "Burak Koç",
"avatar": "https://i.pravatar.cc/150?img=14",
"nationalId": "12345678907",
"birthDate": "18.06.1991",
"birthDate": "08-06-1991",
"gender": "Male",
"maritalStatus": "Married",
"country": "Türkiye",
"city": "Bursa",
"district": "Bursa",
"street": "Osmangazi Mah. No:45",
"country": "TR",
"city": "TR.06",
"district": "Ankara",
"street": "Osmangazi Mah.",
"postalCode": "16000",
"phone": "+90 224 555 0117",
"personalPhone": "+90 532 555 0118",
"phone": "2245550117",
"personalPhone": "5325550118",
"email": "burak.koc@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Elif Koç",
"emergencyContactrelationship": "Eşi",
"emergencyContactphone": "+90 532 555 0119",
"hireDate": "12-07-2021",
"terminationDate": "",
"emergencyContactphone": "5325550119",
"hireDate": "09-07-2021",
"terminationDate": null,
"employmentTypeName": "FullTime",
"jobPositionCode": "7",
"departmentCode": "2",
@ -2976,8 +2976,8 @@
"baseSalary": 75000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "3",
"payrollGroup": "Monthly",
"bankAccountNumber": "3",
"badgeCode": "B007",
"employeeStatus": "Active",
"isActive": true,
@ -2991,24 +2991,24 @@
"fullName": "Elif Şahin",
"avatar": "https://i.pravatar.cc/150?img=20",
"nationalId": "12345678908",
"birthDate": "05.11.1989",
"birthDate": "05-11-1989",
"gender": "Female",
"maritalStatus": "Married",
"country": "Türkiye",
"city": "İzmir",
"country": "TR",
"city": "TR.11",
"district": "İzmir",
"street": "Alsancak Mah. No:88",
"postalCode": "35220",
"phone": "+90 232 555 0120",
"personalPhone": "+90 532 555 0121",
"phone": "2325550120",
"personalPhone": "5325550121",
"email": "elif.sahin@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Murat Şahin",
"emergencyContactrelationship": "Eşi",
"emergencyContactphone": "+90 532 555 0122",
"emergencyContactphone": "5325550122",
"hireDate": "01-09-2018",
"terminationDate": "",
"terminationDate": null,
"employmentTypeName": "FullTime",
"jobPositionCode": "8",
"departmentCode": "2",
@ -3016,8 +3016,8 @@
"baseSalary": 130000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "2",
"payrollGroup": "Monthly",
"bankAccountNumber": "2",
"badgeCode": "B008",
"employeeStatus": "Active",
"isActive": true,
@ -3031,24 +3031,24 @@
"fullName": "Canan Öztürk",
"avatar": "https://i.pravatar.cc/150?img=25",
"nationalId": "12345678909",
"birthDate": "14.04.1992",
"birthDate": "04-04-1992",
"gender": "Female",
"maritalStatus": "Single",
"country": "Türkiye",
"city": "Ankara",
"country": "TR",
"city": "TR.45",
"district": "Ankara",
"street": "Bahçelievler Mah. No:55",
"postalCode": "06490",
"phone": "+90 312 555 0123",
"personalPhone": "+90 532 555 0124",
"phone": "3125550123",
"personalPhone": "5325550124",
"email": "canan.ozturk@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Hüseyin Öztürk",
"emergencyContactrelationship": "Baba",
"emergencyContactphone": "+90 532 555 0125",
"hireDate": "02-11-2020",
"terminationDate": "",
"emergencyContactphone": "5325550125",
"hireDate": "02-06-2020",
"terminationDate": null,
"employmentTypeName": "FullTime",
"jobPositionCode": "9",
"departmentCode": "1",
@ -3056,8 +3056,8 @@
"baseSalary": 50000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "1",
"payrollGroup": "Monthly",
"bankAccountNumber": "1",
"badgeCode": "B009",
"employeeStatus": "Active",
"isActive": true,
@ -3071,24 +3071,24 @@
"fullName": "Murat Aydın",
"avatar": "https://i.pravatar.cc/150?img=30",
"nationalId": "12345678910",
"birthDate": "22.12.1984",
"birthDate": "03-12-1984",
"gender": "Male",
"maritalStatus": "Married",
"country": "Türkiye",
"city": "İstanbul",
"country": "TR",
"city": "TR.34",
"district": "İstanbul",
"street": "Şişli Mah. No:101",
"postalCode": "34360",
"phone": "+90 212 555 0126",
"personalPhone": "+90 532 555 0127",
"phone": "2125550126",
"personalPhone": "5325550127",
"email": "murat.aydin@company.com",
"address1": "",
"address2": "",
"emergencyContactname": "Ayten Aydın",
"emergencyContactrelationship": "Eşi",
"emergencyContactphone": "+90 532 555 0128",
"hireDate": "15-05-2017",
"terminationDate": "",
"emergencyContactphone": "5325550128",
"hireDate": "06-05-2017",
"terminationDate": null,
"employmentTypeName": "FullTime",
"jobPositionCode": "10",
"departmentCode": "1",
@ -3096,8 +3096,8 @@
"baseSalary": 250000,
"managerCode": "1",
"currencyCode": "TRY",
"payrollGroup": "MONTHLY",
"bankAccountCode": "4",
"payrollGroup": "Monthly",
"bankAccountNumber": "4",
"badgeCode": "B010",
"employeeStatus": "Active",
"isActive": true,

View file

@ -996,9 +996,6 @@ public class TenantDataSeeder : IDataSeedContributor, ITransientDependency
foreach (var item in items.Employees)
{
if (string.IsNullOrWhiteSpace(item.Code) || string.IsNullOrWhiteSpace(item.FullName))
continue;
var exists = await _employeeRepository.AnyAsync(x => x.Code == item.Code);
if (exists)
continue;
@ -1037,7 +1034,7 @@ public class TenantDataSeeder : IDataSeedContributor, ITransientDependency
EmergencyContactPhone = item.EmergencyContactPhone,
HireDate = item.HireDate,
TerminationDate = item.TerminationDate,
TerminationDate = item.TerminationDate != null ? item.TerminationDate : null,
EmploymentTypeId = employmentType != null ? employmentType.Id : null,
JobPositionId = jobPosition != null ? jobPosition.Id : null,
DepartmentId = department != null ? department.Id : null,

View file

@ -85,7 +85,7 @@ public class EmployeeSeedDto
public string EmergencyContactPhone { get; set; }
public DateTime HireDate { get; set; }
public DateTime TerminationDate { get; set; }
public DateTime? TerminationDate { get; set; }
public string EmploymentTypeName { get; set; }
public string JobPositionCode { get; set; }
public string DepartmentCode { get; set; }
@ -293,8 +293,8 @@ public class CustomComponentSeedDto
{
public string Name { get; set; }
public string Code { get; set; }
public string? Props { get; set; }
public string? Description { get; set; }
public string Props { get; set; }
public string Description { get; set; }
public bool IsActive { get; set; }
public List<string> Dependencies { get; set; } = new();
}

View file

@ -294,8 +294,8 @@ export interface HrPayroll {
employee?: HrEmployee
period: string
baseSalary: number
allowances: HrPayrollAllowance[]
deductions: HrPayrollDeduction[]
allowances: HrPayrollAllowance[] // İnsan Kaynakları Maaş Ek Ödemeleri
deductions: HrPayrollDeduction[] // İnsan Kaynakları Maaş Kesintileri
overtime: number
bonus: number
grossSalary: number

View file

@ -91,6 +91,14 @@ const DialogShowComponent = (): JSX.Element => {
{...dialogContext.config?.props}
></QuestionDialog>
)
case 'CollectivePayroll':
return (
<QuestionDialog
open={true}
onDialogClose={handleDialogClose}
{...dialogContext.config?.props}
></QuestionDialog>
)
default:
return <></>
}