diff --git a/yuthon_holiday/models/yuthon_vacation_reports.py b/yuthon_holiday/models/yuthon_vacation_reports.py
index 6b6584dd5..6ebfc8df4 100644
--- a/yuthon_holiday/models/yuthon_vacation_reports.py
+++ b/yuthon_holiday/models/yuthon_vacation_reports.py
@@ -98,6 +98,8 @@ class VacationOverline(models.Model):
update_type= fields.Selection([('add', '增加'), ('reduce', '减少')], string='更新类型')
update_date = fields.Date(string='更新时间')
update_lines = fields.Text(string='更新额度')
+ text = fields.Text(string='备注')
+
class VacationMealLine(models.Model):
@@ -108,6 +110,7 @@ class VacationMealLine(models.Model):
update_type= fields.Selection([('add', '增加'), ('reduce', '减少')], string='更新类型')
update_date = fields.Date(string='更新时间')
update_lines = fields.Text(string='更新额度')
+ text = fields.Text(string='备注')
class DetailsTree(models.Model):
diff --git a/yuthon_holiday/views/yuthon_vacation_reports_views.xml b/yuthon_holiday/views/yuthon_vacation_reports_views.xml
index 8353e9459..63fc31798 100644
--- a/yuthon_holiday/views/yuthon_vacation_reports_views.xml
+++ b/yuthon_holiday/views/yuthon_vacation_reports_views.xml
@@ -40,6 +40,7 @@
+
@@ -50,6 +51,7 @@
+
diff --git a/yuthon_salary/__manifest__.py b/yuthon_salary/__manifest__.py
index 528d5f492..6114ccb8c 100644
--- a/yuthon_salary/__manifest__.py
+++ b/yuthon_salary/__manifest__.py
@@ -34,6 +34,7 @@
'wizard/yuthon_payroll_wizard_views.xml',
'wizard/payroll_labor_wizard_views.xml',
'wizard/payroll_retired_wizard_views.xml',
+ 'wizard/payslip_send_wizard_views.xml',
'wizard/salary_year_wizard.xml',
'wizard/salary_compute_wizard_views.xml',
'wizard/salary_payslip_wizard_views.xml',
diff --git a/yuthon_salary/models/inherit_hr_payslip.py b/yuthon_salary/models/inherit_hr_payslip.py
index 8984133fb..c6c242a6b 100644
--- a/yuthon_salary/models/inherit_hr_payslip.py
+++ b/yuthon_salary/models/inherit_hr_payslip.py
@@ -101,6 +101,7 @@ class InheritHrPayslip(models.Model):
cumulative_deductions = fields.Float(string='累计减免税额')
amount_tax_withheld = fields.Float(string='累计应扣缴税额')
is_bold = fields.Boolean()
+ confirm_status = fields.Selection([('confirm', '已确认'), ('un_confirm', '未确认')], string='确认状态', default='un_confirm')
remake = fields.Text(string='备注')
# 物管常用项
@@ -237,6 +238,18 @@ class InheritHrPayslip(models.Model):
}
}
+ def payslip_wizard(self):
+ return {
+ "type": "ir.actions.act_window",
+ "name": "工资条推送",
+ "res_model": "payslip.send.wizard",
+ "view_mode": "form",
+ "target": "new",
+ "context": {
+ 'default_employee_id': self.id.employee_id.id
+ }
+ }
+
def action_salary_payslip_wizard(self):
return {
"type": "ir.actions.act_window",
@@ -415,4 +428,17 @@ class InheritHrPayslip(models.Model):
for record in payslip_ids:
record.write({
'salary_group_id': record.employee_id.contract_id.salary_group_id.id,
- })
\ No newline at end of file
+ })
+
+ @api.model
+ def get_view(self, view_id=None, view_type='form', **options):
+ # 检查是否通过特定动作触发
+ if options.get('action_id') == 3666:
+ # 获取当前用户相关的未确认工资单
+ domain = [
+ ('employee_id.user_id', '=', self.env.uid),
+ ]
+ unconfirmed_slips = self.search(domain)
+ if unconfirmed_slips:
+ unconfirmed_slips.write({'confirm_status': 'confirm'})
+ return super().get_view(view_id, view_type, **options)
\ No newline at end of file
diff --git a/yuthon_salary/models/inherit_hr_payslip_run.py b/yuthon_salary/models/inherit_hr_payslip_run.py
index e41289fe2..e5dcafb2a 100644
--- a/yuthon_salary/models/inherit_hr_payslip_run.py
+++ b/yuthon_salary/models/inherit_hr_payslip_run.py
@@ -11,6 +11,7 @@ class InheritHrPayslipRun(models.Model):
document_ids = fields.Many2many('ir.attachment', string="签名扫描件")
run_stage = fields.Selection([('payroll_calculations', '薪资计算'), ('individual_tax', '个税计算'), ('finalized', '待审定'),
('to_be_signed', '待签名'), ('to_be_issued', '待发放'), ('issued', '已发放')], default='payroll_calculations',
+ store=True,
string="阶段")
def Fileline(self):
@@ -21,6 +22,7 @@ class InheritHrPayslipRun(models.Model):
'res_model': 'hr.payslip',
"view_mode": "tree",
"domain": domain,
+ "context": "{'tree_view_ref': 'yuthon_salary.my_hr_payslip_view_tree'}"
}
@api.onchange('document_ids')
@@ -29,11 +31,6 @@ class InheritHrPayslipRun(models.Model):
if rec.document_ids:
rec.run_stage = 'to_be_issued'
- def add_comment(self):
- for rec in self:
- rec.run_stage = 'issued'
-
-
def open_payslip(self):
return {
"name": "详情",
@@ -43,5 +40,26 @@ class InheritHrPayslipRun(models.Model):
"res_id": self.id,
}
+ def payslip_wizard(self):
+ employee_list = []
+ run_payslips = self.env["hr.payslip"].search([
+ ('payslip_run_id', '=', self.id)
+ ])
+ for slip in run_payslips:
+ employee_list.append(slip.employee_id.id)
+
+ return {
+ "type": "ir.actions.act_window",
+ "name": "工资条推送",
+ "res_model": "payslip.send.wizard",
+ "view_mode": "form",
+ "target": "new",
+ "context": {
+ 'default_employee_ids': employee_list,
+ 'default_payslip_run_id': self.id
+ }
+ }
+
+
diff --git a/yuthon_salary/security/ir.model.access.csv b/yuthon_salary/security/ir.model.access.csv
index 45fdd68a4..b6664dae9 100644
--- a/yuthon_salary/security/ir.model.access.csv
+++ b/yuthon_salary/security/ir.model.access.csv
@@ -9,6 +9,7 @@ access_salary_compute_wizard,access_salary_compute_wizard,model_salary_compute_w
access_yuthon_account_group,access_yuthon_account_group,model_yuthon_account_group,base.group_user,1,1,1,1
access_salary_payslip_wizard,access_salary_payslip_wizard,model_salary_payslip_wizard,base.group_user,1,1,1,1
access_select_delete_wizard,access_select_delete_wizard,model_select_delete_wizard,base.group_user,1,1,1,1
+access_payslip_send_wizard, access_payslip_send_wizard,model_payslip_send_wizard,base.group_user,1,1,1,1
access_yuthon_salary_year,access_yuthon_salary_year,model_yuthon_salary_year,base.group_user,1,1,1,1
access_yuthon_personal_rule,access_yuthon_personal_rule,model_yuthon_personal_rule,base.group_user,1,1,1,1
diff --git a/yuthon_salary/views/inherit_hr_payslip_run_views.xml b/yuthon_salary/views/inherit_hr_payslip_run_views.xml
index 84e4d141d..779078def 100644
--- a/yuthon_salary/views/inherit_hr_payslip_run_views.xml
+++ b/yuthon_salary/views/inherit_hr_payslip_run_views.xml
@@ -15,7 +15,7 @@
-
+
diff --git a/yuthon_salary/views/inherit_hr_payslip_views.xml b/yuthon_salary/views/inherit_hr_payslip_views.xml
index 7f5087ab9..2385b88da 100644
--- a/yuthon_salary/views/inherit_hr_payslip_views.xml
+++ b/yuthon_salary/views/inherit_hr_payslip_views.xml
@@ -108,79 +108,6 @@
-
-
- hr.payslip.tree
- hr.payslip
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
hr.payroll.inherit.form
hr.payslip
@@ -419,6 +346,26 @@
+
+
+ my.hr.payslip.view.tree
+ hr.payslip
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
hr.payslip.view.form.inherit
hr.payslip
@@ -461,7 +408,7 @@
[('is_salary_push', '=', True), ('is_salary_release', '=', True)]
{'search_default_group_by_employee': 1}
@@ -484,6 +431,15 @@
(0, 0, {'view_mode': 'tree', 'view_id': ref('yuthon_salary.view_hr_payslip_tree2')}),
(0, 0, {'view_mode': 'form', 'view_id': ref('hr_payroll.view_hr_payslip_form')})]"/>
+
+ 我的薪资
+ hr.payslip
+ tree,form,search
+ [('is_salary_push', '=', True), ('is_salary_release', '=', True), ('employee_id.user_id', '=', uid)]
+
+
批量退回个税计算
diff --git a/yuthon_salary/wizard/__init__.py b/yuthon_salary/wizard/__init__.py
index 6c7de40ca..9001f1423 100644
--- a/yuthon_salary/wizard/__init__.py
+++ b/yuthon_salary/wizard/__init__.py
@@ -8,4 +8,5 @@ from . import temporary_payslip_wizard
from . import payroll_labor_wizard
from . import payroll_retired_wizard
from . import salary_print_wizard
-from . import salary_year_wizard
\ No newline at end of file
+from . import salary_year_wizard
+from . import payslip_send_wizard
\ No newline at end of file
diff --git a/yuthon_salary/wizard/payslip_send_wizard.py b/yuthon_salary/wizard/payslip_send_wizard.py
new file mode 100644
index 000000000..10da364d6
--- /dev/null
+++ b/yuthon_salary/wizard/payslip_send_wizard.py
@@ -0,0 +1,83 @@
+from odoo import models, fields, api, _, SUPERUSER_ID
+import logging
+from odoo.exceptions import UserError, ValidationError
+
+
+class PayslipSendWizard(models.Model):
+ _name = 'payslip.send.wizard'
+ _description = '发送员工工资条二次确认弹窗'
+
+ employee_id = fields.Many2one('hr.employee', string='员工')
+ name = fields.Char(string='你确定要发送吗?', readonly=1)
+ employee_ids = fields.Many2many('hr.employee', string='员工')
+ payslip_run_id = fields.Many2one('hr.payslip.run', string='工资单')
+
+ def button_send(self):
+ self.ensure_one()
+ for employee_id in self.env['hr.employee'].search([('id', '=', self.employee_id.id)]):
+ if not employee_id.wecom_userid:
+ raise UserError("请同步{}的企业微信".format(employee_id.name))
+ menu_id = self.env['ir.ui.menu'].search([('name', '=', '我的薪资')])
+ url = f'https://oa.thtzjt.com/web?oauth_uid={employee_id.wecom_userid}#id={self.id}&cids=2&action={menu_id.action.id}&model=hr.payslip&view_type=form&menu_id={menu_id.id}'
+ self.sudo().env["wecom.apps"].sync_send_message_textcard(category='task',
+ user_id=employee_id.wecom_userid,
+ title="薪资确认",
+ url=url, btntxt="详细信息")
+
+ def button_all_send(self):
+ self.ensure_one()
+ for employee_id in self.env['hr.employee'].search([('id', '=', self.employee_ids.ids)]):
+ if not employee_id.wecom_userid:
+ raise UserError("请同步{}的企业微信".format(employee_id.name))
+ menu_id = self.env['ir.ui.menu'].search([('name', '=', '我的薪资')])
+ url = f'https://oa.thtzjt.com/web?oauth_uid={employee_id.wecom_userid}#id={self.id}&cids=2&action={menu_id.action.id}&model=hr.payslip&view_type=form&menu_id={menu_id.id}'
+ self.sudo().env["wecom.apps"].sync_send_message_textcard(category='task',
+ user_id=employee_id.wecom_userid,
+ title="薪资确认",
+ url=url, btntxt="详细信息")
+ self.payslip_run_id.run_stage = 'issued'
+ run_payslips = self.env["hr.payslip"].search([
+ ('payslip_run_id', '=', self.payslip_run_id.id)
+ ])
+ for slip in run_payslips:
+ meal_misunderstanding_fee = slip.meal_misunderstanding_fee
+ overtime_pay = slip.overtime_pay
+ base_salary = slip.base_salary
+ # 反推加班小时数
+ overtime_list = []
+ if overtime_pay > 0:
+ overtime_hours = (overtime_pay / ((base_salary / 21.75 / 8) * 1.5)) + 40
+ else:
+ overtime_hours = 0
+ employee = slip.employee_id
+ # 反推误餐次数
+ meal_list = []
+ meal_supplement = employee.meal_supplement
+ # 公式:meal_fee = meal_number * 40 + meal_supplement
+ if meal_misunderstanding_fee > meal_supplement:
+ meal_number = (meal_misunderstanding_fee - meal_supplement) / 40
+ else:
+ meal_number = 0
+
+ reports_id = self.env['yuthon.vacation.reports'].search([
+ ('employee_id', '=', employee.id),
+ ])
+ if reports_id:
+ overtime_list.append((0, 0, {
+ 'vacation_id': reports_id.id,
+ 'update_type': 'reduce',
+ 'update_date': fields.Datetime.now(),
+ 'update_lines': overtime_hours,
+ 'text': f'{self.payslip_run_id.name}薪资结算'
+ }))
+ meal_list.append((0, 0, {
+ 'vacation_id': reports_id.id,
+ 'update_type': 'reduce',
+ 'update_date': fields.Datetime.now(),
+ 'update_lines': meal_number,
+ 'text': f'{self.payslip_run_id.name}薪资结算'
+ }))
+ reports_id.write({
+ 'overtime_ids': overtime_list,
+ 'meal_fee_ids': meal_list,
+ })
\ No newline at end of file
diff --git a/yuthon_salary/wizard/payslip_send_wizard_views.xml b/yuthon_salary/wizard/payslip_send_wizard_views.xml
new file mode 100644
index 000000000..534303f96
--- /dev/null
+++ b/yuthon_salary/wizard/payslip_send_wizard_views.xml
@@ -0,0 +1,27 @@
+
+
+
+ 推送弹窗
+ payslip.send.wizard
+
+
+
+
+
+
diff --git a/yuthon_work_brand/views/hr_menus.xml b/yuthon_work_brand/views/hr_menus.xml
index ef287d326..2f88e9505 100644
--- a/yuthon_work_brand/views/hr_menus.xml
+++ b/yuthon_work_brand/views/hr_menus.xml
@@ -590,11 +590,16 @@
parent="holiday_manage_menu_root_board"
action="yuthon_hr_attendance.hr_attendance_action1"
sequence="5"/>
-
+