151 lines
4.8 KiB
Python
151 lines
4.8 KiB
Python
import os
|
||
os.environ['DB_HOST'] = '192.168.0.61'
|
||
os.environ['DB_PORT'] = '55432'
|
||
os.environ['DB_NAME'] = 'njts_acct'
|
||
os.environ['DB_USER'] = 'njts_app'
|
||
os.environ['DB_PASSWORD'] = 'njts_app2025'
|
||
|
||
import sys
|
||
sys.path.insert(0, os.path.dirname(__file__))
|
||
|
||
from app.core.database import get_connection
|
||
|
||
conn = get_connection()
|
||
cur = conn.cursor()
|
||
|
||
print("\n" + "="*120)
|
||
print("試算表ロジック検証 - 普通預金(102) 2025年6月")
|
||
print("="*120)
|
||
|
||
# 試算表SQLと同じロジックで集計
|
||
cur.execute("""
|
||
SELECT
|
||
jl.account_id,
|
||
SUM(jl.debit) as total_debit,
|
||
SUM(jl.credit) as total_credit
|
||
FROM journal_entries je
|
||
JOIN journal_lines jl ON jl.journal_entry_id = je.journal_entry_id
|
||
LEFT JOIN journal_entries child ON child.parent_entry_id = je.journal_entry_id
|
||
JOIN accounts a ON jl.account_id = a.account_id
|
||
WHERE je.entry_date BETWEEN '2025-06-01' AND '2025-06-30'
|
||
AND je.description <> '前期残高'
|
||
AND je.is_deleted = false
|
||
AND child.journal_entry_id IS NULL
|
||
AND a.account_code = '102'
|
||
GROUP BY jl.account_id
|
||
""")
|
||
|
||
result = cur.fetchone()
|
||
print(f"\n【試算表の集計結果】")
|
||
print(f"借方発生額: {result['total_debit']:>15,.0f} 円")
|
||
print(f"貸方発生額: {result['total_credit']:>15,.0f} 円")
|
||
|
||
# 詳細な内訳を確認
|
||
print(f"\n{'='*120}")
|
||
print("【集計対象の仕訳詳細】")
|
||
print(f"{'='*120}")
|
||
|
||
cur.execute("""
|
||
SELECT
|
||
je.journal_entry_id,
|
||
je.entry_date,
|
||
je.description,
|
||
jl.debit,
|
||
jl.credit,
|
||
je.parent_entry_id,
|
||
CASE WHEN child.journal_entry_id IS NOT NULL THEN 'Y' ELSE 'N' END as has_child
|
||
FROM journal_entries je
|
||
JOIN journal_lines jl ON jl.journal_entry_id = je.journal_entry_id
|
||
LEFT JOIN journal_entries child ON child.parent_entry_id = je.journal_entry_id
|
||
JOIN accounts a ON jl.account_id = a.account_id
|
||
WHERE je.entry_date BETWEEN '2025-06-01' AND '2025-06-30'
|
||
AND je.description <> '前期残高'
|
||
AND je.is_deleted = false
|
||
AND a.account_code = '102'
|
||
ORDER BY je.journal_entry_id
|
||
""")
|
||
|
||
rows = cur.fetchall()
|
||
|
||
debit_sum = 0
|
||
credit_sum = 0
|
||
debit_included = 0
|
||
credit_included = 0
|
||
|
||
print(f"\n{'ID':>3} {'日付':10} {'借方':>13} {'貸方':>13} {'親ID':>5} {'子':3} {'集計':4} 摘要")
|
||
print("-" * 120)
|
||
|
||
for r in rows:
|
||
is_included = r['has_child'] == 'N'
|
||
status = "○" if is_included else "×"
|
||
|
||
debit_sum += r['debit']
|
||
credit_sum += r['credit']
|
||
|
||
if is_included:
|
||
debit_included += r['debit']
|
||
credit_included += r['credit']
|
||
|
||
parent_str = str(r['parent_entry_id']) if r['parent_entry_id'] else "-"
|
||
|
||
# 逆仕訳・修正後をマーク
|
||
desc = r['description'][:60]
|
||
if '[逆仕訳]' in desc:
|
||
desc = f"🔄 {desc}"
|
||
elif '【修正後】' in desc:
|
||
desc = f"✏️ {desc}"
|
||
|
||
print(f"{r['journal_entry_id']:3d} {r['entry_date']} {r['debit']:>13,.0f} {r['credit']:>13,.0f} {parent_str:>5} {r['has_child']:3} {status:4} {desc}")
|
||
|
||
print("-" * 120)
|
||
print(f"{'全仕訳合計':62} {debit_sum:>13,.0f} {credit_sum:>13,.0f}")
|
||
print(f"{'集計対象(子なし)':60} {debit_included:>13,.0f} {credit_included:>13,.0f}")
|
||
|
||
# parent_entry_idの問題を確認
|
||
print(f"\n{'='*120}")
|
||
print("【parent_entry_idチェーン確認】")
|
||
print(f"{'='*120}")
|
||
|
||
cur.execute("""
|
||
SELECT
|
||
je.journal_entry_id as id,
|
||
je.description,
|
||
je.parent_entry_id as parent,
|
||
(SELECT description FROM journal_entries WHERE journal_entry_id = je.parent_entry_id) as parent_desc,
|
||
(SELECT COUNT(*) FROM journal_entries child WHERE child.parent_entry_id = je.journal_entry_id) as child_count
|
||
FROM journal_entries je
|
||
WHERE (je.description LIKE '%社会保険%' OR je.description LIKE '%遠達ビル%')
|
||
AND je.entry_date BETWEEN '2025-06-01' AND '2025-06-30'
|
||
ORDER BY je.journal_entry_id
|
||
""")
|
||
|
||
print(f"\n{'ID':>3} {'親ID':>5} {'子数':>4} 摘要 → 親の摘要")
|
||
print("-" * 120)
|
||
|
||
rows = cur.fetchall()
|
||
for r in rows:
|
||
parent_str = str(r['parent']) if r['parent'] else "-"
|
||
parent_desc_str = r['parent_desc'][:40] if r['parent_desc'] else "-"
|
||
print(f"{r['id']:3d} {parent_str:>5} {r['child_count']:>4} {r['description'][:50]}")
|
||
if r['parent_desc']:
|
||
print(f" └→ 親: {parent_desc_str}")
|
||
|
||
cur.close()
|
||
conn.close()
|
||
|
||
print(f"\n{'='*120}")
|
||
print("【結論】")
|
||
print(f"{'='*120}")
|
||
print("""
|
||
正しい集計方法:
|
||
1. parent_entry_idチェーンが正しく設定されている場合
|
||
→ 最後の修正版のみが「子を持たない」状態になり、それのみが集計される
|
||
|
||
2. parent_entry_idの設定ミスがある場合
|
||
→ 逆仕訳や途中の修正版も「子を持たない」と判定され、重複集計される
|
||
|
||
対策:
|
||
- すべてのparent_entry_idを正しく設定する
|
||
- チェーン: 元 → 逆仕訳 → 修正後 → 逆仕訳 → 修正後 → ...
|
||
""")
|