fix: 劳务协议/实习协议人员薪资计算强制社保公积金为0
calcBatchEntry 查询员工时 include contracts,判断合同类型: - LABOR(劳务协议)/ INTERNSHIP(实习协议)→ 社保公积金基数强制0,跳过社保计算 - 其他合同类型 → 正常计算 无论哪种批次创建模式(copy_last/blank_employees/custom等), 劳务协议人员的社保公积金都为0。 Generated with [Devin](https://devin.ai) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
This commit is contained in:
@@ -206,9 +206,16 @@ export async function calcBatchEntry(
|
|||||||
batchType: string = 'REGULAR',
|
batchType: string = 'REGULAR',
|
||||||
options?: { skipSocial?: boolean; overrideSocial?: { socialEmp?: number; socialOrg?: number; housingEmp?: number; housingOrg?: number }; prevDeferred?: { socialEmp?: number; housingEmp?: number; minWage?: number } },
|
options?: { skipSocial?: boolean; overrideSocial?: { socialEmp?: number; socialOrg?: number; housingEmp?: number; housingOrg?: number }; prevDeferred?: { socialEmp?: number; housingEmp?: number; minWage?: number } },
|
||||||
) {
|
) {
|
||||||
const employee = await prisma.employee.findFirst({ where: { id: employeeId, orgId } })
|
const employee = await prisma.employee.findFirst({
|
||||||
|
where: { id: employeeId, orgId },
|
||||||
|
include: { contracts: { orderBy: { createdAt: 'desc' }, take: 1 } },
|
||||||
|
})
|
||||||
if (!employee) throw { code: 'NOT_FOUND', message: '员工不存在' }
|
if (!employee) throw { code: 'NOT_FOUND', message: '员工不存在' }
|
||||||
|
|
||||||
|
// 劳务协议/实习协议人员:不缴纳社保公积金,基数强制 0
|
||||||
|
const latestContract = employee.contracts[0]
|
||||||
|
const isNoSocialContract = latestContract && ['LABOR', 'INTERNSHIP'].includes(latestContract.contractType)
|
||||||
|
|
||||||
// 通过员工账户查年度标准(新逻辑),回退到旧配置(兼容)
|
// 通过员工账户查年度标准(新逻辑),回退到旧配置(兼容)
|
||||||
const { socialAccount, housingAccount } = await getEmployeeAccounts(orgId, employeeId)
|
const { socialAccount, housingAccount } = await getEmployeeAccounts(orgId, employeeId)
|
||||||
let socialConfig: any = null
|
let socialConfig: any = null
|
||||||
@@ -236,15 +243,15 @@ export async function calcBatchEntry(
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
// 社保基数:优先用员工核定基数(含0,劳务协议人员基数为0不交社保),未设置时回退到基本工资
|
// 社保基数:劳务协议/实习协议人员强制 0;否则优先用员工核定基数(含0),未设置时回退到基本工资
|
||||||
const socialBase = employee.socialInsBase != null ? employee.socialInsBase : inputs.baseSalary
|
const socialBase = isNoSocialContract ? 0 : (employee.socialInsBase != null ? employee.socialInsBase : inputs.baseSalary)
|
||||||
const housingBase = employee.housingFundBase != null ? employee.housingFundBase : inputs.baseSalary
|
const housingBase = isNoSocialContract ? 0 : (employee.housingFundBase != null ? employee.housingFundBase : inputs.baseSalary)
|
||||||
|
|
||||||
let socialEmp = 0, socialOrg = 0, housingEmp = 0, housingOrg = 0
|
let socialEmp = 0, socialOrg = 0, housingEmp = 0, housingOrg = 0
|
||||||
|
|
||||||
// 年终奖/奖金批次、补偿金批次:不扣社保公积金
|
// 年终奖/奖金批次、补偿金批次、劳务协议/实习协议人员:不扣社保公积金
|
||||||
// 其他批次:计算当月应缴全额,减去已归档批次已扣金额,差额为本批次应扣
|
// 其他批次:计算当月应缴全额,减去已归档批次已扣金额,差额为本批次应扣
|
||||||
if (batchType !== 'BONUS' && batchType !== 'SEVERANCE' && !options?.skipSocial) {
|
if (batchType !== 'BONUS' && batchType !== 'SEVERANCE' && !options?.skipSocial && !isNoSocialContract) {
|
||||||
// 1. 计算当月应缴社保公积金全额
|
// 1. 计算当月应缴社保公积金全额
|
||||||
let fullSocialEmp = 0, fullSocialOrg = 0, fullHousingEmp = 0, fullHousingOrg = 0
|
let fullSocialEmp = 0, fullSocialOrg = 0, fullHousingEmp = 0, fullHousingOrg = 0
|
||||||
if (socialConfig) {
|
if (socialConfig) {
|
||||||
|
|||||||
Reference in New Issue
Block a user