Merge branch 'master' into dev_zhou
# Conflicts: # attendance_iot/controllers/kaoqin_test.py
This commit is contained in:
@@ -40,6 +40,7 @@ class BusController(Controller):
|
||||
)
|
||||
if not exist:
|
||||
employee.write({
|
||||
'avatar_image': data.get('photo'),
|
||||
'image_1920': data.get('photo'),
|
||||
'attendance_iot_ids': [(0, 0, {
|
||||
'employee_id': employee.id,
|
||||
@@ -47,6 +48,7 @@ class BusController(Controller):
|
||||
'attendance_address': ''
|
||||
})]
|
||||
})
|
||||
_logger.info(f"-------------{employee.name}人脸更新触发------人脸数据{data.get('photo')}-------------")
|
||||
_logger.info("-------------------------%s创建成功-------------------------------" % (employee.name))
|
||||
return {"Result": 0, "Msg": "添加成功"}
|
||||
|
||||
|
||||
@@ -21,10 +21,10 @@
|
||||
<field name="boss_char"/>
|
||||
<field name="is_legal_trial"/>
|
||||
<field name="co_organizer_dept" readonly="not is_admin and issue_state not in ['to_do', 'cancel','to_modify', 'draft']"/>
|
||||
<field name="is_district_state"/>
|
||||
<field name="is_district_government"/>
|
||||
<field name="is_district_party"/>
|
||||
<field name="is_external_person"/>
|
||||
<field name="is_district_state" column_invisible="1"/>
|
||||
<field name="is_district_government" column_invisible="1"/>
|
||||
<field name="is_district_party" column_invisible="1"/>
|
||||
<field name="is_external_person" column_invisible="1"/>
|
||||
<field name="issue_state"/>
|
||||
<field name="code" column_invisible="1"/>
|
||||
<field name="company_id" column_invisible="1"/>
|
||||
@@ -391,16 +391,17 @@
|
||||
<button name="all_meeting_issue" type="object" string="会议安排" class="oe_highlight"/>
|
||||
<button name="issue_party1_approval" type="object" string="批量审批" class="oe_highlight"/>
|
||||
</header>
|
||||
<field name="name"/>
|
||||
<field name="name" column_invisible="1"/>
|
||||
<field name="name_text" class="list_width"/>
|
||||
<field name="department_id"/>
|
||||
<field name="creart_datetime"/>
|
||||
<field name="is_party" groups="yuthon_salary.group_jtbb_user" string="党总支"/>
|
||||
<field name="is_party" groups="yuthon_salary.group_lc_user,yuthon_salary.group_wg_user"
|
||||
string="党支部会"/>
|
||||
<field name="party_char"/>
|
||||
<field name="is_district_state"/>
|
||||
<field name="is_district_government"/>
|
||||
<field name="is_district_party"/>
|
||||
<field name="is_district_state" column_invisible="1"/>
|
||||
<field name="is_district_government" column_invisible="1"/>
|
||||
<field name="is_district_party" column_invisible="1"/>
|
||||
<field name="is_external_person"/>
|
||||
<field name="issue_state" string="审批状态" />
|
||||
<field name="issue_state_party"/>
|
||||
@@ -435,16 +436,17 @@
|
||||
<button name="all_meeting_issue" type="object" string="会议安排" class="oe_highlight"/>
|
||||
<button name="issue_party_approval" type="object" string="批量审批" class="oe_highlight"/>
|
||||
</header>
|
||||
<field name="name"/>
|
||||
<field name="name" column_invisible="1"/>
|
||||
<field name="name_text" class="list_width"/>
|
||||
<field name="department_id"/>
|
||||
<field name="creart_datetime"/>
|
||||
<field name="is_party" groups="yuthon_salary.group_jtbb_user" string="党总支"/>
|
||||
<field name="is_party" groups="yuthon_salary.group_lc_user,yuthon_salary.group_wg_user"
|
||||
string="党支部会"/>
|
||||
<field name="party_char"/>
|
||||
<field name="is_district_state"/>
|
||||
<field name="is_district_government"/>
|
||||
<field name="is_district_party"/>
|
||||
<field name="is_district_state" column_invisible="1"/>
|
||||
<field name="is_district_government" column_invisible="1"/>
|
||||
<field name="is_district_party" column_invisible="1"/>
|
||||
<field name="is_external_person"/>
|
||||
<field name="issue_state" string="审批状态" />
|
||||
<field name="issue_state_party"/>
|
||||
@@ -586,7 +588,7 @@
|
||||
['draft', 'to_draft'])]
|
||||
</field>
|
||||
<field name="search_view_id" ref="view_issue_library_filter"/>
|
||||
<field name="context">{'from_action': 'issue_library_action3', 'search_default_to_approval': 1}</field>
|
||||
<field name="context">{'from_action': 'issue_library_action3'}</field>
|
||||
<field name="view_ids" eval="[(5, 0, 0),
|
||||
(0, 0, {'view_mode': 'tree', 'view_id': ref('yuthon_issue.view_issue_library_tree2')}),
|
||||
(0, 0, {'view_mode': 'form', 'view_id': ref('yuthon_issue.view_issue_library_form3')})]"/>
|
||||
@@ -599,7 +601,7 @@
|
||||
<field name="domain">[('is_push_party', '=', True),('issue_state', 'not in', ['draft', 'to_draft']),
|
||||
('is_push_depart', '=', True), ('company_id.name', '!=', '集团本部')]
|
||||
</field>
|
||||
<field name="context">{'from_action': 'issue_library_action3', 'search_default_to_approval': 1}</field>
|
||||
<field name="context">{'from_action': 'issue_library_action8'}</field>
|
||||
<field name="search_view_id" ref="view_issue_library_filter"/>
|
||||
<field name="view_ids" eval="[(5, 0, 0),
|
||||
(0, 0, {'view_mode': 'tree', 'view_id': ref('yuthon_issue.view_issue_library_tree3')}),
|
||||
@@ -767,7 +769,7 @@
|
||||
('is_push_depart', '=', True)]
|
||||
</field>
|
||||
<field name="search_view_id" ref="view_issue_library_filter"/>
|
||||
<field name="context">{'from_action': 'issue_library_action4', 'search_default_to_approval': 1}</field>
|
||||
<field name="context">{'from_action': 'issue_library_action4'}</field>
|
||||
<field name="view_ids" eval="[(5, 0, 0),
|
||||
(0, 0, {'view_mode': 'tree', 'view_id': ref('yuthon_issue.view_issue_library_tree4')}),
|
||||
(0, 0, {'view_mode': 'form', 'view_id': ref('yuthon_issue.view_issue_library_form4')})]"/>
|
||||
@@ -933,7 +935,7 @@
|
||||
('is_push_depart', '=', True)]
|
||||
</field>
|
||||
<field name="search_view_id" ref="view_issue_library_filter"/>
|
||||
<field name="context">{'from_action': 'issue_library_action5', 'search_default_to_approval': 1}</field>
|
||||
<field name="context">{'from_action': 'issue_library_action5'}</field>
|
||||
<field name="view_ids" eval="[(5, 0, 0),
|
||||
(0, 0, {'view_mode': 'tree', 'view_id': ref('yuthon_issue.view_issue_library_tree5')}),
|
||||
(0, 0, {'view_mode': 'form', 'view_id': ref('yuthon_issue.view_issue_library_form5')})]"/>
|
||||
|
||||
@@ -28,6 +28,13 @@ class PropertyBillsPayable(models.Model):
|
||||
document_ids = fields.Many2many('ir.attachment', string="附件")
|
||||
active = fields.Boolean('Active', default=True, tracking=True)
|
||||
work_end = fields.Boolean(string="结束")
|
||||
payment_type = fields.Selection([
|
||||
('deposit_refund', '退押'),
|
||||
('lease_refund', '退租'),
|
||||
('engineering', '工程款'),
|
||||
('agency_fee', '中介费'),
|
||||
('other', '其他')
|
||||
], string='付款类型')
|
||||
|
||||
def _get_default_name_title(self):
|
||||
return self._description if self._description else self._name
|
||||
|
||||
@@ -56,6 +56,7 @@
|
||||
<field name="property_name"/>
|
||||
<field name="lessee_id"/>
|
||||
<field name="amount_payable"/>
|
||||
<field name="payment_type"/>
|
||||
<field name="deduction_amount"/>
|
||||
<field name="remake" invisible="not deduction_amount"/>
|
||||
<field name="actual_amount"/>
|
||||
|
||||
@@ -958,18 +958,20 @@
|
||||
</group>
|
||||
</group>
|
||||
</page>
|
||||
<page string="应收明细">
|
||||
<page string="实收明细">
|
||||
<field name="receivable_ids" string=" ">
|
||||
<tree editable="bottom">
|
||||
<field name="contract_id" column_invisible="1"/>
|
||||
<field name="management_type_id"/>
|
||||
<field name="last_month_table"/>
|
||||
<field name="this_month_table"/>
|
||||
<field name="ratio"/>
|
||||
<field name="billable_quantity"/>
|
||||
<field name="due_date"/>
|
||||
<field name="due_date_end"/>
|
||||
<field name="original_amount" string="应计金额"/>
|
||||
<field name="last_month_table" column_invisible="1"/>
|
||||
<field name="this_month_table" column_invisible="1"/>
|
||||
<field name="ratio" column_invisible="1"/>
|
||||
<field name="billable_quantity" column_invisible="1"/>
|
||||
<field name="due_date" string="应收开始日期"/>
|
||||
<field name="due_date_end" string="应收结束日期"/>
|
||||
<field name="original_amount" string="收款金额"/>
|
||||
<field name="payout_date" string="收款日期"/>
|
||||
<field name="delivered1" string="应收金额"/>
|
||||
<field name="pre_collection"/>
|
||||
<field name="actual_coping"/>
|
||||
<field name="remark"/>
|
||||
|
||||
@@ -37,7 +37,7 @@ class InheritPurchaseOrder(models.Model):
|
||||
default=lambda self: [(6, 0, [self.env.user.id])])
|
||||
pay_way = fields.Selection([('onetime', '一次性'), ('installment', '分期')], string="付款方式", default='onetime')
|
||||
reason_text = fields.Text(string="申请事由")
|
||||
purchase_type = fields.Selection([('fixed_asset', '固定资产采购'), ('sporadic', '零星采购'), ('comprehensive', '综合类')], string="采购类型", default='fixed_asset')
|
||||
purchase_type = fields.Selection([('fixed_asset', '固定资产采购'), ('sporadic', '零星采购'), ('comprehensive', '综合类')], string="采购类型", default='comprehensive')
|
||||
is_modify = fields.Boolean(string="可修改")
|
||||
pay_line_ids = fields.One2many('purchase.order.pay.line', 'order_id', string="付款详情")
|
||||
is_company = fields.Boolean(string="本公司", default=True, compute='_compute_is_company',search='_search_part_of_company')
|
||||
|
||||
@@ -41,7 +41,7 @@
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="label">采购标的类型</td>
|
||||
<td colspan="5"><span t-esc="doc.category_id.name or ''"/></td>
|
||||
<td colspan="5"><span t-esc="dict(doc._fields['purchase_type'].selection).get(doc.purchase_type, '')"/></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="label">付款方式</td>
|
||||
|
||||
@@ -9,24 +9,30 @@ class PreArrearsReport(models.Model):
|
||||
@api.model
|
||||
def get_pre_arrears_report(self, params):
|
||||
"""
|
||||
前期欠收报表(数据源:receivable.modify.line):
|
||||
- 查询条件的日期对应应收账单的 due_date(应收日期在查询月内)
|
||||
- 收款日期(reconciliation_date)晚于应收日期(due_date)的记录就是欠收
|
||||
- 金额取收款记录的 not_collected(未收金额/欠收金额)
|
||||
- 按应收账单聚合,每张账单只出一行(汇总该账单下所有欠收收款金额)
|
||||
前期欠收报表(数据源:receivable.modify.line):
|
||||
- 查询条件的日期对应应收账单的 due_date(应收日期在查询月及之前)
|
||||
- 欠收条件:
|
||||
- 收款日期在查询月之后(查询月时点还没收到钱)
|
||||
- 或者 not_collected > 0 (部分收款,还没交完)
|
||||
- 金额取值:
|
||||
- 如果 not_collected > 0,取 not_collected (当前还欠的金额)
|
||||
- 否则取 amount (已收金额)
|
||||
- 按应收账单聚合,每张账单只出一行(汇总该账单下所有欠收收款金额)
|
||||
"""
|
||||
today = datetime.date.today()
|
||||
this_month_first = today.replace(day=1)
|
||||
|
||||
date_start = params.get("date_start")
|
||||
date_end = params.get("date_end")
|
||||
# 应收日期在查询日期之前(不含查询月)
|
||||
cutoff_date = datetime.datetime.fromisoformat(date_start).date() if date_start else this_month_first
|
||||
# 应收日期在查询月及之前(包含查询月)
|
||||
cutoff_date = datetime.datetime.fromisoformat(date_end).date() if date_end else this_month_first
|
||||
# 查询月范围(用于判断收款是否在查询月内)
|
||||
query_month_start = datetime.datetime.fromisoformat(date_start).date() if date_start else this_month_first
|
||||
query_month_end = datetime.datetime.fromisoformat(date_end).date() if date_end else this_month_first
|
||||
|
||||
# 核心逻辑:due_date < cutoff_date,且收款日期 > 应收日期
|
||||
# 核心逻辑:due_date <= cutoff_date(查询月及之前的应收)
|
||||
domain = [
|
||||
('reconciliation_date', '!=', False),
|
||||
('receivable_id.due_date', '<', cutoff_date),
|
||||
('receivable_id.due_date', '<=', cutoff_date),
|
||||
('receivable_id.is_invalid', '=', False),
|
||||
]
|
||||
|
||||
@@ -65,24 +71,43 @@ class PreArrearsReport(models.Model):
|
||||
domain.append(('receivable_id.management_type_id.name', 'not in', ['押金', '违约金']))
|
||||
|
||||
lines = self.sudo().search(domain, order="receivable_id asc, reconciliation_date asc")
|
||||
|
||||
# 欠收条件:reconciliation_date > due_date 且不在同一个月(跨月才算欠收)
|
||||
|
||||
# 欠收条件(同时满足):
|
||||
# 1. reconciliation_date >= query_month_start (收款日期不能小于查询月)
|
||||
# 2. 满足以下任一:
|
||||
# a. reconciliation_date > query_month_end (收款日期在查询月之后,查询月时点还没收到钱)
|
||||
# b. not_collected > 0 (部分收款,还没交完)
|
||||
lines = lines.filtered(
|
||||
lambda l: l.reconciliation_date and l.receivable_id.due_date
|
||||
and l.reconciliation_date > l.receivable_id.due_date
|
||||
and not (
|
||||
l.reconciliation_date.year == l.receivable_id.due_date.year
|
||||
and l.reconciliation_date.month == l.receivable_id.due_date.month
|
||||
)
|
||||
lambda l: l.reconciliation_date and l.reconciliation_date >= query_month_start and (
|
||||
(l.reconciliation_date > query_month_end) or
|
||||
(l.not_collected and l.not_collected > 0)
|
||||
)
|
||||
)
|
||||
|
||||
# 调试日志
|
||||
print(f"[前期欠收报表] 查询到的 lines 数量: {len(lines)}")
|
||||
for line in lines:
|
||||
print(f" - line.id={line.id}, receivable_id={line.receivable_id.id}, "
|
||||
f"due_date={line.receivable_id.due_date}, "
|
||||
f"reconciliation_date={line.reconciliation_date}, "
|
||||
f"not_collected={line.not_collected}, amount={line.amount}")
|
||||
|
||||
# 按应收账单聚合
|
||||
rec_map = {}
|
||||
for line in lines:
|
||||
rid = line.receivable_id.id
|
||||
if rid not in rec_map:
|
||||
rec_map[rid] = {'rec': line.receivable_id, 'amount': 0.0}
|
||||
rec_map[rid]['amount'] += line.not_collected or 0.0
|
||||
rec_map[rid] = {'rec': line.receivable_id, 'amount': 0.0, 'reconciliation_dates': []}
|
||||
# 金额取值:有未收金额取not_collected,否则取amount
|
||||
rec_map[rid]['amount'] += (line.not_collected if (line.not_collected and line.not_collected > 0) else line.amount) or 0.0
|
||||
# 收集收款日期
|
||||
if line.reconciliation_date:
|
||||
rec_map[rid]['reconciliation_dates'].append(line.reconciliation_date)
|
||||
|
||||
# 调试日志
|
||||
print(f"[前期欠收报表] 聚合后的 rec_map 数量: {len(rec_map)}")
|
||||
for rid, data in rec_map.items():
|
||||
print(f" - receivable_id={rid}, amount={data['amount']}")
|
||||
|
||||
rows = []
|
||||
total_amount = 0.0
|
||||
@@ -103,6 +128,13 @@ class PreArrearsReport(models.Model):
|
||||
}
|
||||
elif rec:
|
||||
property_val = rec.property_name or ''
|
||||
|
||||
# 应收开始日期
|
||||
due_date_str = rec.due_date.strftime('%Y-%m-%d') if rec.due_date else ''
|
||||
|
||||
# 收款日期(取所有收款日期,用逗号分隔)
|
||||
reconciliation_dates = data.get('reconciliation_dates', [])
|
||||
reconciliation_date_str = ', '.join([d.strftime('%Y-%m-%d') for d in sorted(set(reconciliation_dates))]) if reconciliation_dates else ''
|
||||
|
||||
rows.append({
|
||||
"序号": idx,
|
||||
@@ -110,6 +142,7 @@ class PreArrearsReport(models.Model):
|
||||
'model': 'property.lease.contract',
|
||||
'id': contract.id,
|
||||
'display_name': contract.contract_code,
|
||||
'view_id': self.env.ref('yuthon_property_approval.view_property_lease_contract_form1').id,
|
||||
} if contract else "",
|
||||
"物业名称": property_val,
|
||||
"承租方名称": {
|
||||
@@ -118,6 +151,8 @@ class PreArrearsReport(models.Model):
|
||||
'display_name': rec.lessee_id.name,
|
||||
} if rec.lessee_id else "",
|
||||
"收款类型": rec.management_type_id.name if rec.management_type_id else "",
|
||||
"应收开始日期": due_date_str,
|
||||
"收款日期": reconciliation_date_str,
|
||||
"金额": amount,
|
||||
"所属公司": contract.lessor_id.name if contract and contract.lessor_id else "",
|
||||
"管理员": {
|
||||
|
||||
@@ -8,48 +8,26 @@ class ReceivableModifyFilterDomains(models.Model):
|
||||
|
||||
@api.model
|
||||
def get_receivable_filter_domains(self, params):
|
||||
"""根据当前筛选条件,返回物业/承租方/合同的候选 ID 集合,用于三个下拉框互相过滤。"""
|
||||
# 注意:这里不按日期限制,只根据当前组合条件(公司/权属/片区/收款类型/物业/承租方/合同)
|
||||
# 来计算三类对象的全集,避免不同报表各自的日期口径导致候选集为空。
|
||||
domain = [
|
||||
('receivable_id.is_invalid', '=', False),
|
||||
]
|
||||
"""根据当前筛选条件,返回物业/承租方/合同的候选 ID 集合,用于三个下拉框互相过滤。
|
||||
|
||||
注意:
|
||||
- 候选集不应受收款类型、是否无效等业务条件过滤
|
||||
- 只根据用户已选择的物业/承租方/合同进行互相过滤
|
||||
- 具体的业务过滤由报表查询方法自己处理
|
||||
"""
|
||||
domain = []
|
||||
|
||||
keyword = params.get("keyword")
|
||||
|
||||
if keyword:
|
||||
domain += [
|
||||
'|', '|',
|
||||
('receivable_id.contract_id.contract_code', 'ilike', keyword),
|
||||
('receivable_id.property_name', 'ilike', keyword),
|
||||
('receivable_id.lessee_id.name', 'ilike', keyword),
|
||||
]
|
||||
|
||||
condition = params.get('condition')
|
||||
partner_id = params.get('partner_id')
|
||||
company_id = params.get('company_id')
|
||||
management_type_id = params.get('management_type_id')
|
||||
# 只根据已选择的条件进行互相过滤,不应用业务过滤
|
||||
property_id = params.get('property_id')
|
||||
lessee_id = params.get('lessee_id')
|
||||
contract_id = params.get('contract_id')
|
||||
|
||||
if condition:
|
||||
domain.append(('receivable_id.tenure_type', '=', condition))
|
||||
if partner_id:
|
||||
domain.append(('receivable_id.precinct_id', '=', partner_id))
|
||||
if company_id:
|
||||
domain.append(('receivable_id.company_id', '=', company_id))
|
||||
if property_id:
|
||||
domain.append(('receivable_id.property_ids', 'in', [property_id]))
|
||||
if lessee_id:
|
||||
domain.append(('receivable_id.lessee_id', '=', lessee_id))
|
||||
if contract_id:
|
||||
domain.append(('receivable_id.contract_id', '=', contract_id))
|
||||
if management_type_id:
|
||||
domain.append(('receivable_id.management_type_id', '=', management_type_id))
|
||||
else:
|
||||
# 与各报表保持一致:默认剔除押金、违约金类型
|
||||
domain.append(('receivable_id.management_type_id.name', 'not in', ['押金', '违约金']))
|
||||
|
||||
lines = self.sudo().search(domain)
|
||||
receivables = lines.mapped('receivable_id')
|
||||
|
||||
@@ -216,7 +216,7 @@ class ReceivableReport extends Component {
|
||||
type: 'ir.actions.act_window',
|
||||
res_model: model,
|
||||
res_id: id,
|
||||
views: [[false, 'form'], [false, 'search']],
|
||||
views: [[view_id || false, 'form'], [false, 'search']],
|
||||
target: 'new'
|
||||
});
|
||||
}
|
||||
|
||||
@@ -13,11 +13,13 @@
|
||||
"dateMode": "single",
|
||||
"columns": [
|
||||
{"headerName": "序号", "field": "序号", "width": 45, "flex": 0, "pinned": "left"},
|
||||
{"headerName": "应收开始日期", "field": "应收开始日期", "flex": 1},
|
||||
{"headerName": "收款日期", "field": "收款日期", "flex": 1},
|
||||
{"headerName": "金额", "field": "金额", "flex": 1, "type": "number"},
|
||||
{"headerName": "合同编号", "field": "合同编号", "flex": 1.2},
|
||||
{"headerName": "物业名称", "field": "物业名称", "flex": 2.5},
|
||||
{"headerName": "承租方名称", "field": "承租方名称", "flex": 1.4},
|
||||
{"headerName": "收款类型", "field": "收款类型", "flex": 1},
|
||||
{"headerName": "金额", "field": "金额", "flex": 1, "type": "number"},
|
||||
{"headerName": "所属公司", "field": "所属公司", "flex": 1},
|
||||
{"headerName": "管理员", "field": "管理员", "flex": 1}
|
||||
]
|
||||
|
||||
@@ -121,6 +121,7 @@ class YuthonWillTask(http.Controller):
|
||||
'employee_num': ','.join(task.employee_ids.mapped('name')) if task.employee_ids else '',
|
||||
'start_date': fields.Date.to_string(task.start_date),
|
||||
'weekday': weekday_str,
|
||||
'address': task.address or '',
|
||||
'request_hour_from': '',
|
||||
'request_hour_to': '',
|
||||
'state': task.task_state,
|
||||
|
||||
@@ -308,11 +308,11 @@
|
||||
parent="attendance_resources_setting_root_board"
|
||||
sequence="8"
|
||||
action="yuthon_hr_attendance.view_overtime_page_action"/>
|
||||
<menuitem id="menu_hr_resource_calendar_board"
|
||||
name="法定节假日表"
|
||||
parent="attendance_resources_setting_root_board"
|
||||
sequence="10"
|
||||
action="yuthon_hr_attendance.resource_calendar_leaves_action_from_calendar"/>
|
||||
<!-- <menuitem id="menu_hr_resource_calendar_board"-->
|
||||
<!-- name="法定节假日表"-->
|
||||
<!-- parent="attendance_resources_setting_root_board"-->
|
||||
<!-- sequence="10"-->
|
||||
<!-- action="yuthon_hr_attendance.resource_calendar_leaves_action_from_calendar"/>-->
|
||||
<menuitem id="holiday_set_type_board2"
|
||||
name="休假类型"
|
||||
parent="attendance_resources_setting_root_board"
|
||||
|
||||
Reference in New Issue
Block a user