Compare commits
1 Commits
version-15
...
mergify/co
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4c643c7591 |
@@ -18,4 +18,8 @@ max_line_length = 110
|
||||
[{*.json}]
|
||||
insert_final_newline = false
|
||||
indent_style = space
|
||||
<<<<<<< HEAD
|
||||
indent_size = 2
|
||||
=======
|
||||
indent_size = 1
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
@@ -30,5 +30,20 @@ b147b85e6ac19a9220cd1e2958a6ebd99373283a
|
||||
# bulk format python code with black
|
||||
baec607ff5905b1c67531096a9cf50ec7ff00a5d
|
||||
|
||||
<<<<<<< HEAD
|
||||
# ruff
|
||||
960ef14b7a68cfec9e309ec12845f521cb6a721c
|
||||
=======
|
||||
# bulk refactor with sourcery
|
||||
eb9ee3f79b94e594fc6dfa4f6514580e125eee8c
|
||||
|
||||
# js formatting
|
||||
ec74a5e56617bbd76ac402451468fd4668af543d
|
||||
|
||||
# ruff formatting
|
||||
a308792ee7fda18a681e9181f4fd00b36385bc23
|
||||
|
||||
# noisy typing refactoring of get_item_details
|
||||
7b7211ac79c248a79ba8a999ff34e734d874c0ae
|
||||
d827ed21adc7b36047e247cbb0dc6388d048a7f9
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
15
.github/helper/documentation.py
vendored
15
.github/helper/documentation.py
vendored
@@ -1,7 +1,13 @@
|
||||
import sys
|
||||
<<<<<<< HEAD
|
||||
import requests
|
||||
from urllib.parse import urlparse
|
||||
|
||||
=======
|
||||
from urllib.parse import urlparse
|
||||
|
||||
import requests
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
WEBSITE_REPOS = [
|
||||
"erpnext_com",
|
||||
@@ -10,7 +16,6 @@ WEBSITE_REPOS = [
|
||||
|
||||
DOCUMENTATION_DOMAINS = [
|
||||
"docs.erpnext.com",
|
||||
"docs.frappe.io",
|
||||
"frappeframework.com",
|
||||
]
|
||||
|
||||
@@ -37,11 +42,15 @@ def is_documentation_link(word: str) -> bool:
|
||||
|
||||
|
||||
def contains_documentation_link(body: str) -> bool:
|
||||
<<<<<<< HEAD
|
||||
return any(
|
||||
is_documentation_link(word)
|
||||
for line in body.splitlines()
|
||||
for word in line.split()
|
||||
)
|
||||
=======
|
||||
return any(is_documentation_link(word) for line in body.splitlines() for word in line.split())
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
|
||||
def check_pull_request(number: str) -> "tuple[int, str]":
|
||||
@@ -54,12 +63,16 @@ def check_pull_request(number: str) -> "tuple[int, str]":
|
||||
head_sha = (payload.get("head") or {}).get("sha")
|
||||
body = (payload.get("body") or "").lower()
|
||||
|
||||
<<<<<<< HEAD
|
||||
if (
|
||||
not title.startswith("feat")
|
||||
or not head_sha
|
||||
or "no-docs" in body
|
||||
or "backport" in body
|
||||
):
|
||||
=======
|
||||
if not title.startswith("feat") or not head_sha or "no-docs" in body or "backport" in body:
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
return 0, "Skipping documentation checks... 🏃"
|
||||
|
||||
if contains_documentation_link(body):
|
||||
|
||||
25
.github/helper/install.sh
vendored
25
.github/helper/install.sh
vendored
@@ -6,15 +6,28 @@ cd ~ || exit
|
||||
|
||||
sudo apt update
|
||||
sudo apt remove mysql-server mysql-client
|
||||
sudo apt install libcups2-dev redis-server mariadb-client
|
||||
sudo apt install libcups2-dev redis-server mariadb-client-10.6
|
||||
|
||||
pip install frappe-bench
|
||||
|
||||
githubbranch=${GITHUB_BASE_REF:-${GITHUB_REF##*/}}
|
||||
frappeuser=${FRAPPE_USER:-"frappe"}
|
||||
<<<<<<< HEAD
|
||||
frappebranch=${FRAPPE_BRANCH:-$githubbranch}
|
||||
|
||||
git clone "https://github.com/${frappeuser}/frappe" --branch "${frappebranch}" --depth 1
|
||||
=======
|
||||
frappecommitish=${FRAPPE_BRANCH:-$githubbranch}
|
||||
|
||||
mkdir frappe
|
||||
pushd frappe
|
||||
git init
|
||||
git remote add origin "https://github.com/${frappeuser}/frappe"
|
||||
git fetch origin "${frappecommitish}" --depth 1
|
||||
git checkout FETCH_HEAD
|
||||
popd
|
||||
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
bench init --skip-assets --frappe-path ~/frappe --python "$(which python)" frappe-bench
|
||||
|
||||
mkdir ~/frappe-bench/sites/test_site
|
||||
@@ -44,9 +57,13 @@ fi
|
||||
|
||||
|
||||
install_whktml() {
|
||||
wget -O /tmp/wkhtmltox.deb https://github.com/wkhtmltopdf/packaging/releases/download/0.12.6.1-2/wkhtmltox_0.12.6.1-2.jammy_amd64.deb
|
||||
sudo apt install /tmp/wkhtmltox.deb
|
||||
|
||||
if [ "$(lsb_release -rs)" = "22.04" ]; then
|
||||
wget -O /tmp/wkhtmltox.deb https://github.com/wkhtmltopdf/packaging/releases/download/0.12.6.1-2/wkhtmltox_0.12.6.1-2.jammy_amd64.deb
|
||||
sudo apt install /tmp/wkhtmltox.deb
|
||||
else
|
||||
echo "Please update this script to support wkhtmltopdf for $(lsb_release -ds)"
|
||||
exit 1
|
||||
fi
|
||||
}
|
||||
install_whktml &
|
||||
wkpid=$!
|
||||
|
||||
68
.github/helper/translation.py
vendored
Normal file
68
.github/helper/translation.py
vendored
Normal file
@@ -0,0 +1,68 @@
|
||||
import re
|
||||
import sys
|
||||
|
||||
errors_encounter = 0
|
||||
pattern = re.compile(
|
||||
r"_\(([\"']{,3})(?P<message>((?!\1).)*)\1(\s*,\s*context\s*=\s*([\"'])(?P<py_context>((?!\5).)*)\5)*(\s*,(\s*?.*?\n*?)*(,\s*([\"'])(?P<js_context>((?!\11).)*)\11)*)*\)"
|
||||
)
|
||||
words_pattern = re.compile(r"_{1,2}\([\"'`]{1,3}.*?[a-zA-Z]")
|
||||
start_pattern = re.compile(r"_{1,2}\([f\"'`]{1,3}")
|
||||
f_string_pattern = re.compile(r"_\(f[\"']")
|
||||
starts_with_f_pattern = re.compile(r"_\(f")
|
||||
|
||||
# skip first argument
|
||||
files = sys.argv[1:]
|
||||
files_to_scan = [_file for _file in files if _file.endswith((".py", ".js"))]
|
||||
|
||||
for _file in files_to_scan:
|
||||
with open(_file) as f:
|
||||
print(f"Checking: {_file}")
|
||||
file_lines = f.readlines()
|
||||
for line_number, line in enumerate(file_lines, 1):
|
||||
if "frappe-lint: disable-translate" in line:
|
||||
continue
|
||||
|
||||
start_matches = start_pattern.search(line)
|
||||
if start_matches:
|
||||
starts_with_f = starts_with_f_pattern.search(line)
|
||||
|
||||
if starts_with_f:
|
||||
has_f_string = f_string_pattern.search(line)
|
||||
if has_f_string:
|
||||
errors_encounter += 1
|
||||
print(
|
||||
f"\nF-strings are not supported for translations at line number {line_number}\n{line.strip()[:100]}"
|
||||
)
|
||||
continue
|
||||
else:
|
||||
continue
|
||||
|
||||
match = pattern.search(line)
|
||||
error_found = False
|
||||
|
||||
if not match and line.endswith((",\n", "[\n")):
|
||||
# concat remaining text to validate multiline pattern
|
||||
line = "".join(file_lines[line_number - 1 :])
|
||||
line = line[start_matches.start() + 1 :]
|
||||
match = pattern.match(line)
|
||||
|
||||
if not match:
|
||||
error_found = True
|
||||
print(f"\nTranslation syntax error at line number {line_number}\n{line.strip()[:100]}")
|
||||
|
||||
if not error_found and not words_pattern.search(line):
|
||||
error_found = True
|
||||
print(
|
||||
f"\nTranslation is useless because it has no words at line number {line_number}\n{line.strip()[:100]}"
|
||||
)
|
||||
|
||||
if error_found:
|
||||
errors_encounter += 1
|
||||
|
||||
if errors_encounter > 0:
|
||||
print(
|
||||
'\nVisit "https://frappeframework.com/docs/user/en/translations" to learn about valid translation strings.'
|
||||
)
|
||||
sys.exit(1)
|
||||
else:
|
||||
print("\nGood To Go!")
|
||||
40
.github/helper/update_pot_file.sh
vendored
Normal file
40
.github/helper/update_pot_file.sh
vendored
Normal file
@@ -0,0 +1,40 @@
|
||||
#!/bin/bash
|
||||
set -e
|
||||
cd ~ || exit
|
||||
|
||||
echo "Setting Up Bench..."
|
||||
|
||||
pip install frappe-bench
|
||||
bench -v init frappe-bench --skip-assets --skip-redis-config-generation --python "$(which python)"
|
||||
cd ./frappe-bench || exit
|
||||
|
||||
echo "Get ERPNext..."
|
||||
bench get-app --skip-assets erpnext "${GITHUB_WORKSPACE}"
|
||||
|
||||
echo "Generating POT file..."
|
||||
bench generate-pot-file --app erpnext
|
||||
|
||||
cd ./apps/erpnext || exit
|
||||
|
||||
echo "Configuring git user..."
|
||||
git config user.email "developers@erpnext.com"
|
||||
git config user.name "frappe-pr-bot"
|
||||
|
||||
echo "Setting the correct git remote..."
|
||||
# Here, the git remote is a local file path by default. Let's change it to the upstream repo.
|
||||
git remote set-url upstream https://github.com/frappe/erpnext.git
|
||||
|
||||
echo "Creating a new branch..."
|
||||
isodate=$(date -u +"%Y-%m-%d")
|
||||
branch_name="pot_${BASE_BRANCH}_${isodate}"
|
||||
git checkout -b "${branch_name}"
|
||||
|
||||
echo "Commiting changes..."
|
||||
git add erpnext/locale/main.pot
|
||||
git commit -m "chore: update POT file"
|
||||
|
||||
gh auth setup-git
|
||||
git push -u upstream "${branch_name}"
|
||||
|
||||
echo "Creating a PR..."
|
||||
gh pr create --fill --base "${BASE_BRANCH}" --head "${branch_name}" --reviewer ${PR_REVIEWER} -R frappe/erpnext
|
||||
4
.github/release.yml
vendored
4
.github/release.yml
vendored
@@ -1,4 +0,0 @@
|
||||
changelog:
|
||||
exclude:
|
||||
labels:
|
||||
- skip-release-notes
|
||||
11
.github/stale.yml
vendored
11
.github/stale.yml
vendored
@@ -12,6 +12,17 @@ exemptProjects: true
|
||||
# Set to true to ignore issues in a milestone (defaults to false)
|
||||
exemptMilestones: true
|
||||
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
# Skip the stale action for draft PRs
|
||||
exemptDraftPr: true
|
||||
|
||||
# Issues or Pull Requests with these labels will never be considered stale. Set to `[]` to disable
|
||||
exemptLabels:
|
||||
- hotfix
|
||||
- no-stale
|
||||
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pulls:
|
||||
daysUntilStale: 15
|
||||
daysUntilClose: 3
|
||||
|
||||
26
.github/workflows/backport.yml
vendored
Normal file
26
.github/workflows/backport.yml
vendored
Normal file
@@ -0,0 +1,26 @@
|
||||
name: Backport
|
||||
on:
|
||||
pull_request_target:
|
||||
types:
|
||||
- closed
|
||||
- labeled
|
||||
|
||||
jobs:
|
||||
main:
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 60
|
||||
steps:
|
||||
- name: Checkout Actions
|
||||
uses: actions/checkout@v2
|
||||
with:
|
||||
repository: "frappe/backport"
|
||||
path: ./actions
|
||||
ref: develop
|
||||
- name: Install Actions
|
||||
run: npm install --production --prefix ./actions
|
||||
- name: Run backport
|
||||
uses: ./actions/backport
|
||||
with:
|
||||
token: ${{secrets.RELEASE_TOKEN}}
|
||||
labelsToAdd: "backport"
|
||||
title: "{{originalTitle}}"
|
||||
39
.github/workflows/generate-pot-file.yml
vendored
Normal file
39
.github/workflows/generate-pot-file.yml
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
# This workflow is agnostic to branches. Only maintain on develop branch.
|
||||
# To add/remove branches just modify the matrix.
|
||||
|
||||
name: Regenerate POT file (translatable strings)
|
||||
on:
|
||||
schedule:
|
||||
# 9:30 UTC => 3 PM IST Sunday
|
||||
- cron: "30 9 * * 0"
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
regenerate-pot-file:
|
||||
name: Regenerate POT file
|
||||
runs-on: ubuntu-latest
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
branch: ["develop"]
|
||||
permissions:
|
||||
contents: write
|
||||
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
ref: ${{ matrix.branch }}
|
||||
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: "3.12"
|
||||
|
||||
- name: Run script to update POT file
|
||||
run: |
|
||||
bash ${GITHUB_WORKSPACE}/.github/helper/update_pot_file.sh
|
||||
env:
|
||||
GH_TOKEN: ${{ secrets.RELEASE_TOKEN }}
|
||||
BASE_BRANCH: ${{ matrix.branch }}
|
||||
PR_REVIEWER: barredterra # change to your GitHub username if you copied this file
|
||||
32
.github/workflows/initiate_release.yml
vendored
Normal file
32
.github/workflows/initiate_release.yml
vendored
Normal file
@@ -0,0 +1,32 @@
|
||||
# This workflow is agnostic to branches. Only maintain on develop branch.
|
||||
# To add/remove versions just modify the matrix.
|
||||
|
||||
name: Create weekly release pull requests
|
||||
on:
|
||||
schedule:
|
||||
# 9:30 UTC => 3 PM IST Tuesday
|
||||
- cron: "30 9 * * 2"
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
stable-release:
|
||||
name: Release
|
||||
runs-on: ubuntu-latest
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
version: ["14", "15"]
|
||||
|
||||
steps:
|
||||
- uses: octokit/request-action@v2.x
|
||||
with:
|
||||
route: POST /repos/{owner}/{repo}/pulls
|
||||
owner: frappe
|
||||
repo: erpnext
|
||||
title: |-
|
||||
"chore: release v${{ matrix.version }}"
|
||||
body: "Automated weekly release."
|
||||
base: version-${{ matrix.version }}
|
||||
head: version-${{ matrix.version }}-hotfix
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.RELEASE_TOKEN }}
|
||||
30
.github/workflows/label-base-on-title.yml
vendored
30
.github/workflows/label-base-on-title.yml
vendored
@@ -1,30 +0,0 @@
|
||||
name: "Auto-label PRs based on title"
|
||||
|
||||
on:
|
||||
pull_request_target:
|
||||
types: [opened, reopened]
|
||||
|
||||
jobs:
|
||||
add-label-if-prefix-matches:
|
||||
permissions:
|
||||
contents: read
|
||||
pull-requests: write
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Check PR title and add label if it matches prefixes
|
||||
uses: actions/github-script@v7
|
||||
continue-on-error: true
|
||||
with:
|
||||
script: |
|
||||
const title = context.payload.pull_request.title.toLowerCase();
|
||||
const prefixes = ['chore', 'ci', 'style', 'test', 'refactor'];
|
||||
|
||||
// Check if the PR title starts with any of the prefixes
|
||||
if (prefixes.some(prefix => title.startsWith(prefix))) {
|
||||
await github.rest.issues.addLabels({
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
issue_number: context.payload.pull_request.number,
|
||||
labels: ['skip-release-notes']
|
||||
});
|
||||
}
|
||||
15
.github/workflows/linters.yml
vendored
15
.github/workflows/linters.yml
vendored
@@ -20,6 +20,21 @@ jobs:
|
||||
- name: Install and Run Pre-commit
|
||||
uses: pre-commit/action@v3.0.0
|
||||
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
semgrep:
|
||||
name: semgrep
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
|
||||
- name: Set up Python 3.10
|
||||
uses: actions/setup-python@v4
|
||||
with:
|
||||
python-version: '3.10'
|
||||
cache: pip
|
||||
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
- name: Download Semgrep rules
|
||||
run: git clone --depth 1 https://github.com/frappe/semgrep-rules.git frappe-semgrep-rules
|
||||
|
||||
|
||||
21
.github/workflows/lock.yml
vendored
Normal file
21
.github/workflows/lock.yml
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
name: 'Lock threads'
|
||||
|
||||
on:
|
||||
schedule:
|
||||
- cron: '0 0 * * *'
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
issues: write
|
||||
pull-requests: write
|
||||
|
||||
|
||||
jobs:
|
||||
lock:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: dessant/lock-threads@v5
|
||||
with:
|
||||
github-token: ${{ github.token }}
|
||||
issue-inactive-days: 14
|
||||
pr-inactive-days: 14
|
||||
33
.github/workflows/patch.yml
vendored
33
.github/workflows/patch.yml
vendored
@@ -32,7 +32,11 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Clone
|
||||
<<<<<<< HEAD
|
||||
uses: actions/checkout@v2
|
||||
=======
|
||||
uses: actions/checkout@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
- name: Check for valid Python & Merge Conflicts
|
||||
run: |
|
||||
@@ -43,12 +47,21 @@ jobs:
|
||||
fi
|
||||
|
||||
- name: Setup Python
|
||||
<<<<<<< HEAD
|
||||
uses: "actions/setup-python@v4"
|
||||
with:
|
||||
python-version: '3.10'
|
||||
|
||||
- name: Setup Node
|
||||
uses: actions/setup-node@v2
|
||||
=======
|
||||
uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: '3.11'
|
||||
|
||||
- name: Setup Node
|
||||
uses: actions/setup-node@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
with:
|
||||
node-version: 18
|
||||
check-latest: true
|
||||
@@ -57,7 +70,11 @@ jobs:
|
||||
run: echo "127.0.0.1 test_site" | sudo tee -a /etc/hosts
|
||||
|
||||
- name: Cache pip
|
||||
<<<<<<< HEAD
|
||||
uses: actions/cache@v2
|
||||
=======
|
||||
uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
with:
|
||||
path: ~/.cache/pip
|
||||
key: ${{ runner.os }}-pip-${{ hashFiles('**/*requirements.txt', '**/pyproject.toml') }}
|
||||
@@ -66,7 +83,11 @@ jobs:
|
||||
${{ runner.os }}-
|
||||
|
||||
- name: Cache node modules
|
||||
<<<<<<< HEAD
|
||||
uses: actions/cache@v2
|
||||
=======
|
||||
uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
env:
|
||||
cache-name: cache-node-modules
|
||||
with:
|
||||
@@ -81,7 +102,11 @@ jobs:
|
||||
id: yarn-cache-dir-path
|
||||
run: echo "::set-output name=dir::$(yarn cache dir)"
|
||||
|
||||
<<<<<<< HEAD
|
||||
- uses: actions/cache@v2
|
||||
=======
|
||||
- uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
id: yarn-cache
|
||||
with:
|
||||
path: ${{ steps.yarn-cache-dir-path.outputs.dir }}
|
||||
@@ -134,9 +159,17 @@ jobs:
|
||||
}
|
||||
|
||||
update_to_version 14
|
||||
<<<<<<< HEAD
|
||||
|
||||
echo "Updating to latest version"
|
||||
git -C "apps/frappe" checkout -q -f "${GITHUB_BASE_REF:-${GITHUB_REF##*/}}"
|
||||
=======
|
||||
update_to_version 15
|
||||
|
||||
echo "Updating to latest version"
|
||||
git -C "apps/frappe" fetch --depth 1 upstream "${GITHUB_BASE_REF:-${GITHUB_REF##*/}}"
|
||||
git -C "apps/frappe" checkout -q -f FETCH_HEAD
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
git -C "apps/erpnext" checkout -q -f "$GITHUB_SHA"
|
||||
|
||||
pgrep honcho | xargs kill
|
||||
|
||||
22
.github/workflows/patch_faux.yml
vendored
Normal file
22
.github/workflows/patch_faux.yml
vendored
Normal file
@@ -0,0 +1,22 @@
|
||||
# Tests are skipped for these files but github doesn't allow "passing" hence this is required.
|
||||
|
||||
name: Skipped Patch Test
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
paths:
|
||||
- "**.js"
|
||||
- "**.css"
|
||||
- "**.md"
|
||||
- "**.html"
|
||||
- "**.csv"
|
||||
|
||||
jobs:
|
||||
test:
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
name: Patch Test
|
||||
|
||||
steps:
|
||||
- name: Pass skipped tests unconditionally
|
||||
run: "echo Skipped"
|
||||
14
.github/workflows/release.yml
vendored
14
.github/workflows/release.yml
vendored
@@ -2,23 +2,37 @@ name: Generate Semantic Release
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
<<<<<<< HEAD
|
||||
- version-15
|
||||
=======
|
||||
- version-13
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
jobs:
|
||||
release:
|
||||
name: Release
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Checkout Entire Repository
|
||||
<<<<<<< HEAD
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
fetch-depth: 0
|
||||
persist-credentials: false
|
||||
|
||||
=======
|
||||
uses: actions/checkout@v2
|
||||
with:
|
||||
fetch-depth: 0
|
||||
persist-credentials: false
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
- name: Setup Node.js
|
||||
uses: actions/setup-node@v2
|
||||
with:
|
||||
node-version: 20
|
||||
<<<<<<< HEAD
|
||||
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
- name: Setup dependencies
|
||||
run: |
|
||||
npm install @semantic-release/git @semantic-release/exec --no-save
|
||||
|
||||
8
.github/workflows/release_notes.yml
vendored
8
.github/workflows/release_notes.yml
vendored
@@ -29,7 +29,15 @@ jobs:
|
||||
steps:
|
||||
- name: Update notes
|
||||
run: |
|
||||
<<<<<<< HEAD
|
||||
NEW_NOTES=$(gh api --method POST -H "Accept: application/vnd.github+json" /repos/frappe/erpnext/releases/generate-notes -f tag_name=$RELEASE_TAG | jq -r '.body' | sed -E '/^\* (chore|ci|test|docs|style)/d' )
|
||||
=======
|
||||
NEW_NOTES=$(gh api --method POST -H "Accept: application/vnd.github+json" /repos/frappe/erpnext/releases/generate-notes -f tag_name=$RELEASE_TAG \
|
||||
| jq -r '.body' \
|
||||
| sed -E '/^\* (chore|ci|test|docs|style)/d' \
|
||||
| sed -E 's/by @mergify //'
|
||||
)
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
RELEASE_ID=$(gh api -H "Accept: application/vnd.github+json" /repos/frappe/erpnext/releases/tags/$RELEASE_TAG | jq -r '.id')
|
||||
gh api --method PATCH -H "Accept: application/vnd.github+json" /repos/frappe/erpnext/releases/$RELEASE_ID -f body="$NEW_NOTES"
|
||||
|
||||
|
||||
130
.github/workflows/run-indinvidual-tests.yml
vendored
Normal file
130
.github/workflows/run-indinvidual-tests.yml
vendored
Normal file
@@ -0,0 +1,130 @@
|
||||
name: Individual
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
|
||||
concurrency:
|
||||
group: server-individual-tests-develop-${{ github.event_name }}-${{ github.event.number || github.event_name == 'workflow_dispatch' && github.run_id || '' }}
|
||||
cancel-in-progress: false
|
||||
|
||||
jobs:
|
||||
discover:
|
||||
runs-on: ubuntu-latest
|
||||
outputs:
|
||||
matrix: ${{ steps.set-matrix.outputs.matrix }}
|
||||
steps:
|
||||
- name: Clone
|
||||
uses: actions/checkout@v4
|
||||
- id: set-matrix
|
||||
run: |
|
||||
# Use grep and find to get the list of test files
|
||||
matrix=$(find . -path '*/doctype/*/test_*.py' | xargs grep -l 'def test_' | awk '{
|
||||
# Remove ./ prefix, file extension, and replace / with .
|
||||
gsub(/^\.\//, "", $0)
|
||||
gsub(/\.py$/, "", $0)
|
||||
gsub(/\//, ".", $0)
|
||||
# Add to array
|
||||
tests[NR] = $0
|
||||
}
|
||||
END {
|
||||
# Start JSON array
|
||||
printf "{\n \"include\": [\n"
|
||||
# Loop through array and create JSON objects
|
||||
for (i=1; i<=NR; i++) {
|
||||
printf " {\"test\": \"%s\"}", tests[i]
|
||||
if (i < NR) printf ","
|
||||
printf "\n"
|
||||
}
|
||||
# Close JSON array
|
||||
printf " ]\n}"
|
||||
}')
|
||||
|
||||
# Output the matrix
|
||||
echo "matrix=$(echo "$matrix" | jq -c)" >> $GITHUB_OUTPUT
|
||||
|
||||
# For debugging (optional)
|
||||
echo "Generated matrix:"
|
||||
echo "$matrix"
|
||||
test:
|
||||
needs: discover
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 60
|
||||
env:
|
||||
NODE_ENV: "production"
|
||||
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix: ${{fromJson(needs.discover.outputs.matrix)}}
|
||||
|
||||
name: Test
|
||||
|
||||
services:
|
||||
mysql:
|
||||
image: mariadb:10.6
|
||||
env:
|
||||
MARIADB_ROOT_PASSWORD: 'root'
|
||||
ports:
|
||||
- 3306:3306
|
||||
options: --health-cmd="mariadb-admin ping" --health-interval=5s --health-timeout=2s --health-retries=3
|
||||
|
||||
steps:
|
||||
- name: Clone
|
||||
uses: actions/checkout@v4
|
||||
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: '3.12'
|
||||
|
||||
- name: Setup Node
|
||||
uses: actions/setup-node@v4
|
||||
with:
|
||||
node-version: 18
|
||||
check-latest: true
|
||||
|
||||
- name: Add to Hosts
|
||||
run: echo "127.0.0.1 test_site" | sudo tee -a /etc/hosts
|
||||
|
||||
- name: Cache pip
|
||||
uses: actions/cache@v4
|
||||
with:
|
||||
path: ~/.cache/pip
|
||||
key: ${{ runner.os }}-pip-${{ hashFiles('**/*requirements.txt', '**/pyproject.toml') }}
|
||||
restore-keys: |
|
||||
${{ runner.os }}-pip-
|
||||
${{ runner.os }}-
|
||||
|
||||
- name: Cache node modules
|
||||
uses: actions/cache@v4
|
||||
env:
|
||||
cache-name: cache-node-modules
|
||||
with:
|
||||
path: ~/.npm
|
||||
key: ${{ runner.os }}-build-${{ env.cache-name }}-${{ hashFiles('**/package-lock.json') }}
|
||||
restore-keys: |
|
||||
${{ runner.os }}-build-${{ env.cache-name }}-
|
||||
${{ runner.os }}-build-
|
||||
${{ runner.os }}-
|
||||
|
||||
- name: Get yarn cache directory path
|
||||
id: yarn-cache-dir-path
|
||||
run: echo "::set-output name=dir::$(yarn cache dir)"
|
||||
|
||||
- uses: actions/cache@v4
|
||||
id: yarn-cache
|
||||
with:
|
||||
path: ${{ steps.yarn-cache-dir-path.outputs.dir }}
|
||||
key: ${{ runner.os }}-yarn-${{ hashFiles('**/yarn.lock') }}
|
||||
restore-keys: |
|
||||
${{ runner.os }}-yarn-
|
||||
|
||||
- name: Install
|
||||
run: bash ${GITHUB_WORKSPACE}/.github/helper/install.sh
|
||||
env:
|
||||
DB: mariadb
|
||||
TYPE: server
|
||||
FRAPPE_USER: ${{ github.event.inputs.user }}
|
||||
FRAPPE_BRANCH: ${{ github.event.inputs.branch }}
|
||||
|
||||
- name: Run Tests
|
||||
run: 'cd ~/frappe-bench/ && bench --site test_site run-tests --app erpnext --module ${{ matrix.test }}'
|
||||
24
.github/workflows/server-tests-mariadb-faux.yml
vendored
Normal file
24
.github/workflows/server-tests-mariadb-faux.yml
vendored
Normal file
@@ -0,0 +1,24 @@
|
||||
# Tests are skipped for these files but github doesn't allow "passing" hence this is required.
|
||||
|
||||
name: Skipped Tests
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
paths:
|
||||
- "**.js"
|
||||
- "**.css"
|
||||
- "**.md"
|
||||
- "**.html"
|
||||
|
||||
jobs:
|
||||
test:
|
||||
runs-on: ubuntu-latest
|
||||
strategy:
|
||||
matrix:
|
||||
container: [1, 2, 3, 4]
|
||||
|
||||
name: Python Unit Tests
|
||||
|
||||
steps:
|
||||
- name: Pass skipped tests unconditionally
|
||||
run: "echo Skipped"
|
||||
77
.github/workflows/server-tests-mariadb.yml
vendored
77
.github/workflows/server-tests-mariadb.yml
vendored
@@ -1,6 +1,11 @@
|
||||
name: Server (Mariadb)
|
||||
|
||||
on:
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
repository_dispatch:
|
||||
types: [frappe-framework-change]
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pull_request:
|
||||
paths-ignore:
|
||||
- '**.js'
|
||||
@@ -31,6 +36,12 @@ jobs:
|
||||
test:
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 60
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
env:
|
||||
NODE_ENV: "production"
|
||||
WITH_COVERAGE: ${{ github.event_name != 'pull_request' }}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
strategy:
|
||||
fail-fast: false
|
||||
@@ -51,12 +62,21 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Clone
|
||||
<<<<<<< HEAD
|
||||
uses: actions/checkout@v2
|
||||
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v2
|
||||
with:
|
||||
python-version: '3.11'
|
||||
=======
|
||||
uses: actions/checkout@v4
|
||||
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: '3.12'
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
- name: Check for valid Python & Merge Conflicts
|
||||
run: |
|
||||
@@ -67,7 +87,11 @@ jobs:
|
||||
fi
|
||||
|
||||
- name: Setup Node
|
||||
<<<<<<< HEAD
|
||||
uses: actions/setup-node@v2
|
||||
=======
|
||||
uses: actions/setup-node@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
with:
|
||||
node-version: 18
|
||||
check-latest: true
|
||||
@@ -76,7 +100,11 @@ jobs:
|
||||
run: echo "127.0.0.1 test_site" | sudo tee -a /etc/hosts
|
||||
|
||||
- name: Cache pip
|
||||
<<<<<<< HEAD
|
||||
uses: actions/cache@v2
|
||||
=======
|
||||
uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
with:
|
||||
path: ~/.cache/pip
|
||||
key: ${{ runner.os }}-pip-${{ hashFiles('**/*requirements.txt', '**/pyproject.toml') }}
|
||||
@@ -85,7 +113,11 @@ jobs:
|
||||
${{ runner.os }}-
|
||||
|
||||
- name: Cache node modules
|
||||
<<<<<<< HEAD
|
||||
uses: actions/cache@v2
|
||||
=======
|
||||
uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
env:
|
||||
cache-name: cache-node-modules
|
||||
with:
|
||||
@@ -100,7 +132,11 @@ jobs:
|
||||
id: yarn-cache-dir-path
|
||||
run: echo "::set-output name=dir::$(yarn cache dir)"
|
||||
|
||||
<<<<<<< HEAD
|
||||
- uses: actions/cache@v2
|
||||
=======
|
||||
- uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
id: yarn-cache
|
||||
with:
|
||||
path: ${{ steps.yarn-cache-dir-path.outputs.dir }}
|
||||
@@ -114,6 +150,7 @@ jobs:
|
||||
DB: mariadb
|
||||
TYPE: server
|
||||
FRAPPE_USER: ${{ github.event.inputs.user }}
|
||||
<<<<<<< HEAD
|
||||
FRAPPE_BRANCH: ${{ github.event.inputs.branch }}
|
||||
|
||||
- name: Run Tests
|
||||
@@ -122,7 +159,47 @@ jobs:
|
||||
TYPE: server
|
||||
CI_BUILD_ID: ${{ github.run_id }}
|
||||
ORCHESTRATOR_URL: http://test-orchestrator.frappe.io
|
||||
=======
|
||||
FRAPPE_BRANCH: ${{ github.event.client_payload.sha || github.event.inputs.branch }}
|
||||
|
||||
- name: Run Tests
|
||||
run: 'cd ~/frappe-bench/ && bench --site test_site run-parallel-tests --app erpnext --total-builds ${{ strategy.job-total }} --build-number ${{ matrix.container }}'
|
||||
env:
|
||||
TYPE: server
|
||||
CAPTURE_COVERAGE: ${{ github.event_name != 'pull_request' }}
|
||||
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
- name: Show bench output
|
||||
if: ${{ always() }}
|
||||
run: cat ~/frappe-bench/bench_start.log || true
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
|
||||
- name: Upload coverage data
|
||||
uses: actions/upload-artifact@v3
|
||||
if: github.event_name != 'pull_request'
|
||||
with:
|
||||
name: coverage-${{ matrix.container }}
|
||||
path: /home/runner/frappe-bench/sites/coverage.xml
|
||||
|
||||
coverage:
|
||||
name: Coverage Wrap Up
|
||||
needs: test
|
||||
runs-on: ubuntu-latest
|
||||
if: ${{ github.event_name != 'pull_request' }}
|
||||
steps:
|
||||
- name: Clone
|
||||
uses: actions/checkout@v4
|
||||
|
||||
- name: Download artifacts
|
||||
uses: actions/download-artifact@v3
|
||||
|
||||
- name: Upload coverage data
|
||||
uses: codecov/codecov-action@v4
|
||||
with:
|
||||
name: MariaDB
|
||||
token: ${{ secrets.CODECOV_TOKEN }}
|
||||
fail_ci_if_error: true
|
||||
verbose: true
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
25
.github/workflows/server-tests-postgres.yml
vendored
25
.github/workflows/server-tests-postgres.yml
vendored
@@ -41,12 +41,21 @@ jobs:
|
||||
steps:
|
||||
|
||||
- name: Clone
|
||||
<<<<<<< HEAD
|
||||
uses: actions/checkout@v2
|
||||
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v2
|
||||
with:
|
||||
python-version: '3.10'
|
||||
=======
|
||||
uses: actions/checkout@v4
|
||||
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: '3.12'
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
- name: Check for valid Python & Merge Conflicts
|
||||
run: |
|
||||
@@ -57,7 +66,11 @@ jobs:
|
||||
fi
|
||||
|
||||
- name: Setup Node
|
||||
<<<<<<< HEAD
|
||||
uses: actions/setup-node@v2
|
||||
=======
|
||||
uses: actions/setup-node@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
with:
|
||||
node-version: 18
|
||||
check-latest: true
|
||||
@@ -66,7 +79,11 @@ jobs:
|
||||
run: echo "127.0.0.1 test_site" | sudo tee -a /etc/hosts
|
||||
|
||||
- name: Cache pip
|
||||
<<<<<<< HEAD
|
||||
uses: actions/cache@v2
|
||||
=======
|
||||
uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
with:
|
||||
path: ~/.cache/pip
|
||||
key: ${{ runner.os }}-pip-${{ hashFiles('**/*requirements.txt', '**/pyproject.toml') }}
|
||||
@@ -75,7 +92,11 @@ jobs:
|
||||
${{ runner.os }}-
|
||||
|
||||
- name: Cache node modules
|
||||
<<<<<<< HEAD
|
||||
uses: actions/cache@v2
|
||||
=======
|
||||
uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
env:
|
||||
cache-name: cache-node-modules
|
||||
with:
|
||||
@@ -90,7 +111,11 @@ jobs:
|
||||
id: yarn-cache-dir-path
|
||||
run: echo "::set-output name=dir::$(yarn cache dir)"
|
||||
|
||||
<<<<<<< HEAD
|
||||
- uses: actions/cache@v2
|
||||
=======
|
||||
- uses: actions/cache@v4
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
id: yarn-cache
|
||||
with:
|
||||
path: ${{ steps.yarn-cache-dir-path.outputs.dir }}
|
||||
|
||||
13
.gitignore
vendored
13
.gitignore
vendored
@@ -2,7 +2,10 @@
|
||||
*.py~
|
||||
.DS_Store
|
||||
conf.py
|
||||
<<<<<<< HEAD
|
||||
locale
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
latest_updates.json
|
||||
.wnf-lang-status
|
||||
*.egg-info
|
||||
@@ -15,5 +18,13 @@ __pycache__
|
||||
*~
|
||||
.idea/
|
||||
.vscode/
|
||||
<<<<<<< HEAD
|
||||
node_modules/
|
||||
.backportrc.json
|
||||
.backportrc.json
|
||||
=======
|
||||
.helix/
|
||||
node_modules/
|
||||
.backportrc.json
|
||||
# Aider AI Chat
|
||||
.aider*
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
20
.mergify.yml
20
.mergify.yml
@@ -17,6 +17,10 @@ pull_request_rules:
|
||||
- base=version-12
|
||||
- base=version-14
|
||||
- base=version-15
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
- base=version-16
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
actions:
|
||||
close:
|
||||
comment:
|
||||
@@ -24,6 +28,7 @@ pull_request_rules:
|
||||
@{{author}}, thanks for the contribution, but we do not accept pull requests on a stable branch. Please raise PR on an appropriate hotfix branch.
|
||||
https://github.com/frappe/erpnext/wiki/Pull-Request-Checklist#which-branch
|
||||
|
||||
<<<<<<< HEAD
|
||||
- name: Auto-close PRs on pre-release branch
|
||||
conditions:
|
||||
- base=version-13-pre-release
|
||||
@@ -34,6 +39,8 @@ pull_request_rules:
|
||||
@{{author}}, pre-release branch is not maintained anymore. Releases are directly done by merging hotfix branch to stable branches.
|
||||
|
||||
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
- name: backport to develop
|
||||
conditions:
|
||||
- label="backport develop"
|
||||
@@ -54,6 +61,7 @@ pull_request_rules:
|
||||
assignees:
|
||||
- "{{ author }}"
|
||||
|
||||
<<<<<<< HEAD
|
||||
- name: backport to version-14-pre-release
|
||||
conditions:
|
||||
- label="backport version-14-pre-release"
|
||||
@@ -61,6 +69,15 @@ pull_request_rules:
|
||||
backport:
|
||||
branches:
|
||||
- version-14-pre-release
|
||||
=======
|
||||
- name: backport to version-15-hotfix
|
||||
conditions:
|
||||
- label="backport version-15-hotfix"
|
||||
actions:
|
||||
backport:
|
||||
branches:
|
||||
- version-15-hotfix
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
assignees:
|
||||
- "{{ author }}"
|
||||
|
||||
@@ -74,6 +91,7 @@ pull_request_rules:
|
||||
assignees:
|
||||
- "{{ author }}"
|
||||
|
||||
<<<<<<< HEAD
|
||||
- name: backport to version-13-pre-release
|
||||
conditions:
|
||||
- label="backport version-13-pre-release"
|
||||
@@ -103,6 +121,8 @@ pull_request_rules:
|
||||
- version-12-pre-release
|
||||
assignees:
|
||||
- "{{ author }}"
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
- name: Automatic merge on CI success and review
|
||||
conditions:
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
exclude: 'node_modules|.git'
|
||||
default_stages: [pre-commit]
|
||||
default_stages: [commit]
|
||||
fail_fast: false
|
||||
|
||||
|
||||
|
||||
@@ -1,5 +1,9 @@
|
||||
{
|
||||
<<<<<<< HEAD
|
||||
"branches": ["version-15"],
|
||||
=======
|
||||
"branches": ["version-13"],
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"plugins": [
|
||||
"@semantic-release/commit-analyzer", {
|
||||
"preset": "angular",
|
||||
@@ -21,4 +25,8 @@
|
||||
],
|
||||
"@semantic-release/github"
|
||||
]
|
||||
<<<<<<< HEAD
|
||||
}
|
||||
=======
|
||||
}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
15
CODEOWNERS
15
CODEOWNERS
@@ -3,11 +3,19 @@
|
||||
# These owners will be the default owners for everything in
|
||||
# the repo. Unless a later match takes precedence,
|
||||
|
||||
<<<<<<< HEAD
|
||||
erpnext/accounts/ @deepeshgarg007 @ruthra-kumar
|
||||
erpnext/assets/ @khushi8112 @deepeshgarg007
|
||||
erpnext/regional @deepeshgarg007 @ruthra-kumar
|
||||
erpnext/selling @deepeshgarg007 @ruthra-kumar
|
||||
erpnext/support/ @deepeshgarg007
|
||||
=======
|
||||
erpnext/accounts/ @ruthra-kumar
|
||||
erpnext/assets/ @khushi8112
|
||||
erpnext/regional @ruthra-kumar
|
||||
erpnext/selling @ruthra-kumar
|
||||
erpnext/support/ @ruthra-kumar
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pos*
|
||||
|
||||
erpnext/buying/ @rohitwaghchaure
|
||||
@@ -17,8 +25,15 @@ erpnext/quality_management/ @rohitwaghchaure
|
||||
erpnext/stock/ @rohitwaghchaure
|
||||
erpnext/subcontracting @rohitwaghchaure
|
||||
|
||||
<<<<<<< HEAD
|
||||
erpnext/controllers/ @deepeshgarg007 @rohitwaghchaure
|
||||
erpnext/patches/ @deepeshgarg007
|
||||
|
||||
.github/ @deepeshgarg007
|
||||
=======
|
||||
erpnext/controllers/ @ruthra-kumar @rohitwaghchaure
|
||||
erpnext/patches/ @ruthra-kumar
|
||||
|
||||
.github/ @ruthra-kumar
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pyproject.toml @akhilnarang
|
||||
|
||||
@@ -7,8 +7,12 @@
|
||||
<p>ERP made simple</p>
|
||||
</p>
|
||||
|
||||
<<<<<<< HEAD
|
||||
[](https://github.com/frappe/erpnext/actions/workflows/server-tests.yml)
|
||||
[](https://github.com/erpnext/erpnext_ui_tests/actions/workflows/ui-tests.yml)
|
||||
=======
|
||||
[](https://github.com/frappe/erpnext/actions/workflows/server-tests-mariadb.yml)
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
[](https://www.codetriage.com/frappe/erpnext)
|
||||
[](https://codecov.io/gh/frappe/erpnext)
|
||||
[](https://hub.docker.com/r/frappe/erpnext-worker)
|
||||
@@ -62,7 +66,7 @@ New passwords will be created for the ERPNext "Administrator" user, the MariaDB
|
||||
|
||||
## Learning and community
|
||||
|
||||
1. [Frappe School](https://school.frappe.io) - Learn Frappe Framework and ERPNext from the various courses by the maintainers or from the community.
|
||||
1. [Frappe School](https://frappe.school) - Learn Frappe Framework and ERPNext from the various courses by the maintainers or from the community.
|
||||
2. [Official documentation](https://docs.erpnext.com/) - Extensive documentation for ERPNext.
|
||||
3. [Discussion Forum](https://discuss.erpnext.com/) - Engage with community of ERPNext users and service providers.
|
||||
4. [Telegram Group](https://erpnext_public.t.me) - Get instant help from huge community of users.
|
||||
@@ -73,8 +77,11 @@ New passwords will be created for the ERPNext "Administrator" user, the MariaDB
|
||||
1. [Issue Guidelines](https://github.com/frappe/erpnext/wiki/Issue-Guidelines)
|
||||
1. [Report Security Vulnerabilities](https://erpnext.com/security)
|
||||
1. [Pull Request Requirements](https://github.com/frappe/erpnext/wiki/Contribution-Guidelines)
|
||||
<<<<<<< HEAD
|
||||
1. [Translations](https://translate.erpnext.com)
|
||||
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
## License
|
||||
|
||||
|
||||
3
babel_extractors.csv
Normal file
3
babel_extractors.csv
Normal file
@@ -0,0 +1,3 @@
|
||||
**/setup/setup_wizard/data/uom_data.json,erpnext.gettext.extractors.uom_data.extract
|
||||
**/setup/doctype/incoterm/incoterms.csv,erpnext.gettext.extractors.incoterms.extract
|
||||
**/setup/setup_wizard/data/*.txt,erpnext.gettext.extractors.lines_from_txt_file.extract
|
||||
|
10
crowdin.yml
Normal file
10
crowdin.yml
Normal file
@@ -0,0 +1,10 @@
|
||||
files:
|
||||
- source: /erpnext/locale/main.pot
|
||||
translation: /erpnext/locale/%two_letters_code%.po
|
||||
pull_request_title: "fix: sync translations from crowdin"
|
||||
pull_request_labels:
|
||||
- translation
|
||||
pull_request_reviewers:
|
||||
- barredterra # change to your GitHub username if you copied this file
|
||||
commit_message: "fix: %language% translations"
|
||||
append_commit_message: false
|
||||
@@ -1,10 +1,20 @@
|
||||
import functools
|
||||
import inspect
|
||||
<<<<<<< HEAD
|
||||
|
||||
import frappe
|
||||
from frappe.utils.user import is_website_user
|
||||
|
||||
__version__ = "15.66.1"
|
||||
__version__ = "15.45.4"
|
||||
=======
|
||||
from typing import TypeVar
|
||||
|
||||
import frappe
|
||||
from frappe.model.document import Document
|
||||
from frappe.utils.user import is_website_user
|
||||
|
||||
__version__ = "16.0.0-dev"
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
|
||||
def get_default_company(user=None):
|
||||
@@ -160,3 +170,37 @@ def check_app_permission():
|
||||
return False
|
||||
|
||||
return True
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
|
||||
|
||||
T = TypeVar("T")
|
||||
|
||||
|
||||
def normalize_ctx_input(T: type) -> callable:
|
||||
"""
|
||||
Normalizes the first argument (ctx) of the decorated function by:
|
||||
- Converting Document objects to dictionaries
|
||||
- Parsing JSON strings
|
||||
- Casting the result to the specified type T
|
||||
"""
|
||||
|
||||
def decorator(func: callable):
|
||||
# conserve annotations for frappe.utils.typing_validations
|
||||
@functools.wraps(func, assigned=(a for a in functools.WRAPPER_ASSIGNMENTS if a != "__annotations__"))
|
||||
def wrapper(ctx: T | Document | dict | str, *args, **kwargs):
|
||||
if isinstance(ctx, Document):
|
||||
ctx = T(**ctx.as_dict())
|
||||
elif isinstance(ctx, dict):
|
||||
ctx = T(**ctx)
|
||||
else:
|
||||
ctx = T(**frappe.parse_json(ctx))
|
||||
|
||||
return func(ctx, *args, **kwargs)
|
||||
|
||||
# set annotations from function
|
||||
wrapper.__annotations__.update({k: v for k, v in func.__annotations__.items() if k != "ctx"})
|
||||
return wrapper
|
||||
|
||||
return decorator
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
@@ -220,7 +220,11 @@ def calculate_monthly_amount(
|
||||
if amount + already_booked_amount_in_account_currency > item.net_amount:
|
||||
amount = item.net_amount - already_booked_amount_in_account_currency
|
||||
|
||||
<<<<<<< HEAD
|
||||
if not (get_first_day(start_date) == start_date and get_last_day(end_date) == end_date):
|
||||
=======
|
||||
if get_first_day(start_date) != start_date or get_last_day(end_date) != end_date:
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
partial_month = flt(date_diff(end_date, start_date)) / flt(
|
||||
date_diff(get_last_day(end_date), get_first_day(start_date))
|
||||
)
|
||||
|
||||
@@ -64,6 +64,11 @@
|
||||
"label": "Is Group"
|
||||
},
|
||||
{
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
"fetch_from": "parent_account.company",
|
||||
"fetch_if_empty": 1,
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"fieldname": "company",
|
||||
"fieldtype": "Link",
|
||||
"in_standard_filter": 1,
|
||||
@@ -106,6 +111,10 @@
|
||||
"fieldname": "parent_account",
|
||||
"fieldtype": "Link",
|
||||
"ignore_user_permissions": 1,
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
"in_preview": 1,
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"label": "Parent Account",
|
||||
"oldfieldname": "parent_account",
|
||||
"oldfieldtype": "Link",
|
||||
@@ -128,7 +137,7 @@
|
||||
"description": "Rate at which this tax is applied",
|
||||
"fieldname": "tax_rate",
|
||||
"fieldtype": "Float",
|
||||
"label": "Tax Rate",
|
||||
"label": "Rate",
|
||||
"oldfieldname": "tax_rate",
|
||||
"oldfieldtype": "Currency"
|
||||
},
|
||||
@@ -248,8 +257,17 @@
|
||||
],
|
||||
"search_fields": "account_number",
|
||||
"show_name_in_global_search": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "ASC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
}
|
||||
=======
|
||||
"show_preview_popup": 1,
|
||||
"sort_field": "creation",
|
||||
"sort_order": "ASC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
import frappe
|
||||
from frappe import _, throw
|
||||
from frappe.utils import add_to_date, cint, cstr, pretty_date
|
||||
from frappe.utils import cint, cstr
|
||||
from frappe.utils.nestedset import NestedSet, get_ancestors_of, get_descendants_of
|
||||
|
||||
import erpnext
|
||||
@@ -92,9 +92,13 @@ class Account(NestedSet):
|
||||
super().on_update()
|
||||
|
||||
def onload(self):
|
||||
<<<<<<< HEAD
|
||||
frozen_accounts_modifier = frappe.db.get_value(
|
||||
"Accounts Settings", "Accounts Settings", "frozen_accounts_modifier"
|
||||
)
|
||||
=======
|
||||
frozen_accounts_modifier = frappe.db.get_single_value("Accounts Settings", "frozen_accounts_modifier")
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
if not frozen_accounts_modifier or frozen_accounts_modifier in frappe.get_roles():
|
||||
self.set_onload("can_freeze_account", True)
|
||||
|
||||
@@ -481,7 +485,6 @@ def get_account_autoname(account_number, account_name, company):
|
||||
|
||||
@frappe.whitelist()
|
||||
def update_account_number(name, account_name, account_number=None, from_descendant=False):
|
||||
_ensure_idle_system()
|
||||
account = frappe.get_cached_doc("Account", name)
|
||||
if not account:
|
||||
return
|
||||
@@ -502,7 +505,7 @@ def update_account_number(name, account_name, account_number=None, from_descenda
|
||||
"name",
|
||||
)
|
||||
|
||||
if old_name and not from_descendant:
|
||||
if old_name:
|
||||
# same account in parent company exists
|
||||
allow_child_account_creation = _("Allow Account Creation Against Child Company")
|
||||
|
||||
@@ -543,7 +546,6 @@ def update_account_number(name, account_name, account_number=None, from_descenda
|
||||
|
||||
@frappe.whitelist()
|
||||
def merge_account(old, new):
|
||||
_ensure_idle_system()
|
||||
# Validate properties before merging
|
||||
new_account = frappe.get_cached_doc("Account", new)
|
||||
old_account = frappe.get_cached_doc("Account", old)
|
||||
@@ -597,31 +599,3 @@ def sync_update_account_number_in_child(
|
||||
|
||||
for d in frappe.db.get_values("Account", filters=filters, fieldname=["company", "name"], as_dict=True):
|
||||
update_account_number(d["name"], account_name, account_number, from_descendant=True)
|
||||
|
||||
|
||||
def _ensure_idle_system():
|
||||
# Don't allow renaming if accounting entries are actively being updated, there are two main reasons:
|
||||
# 1. Correctness: It's next to impossible to ensure that renamed account is not being used *right now*.
|
||||
# 2. Performance: Renaming requires locking out many tables entirely and severely degrades performance.
|
||||
|
||||
if frappe.flags.in_test:
|
||||
return
|
||||
|
||||
last_gl_update = None
|
||||
try:
|
||||
# We also lock inserts to GL entry table with for_update here.
|
||||
last_gl_update = frappe.db.get_value("GL Entry", {}, "modified", for_update=True, wait=False)
|
||||
except frappe.QueryTimeoutError:
|
||||
# wait=False fails immediately if there's an active transaction.
|
||||
last_gl_update = add_to_date(None, seconds=-1)
|
||||
|
||||
if not last_gl_update:
|
||||
return
|
||||
|
||||
if last_gl_update > add_to_date(None, minutes=-5):
|
||||
frappe.throw(
|
||||
_(
|
||||
"Last GL Entry update was done {}. This operation is not allowed while system is actively being used. Please wait for 5 minutes before retrying."
|
||||
).format(pretty_date(last_gl_update)),
|
||||
title=_("System In Use"),
|
||||
)
|
||||
|
||||
@@ -81,7 +81,11 @@ frappe.treeview_settings["Account"] = {
|
||||
|
||||
// show Dr if positive since balance is calculated as debit - credit else show Cr
|
||||
const balance = account.balance_in_account_currency || account.balance;
|
||||
<<<<<<< HEAD
|
||||
const dr_or_cr = balance > 0 ? "Dr" : "Cr";
|
||||
=======
|
||||
const dr_or_cr = balance > 0 ? __("Dr") : __("Cr");
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
const format = (value, currency) => format_currency(Math.abs(value), currency);
|
||||
|
||||
if (account.balance !== undefined) {
|
||||
@@ -138,11 +142,6 @@ frappe.treeview_settings["Account"] = {
|
||||
description: __(
|
||||
"Further accounts can be made under Groups, but entries can be made against non-Groups"
|
||||
),
|
||||
onchange: function () {
|
||||
if (!this.value) {
|
||||
this.layout.set_value("root_type", "");
|
||||
}
|
||||
},
|
||||
},
|
||||
{
|
||||
fieldtype: "Select",
|
||||
@@ -242,22 +241,19 @@ frappe.treeview_settings["Account"] = {
|
||||
},
|
||||
post_render: function (treeview) {
|
||||
frappe.treeview_settings["Account"].treeview["tree"] = treeview.tree;
|
||||
if (treeview.can_create) {
|
||||
treeview.page.set_primary_action(
|
||||
__("New"),
|
||||
function () {
|
||||
let root_company = treeview.page.fields_dict.root_company.get_value();
|
||||
if (root_company) {
|
||||
frappe.throw(__("Please add the account to root level Company - {0}"), [
|
||||
root_company,
|
||||
]);
|
||||
} else {
|
||||
treeview.new_node();
|
||||
}
|
||||
},
|
||||
"add"
|
||||
);
|
||||
}
|
||||
treeview.page.set_primary_action(
|
||||
__("New"),
|
||||
function () {
|
||||
let root_company = treeview.page.fields_dict.root_company.get_value();
|
||||
|
||||
if (root_company) {
|
||||
frappe.throw(__("Please add the account to root level Company - {0}"), [root_company]);
|
||||
} else {
|
||||
treeview.new_node();
|
||||
}
|
||||
},
|
||||
"add"
|
||||
);
|
||||
},
|
||||
toolbar: [
|
||||
{
|
||||
|
||||
@@ -75,7 +75,11 @@ def create_charts(
|
||||
# after all accounts are already inserted.
|
||||
frappe.local.flags.ignore_update_nsm = True
|
||||
_import_accounts(chart, None, None, root_account=True)
|
||||
<<<<<<< HEAD
|
||||
rebuild_tree("Account", "parent_account")
|
||||
=======
|
||||
rebuild_tree("Account")
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
frappe.local.flags.ignore_update_nsm = False
|
||||
|
||||
|
||||
@@ -116,7 +120,6 @@ def identify_is_group(child):
|
||||
return is_group
|
||||
|
||||
|
||||
@frappe.whitelist()
|
||||
def get_chart(chart_template, existing_company=None):
|
||||
chart = {}
|
||||
if existing_company:
|
||||
@@ -233,6 +236,11 @@ def build_account_tree(tree, parent, all_accounts):
|
||||
tree[child.account_name]["account_type"] = child.account_type
|
||||
if child.tax_rate:
|
||||
tree[child.account_name]["tax_rate"] = child.tax_rate
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
if child.account_currency:
|
||||
tree[child.account_name]["account_currency"] = child.account_currency
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
if not parent:
|
||||
tree[child.account_name]["root_type"] = child.root_type
|
||||
|
||||
|
||||
@@ -1,532 +0,0 @@
|
||||
{
|
||||
"country_code": "ch",
|
||||
"name": "240812 Schulkontenrahmen VEB - DE",
|
||||
"tree": {
|
||||
"Aktiven": {
|
||||
"account_number": "1",
|
||||
"is_group": 1,
|
||||
"root_type": "Asset",
|
||||
"Umlaufvermögen": {
|
||||
"account_number": "10",
|
||||
"is_group": 1,
|
||||
"Flüssige Mittel": {
|
||||
"account_number": "100",
|
||||
"is_group": 1,
|
||||
"Kasse": {
|
||||
"account_number": "1000",
|
||||
"account_type": "Cash"
|
||||
},
|
||||
"Bankguthaben": {
|
||||
"account_number": "1020",
|
||||
"account_type": "Bank"
|
||||
}
|
||||
},
|
||||
"Kurzfristig gehaltene Aktiven mit Börsenkurs": {
|
||||
"account_number": "106",
|
||||
"is_group": 1,
|
||||
"Wertschriften": {
|
||||
"account_number": "1060"
|
||||
},
|
||||
"Wertberichtigungen Wertschriften": {
|
||||
"account_number": "1069"
|
||||
}
|
||||
},
|
||||
"Forderungen aus Lieferungen und Leistungen": {
|
||||
"account_number": "110",
|
||||
"is_group": 1,
|
||||
"Forderungen aus Lieferungen und Leistungen (Debitoren)": {
|
||||
"account_number": "1100"
|
||||
},
|
||||
"Delkredere": {
|
||||
"account_number": "1109"
|
||||
}
|
||||
},
|
||||
"Übrige kurzfristige Forderungen": {
|
||||
"account_number": "114",
|
||||
"is_group": 1,
|
||||
"Vorschüsse und Darlehen": {
|
||||
"account_number": "1140"
|
||||
},
|
||||
"Wertberichtigungen Vorschüsse und Darlehen": {
|
||||
"account_number": "1149"
|
||||
},
|
||||
"Vorsteuer MWST Material, Waren, Dienstleistungen, Energie": {
|
||||
"account_number": "1170"
|
||||
},
|
||||
"Vorsteuer MWST Investitionen, übriger Betriebsaufwand": {
|
||||
"account_number": "1171"
|
||||
},
|
||||
"Verrechnungssteuer": {
|
||||
"account_number": "1176"
|
||||
},
|
||||
"Forderungen gegenüber Sozialversicherungen und Vorsorgeeinrichtungen": {
|
||||
"account_number": "1180"
|
||||
},
|
||||
"Quellensteuer": {
|
||||
"account_number": "1189"
|
||||
},
|
||||
"Sonstige kurzfristige Forderungen": {
|
||||
"account_number": "1190"
|
||||
},
|
||||
"Wertberichtigungen sonstige kurzfristige Forderungen": {
|
||||
"account_number": "1199"
|
||||
}
|
||||
},
|
||||
"Vorräte und nicht fakturierte Dienstleistungen": {
|
||||
"account_number": "120",
|
||||
"is_group": 1,
|
||||
"Handelswaren": {
|
||||
"account_number": "1200"
|
||||
},
|
||||
"Rohstoffe": {
|
||||
"account_number": "1210"
|
||||
},
|
||||
"Werkstoffe": {
|
||||
"account_number": "1220"
|
||||
},
|
||||
"Hilfs- und Verbrauchsmaterial": {
|
||||
"account_number": "1230"
|
||||
},
|
||||
"Handelswaren in Konsignation": {
|
||||
"account_number": "1250"
|
||||
},
|
||||
"Fertige Erzeugnisse": {
|
||||
"account_number": "1260"
|
||||
},
|
||||
"Unfertige Erzeugnisse": {
|
||||
"account_number": "1270"
|
||||
},
|
||||
"Nicht fakturierte Dienstleistungen": {
|
||||
"account_number": "1280"
|
||||
}
|
||||
},
|
||||
"Aktive Rechnungsabgrenzungen": {
|
||||
"account_number": "130",
|
||||
"is_group": 1,
|
||||
"Bezahlter Aufwand des Folgejahres": {
|
||||
"account_number": "1300"
|
||||
},
|
||||
"Noch nicht erhaltener Ertrag": {
|
||||
"account_number": "1301"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Anlagevermögen": {
|
||||
"account_number": "14",
|
||||
"is_group": 1,
|
||||
"Finanzanlagen": {
|
||||
"account_number": "140",
|
||||
"is_group": 1,
|
||||
"Wertschriften": {
|
||||
"account_number": "1400"
|
||||
},
|
||||
"Wertberichtigungen Wertschriften": {
|
||||
"account_number": "1409"
|
||||
},
|
||||
"Darlehen": {
|
||||
"account_number": "1440"
|
||||
},
|
||||
"Hypotheken": {
|
||||
"account_number": "1441"
|
||||
},
|
||||
"Wertberichtigungen langfristige Forderungen": {
|
||||
"account_number": "1449"
|
||||
}
|
||||
},
|
||||
"Beteiligungen": {
|
||||
"account_number": "148",
|
||||
"is_group": 1,
|
||||
"Beteiligungen": {
|
||||
"account_number": "1480"
|
||||
},
|
||||
"Wertberichtigungen Beteiligungen": {
|
||||
"account_number": "1489"
|
||||
}
|
||||
},
|
||||
"Mobile Sachanlagen": {
|
||||
"account_number": "150",
|
||||
"is_group": 1,
|
||||
"Maschinen und Apparate": {
|
||||
"account_number": "1500"
|
||||
},
|
||||
"Wertberichtigungen Maschinen und Apparate": {
|
||||
"account_number": "1509"
|
||||
},
|
||||
"Mobiliar und Einrichtungen": {
|
||||
"account_number": "1510"
|
||||
},
|
||||
"Wertberichtigungen Mobiliar und Einrichtungen": {
|
||||
"account_number": "1519"
|
||||
},
|
||||
"Büromaschinen, Informatik, Kommunikationstechnologie": {
|
||||
"account_number": "1520"
|
||||
},
|
||||
"Wertberichtigungen Büromaschinen, Informatik, Kommunikationstechnologie": {
|
||||
"account_number": "1529"
|
||||
},
|
||||
"Fahrzeuge": {
|
||||
"account_number": "1530"
|
||||
},
|
||||
"Wertberichtigungen Fahrzeuge": {
|
||||
"account_number": "1539"
|
||||
},
|
||||
"Werkzeuge und Geräte": {
|
||||
"account_number": "1540"
|
||||
},
|
||||
"Wertberichtigungen Werkzeuge und Geräte": {
|
||||
"account_number": "1549"
|
||||
}
|
||||
},
|
||||
"Immobile Sachanlagen": {
|
||||
"account_number": "160",
|
||||
"is_group": 1,
|
||||
"Geschäftsliegenschaften": {
|
||||
"account_number": "1600"
|
||||
},
|
||||
"Wertberichtigungen Geschäftsliegenschaften": {
|
||||
"account_number": "1609"
|
||||
}
|
||||
},
|
||||
"Immaterielle Werte": {
|
||||
"account_number": "170",
|
||||
"is_group": 1,
|
||||
"Patente, Know-how, Lizenzen, Rechte, Entwicklungen": {
|
||||
"account_number": "1700"
|
||||
},
|
||||
"Wertberichtigungen Patente, Know-how, Lizenzen, Rechte, Entwicklungen": {
|
||||
"account_number": "1709"
|
||||
},
|
||||
"Goodwill": {
|
||||
"account_number": "1770"
|
||||
},
|
||||
"Wertberichtigungen Goodwill": {
|
||||
"account_number": "1779"
|
||||
}
|
||||
},
|
||||
"Nicht einbezahltes Grund-, Gesellschafter- oder Stiftungskapital": {
|
||||
"account_number": "180",
|
||||
"is_group": 1,
|
||||
"Nicht einbezahltes Aktien-, Stamm-, Anteilschein- oder Stiftungskapital": {
|
||||
"account_number": "1850"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"Passiven": {
|
||||
"account_number": "2",
|
||||
"is_group": 1,
|
||||
"root_type": "Liability",
|
||||
"Kurzfristiges Fremdkapital": {
|
||||
"account_number": "20",
|
||||
"is_group": 1,
|
||||
"Verbindlichkeiten aus Lieferungen und Leistungen": {
|
||||
"account_number": "200",
|
||||
"is_group": 1,
|
||||
"Verbindlichkeiten aus Lieferungen und Leistungen (Kreditoren)": {
|
||||
"account_number": "2000"
|
||||
},
|
||||
"Erhaltene Anzahlungen": {
|
||||
"account_number": "2030"
|
||||
}
|
||||
},
|
||||
"Kurzfristige verzinsliche Verbindlichkeiten": {
|
||||
"account_number": "210",
|
||||
"is_group": 1,
|
||||
"Bankverbindlichkeiten": {
|
||||
"account_number": "2100"
|
||||
},
|
||||
"Verbindlichkeiten aus Finanzierungsleasing": {
|
||||
"account_number": "2120"
|
||||
},
|
||||
"Übrige verzinsliche Verbindlichkeiten": {
|
||||
"account_number": "2140"
|
||||
}
|
||||
},
|
||||
"Übrige kurzfristige Verbindlichkeiten": {
|
||||
"account_number": "220",
|
||||
"is_group": 1,
|
||||
"Geschuldete MWST (Umsatzsteuer)": {
|
||||
"account_number": "2200"
|
||||
},
|
||||
"Abrechnungskonto MWST": {
|
||||
"account_number": "2201"
|
||||
},
|
||||
"Verrechnungssteuer": {
|
||||
"account_number": "2206"
|
||||
},
|
||||
"Direkte Steuern": {
|
||||
"account_number": "2208"
|
||||
},
|
||||
"Sonstige kurzfristige Verbindlichkeiten": {
|
||||
"account_number": "2210"
|
||||
},
|
||||
"Beschlossene Ausschüttungen": {
|
||||
"account_number": "2261"
|
||||
},
|
||||
"Sozialversicherungen und Vorsorgeeinrichtungen": {
|
||||
"account_number": "2270"
|
||||
},
|
||||
"Quellensteuer": {
|
||||
"account_number": "2279"
|
||||
}
|
||||
},
|
||||
"Passive Rechnungsabgrenzungen und kurzfristige Rückstellungen": {
|
||||
"account_number": "230",
|
||||
"is_group": 1,
|
||||
"Noch nicht bezahlter Aufwand": {
|
||||
"account_number": "2300"
|
||||
},
|
||||
"Erhaltener Ertrag des Folgejahres": {
|
||||
"account_number": "2301"
|
||||
},
|
||||
"Kurzfristige Rückstellungen": {
|
||||
"account_number": "2330"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Langfristiges Fremdkapital": {
|
||||
"account_number": "24",
|
||||
"is_group": 1,
|
||||
"Langfristige verzinsliche Verbindlichkeiten": {
|
||||
"account_number": "240",
|
||||
"is_group": 1,
|
||||
"Bankverbindlichkeiten": {
|
||||
"account_number": "2400"
|
||||
},
|
||||
"Verbindlichkeiten aus Finanzierungsleasing": {
|
||||
"account_number": "2420"
|
||||
},
|
||||
"Obligationenanleihen": {
|
||||
"account_number": "2430"
|
||||
},
|
||||
"Darlehen": {
|
||||
"account_number": "2450"
|
||||
},
|
||||
"Hypotheken": {
|
||||
"account_number": "2451"
|
||||
}
|
||||
},
|
||||
"Übrige langfristige Verbindlichkeiten": {
|
||||
"account_number": "250",
|
||||
"is_group": 1,
|
||||
"Übrige langfristige Verbindlichkeiten (unverzinslich)": {
|
||||
"account_number": "2500"
|
||||
}
|
||||
},
|
||||
"Rückstellungen sowie vom Gesetz vorgesehene ähnliche Positionen": {
|
||||
"account_number": "260",
|
||||
"is_group": 1,
|
||||
"Rückstellungen": {
|
||||
"account_number": "2600"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Eigenkapital (juristische Personen)": {
|
||||
"account_number": "28",
|
||||
"is_group": 1,
|
||||
"Grund-, Gesellschafter- oder Stiftungskapital": {
|
||||
"account_number": "280",
|
||||
"is_group": 1,
|
||||
"Aktien-, Stamm-, Anteilschein- oder Stiftungskapital": {
|
||||
"account_number": "2800"
|
||||
}
|
||||
},
|
||||
"Reserven und Jahresgewinn oder Jahresverlust": {
|
||||
"account_number": "290",
|
||||
"is_group": 1,
|
||||
"Gesetzliche Kapitalreserve": {
|
||||
"account_number": "2900"
|
||||
},
|
||||
"Reserve für eigene Kapitalanteile": {
|
||||
"account_number": "2930"
|
||||
},
|
||||
"Aufwertungsreserve": {
|
||||
"account_number": "2940"
|
||||
},
|
||||
"Gesetzliche Gewinnreserve": {
|
||||
"account_number": "2950"
|
||||
},
|
||||
"Freiwillige Gewinnreserven": {
|
||||
"account_number": "2960"
|
||||
},
|
||||
"Gewinnvortrag oder Verlustvortrag": {
|
||||
"account_number": "2970"
|
||||
},
|
||||
"Jahresgewinn oder Jahresverlust": {
|
||||
"account_number": "2979"
|
||||
},
|
||||
"Eigene Aktien, Stammanteile oder Anteilscheine (Minusposten)": {
|
||||
"account_number": "2980"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"Betrieblicher Ertrag aus Lieferungen und Leistungen": {
|
||||
"account_number": "3",
|
||||
"is_group": 1,
|
||||
"root_type": "Income",
|
||||
"Produktionserlöse": {
|
||||
"account_number": "3000"
|
||||
},
|
||||
"Handelserlöse": {
|
||||
"account_number": "3200"
|
||||
},
|
||||
"Dienstleistungserlöse": {
|
||||
"account_number": "3400"
|
||||
},
|
||||
"Übrige Erlöse aus Lieferungen und Leistungen": {
|
||||
"account_number": "3600"
|
||||
},
|
||||
"Eigenleistungen": {
|
||||
"account_number": "3700"
|
||||
},
|
||||
"Eigenverbrauch": {
|
||||
"account_number": "3710"
|
||||
},
|
||||
"Erlösminderungen": {
|
||||
"account_number": "3800"
|
||||
},
|
||||
"Verluste Forderungen (Debitoren), Veränderung Delkredere": {
|
||||
"account_number": "3805"
|
||||
},
|
||||
"Bestandesänderungen unfertige Erzeugnisse": {
|
||||
"account_number": "3900"
|
||||
},
|
||||
"Bestandesänderungen fertige Erzeugnisse": {
|
||||
"account_number": "3901"
|
||||
},
|
||||
"Bestandesänderungen nicht fakturierte Dienstleistungen": {
|
||||
"account_number": "3940"
|
||||
}
|
||||
},
|
||||
"Aufwand für Material, Handelswaren, Dienstleistungen und Energie": {
|
||||
"account_number": "4",
|
||||
"is_group": 1,
|
||||
"root_type": "Expense",
|
||||
"Materialaufwand Produktion": {
|
||||
"account_number": "4000"
|
||||
},
|
||||
"Handelswarenaufwand": {
|
||||
"account_number": "4200"
|
||||
},
|
||||
"Aufwand für bezogene Dienstleistungen": {
|
||||
"account_number": "4400"
|
||||
},
|
||||
"Energieaufwand zur Leistungserstellung": {
|
||||
"account_number": "4500"
|
||||
},
|
||||
"Aufwandminderungen": {
|
||||
"account_number": "4900"
|
||||
}
|
||||
},
|
||||
"Personalaufwand": {
|
||||
"account_number": "5",
|
||||
"is_group": 1,
|
||||
"root_type": "Expense",
|
||||
"Lohnaufwand": {
|
||||
"account_number": "5000"
|
||||
},
|
||||
"Sozialversicherungsaufwand": {
|
||||
"account_number": "5700"
|
||||
},
|
||||
"Übriger Personalaufwand": {
|
||||
"account_number": "5800"
|
||||
},
|
||||
"Leistungen Dritter": {
|
||||
"account_number": "5900"
|
||||
}
|
||||
},
|
||||
"Übriger betrieblicher Aufwand, Abschreibungen und Wertberichtigungen sowie Finanzergebnis": {
|
||||
"account_number": "6",
|
||||
"is_group": 1,
|
||||
"root_type": "Expense",
|
||||
"Raumaufwand": {
|
||||
"account_number": "6000"
|
||||
},
|
||||
"Unterhalt, Reparaturen, Ersatz mobile Sachanlagen": {
|
||||
"account_number": "6100"
|
||||
},
|
||||
"Leasingaufwand mobile Sachanlagen": {
|
||||
"account_number": "6105"
|
||||
},
|
||||
"Fahrzeug- und Transportaufwand": {
|
||||
"account_number": "6200"
|
||||
},
|
||||
"Fahrzeugleasing und -mieten": {
|
||||
"account_number": "6260"
|
||||
},
|
||||
"Sachversicherungen, Abgaben, Gebühren, Bewilligungen": {
|
||||
"account_number": "6300"
|
||||
},
|
||||
"Energie- und Entsorgungsaufwand": {
|
||||
"account_number": "6400"
|
||||
},
|
||||
"Verwaltungsaufwand": {
|
||||
"account_number": "6500"
|
||||
},
|
||||
"Informatikaufwand inkl. Leasing": {
|
||||
"account_number": "6570"
|
||||
},
|
||||
"Werbeaufwand": {
|
||||
"account_number": "6600"
|
||||
},
|
||||
"Sonstiger betrieblicher Aufwand": {
|
||||
"account_number": "6700"
|
||||
},
|
||||
"Abschreibungen und Wertberichtigungen auf Positionen des Anlagevermögens": {
|
||||
"account_number": "6800"
|
||||
},
|
||||
"Finanzaufwand": {
|
||||
"account_number": "6900"
|
||||
},
|
||||
"Finanzertrag": {
|
||||
"account_number": "6950"
|
||||
}
|
||||
},
|
||||
"Betrieblicher Nebenerfolg": {
|
||||
"account_number": "7",
|
||||
"is_group": 1,
|
||||
"root_type": "Income",
|
||||
"Ertrag Nebenbetrieb": {
|
||||
"account_number": "7000"
|
||||
},
|
||||
"Aufwand Nebenbetrieb": {
|
||||
"account_number": "7010"
|
||||
},
|
||||
"Ertrag betriebliche Liegenschaft": {
|
||||
"account_number": "7500"
|
||||
},
|
||||
"Aufwand betriebliche Liegenschaft": {
|
||||
"account_number": "7510"
|
||||
}
|
||||
},
|
||||
"Betriebsfremder, ausserordentlicher, einmaliger oder periodenfremder Aufwand und Ertrag": {
|
||||
"account_number": "8",
|
||||
"is_group": 1,
|
||||
"root_type": "Expense",
|
||||
"Betriebsfremder Aufwand": {
|
||||
"account_number": "8000"
|
||||
},
|
||||
"Betriebsfremder Ertrag": {
|
||||
"account_number": "8100"
|
||||
},
|
||||
"Ausserordentlicher, einmaliger oder periodenfremder Aufwand": {
|
||||
"account_number": "8500"
|
||||
},
|
||||
"Ausserordentlicher, einmaliger oder periodenfremder Ertrag": {
|
||||
"account_number": "8510"
|
||||
},
|
||||
"Direkte Steuern": {
|
||||
"account_number": "8900"
|
||||
}
|
||||
},
|
||||
"Abschluss": {
|
||||
"account_number": "9",
|
||||
"is_group": 1,
|
||||
"root_type": "Equity",
|
||||
"Jahresgewinn oder Jahresverlust": {
|
||||
"account_number": "9200"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,569 @@
|
||||
{
|
||||
"country_code": "de",
|
||||
"name": "SKR03 mit Kontonummern",
|
||||
"tree": {
|
||||
"Aktiva": {
|
||||
"is_group": 1,
|
||||
"root_type": "Asset",
|
||||
"A - Anlagevermögen": {
|
||||
"is_group": 1,
|
||||
"EDV-Software": {
|
||||
"account_number": "0027",
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Geschäftsausstattung": {
|
||||
"account_number": "0410",
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Büroeinrichtung": {
|
||||
"account_number": "0420",
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Darlehen": {
|
||||
"account_number": "0565"
|
||||
},
|
||||
"Maschinen": {
|
||||
"account_number": "0210",
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Betriebsausstattung": {
|
||||
"account_number": "0400",
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Ladeneinrichtung": {
|
||||
"account_number": "0430",
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Accumulated Depreciation": {
|
||||
"account_type": "Accumulated Depreciation"
|
||||
}
|
||||
},
|
||||
"B - Umlaufvermögen": {
|
||||
"is_group": 1,
|
||||
"I. Vorräte": {
|
||||
"is_group": 1,
|
||||
"Roh-, Hilfs- und Betriebsstoffe (Bestand)": {
|
||||
"account_number": "3970",
|
||||
"account_type": "Stock"
|
||||
},
|
||||
"Waren (Bestand)": {
|
||||
"account_number": "3980",
|
||||
"account_type": "Stock"
|
||||
}
|
||||
},
|
||||
"II. Forderungen und sonstige Vermögensgegenstände": {
|
||||
"is_group": 1,
|
||||
"Forderungen aus Lieferungen und Leistungen mit Kontokorrent": {
|
||||
"account_number": "1400",
|
||||
"account_type": "Receivable",
|
||||
"is_group": 1
|
||||
},
|
||||
"Forderungen aus Lieferungen und Leistungen ohne Kontokorrent": {
|
||||
"account_number": "1410",
|
||||
"account_type": "Receivable"
|
||||
},
|
||||
"Durchlaufende Posten": {
|
||||
"account_number": "1590"
|
||||
},
|
||||
"Verrechnungskonto Gewinnermittlung § 4 Abs. 3 EStG, nicht ergebniswirksam": {
|
||||
"account_number": "1371"
|
||||
},
|
||||
"Abziehbare Vorsteuer": {
|
||||
"is_group": 1,
|
||||
"Abziehbare Vorsteuer 7 %": {
|
||||
"account_number": "1571",
|
||||
"account_type": "Tax",
|
||||
"tax_rate": 7.0
|
||||
},
|
||||
"Abziehbare Vorsteuer 19 %": {
|
||||
"account_number": "1576",
|
||||
"account_type": "Tax",
|
||||
"tax_rate": 19.0
|
||||
},
|
||||
"Abziehbare Vorsteuer nach § 13b UStG 19 %": {
|
||||
"account_number": "1577",
|
||||
"account_type": "Tax",
|
||||
"tax_rate": 19.0
|
||||
}
|
||||
}
|
||||
},
|
||||
"III. Wertpapiere": {
|
||||
"is_group": 1,
|
||||
"Anteile an verbundenen Unternehmen (Umlaufvermögen)": {
|
||||
"account_number": "1340"
|
||||
},
|
||||
"Anteile an herrschender oder mit Mehrheit beteiligter Gesellschaft": {
|
||||
"account_number": "1344"
|
||||
},
|
||||
"Sonstige Wertpapiere": {
|
||||
"account_number": "1348"
|
||||
}
|
||||
},
|
||||
"IV. Kassenbestand, Bundesbankguthaben, Guthaben bei Kreditinstituten und Schecks.": {
|
||||
"is_group": 1,
|
||||
"Kasse": {
|
||||
"is_group": 1,
|
||||
"account_type": "Cash",
|
||||
"Kasse": {
|
||||
"account_number": "1000",
|
||||
"account_type": "Cash"
|
||||
}
|
||||
},
|
||||
"Bank": {
|
||||
"is_group": 1,
|
||||
"account_type": "Bank",
|
||||
"Postbank": {
|
||||
"account_number": "1100",
|
||||
"account_type": "Bank"
|
||||
},
|
||||
"Bankkonto": {
|
||||
"account_number": "1200",
|
||||
"account_type": "Bank"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"C - Rechnungsabgrenzungsposten": {
|
||||
"is_group": 1,
|
||||
"Aktive Rechnungsabgrenzung": {
|
||||
"account_number": "0980"
|
||||
}
|
||||
},
|
||||
"D - Aktive latente Steuern": {
|
||||
"is_group": 1,
|
||||
"Aktive latente Steuern": {
|
||||
"account_number": "0983"
|
||||
}
|
||||
},
|
||||
"E - Aktiver Unterschiedsbetrag aus der Vermögensverrechnung": {
|
||||
"is_group": 1
|
||||
}
|
||||
},
|
||||
"Passiva": {
|
||||
"is_group": 1,
|
||||
"root_type": "Liability",
|
||||
"A. Eigenkapital": {
|
||||
"is_group": 1,
|
||||
"I. Gezeichnetes Kapital": {
|
||||
"is_group": 1
|
||||
},
|
||||
"II. Kapitalrücklage": {
|
||||
"is_group": 1
|
||||
},
|
||||
"III. Gewinnrücklagen": {
|
||||
"is_group": 1
|
||||
},
|
||||
"IV. Gewinnvortrag/Verlustvortrag": {
|
||||
"is_group": 1
|
||||
},
|
||||
"V. Jahresüberschuß/Jahresfehlbetrag": {
|
||||
"is_group": 1
|
||||
}
|
||||
},
|
||||
"B. Rückstellungen": {
|
||||
"is_group": 1,
|
||||
"I. Rückstellungen für Pensionen und ähnliche Verpflichtungen": {
|
||||
"is_group": 1
|
||||
},
|
||||
"II. Steuerrückstellungen": {
|
||||
"is_group": 1
|
||||
},
|
||||
"III. sonstige Rückstellungen": {
|
||||
"is_group": 1
|
||||
}
|
||||
},
|
||||
"C. Verbindlichkeiten": {
|
||||
"is_group": 1,
|
||||
"I. Anleihen": {
|
||||
"is_group": 1
|
||||
},
|
||||
"II. Verbindlichkeiten gegenüber Kreditinstituten": {
|
||||
"is_group": 1
|
||||
},
|
||||
"III. Erhaltene Anzahlungen auf Bestellungen": {
|
||||
"is_group": 1
|
||||
},
|
||||
"IV. Verbindlichkeiten aus Lieferungen und Leistungen": {
|
||||
"is_group": 1,
|
||||
"Verbindlichkeiten aus Lieferungen und Leistungen mit Kontokorrent": {
|
||||
"account_number": "1600",
|
||||
"account_type": "Payable",
|
||||
"is_group": 1
|
||||
},
|
||||
"Verbindlichkeiten aus Lieferungen und Leistungen ohne Kontokorrent": {
|
||||
"account_number": "1610",
|
||||
"account_type": "Payable"
|
||||
}
|
||||
},
|
||||
"V. Verbindlichkeiten aus der Annahme gezogener Wechsel und der Ausstellung eigener Wechsel": {
|
||||
"is_group": 1
|
||||
},
|
||||
"VI. Verbindlichkeiten gegenüber verbundenen Unternehmen": {
|
||||
"is_group": 1
|
||||
},
|
||||
"VII. Verbindlichkeiten gegenüber Unternehmen, mit denen ein Beteiligungsverhältnis besteht": {
|
||||
"is_group": 1
|
||||
},
|
||||
"VIII. sonstige Verbindlichkeiten": {
|
||||
"is_group": 1,
|
||||
"Sonstige Verbindlichkeiten": {
|
||||
"account_number": "1700",
|
||||
"account_type": "Asset Received But Not Billed"
|
||||
},
|
||||
"Sonstige Verbindlichkeiten (1 bis 5 Jahre)": {
|
||||
"account_number": "1702",
|
||||
"account_type": "Stock Received But Not Billed"
|
||||
},
|
||||
"Verbindlichkeiten aus Lohn und Gehalt": {
|
||||
"account_number": "1740",
|
||||
"account_type": "Payable"
|
||||
},
|
||||
"Umsatzsteuer": {
|
||||
"is_group": 1,
|
||||
"Umsatzsteuer 7 %": {
|
||||
"account_number": "1771",
|
||||
"account_type": "Tax",
|
||||
"tax_rate": 7.0
|
||||
},
|
||||
"Umsatzsteuer 19 %": {
|
||||
"account_number": "1776",
|
||||
"account_type": "Tax",
|
||||
"tax_rate": 19.0
|
||||
},
|
||||
"Umsatzsteuer-Vorauszahlung": {
|
||||
"account_number": "1780",
|
||||
"account_type": "Tax"
|
||||
},
|
||||
"Umsatzsteuer-Vorauszahlung 1/11": {
|
||||
"account_number": "1781"
|
||||
},
|
||||
"Umsatzsteuer nach § 13b UStG 19 %": {
|
||||
"account_number": "1787",
|
||||
"account_type": "Tax",
|
||||
"tax_rate": 19.0
|
||||
},
|
||||
"Umsatzsteuer Vorjahr": {
|
||||
"account_number": "1790"
|
||||
},
|
||||
"Umsatzsteuer frühere Jahre": {
|
||||
"account_number": "1791"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"D. Rechnungsabgrenzungsposten": {
|
||||
"is_group": 1,
|
||||
"Passive Rechnungsabgrenzung": {
|
||||
"account_number": "0990"
|
||||
}
|
||||
},
|
||||
"E. Passive latente Steuern": {
|
||||
"is_group": 1
|
||||
}
|
||||
},
|
||||
"Erlöse u. Erträge 2/8": {
|
||||
"is_group": 1,
|
||||
"root_type": "Income",
|
||||
"Erlöskonten 8": {
|
||||
"is_group": 1,
|
||||
"Erlöse": {
|
||||
"account_number": "8200",
|
||||
"account_type": "Income Account"
|
||||
},
|
||||
"Erlöse USt. 19 %": {
|
||||
"account_number": "8400",
|
||||
"account_type": "Income Account"
|
||||
},
|
||||
"Erlöse USt. 7 %": {
|
||||
"account_number": "8300",
|
||||
"account_type": "Income Account"
|
||||
}
|
||||
},
|
||||
"Ertragskonten 2": {
|
||||
"is_group": 1,
|
||||
"sonstige Zinsen und ähnliche Erträge": {
|
||||
"account_number": "2650",
|
||||
"account_type": "Income Account"
|
||||
},
|
||||
"Außerordentliche Erträge": {
|
||||
"account_number": "2500",
|
||||
"account_type": "Income Account"
|
||||
},
|
||||
"Sonstige Erträge": {
|
||||
"account_number": "2700",
|
||||
"account_type": "Income Account"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Aufwendungen 2/4": {
|
||||
"is_group": 1,
|
||||
"root_type": "Expense",
|
||||
"Fremdleistungen": {
|
||||
"account_number": "3100",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Fremdleistungen ohne Vorsteuer": {
|
||||
"account_number": "3109",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Bauleistungen eines im Inland ansässigen Unternehmers 19 % Vorsteuer und 19 % Umsatzsteuer": {
|
||||
"account_number": "3120",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Wareneingang": {
|
||||
"account_number": "3200"
|
||||
},
|
||||
"Bezugsnebenkosten": {
|
||||
"account_number": "3800",
|
||||
"account_type": "Expenses Included In Asset Valuation"
|
||||
},
|
||||
"Herstellungskosten": {
|
||||
"account_number": "4996",
|
||||
"account_type": "Cost of Goods Sold"
|
||||
},
|
||||
"Verluste aus dem Abgang von Gegenständen des Anlagevermögens": {
|
||||
"account_number": "2320",
|
||||
"account_type": "Stock Adjustment"
|
||||
},
|
||||
"Verwaltungskosten": {
|
||||
"account_number": "4997",
|
||||
"account_type": "Expenses Included In Valuation"
|
||||
},
|
||||
"Vertriebskosten": {
|
||||
"account_number": "4998",
|
||||
"account_type": "Expenses Included In Valuation"
|
||||
},
|
||||
"Gegenkonto 4996-4998": {
|
||||
"account_number": "4999"
|
||||
},
|
||||
"Abschreibungen": {
|
||||
"is_group": 1,
|
||||
"Abschreibungen auf Sachanlagen (ohne AfA auf Kfz und Gebäude)": {
|
||||
"account_number": "4830",
|
||||
"account_type": "Accumulated Depreciation"
|
||||
},
|
||||
"Abschreibungen auf Gebäude": {
|
||||
"account_number": "4831",
|
||||
"account_type": "Depreciation"
|
||||
},
|
||||
"Abschreibungen auf Kfz": {
|
||||
"account_number": "4832",
|
||||
"account_type": "Depreciation"
|
||||
},
|
||||
"Sofortabschreibung GWG": {
|
||||
"account_number": "4855",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"Kfz-Kosten": {
|
||||
"is_group": 1,
|
||||
"Kfz-Steuer": {
|
||||
"account_number": "4510",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Kfz-Versicherungen": {
|
||||
"account_number": "4520",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"laufende Kfz-Betriebskosten": {
|
||||
"account_number": "4530",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Kfz-Reparaturen": {
|
||||
"account_number": "4540",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Fremdfahrzeuge": {
|
||||
"account_number": "4570",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"sonstige Kfz-Kosten": {
|
||||
"account_number": "4580",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"Personalkosten": {
|
||||
"is_group": 1,
|
||||
"Gehälter": {
|
||||
"account_number": "4120",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"gesetzliche soziale Aufwendungen": {
|
||||
"account_number": "4130",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Aufwendungen für Altersvorsorge": {
|
||||
"account_number": "4165",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Vermögenswirksame Leistungen": {
|
||||
"account_number": "4170",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Aushilfslöhne": {
|
||||
"account_number": "4190",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"Raumkosten": {
|
||||
"is_group": 1,
|
||||
"Miete und Nebenkosten": {
|
||||
"account_number": "4210",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Gas, Wasser, Strom (Verwaltung, Vertrieb)": {
|
||||
"account_number": "4240",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Reinigung": {
|
||||
"account_number": "4250",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"Reparatur/Instandhaltung": {
|
||||
"is_group": 1,
|
||||
"Reparaturen und Instandhaltungen von anderen Anlagen und Betriebs- und Geschäftsausstattung": {
|
||||
"account_number": "4805",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"Versicherungsbeiträge": {
|
||||
"is_group": 1,
|
||||
"Versicherungen": {
|
||||
"account_number": "4360",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Beiträge": {
|
||||
"account_number": "4380",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"sonstige Ausgaben": {
|
||||
"account_number": "4390",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"steuerlich abzugsfähige Verspätungszuschläge und Zwangsgelder": {
|
||||
"account_number": "4396",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"Werbe-/Reisekosten": {
|
||||
"is_group": 1,
|
||||
"Werbekosten": {
|
||||
"account_number": "4610",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Aufmerksamkeiten": {
|
||||
"account_number": "4653",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"nicht abzugsfähige Betriebsausg. aus Werbe-, Repräs.- u. Reisekosten": {
|
||||
"account_number": "4665",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Reisekosten Unternehmer": {
|
||||
"account_number": "4670",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"verschiedene Kosten": {
|
||||
"is_group": 1,
|
||||
"Porto": {
|
||||
"account_number": "4910",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Telekom": {
|
||||
"account_number": "4920",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Mobilfunk D2": {
|
||||
"account_number": "4921",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Internet": {
|
||||
"account_number": "4922",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Bürobedarf": {
|
||||
"account_number": "4930",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Zeitschriften, Bücher": {
|
||||
"account_number": "4940",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Fortbildungskosten": {
|
||||
"account_number": "4945",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Buchführungskosten": {
|
||||
"account_number": "4955",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Abschluß- u. Prüfungskosten": {
|
||||
"account_number": "4957",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Nebenkosten des Geldverkehrs": {
|
||||
"account_number": "4970",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Werkzeuge und Kleingeräte": {
|
||||
"account_number": "4985",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
},
|
||||
"Zinsaufwendungen": {
|
||||
"is_group": 1,
|
||||
"Zinsaufwendungen für kurzfristige Verbindlichkeiten": {
|
||||
"account_number": "2110",
|
||||
"account_type": "Expense Account"
|
||||
},
|
||||
"Zinsaufwendungen für KFZ Finanzierung": {
|
||||
"account_number": "2121",
|
||||
"account_type": "Expense Account"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Anfangsbestand 9": {
|
||||
"is_group": 1,
|
||||
"root_type": "Equity",
|
||||
"Saldenvortragskonten": {
|
||||
"is_group": 1,
|
||||
"Saldenvortrag Sachkonten": {
|
||||
"account_number": "9000"
|
||||
},
|
||||
"Saldenvorträge Debitoren": {
|
||||
"account_number": "9008"
|
||||
},
|
||||
"Saldenvorträge Kreditoren": {
|
||||
"account_number": "9009"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Privatkonten 1": {
|
||||
"is_group": 1,
|
||||
"root_type": "Equity",
|
||||
"Privatentnahmen/-einlagen": {
|
||||
"is_group": 1,
|
||||
"Privatentnahme allgemein": {
|
||||
"account_number": "1800"
|
||||
},
|
||||
"Privatsteuern": {
|
||||
"account_number": "1810"
|
||||
},
|
||||
"Sonderausgaben beschränkt abzugsfähig": {
|
||||
"account_number": "1820"
|
||||
},
|
||||
"Sonderausgaben unbeschränkt abzugsfähig": {
|
||||
"account_number": "1830"
|
||||
},
|
||||
"Außergewöhnliche Belastungen": {
|
||||
"account_number": "1850"
|
||||
},
|
||||
"Privateinlagen": {
|
||||
"account_number": "1890"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1653,4 +1653,8 @@
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
<<<<<<< HEAD
|
||||
}
|
||||
=======
|
||||
}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
@@ -36,6 +36,7 @@
|
||||
}
|
||||
},
|
||||
"Fixed Assets": {
|
||||
<<<<<<< HEAD
|
||||
"Capital Equipments": {
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
@@ -46,6 +47,18 @@
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Office Equipments": {
|
||||
=======
|
||||
"Capital Equipment": {
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Electronic Equipment": {
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Furniture and Fixtures": {
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Office Equipment": {
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"account_type": "Fixed Asset"
|
||||
},
|
||||
"Plants and Machineries": {
|
||||
@@ -98,7 +111,7 @@
|
||||
"Office Maintenance Expenses": {},
|
||||
"Office Rent": {},
|
||||
"Postal Expenses": {},
|
||||
"Print and Stationery": {},
|
||||
"Print and Stationary": {},
|
||||
"Rounded Off": {
|
||||
"account_type": "Round Off"
|
||||
},
|
||||
|
||||
@@ -1,6 +1,10 @@
|
||||
{
|
||||
"country_code": "ni",
|
||||
<<<<<<< HEAD
|
||||
"name": "Nicaragua - Catalogo de Cuentas",
|
||||
=======
|
||||
"name": "Nicaragua - Catálogo de Cuentas",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"tree": {
|
||||
"Activo": {
|
||||
"Activo Corriente": {
|
||||
@@ -491,4 +495,8 @@
|
||||
"root_type": "Liability"
|
||||
}
|
||||
}
|
||||
}
|
||||
<<<<<<< HEAD
|
||||
}
|
||||
=======
|
||||
}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -23,6 +23,7 @@ def get():
|
||||
_("Tax Assets"): {"is_group": 1},
|
||||
},
|
||||
_("Fixed Assets"): {
|
||||
<<<<<<< HEAD
|
||||
_("Capital Equipments"): {"account_type": "Fixed Asset"},
|
||||
_("Electronic Equipments"): {"account_type": "Fixed Asset"},
|
||||
_("Furnitures and Fixtures"): {"account_type": "Fixed Asset"},
|
||||
@@ -30,6 +31,15 @@ def get():
|
||||
_("Plants and Machineries"): {"account_type": "Fixed Asset"},
|
||||
_("Buildings"): {"account_type": "Fixed Asset"},
|
||||
_("Softwares"): {"account_type": "Fixed Asset"},
|
||||
=======
|
||||
_("Capital Equipment"): {"account_type": "Fixed Asset"},
|
||||
_("Electronic Equipment"): {"account_type": "Fixed Asset"},
|
||||
_("Furniture and Fixtures"): {"account_type": "Fixed Asset"},
|
||||
_("Office Equipment"): {"account_type": "Fixed Asset"},
|
||||
_("Plants and Machineries"): {"account_type": "Fixed Asset"},
|
||||
_("Buildings"): {"account_type": "Fixed Asset"},
|
||||
_("Software"): {"account_type": "Fixed Asset"},
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
_("Accumulated Depreciation"): {"account_type": "Accumulated Depreciation"},
|
||||
_("CWIP Account"): {
|
||||
"account_type": "Capital Work in Progress",
|
||||
|
||||
@@ -36,6 +36,7 @@ def get():
|
||||
"account_number": "1100-1600",
|
||||
},
|
||||
_("Fixed Assets"): {
|
||||
<<<<<<< HEAD
|
||||
_("Capital Equipments"): {"account_type": "Fixed Asset", "account_number": "1710"},
|
||||
_("Electronic Equipments"): {"account_type": "Fixed Asset", "account_number": "1720"},
|
||||
_("Furnitures and Fixtures"): {"account_type": "Fixed Asset", "account_number": "1730"},
|
||||
@@ -43,6 +44,15 @@ def get():
|
||||
_("Plants and Machineries"): {"account_type": "Fixed Asset", "account_number": "1750"},
|
||||
_("Buildings"): {"account_type": "Fixed Asset", "account_number": "1760"},
|
||||
_("Softwares"): {"account_type": "Fixed Asset", "account_number": "1770"},
|
||||
=======
|
||||
_("Capital Equipment"): {"account_type": "Fixed Asset", "account_number": "1710"},
|
||||
_("Electronic Equipment"): {"account_type": "Fixed Asset", "account_number": "1720"},
|
||||
_("Furniture and Fixtures"): {"account_type": "Fixed Asset", "account_number": "1730"},
|
||||
_("Office Equipment"): {"account_type": "Fixed Asset", "account_number": "1740"},
|
||||
_("Plants and Machineries"): {"account_type": "Fixed Asset", "account_number": "1750"},
|
||||
_("Buildings"): {"account_type": "Fixed Asset", "account_number": "1760"},
|
||||
_("Software"): {"account_type": "Fixed Asset", "account_number": "1770"},
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
_("Accumulated Depreciation"): {
|
||||
"account_type": "Accumulated Depreciation",
|
||||
"account_number": "1780",
|
||||
|
||||
@@ -1,11 +1,18 @@
|
||||
# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# License: GNU General Public License v3. See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
from frappe.test_runner import make_test_records
|
||||
=======
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
from frappe.tests import IntegrationTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
from frappe.utils import nowdate
|
||||
|
||||
from erpnext.accounts.doctype.account.account import (
|
||||
@@ -15,10 +22,17 @@ from erpnext.accounts.doctype.account.account import (
|
||||
)
|
||||
from erpnext.stock import get_company_default_inventory_account, get_warehouse_account
|
||||
|
||||
<<<<<<< HEAD
|
||||
test_dependencies = ["Company"]
|
||||
|
||||
|
||||
class TestAccount(unittest.TestCase):
|
||||
=======
|
||||
EXTRA_TEST_RECORD_DEPENDENCIES = ["Company"]
|
||||
|
||||
|
||||
class TestAccount(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def test_rename_account(self):
|
||||
if not frappe.db.exists("Account", "1210 - Debtors - _TC"):
|
||||
acc = frappe.new_doc("Account")
|
||||
@@ -120,7 +134,11 @@ class TestAccount(unittest.TestCase):
|
||||
InvalidAccountMergeError,
|
||||
merge_account,
|
||||
"Capital Stock - _TC",
|
||||
<<<<<<< HEAD
|
||||
"Softwares - _TC",
|
||||
=======
|
||||
"Software - _TC",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
)
|
||||
|
||||
# Raise error as currency doesn't match
|
||||
@@ -203,8 +221,11 @@ class TestAccount(unittest.TestCase):
|
||||
In a parent->child company setup, child should inherit parent account currency if explicitly specified.
|
||||
"""
|
||||
|
||||
<<<<<<< HEAD
|
||||
make_test_records("Company")
|
||||
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
frappe.local.flags.pop("ignore_root_company_validation", None)
|
||||
|
||||
def create_bank_account():
|
||||
@@ -328,7 +349,11 @@ class TestAccount(unittest.TestCase):
|
||||
|
||||
|
||||
def _make_test_records(verbose=None):
|
||||
<<<<<<< HEAD
|
||||
from frappe.test_runner import make_test_objects
|
||||
=======
|
||||
from frappe.tests.utils import make_test_objects
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
accounts = [
|
||||
# [account_name, parent_account, is_group]
|
||||
|
||||
3
erpnext/accounts/doctype/account/test_records.toml
Normal file
3
erpnext/accounts/doctype/account/test_records.toml
Normal file
@@ -0,0 +1,3 @@
|
||||
[[Account]]
|
||||
name = "_Test Account 1"
|
||||
|
||||
@@ -129,7 +129,11 @@
|
||||
"icon": "fa fa-list",
|
||||
"in_create": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2023-03-06 08:56:36.393237",
|
||||
=======
|
||||
"modified": "2024-03-27 13:05:56.710541",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Account Closing Balance",
|
||||
@@ -158,7 +162,11 @@
|
||||
"role": "Auditor"
|
||||
}
|
||||
],
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"sort_order": "DESC",
|
||||
"states": []
|
||||
}
|
||||
@@ -2,8 +2,24 @@
|
||||
# See license.txt
|
||||
|
||||
# import frappe
|
||||
<<<<<<< HEAD
|
||||
from frappe.tests.utils import FrappeTestCase
|
||||
|
||||
|
||||
class TestAccountClosingBalance(FrappeTestCase):
|
||||
=======
|
||||
from frappe.tests import IntegrationTestCase, UnitTestCase
|
||||
|
||||
|
||||
class UnitTestAccountClosingBalance(UnitTestCase):
|
||||
"""
|
||||
Unit tests for AccountClosingBalance.
|
||||
Use this class for testing individual functions and methods.
|
||||
"""
|
||||
|
||||
pass
|
||||
|
||||
|
||||
class TestAccountClosingBalance(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pass
|
||||
|
||||
@@ -31,8 +31,7 @@
|
||||
"label": "Reference Document Type",
|
||||
"options": "DocType",
|
||||
"read_only_depends_on": "eval:!doc.__islocal",
|
||||
"reqd": 1,
|
||||
"search_index": 1
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
@@ -50,7 +49,11 @@
|
||||
}
|
||||
],
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2021-02-08 16:37:53.936656",
|
||||
=======
|
||||
"modified": "2024-03-27 13:05:56.890002",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Accounting Dimension",
|
||||
@@ -81,7 +84,13 @@
|
||||
"write": 1
|
||||
}
|
||||
],
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "ASC",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "ASC",
|
||||
"states": [],
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"track_changes": 1
|
||||
}
|
||||
@@ -41,11 +41,6 @@ class AccountingDimension(Document):
|
||||
self.set_fieldname_and_label()
|
||||
|
||||
def validate(self):
|
||||
self.validate_doctype()
|
||||
validate_column_name(self.fieldname)
|
||||
self.validate_dimension_defaults()
|
||||
|
||||
def validate_doctype(self):
|
||||
if self.document_type in (
|
||||
*core_doctypes_list,
|
||||
"Accounting Dimension",
|
||||
@@ -54,7 +49,6 @@ class AccountingDimension(Document):
|
||||
"Accounting Dimension Detail",
|
||||
"Company",
|
||||
"Account",
|
||||
"Finance Book",
|
||||
):
|
||||
msg = _("Not allowed to create accounting dimension for {0}").format(self.document_type)
|
||||
frappe.throw(msg)
|
||||
@@ -67,6 +61,9 @@ class AccountingDimension(Document):
|
||||
if not self.is_new():
|
||||
self.validate_document_type_change()
|
||||
|
||||
validate_column_name(self.fieldname)
|
||||
self.validate_dimension_defaults()
|
||||
|
||||
def validate_document_type_change(self):
|
||||
doctype_before_save = frappe.db.get_value("Accounting Dimension", self.name, "document_type")
|
||||
if doctype_before_save != self.document_type:
|
||||
@@ -105,7 +102,6 @@ class AccountingDimension(Document):
|
||||
|
||||
def on_update(self):
|
||||
frappe.flags.accounting_dimensions = None
|
||||
frappe.flags.accounting_dimensions_details = None
|
||||
|
||||
|
||||
def make_dimension_in_accounting_doctypes(doc, doclist=None):
|
||||
@@ -266,7 +262,7 @@ def get_checks_for_pl_and_bs_accounts():
|
||||
frappe.flags.accounting_dimensions_details = frappe.db.sql(
|
||||
"""SELECT p.label, p.disabled, p.fieldname, c.default_dimension, c.company, c.mandatory_for_pl, c.mandatory_for_bs
|
||||
FROM `tabAccounting Dimension`p ,`tabAccounting Dimension Detail` c
|
||||
WHERE p.name = c.parent AND p.disabled = 0""",
|
||||
WHERE p.name = c.parent""",
|
||||
as_dict=1,
|
||||
)
|
||||
|
||||
|
||||
@@ -1,17 +1,31 @@
|
||||
# Copyright (c) 2019, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
=======
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
from frappe.tests import IntegrationTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
from erpnext.accounts.doctype.journal_entry.test_journal_entry import make_journal_entry
|
||||
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
|
||||
|
||||
<<<<<<< HEAD
|
||||
test_dependencies = ["Cost Center", "Location", "Warehouse", "Department"]
|
||||
|
||||
|
||||
class TestAccountingDimension(unittest.TestCase):
|
||||
=======
|
||||
EXTRA_TEST_RECORD_DEPENDENCIES = ["Cost Center", "Location", "Warehouse", "Department"]
|
||||
|
||||
|
||||
class TestAccountingDimension(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def setUp(self):
|
||||
create_dimension()
|
||||
|
||||
|
||||
@@ -1,4 +1,8 @@
|
||||
{
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
"actions": [],
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"creation": "2019-07-16 17:53:18.718831",
|
||||
"doctype": "DocType",
|
||||
"editable_grid": 1,
|
||||
@@ -73,13 +77,24 @@
|
||||
}
|
||||
],
|
||||
"istable": 1,
|
||||
<<<<<<< HEAD
|
||||
"modified": "2019-08-15 11:59:09.389891",
|
||||
=======
|
||||
"links": [],
|
||||
"modified": "2024-03-27 13:05:57.056874",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Accounting Dimension Detail",
|
||||
"owner": "Administrator",
|
||||
"permissions": [],
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"track_changes": 1
|
||||
}
|
||||
@@ -94,7 +94,11 @@
|
||||
],
|
||||
"index_web_pages_for_search": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2023-06-07 14:59:41.869117",
|
||||
=======
|
||||
"modified": "2024-03-27 13:05:57.199186",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Accounting Dimension Filter",
|
||||
@@ -139,7 +143,11 @@
|
||||
}
|
||||
],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
|
||||
@@ -67,7 +67,10 @@ class AccountingDimensionFilter(Document):
|
||||
|
||||
def get_dimension_filter_map():
|
||||
if not frappe.flags.get("dimension_filter_map"):
|
||||
<<<<<<< HEAD
|
||||
# nosemgrep
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
filters = frappe.db.sql(
|
||||
"""
|
||||
SELECT
|
||||
|
||||
@@ -12,7 +12,11 @@ from erpnext.accounts.doctype.accounting_dimension.test_accounting_dimension imp
|
||||
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
|
||||
from erpnext.exceptions import InvalidAccountDimensionError, MandatoryAccountDimensionError
|
||||
|
||||
<<<<<<< HEAD
|
||||
test_dependencies = ["Location", "Cost Center", "Department"]
|
||||
=======
|
||||
EXTRA_TEST_RECORD_DEPENDENCIES = ["Location", "Cost Center", "Department"]
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
|
||||
class TestAccountingDimensionFilter(unittest.TestCase):
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
<<<<<<< HEAD
|
||||
"allow_copy": 0,
|
||||
"allow_guest_to_view": 0,
|
||||
"allow_import": 0,
|
||||
@@ -314,4 +315,116 @@
|
||||
"sort_order": "DESC",
|
||||
"track_changes": 1,
|
||||
"track_seen": 0
|
||||
=======
|
||||
"actions": [],
|
||||
"autoname": "field:period_name",
|
||||
"creation": "2018-04-13 18:50:14.672323",
|
||||
"doctype": "DocType",
|
||||
"editable_grid": 1,
|
||||
"engine": "InnoDB",
|
||||
"field_order": [
|
||||
"period_name",
|
||||
"start_date",
|
||||
"end_date",
|
||||
"column_break_4",
|
||||
"company",
|
||||
"section_break_7",
|
||||
"closed_documents"
|
||||
],
|
||||
"fields": [
|
||||
{
|
||||
"fieldname": "period_name",
|
||||
"fieldtype": "Data",
|
||||
"in_list_view": 1,
|
||||
"label": "Period Name",
|
||||
"reqd": 1,
|
||||
"unique": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "start_date",
|
||||
"fieldtype": "Date",
|
||||
"in_list_view": 1,
|
||||
"label": "Start Date",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "end_date",
|
||||
"fieldtype": "Date",
|
||||
"in_list_view": 1,
|
||||
"label": "End Date",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_4",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"fieldname": "company",
|
||||
"fieldtype": "Link",
|
||||
"in_list_view": 1,
|
||||
"label": "Company",
|
||||
"options": "Company",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "section_break_7",
|
||||
"fieldtype": "Section Break"
|
||||
},
|
||||
{
|
||||
"fieldname": "closed_documents",
|
||||
"fieldtype": "Table",
|
||||
"label": "Closed Documents",
|
||||
"options": "Closed Document",
|
||||
"reqd": 1
|
||||
}
|
||||
],
|
||||
"links": [],
|
||||
"modified": "2024-03-27 13:05:57.388109",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Accounting Period",
|
||||
"owner": "Administrator",
|
||||
"permissions": [
|
||||
{
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "System Manager",
|
||||
"share": 1,
|
||||
"write": 1
|
||||
},
|
||||
{
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "Accounts Manager",
|
||||
"share": 1,
|
||||
"write": 1
|
||||
},
|
||||
{
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "Accounts User",
|
||||
"share": 1,
|
||||
"write": 1
|
||||
}
|
||||
],
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
@@ -1,9 +1,16 @@
|
||||
# Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
=======
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
from frappe.tests import IntegrationTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
from frappe.utils import add_months, nowdate
|
||||
|
||||
from erpnext.accounts.doctype.accounting_period.accounting_period import (
|
||||
@@ -12,10 +19,17 @@ from erpnext.accounts.doctype.accounting_period.accounting_period import (
|
||||
)
|
||||
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
|
||||
|
||||
<<<<<<< HEAD
|
||||
test_dependencies = ["Item"]
|
||||
|
||||
|
||||
class TestAccountingPeriod(unittest.TestCase):
|
||||
=======
|
||||
EXTRA_TEST_RECORD_DEPENDENCIES = ["Item"]
|
||||
|
||||
|
||||
class TestAccountingPeriod(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def test_overlap(self):
|
||||
ap1 = create_accounting_period(
|
||||
start_date="2018-04-01", end_date="2018-06-30", company="Wind Power LLC"
|
||||
|
||||
@@ -12,7 +12,7 @@ frappe.ui.form.on("Accounts Settings", {
|
||||
msg += " ";
|
||||
msg += __("Please enable only if the understand the effects of enabling this.");
|
||||
msg += "<br>";
|
||||
msg += __("Do you still want to enable immutable ledger?");
|
||||
msg += "Do you still want to enable immutable ledger?";
|
||||
|
||||
frappe.confirm(
|
||||
msg,
|
||||
@@ -22,21 +22,4 @@ frappe.ui.form.on("Accounts Settings", {
|
||||
}
|
||||
);
|
||||
},
|
||||
|
||||
add_taxes_from_taxes_and_charges_template(frm) {
|
||||
toggle_tax_settings(frm, "add_taxes_from_taxes_and_charges_template");
|
||||
},
|
||||
add_taxes_from_item_tax_template(frm) {
|
||||
toggle_tax_settings(frm, "add_taxes_from_item_tax_template");
|
||||
},
|
||||
});
|
||||
|
||||
function toggle_tax_settings(frm, field_name) {
|
||||
if (frm.doc[field_name]) {
|
||||
const other_field =
|
||||
field_name === "add_taxes_from_item_tax_template"
|
||||
? "add_taxes_from_taxes_and_charges_template"
|
||||
: "add_taxes_from_item_tax_template";
|
||||
frm.set_value(other_field, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -31,7 +31,6 @@
|
||||
"determine_address_tax_category_from",
|
||||
"column_break_19",
|
||||
"add_taxes_from_item_tax_template",
|
||||
"add_taxes_from_taxes_and_charges_template",
|
||||
"book_tax_discount_loss",
|
||||
"round_row_wise_tax",
|
||||
"print_settings",
|
||||
@@ -39,22 +38,11 @@
|
||||
"show_taxes_as_table_in_print",
|
||||
"column_break_12",
|
||||
"show_payment_schedule_in_print",
|
||||
"item_price_settings_section",
|
||||
"maintain_same_internal_transaction_rate",
|
||||
"column_break_feyo",
|
||||
"maintain_same_rate_action",
|
||||
"role_to_override_stop_action",
|
||||
"currency_exchange_section",
|
||||
"allow_stale",
|
||||
"allow_pegged_currencies_exchange_rates",
|
||||
"column_break_yuug",
|
||||
"stale_days",
|
||||
"section_break_jpd0",
|
||||
"auto_reconcile_payments",
|
||||
"auto_reconciliation_job_trigger",
|
||||
"reconciliation_queue_size",
|
||||
"column_break_resa",
|
||||
"exchange_gain_loss_posting_date",
|
||||
"stale_days",
|
||||
"invoicing_settings_tab",
|
||||
"accounts_transactions_settings_section",
|
||||
"over_billing_allowance",
|
||||
@@ -86,10 +74,6 @@
|
||||
"general_ledger_remarks_length",
|
||||
"column_break_lvjk",
|
||||
"receivable_payable_remarks_length",
|
||||
"accounts_receivable_payable_tuning_section",
|
||||
"receivable_payable_fetch_method",
|
||||
"legacy_section",
|
||||
"ignore_is_opening_check_for_reporting",
|
||||
"payment_request_settings",
|
||||
"create_pr_in_draft_status"
|
||||
],
|
||||
@@ -400,7 +384,7 @@
|
||||
{
|
||||
"fieldname": "section_break_jpd0",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Payment Reconciliation Settings"
|
||||
"label": "Payment Reconciliations"
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
@@ -505,110 +489,6 @@
|
||||
"fieldname": "create_pr_in_draft_status",
|
||||
"fieldtype": "Check",
|
||||
"label": "Create in Draft Status"
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_yuug",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_resa",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"default": "15",
|
||||
"description": "Interval should be between 1 to 59 MInutes",
|
||||
"fieldname": "auto_reconciliation_job_trigger",
|
||||
"fieldtype": "Int",
|
||||
"label": "Auto Reconciliation Job Trigger"
|
||||
},
|
||||
{
|
||||
"default": "5",
|
||||
"description": "Documents Processed on each trigger. Queue Size should be between 5 and 100",
|
||||
"fieldname": "reconciliation_queue_size",
|
||||
"fieldtype": "Int",
|
||||
"label": "Reconciliation Queue Size"
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
"description": "Ignores legacy Is Opening field in GL Entry that allows adding opening balance post the system is in use while generating reports",
|
||||
"fieldname": "ignore_is_opening_check_for_reporting",
|
||||
"fieldtype": "Check",
|
||||
"label": "Ignore Is Opening check for reporting"
|
||||
},
|
||||
{
|
||||
"default": "Payment",
|
||||
"description": "Only applies for Normal Payments",
|
||||
"fieldname": "exchange_gain_loss_posting_date",
|
||||
"fieldtype": "Select",
|
||||
"label": "Posting Date Inheritance for Exchange Gain / Loss",
|
||||
"options": "Invoice\nPayment\nReconciliation Date"
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_xrnd",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"default": "Buffered Cursor",
|
||||
"fieldname": "receivable_payable_fetch_method",
|
||||
"fieldtype": "Select",
|
||||
"label": "Data Fetch Method",
|
||||
"options": "Buffered Cursor\nUnBuffered Cursor"
|
||||
},
|
||||
{
|
||||
"fieldname": "accounts_receivable_payable_tuning_section",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Accounts Receivable / Payable Tuning"
|
||||
},
|
||||
{
|
||||
"fieldname": "legacy_section",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Legacy Fields"
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
"fieldname": "maintain_same_internal_transaction_rate",
|
||||
"fieldtype": "Check",
|
||||
"label": "Maintain Same Rate Throughout Internal Transaction"
|
||||
},
|
||||
{
|
||||
"default": "Stop",
|
||||
"depends_on": "maintain_same_internal_transaction_rate",
|
||||
"fieldname": "maintain_same_rate_action",
|
||||
"fieldtype": "Select",
|
||||
"label": "Action if Same Rate is Not Maintained Throughout Internal Transaction",
|
||||
"mandatory_depends_on": "maintain_same_internal_transaction_rate",
|
||||
"options": "Stop\nWarn"
|
||||
},
|
||||
{
|
||||
"depends_on": "eval: doc.maintain_same_internal_transaction_rate && doc.maintain_same_rate_action == 'Stop'",
|
||||
"fieldname": "role_to_override_stop_action",
|
||||
"fieldtype": "Link",
|
||||
"label": "Role Allowed to Override Stop Action",
|
||||
"options": "Role"
|
||||
},
|
||||
{
|
||||
"fieldname": "item_price_settings_section",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Item Price Settings"
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_feyo",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
"description": "System will do an implicit conversion using the pegged currency. <br>\nEx: Instead of AED -> INR, system will do AED -> USD -> INR using the pegged exchange rate of AED against USD.",
|
||||
"documentation_url": "/app/pegged-currencies/Pegged Currencies",
|
||||
"fieldname": "allow_pegged_currencies_exchange_rates",
|
||||
"fieldtype": "Check",
|
||||
"label": "Allow Implicit Pegged Currency Conversion"
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
"description": "If no taxes are set, and Taxes and Charges Template is selected, the system will automatically apply the taxes from the chosen template.",
|
||||
"fieldname": "add_taxes_from_taxes_and_charges_template",
|
||||
"fieldtype": "Check",
|
||||
"label": "Automatically Add Taxes from Taxes and Charges Template"
|
||||
}
|
||||
],
|
||||
"icon": "icon-cog",
|
||||
@@ -616,7 +496,7 @@
|
||||
"index_web_pages_for_search": 1,
|
||||
"issingle": 1,
|
||||
"links": [],
|
||||
"modified": "2025-06-23 15:55:33.346398",
|
||||
"modified": "2024-07-26 06:48:52.714630",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Accounts Settings",
|
||||
@@ -641,8 +521,12 @@
|
||||
}
|
||||
],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"sort_order": "ASC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
}
|
||||
}
|
||||
@@ -10,7 +10,6 @@ from frappe.custom.doctype.property_setter.property_setter import make_property_
|
||||
from frappe.model.document import Document
|
||||
from frappe.utils import cint
|
||||
|
||||
from erpnext.accounts.utils import sync_auto_reconcile_config
|
||||
from erpnext.stock.utils import check_pending_reposting
|
||||
|
||||
|
||||
@@ -25,12 +24,9 @@ class AccountsSettings(Document):
|
||||
|
||||
acc_frozen_upto: DF.Date | None
|
||||
add_taxes_from_item_tax_template: DF.Check
|
||||
add_taxes_from_taxes_and_charges_template: DF.Check
|
||||
allow_multi_currency_invoices_against_single_party_account: DF.Check
|
||||
allow_pegged_currencies_exchange_rates: DF.Check
|
||||
allow_stale: DF.Check
|
||||
auto_reconcile_payments: DF.Check
|
||||
auto_reconciliation_job_trigger: DF.Int
|
||||
automatically_fetch_payment_terms: DF.Check
|
||||
automatically_process_deferred_accounting_entry: DF.Check
|
||||
book_asset_depreciation_entry_automatically: DF.Check
|
||||
@@ -47,22 +43,15 @@ class AccountsSettings(Document):
|
||||
enable_fuzzy_matching: DF.Check
|
||||
enable_immutable_ledger: DF.Check
|
||||
enable_party_matching: DF.Check
|
||||
exchange_gain_loss_posting_date: DF.Literal["Invoice", "Payment", "Reconciliation Date"]
|
||||
frozen_accounts_modifier: DF.Link | None
|
||||
general_ledger_remarks_length: DF.Int
|
||||
ignore_account_closing_balance: DF.Check
|
||||
ignore_is_opening_check_for_reporting: DF.Check
|
||||
maintain_same_internal_transaction_rate: DF.Check
|
||||
maintain_same_rate_action: DF.Literal["Stop", "Warn"]
|
||||
make_payment_via_journal_entry: DF.Check
|
||||
merge_similar_account_heads: DF.Check
|
||||
over_billing_allowance: DF.Currency
|
||||
post_change_gl_entries: DF.Check
|
||||
receivable_payable_fetch_method: DF.Literal["Buffered Cursor", "UnBuffered Cursor"]
|
||||
receivable_payable_remarks_length: DF.Int
|
||||
reconciliation_queue_size: DF.Int
|
||||
role_allowed_to_over_bill: DF.Link | None
|
||||
role_to_override_stop_action: DF.Link | None
|
||||
round_row_wise_tax: DF.Check
|
||||
show_balance_in_coa: DF.Check
|
||||
show_inclusive_tax_in_print: DF.Check
|
||||
@@ -75,7 +64,6 @@ class AccountsSettings(Document):
|
||||
# end: auto-generated types
|
||||
|
||||
def validate(self):
|
||||
self.validate_auto_tax_settings()
|
||||
old_doc = self.get_doc_before_save()
|
||||
clear_cache = False
|
||||
|
||||
@@ -102,8 +90,6 @@ class AccountsSettings(Document):
|
||||
if clear_cache:
|
||||
frappe.clear_cache()
|
||||
|
||||
self.validate_and_sync_auto_reconcile_config()
|
||||
|
||||
def validate_stale_days(self):
|
||||
if not self.allow_stale and cint(self.stale_days) <= 0:
|
||||
frappe.msgprint(
|
||||
@@ -128,27 +114,3 @@ class AccountsSettings(Document):
|
||||
def validate_pending_reposts(self):
|
||||
if self.acc_frozen_upto:
|
||||
check_pending_reposting(self.acc_frozen_upto)
|
||||
|
||||
def validate_and_sync_auto_reconcile_config(self):
|
||||
if self.has_value_changed("auto_reconciliation_job_trigger"):
|
||||
if (
|
||||
cint(self.auto_reconciliation_job_trigger) > 0
|
||||
and cint(self.auto_reconciliation_job_trigger) < 60
|
||||
):
|
||||
sync_auto_reconcile_config(self.auto_reconciliation_job_trigger)
|
||||
else:
|
||||
frappe.throw(_("Cron Interval should be between 1 and 59 Min"))
|
||||
|
||||
if self.has_value_changed("reconciliation_queue_size"):
|
||||
if cint(self.reconciliation_queue_size) < 5 or cint(self.reconciliation_queue_size) > 100:
|
||||
frappe.throw(_("Queue Size should be between 5 and 100"))
|
||||
|
||||
def validate_auto_tax_settings(self):
|
||||
if self.add_taxes_from_item_tax_template and self.add_taxes_from_taxes_and_charges_template:
|
||||
frappe.throw(
|
||||
_("You cannot enable both the settings '{0}' and '{1}'.").format(
|
||||
frappe.bold(self.meta.get_label("add_taxes_from_item_tax_template")),
|
||||
frappe.bold(self.meta.get_label("add_taxes_from_taxes_and_charges_template")),
|
||||
),
|
||||
title=_("Auto Tax Settings Error"),
|
||||
)
|
||||
|
||||
@@ -1,9 +1,16 @@
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
<<<<<<< HEAD
|
||||
|
||||
|
||||
class TestAccountsSettings(unittest.TestCase):
|
||||
=======
|
||||
from frappe.tests import IntegrationTestCase
|
||||
|
||||
|
||||
class TestAccountsSettings(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def tearDown(self):
|
||||
# Just in case `save` method succeeds, we need to take things back to default so that other tests
|
||||
# don't break
|
||||
|
||||
@@ -2,7 +2,11 @@
|
||||
# See license.txt
|
||||
|
||||
import frappe
|
||||
<<<<<<< HEAD
|
||||
from frappe.tests.utils import FrappeTestCase
|
||||
=======
|
||||
from frappe.tests import IntegrationTestCase, UnitTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
from frappe.utils import nowdate, today
|
||||
|
||||
from erpnext.accounts.doctype.payment_entry.test_payment_entry import get_payment_entry
|
||||
@@ -10,8 +14,19 @@ from erpnext.accounts.test.accounts_mixin import AccountsTestMixin
|
||||
from erpnext.buying.doctype.purchase_order.test_purchase_order import create_purchase_order
|
||||
from erpnext.selling.doctype.sales_order.test_sales_order import make_sales_order
|
||||
|
||||
<<<<<<< HEAD
|
||||
|
||||
class TestAdvancePaymentLedgerEntry(AccountsTestMixin, FrappeTestCase):
|
||||
=======
|
||||
# On IntegrationTestCase, the doctype test records and all
|
||||
# link-field test record depdendencies are recursively loaded
|
||||
# Use these module variables to add/remove to/from that list
|
||||
EXTRA_TEST_RECORD_DEPENDENCIES = [] # eg. ["User"]
|
||||
IGNORE_TEST_RECORD_DEPENDENCIES = [] # eg. ["User"]
|
||||
|
||||
|
||||
class TestAdvancePaymentLedgerEntry(AccountsTestMixin, IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"""
|
||||
Integration tests for AdvancePaymentLedgerEntry.
|
||||
Use this class for testing interactions between multiple components.
|
||||
|
||||
@@ -45,12 +45,22 @@
|
||||
"index_web_pages_for_search": 1,
|
||||
"istable": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2021-11-25 10:27:51.712286",
|
||||
=======
|
||||
"modified": "2024-03-27 13:05:58.308002",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Advance Tax",
|
||||
"owner": "Administrator",
|
||||
"permissions": [],
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC"
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": []
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
@@ -13,6 +13,10 @@
|
||||
"col_break_1",
|
||||
"description",
|
||||
"included_in_paid_amount",
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
"set_by_item_tax_template",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"accounting_dimensions_section",
|
||||
"cost_center",
|
||||
"dimension_col_break",
|
||||
@@ -20,11 +24,19 @@
|
||||
"rate",
|
||||
"section_break_9",
|
||||
"currency",
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
"net_amount",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"tax_amount",
|
||||
"total",
|
||||
"allocated_amount",
|
||||
"column_break_13",
|
||||
"base_tax_amount",
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
"base_net_amount",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"base_total"
|
||||
],
|
||||
"fields": [
|
||||
@@ -101,7 +113,7 @@
|
||||
"fieldname": "rate",
|
||||
"fieldtype": "Float",
|
||||
"in_list_view": 1,
|
||||
"label": "Tax Rate",
|
||||
"label": "Rate",
|
||||
"oldfieldname": "rate",
|
||||
"oldfieldtype": "Currency"
|
||||
},
|
||||
@@ -174,17 +186,58 @@
|
||||
"label": "Account Currency",
|
||||
"options": "Currency",
|
||||
"read_only": 1
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
"fieldname": "net_amount",
|
||||
"fieldtype": "Currency",
|
||||
"in_list_view": 1,
|
||||
"label": "Net Amount",
|
||||
"options": "currency",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "base_net_amount",
|
||||
"fieldtype": "Currency",
|
||||
"label": "Net Amount (Company Currency)",
|
||||
"oldfieldname": "tax_amount",
|
||||
"oldfieldtype": "Currency",
|
||||
"options": "Company:company:default_currency",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
"fieldname": "set_by_item_tax_template",
|
||||
"fieldtype": "Check",
|
||||
"hidden": 1,
|
||||
"label": "Set by Item Tax Template",
|
||||
"print_hide": 1,
|
||||
"read_only": 1,
|
||||
"report_hide": 1
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
],
|
||||
"index_web_pages_for_search": 1,
|
||||
"istable": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2021-11-25 11:10:10.945027",
|
||||
=======
|
||||
"modified": "2024-11-22 19:16:22.346267",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Advance Taxes and Charges",
|
||||
"owner": "Administrator",
|
||||
"permissions": [],
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "ASC"
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "ASC",
|
||||
"states": []
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
@@ -18,6 +18,10 @@ class AdvanceTaxesandCharges(Document):
|
||||
account_head: DF.Link
|
||||
add_deduct_tax: DF.Literal["Add", "Deduct"]
|
||||
allocated_amount: DF.Currency
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
base_net_amount: DF.Currency
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
base_tax_amount: DF.Currency
|
||||
base_total: DF.Currency
|
||||
charge_type: DF.Literal[
|
||||
@@ -27,11 +31,19 @@ class AdvanceTaxesandCharges(Document):
|
||||
currency: DF.Link | None
|
||||
description: DF.SmallText
|
||||
included_in_paid_amount: DF.Check
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
net_amount: DF.Currency
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
parent: DF.Data
|
||||
parentfield: DF.Data
|
||||
parenttype: DF.Data
|
||||
rate: DF.Float
|
||||
row_id: DF.Data | None
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
set_by_item_tax_template: DF.Check
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
tax_amount: DF.Currency
|
||||
total: DF.Currency
|
||||
# end: auto-generated types
|
||||
|
||||
@@ -14,30 +14,48 @@
|
||||
"fieldtype": "Link",
|
||||
"label": "Accounting Dimension",
|
||||
"options": "DocType",
|
||||
<<<<<<< HEAD
|
||||
"read_only": 1,
|
||||
"show_days": 1,
|
||||
"show_seconds": 1
|
||||
=======
|
||||
"read_only": 1
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
},
|
||||
{
|
||||
"fieldname": "dimension_value",
|
||||
"fieldtype": "Dynamic Link",
|
||||
"in_list_view": 1,
|
||||
<<<<<<< HEAD
|
||||
"options": "accounting_dimension",
|
||||
"show_days": 1,
|
||||
"show_seconds": 1
|
||||
=======
|
||||
"options": "accounting_dimension"
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
],
|
||||
"index_web_pages_for_search": 1,
|
||||
"istable": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2020-11-23 09:56:19.744200",
|
||||
=======
|
||||
"modified": "2024-03-27 13:05:58.587487",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Allowed Dimension",
|
||||
"owner": "Administrator",
|
||||
"permissions": [],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"track_changes": 1
|
||||
}
|
||||
@@ -20,14 +20,22 @@
|
||||
],
|
||||
"istable": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2024-01-03 11:13:02.669632",
|
||||
=======
|
||||
"modified": "2024-03-27 13:05:58.698893",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Allowed To Transact With",
|
||||
"owner": "Administrator",
|
||||
"permissions": [],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
|
||||
@@ -15,9 +15,13 @@
|
||||
"in_list_view": 1,
|
||||
"label": "Accounts",
|
||||
"options": "Account",
|
||||
<<<<<<< HEAD
|
||||
"reqd": 1,
|
||||
"show_days": 1,
|
||||
"show_seconds": 1
|
||||
=======
|
||||
"reqd": 1
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
@@ -25,22 +29,36 @@
|
||||
"fieldname": "is_mandatory",
|
||||
"fieldtype": "Check",
|
||||
"in_list_view": 1,
|
||||
<<<<<<< HEAD
|
||||
"label": "Is Mandatory",
|
||||
"show_days": 1,
|
||||
"show_seconds": 1
|
||||
=======
|
||||
"label": "Is Mandatory"
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
],
|
||||
"index_web_pages_for_search": 1,
|
||||
"istable": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2020-11-22 19:55:13.324136",
|
||||
=======
|
||||
"modified": "2024-03-27 13:05:59.168897",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Applicable On Account",
|
||||
"owner": "Administrator",
|
||||
"permissions": [],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"track_changes": 1
|
||||
}
|
||||
@@ -101,7 +101,11 @@
|
||||
}
|
||||
],
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2020-07-17 14:00:13.105433",
|
||||
=======
|
||||
"modified": "2024-03-27 13:06:36.896195",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Bank",
|
||||
@@ -121,7 +125,13 @@
|
||||
}
|
||||
],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"track_changes": 1
|
||||
}
|
||||
@@ -1,8 +1,17 @@
|
||||
# Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
import unittest
|
||||
|
||||
|
||||
class TestBank(unittest.TestCase):
|
||||
=======
|
||||
import unittest
|
||||
|
||||
from frappe.tests import IntegrationTestCase
|
||||
|
||||
|
||||
class TestBank(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pass
|
||||
|
||||
@@ -283,8 +283,16 @@
|
||||
}
|
||||
],
|
||||
"search_fields": "bank,account",
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
}
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
@@ -48,7 +48,7 @@ class BankAccount(Document):
|
||||
self.name = self.account_name + " - " + self.bank
|
||||
|
||||
def on_trash(self):
|
||||
delete_contact_and_address("Bank Account", self.name)
|
||||
delete_contact_and_address("BankAccount", self.name)
|
||||
|
||||
def validate(self):
|
||||
self.validate_company()
|
||||
@@ -70,7 +70,11 @@ class BankAccount(Document):
|
||||
|
||||
def validate_company(self):
|
||||
if self.is_company_account and not self.company:
|
||||
<<<<<<< HEAD
|
||||
frappe.throw(_("Company is manadatory for company account"))
|
||||
=======
|
||||
frappe.throw(_("Company is mandatory for company account"))
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
def validate_iban(self):
|
||||
"""
|
||||
|
||||
@@ -1,15 +1,25 @@
|
||||
# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
from frappe import ValidationError
|
||||
<<<<<<< HEAD
|
||||
|
||||
# test_records = frappe.get_test_records('Bank Account')
|
||||
|
||||
|
||||
class TestBankAccount(unittest.TestCase):
|
||||
=======
|
||||
from frappe.tests import IntegrationTestCase
|
||||
|
||||
|
||||
class TestBankAccount(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def test_validate_iban(self):
|
||||
valid_ibans = [
|
||||
"GB82 WEST 1234 5698 7654 32",
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
<<<<<<< HEAD
|
||||
"allow_copy": 0,
|
||||
"allow_events_in_timeline": 0,
|
||||
"allow_guest_to_view": 0,
|
||||
@@ -67,17 +68,50 @@
|
||||
{
|
||||
"amend": 0,
|
||||
"cancel": 0,
|
||||
=======
|
||||
"actions": [],
|
||||
"allow_import": 1,
|
||||
"allow_rename": 1,
|
||||
"autoname": "field:account_subtype",
|
||||
"creation": "2018-10-25 15:46:08.054586",
|
||||
"doctype": "DocType",
|
||||
"editable_grid": 1,
|
||||
"engine": "InnoDB",
|
||||
"field_order": [
|
||||
"account_subtype"
|
||||
],
|
||||
"fields": [
|
||||
{
|
||||
"fieldname": "account_subtype",
|
||||
"fieldtype": "Data",
|
||||
"label": "Account Subtype",
|
||||
"unique": 1
|
||||
}
|
||||
],
|
||||
"links": [],
|
||||
"modified": "2024-03-27 13:06:37.221876",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Bank Account Subtype",
|
||||
"owner": "Administrator",
|
||||
"permissions": [
|
||||
{
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
<<<<<<< HEAD
|
||||
"if_owner": 0,
|
||||
"import": 0,
|
||||
"permlevel": 0,
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "System Manager",
|
||||
<<<<<<< HEAD
|
||||
"set_user_permissions": 0,
|
||||
"share": 1,
|
||||
"submit": 0,
|
||||
@@ -86,17 +120,27 @@
|
||||
{
|
||||
"amend": 0,
|
||||
"cancel": 0,
|
||||
=======
|
||||
"share": 1,
|
||||
"write": 1
|
||||
},
|
||||
{
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
<<<<<<< HEAD
|
||||
"if_owner": 0,
|
||||
"import": 0,
|
||||
"permlevel": 0,
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "Accounts Manager",
|
||||
<<<<<<< HEAD
|
||||
"set_user_permissions": 0,
|
||||
"share": 1,
|
||||
"submit": 0,
|
||||
@@ -105,24 +149,38 @@
|
||||
{
|
||||
"amend": 0,
|
||||
"cancel": 0,
|
||||
=======
|
||||
"share": 1,
|
||||
"write": 1
|
||||
},
|
||||
{
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
<<<<<<< HEAD
|
||||
"if_owner": 0,
|
||||
"import": 0,
|
||||
"permlevel": 0,
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "Accounts User",
|
||||
<<<<<<< HEAD
|
||||
"set_user_permissions": 0,
|
||||
"share": 1,
|
||||
"submit": 0,
|
||||
=======
|
||||
"share": 1,
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"write": 1
|
||||
}
|
||||
],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"read_only": 0,
|
||||
"read_only_onload": 0,
|
||||
"show_name_in_global_search": 0,
|
||||
@@ -131,4 +189,9 @@
|
||||
"track_changes": 0,
|
||||
"track_seen": 0,
|
||||
"track_views": 0
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": []
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
@@ -1,8 +1,17 @@
|
||||
# Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
import unittest
|
||||
|
||||
|
||||
class TestBankAccountSubtype(unittest.TestCase):
|
||||
=======
|
||||
import unittest
|
||||
|
||||
from frappe.tests import IntegrationTestCase
|
||||
|
||||
|
||||
class TestBankAccountSubtype(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pass
|
||||
|
||||
@@ -19,7 +19,11 @@
|
||||
}
|
||||
],
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2020-04-10 21:13:09.137898",
|
||||
=======
|
||||
"modified": "2024-03-27 13:06:37.347035",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Bank Account Type",
|
||||
@@ -63,6 +67,12 @@
|
||||
}
|
||||
],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC"
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": []
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
@@ -1,9 +1,19 @@
|
||||
# Copyright (c) 2020, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
# import frappe
|
||||
import unittest
|
||||
|
||||
|
||||
class TestBankAccountType(unittest.TestCase):
|
||||
=======
|
||||
# import frappe
|
||||
import unittest
|
||||
|
||||
from frappe.tests import IntegrationTestCase
|
||||
|
||||
|
||||
class TestBankAccountType(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pass
|
||||
|
||||
@@ -91,7 +91,11 @@
|
||||
"idx": 1,
|
||||
"issingle": 1,
|
||||
"links": [],
|
||||
<<<<<<< HEAD
|
||||
"modified": "2022-11-28 17:24:13.008692",
|
||||
=======
|
||||
"modified": "2024-03-27 13:06:37.477927",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Bank Clearance",
|
||||
@@ -107,7 +111,11 @@
|
||||
],
|
||||
"quick_entry": 1,
|
||||
"read_only": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
"sort_order": "ASC",
|
||||
"states": []
|
||||
}
|
||||
@@ -117,9 +117,9 @@ class BankClearance(Document):
|
||||
)
|
||||
|
||||
else:
|
||||
# using db_set to trigger notification
|
||||
payment_entry = frappe.get_doc(d.payment_document, d.payment_entry)
|
||||
payment_entry.db_set("clearance_date", d.clearance_date)
|
||||
frappe.db.set_value(
|
||||
d.payment_document, d.payment_entry, "clearance_date", d.clearance_date
|
||||
)
|
||||
|
||||
clearance_date_updated = True
|
||||
|
||||
@@ -159,6 +159,9 @@ def get_payment_entries_for_bank_clearance(
|
||||
as_dict=1,
|
||||
)
|
||||
|
||||
if bank_account:
|
||||
condition += "and bank_account = %(bank_account)s"
|
||||
|
||||
payment_entries = frappe.db.sql(
|
||||
f"""
|
||||
select
|
||||
@@ -180,6 +183,7 @@ def get_payment_entries_for_bank_clearance(
|
||||
"account": account,
|
||||
"from": from_date,
|
||||
"to": to_date,
|
||||
"bank_account": bank_account,
|
||||
},
|
||||
as_dict=1,
|
||||
)
|
||||
|
||||
@@ -1,15 +1,19 @@
|
||||
# Copyright (c) 2020, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
=======
|
||||
import unittest
|
||||
|
||||
import frappe
|
||||
from frappe.tests import IntegrationTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
from frappe.utils import add_months, getdate
|
||||
|
||||
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
|
||||
from erpnext.accounts.doctype.mode_of_payment.test_mode_of_payment import (
|
||||
set_default_account_for_mode_of_payment,
|
||||
)
|
||||
from erpnext.accounts.doctype.payment_entry.test_payment_entry import get_payment_entry
|
||||
from erpnext.accounts.doctype.purchase_invoice.test_purchase_invoice import make_purchase_invoice
|
||||
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
|
||||
@@ -18,9 +22,16 @@ from erpnext.stock.doctype.warehouse.test_warehouse import create_warehouse
|
||||
from erpnext.tests.utils import if_lending_app_installed, if_lending_app_not_installed
|
||||
|
||||
|
||||
<<<<<<< HEAD
|
||||
class TestBankClearance(unittest.TestCase):
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
=======
|
||||
class TestBankClearance(IntegrationTestCase):
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
super().setUpClass()
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
create_warehouse(
|
||||
warehouse_name="_Test Warehouse",
|
||||
properties={"parent_warehouse": "All Warehouses - _TC"},
|
||||
@@ -29,9 +40,12 @@ class TestBankClearance(unittest.TestCase):
|
||||
create_item("_Test Item")
|
||||
create_cost_center(cost_center_name="_Test Cost Center", company="_Test Company")
|
||||
|
||||
<<<<<<< HEAD
|
||||
clear_payment_entries()
|
||||
clear_loan_transactions()
|
||||
clear_pos_sales_invoices()
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
make_bank_account()
|
||||
add_transactions()
|
||||
|
||||
@@ -126,6 +140,7 @@ class TestBankClearance(unittest.TestCase):
|
||||
self.assertEqual(si_clearance_date, date)
|
||||
|
||||
|
||||
<<<<<<< HEAD
|
||||
def clear_payment_entries():
|
||||
frappe.db.delete("Payment Entry")
|
||||
|
||||
@@ -143,6 +158,8 @@ def clear_loan_transactions():
|
||||
frappe.db.delete(dt)
|
||||
|
||||
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def make_bank_account():
|
||||
if not frappe.db.get_value("Account", "_Test Bank Clearance - _TC"):
|
||||
frappe.get_doc(
|
||||
@@ -194,13 +211,11 @@ def make_pos_sales_invoice():
|
||||
|
||||
customer = make_customer(customer="_Test Customer")
|
||||
|
||||
mode_of_payment = frappe.get_doc("Mode of Payment", "Wire Transfer")
|
||||
|
||||
set_default_account_for_mode_of_payment(mode_of_payment, "_Test Company", "_Test Bank Clearance - _TC")
|
||||
|
||||
si = create_sales_invoice(customer=customer, item="_Test Item", is_pos=1, qty=1, rate=1000, do_not_save=1)
|
||||
si.set("payments", [])
|
||||
si.append("payments", {"mode_of_payment": "Wire Transfer", "amount": 1000})
|
||||
si.append(
|
||||
"payments", {"mode_of_payment": "Cash", "account": "_Test Bank Clearance - _TC", "amount": 1000}
|
||||
)
|
||||
si.insert()
|
||||
si.submit()
|
||||
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
<<<<<<< HEAD
|
||||
"allow_copy": 0,
|
||||
"allow_events_in_timeline": 0,
|
||||
"allow_guest_to_view": 0,
|
||||
@@ -337,4 +338,116 @@
|
||||
"track_changes": 0,
|
||||
"track_seen": 0,
|
||||
"track_views": 0
|
||||
=======
|
||||
"actions": [],
|
||||
"creation": "2013-02-22 01:27:37",
|
||||
"doctype": "DocType",
|
||||
"editable_grid": 1,
|
||||
"engine": "InnoDB",
|
||||
"field_order": [
|
||||
"payment_document",
|
||||
"payment_entry",
|
||||
"against_account",
|
||||
"amount",
|
||||
"column_break_5",
|
||||
"posting_date",
|
||||
"cheque_number",
|
||||
"cheque_date",
|
||||
"clearance_date"
|
||||
],
|
||||
"fields": [
|
||||
{
|
||||
"fieldname": "payment_document",
|
||||
"fieldtype": "Link",
|
||||
"label": "Payment Document",
|
||||
"options": "DocType"
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
"fieldname": "payment_entry",
|
||||
"fieldtype": "Dynamic Link",
|
||||
"in_list_view": 1,
|
||||
"label": "Payment Entry",
|
||||
"oldfieldname": "voucher_id",
|
||||
"oldfieldtype": "Link",
|
||||
"options": "payment_document",
|
||||
"width": "50"
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
"fieldname": "against_account",
|
||||
"fieldtype": "Data",
|
||||
"in_list_view": 1,
|
||||
"label": "Against Account",
|
||||
"oldfieldname": "against_account",
|
||||
"oldfieldtype": "Data",
|
||||
"read_only": 1,
|
||||
"width": "15"
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
"fieldname": "amount",
|
||||
"fieldtype": "Data",
|
||||
"in_list_view": 1,
|
||||
"label": "Amount",
|
||||
"oldfieldname": "debit",
|
||||
"oldfieldtype": "Currency",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_5",
|
||||
"fieldtype": "Column Break",
|
||||
"width": "50%"
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
"fieldname": "posting_date",
|
||||
"fieldtype": "Date",
|
||||
"label": "Posting Date",
|
||||
"oldfieldname": "posting_date",
|
||||
"oldfieldtype": "Date",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
"fieldname": "cheque_number",
|
||||
"fieldtype": "Data",
|
||||
"in_list_view": 1,
|
||||
"label": "Cheque Number",
|
||||
"oldfieldname": "cheque_number",
|
||||
"oldfieldtype": "Data",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "cheque_date",
|
||||
"fieldtype": "Date",
|
||||
"label": "Cheque Date",
|
||||
"oldfieldname": "cheque_date",
|
||||
"oldfieldtype": "Date",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"columns": 2,
|
||||
"fieldname": "clearance_date",
|
||||
"fieldtype": "Date",
|
||||
"in_list_view": 1,
|
||||
"label": "Clearance Date",
|
||||
"oldfieldname": "clearance_date",
|
||||
"oldfieldtype": "Date"
|
||||
}
|
||||
],
|
||||
"idx": 1,
|
||||
"istable": 1,
|
||||
"links": [],
|
||||
"modified": "2024-03-27 13:06:37.609319",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Bank Clearance Detail",
|
||||
"owner": "Administrator",
|
||||
"permissions": [],
|
||||
"quick_entry": 1,
|
||||
"sort_field": "creation",
|
||||
"sort_order": "ASC",
|
||||
"states": []
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
<<<<<<< HEAD
|
||||
"allow_copy": 0,
|
||||
"allow_guest_to_view": 0,
|
||||
"allow_import": 0,
|
||||
@@ -1053,4 +1054,262 @@
|
||||
"track_changes": 0,
|
||||
"track_seen": 0,
|
||||
"track_views": 0
|
||||
=======
|
||||
"actions": [],
|
||||
"autoname": "ACC-BG-.YYYY.-.#####",
|
||||
"creation": "2016-12-17 10:43:35.731631",
|
||||
"doctype": "DocType",
|
||||
"document_type": "Document",
|
||||
"editable_grid": 1,
|
||||
"engine": "InnoDB",
|
||||
"field_order": [
|
||||
"bg_type",
|
||||
"reference_doctype",
|
||||
"reference_docname",
|
||||
"customer",
|
||||
"supplier",
|
||||
"project",
|
||||
"column_break_6",
|
||||
"amount",
|
||||
"start_date",
|
||||
"validity",
|
||||
"end_date",
|
||||
"bank_account_info",
|
||||
"bank",
|
||||
"bank_account",
|
||||
"account",
|
||||
"bank_account_no",
|
||||
"column_break_17",
|
||||
"iban",
|
||||
"branch_code",
|
||||
"swift_number",
|
||||
"section_break_14",
|
||||
"more_information",
|
||||
"margin_details",
|
||||
"bank_guarantee_number",
|
||||
"name_of_beneficiary",
|
||||
"column_break_19",
|
||||
"margin_money",
|
||||
"charges",
|
||||
"fixed_deposit_number",
|
||||
"amended_from"
|
||||
],
|
||||
"fields": [
|
||||
{
|
||||
"fieldname": "bg_type",
|
||||
"fieldtype": "Select",
|
||||
"label": "Bank Guarantee Type",
|
||||
"options": "\nReceiving\nProviding",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "reference_doctype",
|
||||
"fieldtype": "Link",
|
||||
"label": "Reference Document Type",
|
||||
"options": "DocType",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "reference_docname",
|
||||
"fieldtype": "Dynamic Link",
|
||||
"label": "Reference Document Name",
|
||||
"options": "reference_doctype"
|
||||
},
|
||||
{
|
||||
"depends_on": "eval: doc.bg_type == \"Receiving\"",
|
||||
"fieldname": "customer",
|
||||
"fieldtype": "Link",
|
||||
"label": "Customer",
|
||||
"options": "Customer"
|
||||
},
|
||||
{
|
||||
"depends_on": "eval: doc.bg_type == \"Providing\"",
|
||||
"fieldname": "supplier",
|
||||
"fieldtype": "Link",
|
||||
"label": "Supplier",
|
||||
"options": "Supplier"
|
||||
},
|
||||
{
|
||||
"allow_on_submit": 1,
|
||||
"fieldname": "project",
|
||||
"fieldtype": "Link",
|
||||
"label": "Project",
|
||||
"options": "Project"
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_6",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"fieldname": "amount",
|
||||
"fieldtype": "Currency",
|
||||
"in_list_view": 1,
|
||||
"label": "Amount",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "start_date",
|
||||
"fieldtype": "Date",
|
||||
"label": "Start Date",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "validity",
|
||||
"fieldtype": "Int",
|
||||
"label": "Validity in Days"
|
||||
},
|
||||
{
|
||||
"fieldname": "end_date",
|
||||
"fieldtype": "Date",
|
||||
"label": "End Date",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "bank_account_info",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Bank Account Info"
|
||||
},
|
||||
{
|
||||
"fieldname": "bank",
|
||||
"fieldtype": "Link",
|
||||
"label": "Bank",
|
||||
"options": "Bank"
|
||||
},
|
||||
{
|
||||
"fieldname": "bank_account",
|
||||
"fieldtype": "Link",
|
||||
"label": "Bank Account",
|
||||
"options": "Bank Account"
|
||||
},
|
||||
{
|
||||
"fieldname": "account",
|
||||
"fieldtype": "Link",
|
||||
"label": "Account",
|
||||
"options": "Account",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "bank_account_no",
|
||||
"fieldtype": "Data",
|
||||
"label": "Bank Account No",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_17",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"fieldname": "iban",
|
||||
"fieldtype": "Data",
|
||||
"label": "IBAN",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "branch_code",
|
||||
"fieldtype": "Data",
|
||||
"label": "Branch Code",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "swift_number",
|
||||
"fieldtype": "Data",
|
||||
"label": "SWIFT number",
|
||||
"read_only": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "section_break_14",
|
||||
"fieldtype": "Section Break"
|
||||
},
|
||||
{
|
||||
"fieldname": "more_information",
|
||||
"fieldtype": "Text Editor",
|
||||
"label": "Clauses and Conditions"
|
||||
},
|
||||
{
|
||||
"fieldname": "margin_details",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Other Details"
|
||||
},
|
||||
{
|
||||
"fieldname": "bank_guarantee_number",
|
||||
"fieldtype": "Data",
|
||||
"label": "Bank Guarantee Number",
|
||||
"unique": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "name_of_beneficiary",
|
||||
"fieldtype": "Data",
|
||||
"label": "Name of Beneficiary"
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_19",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"fieldname": "margin_money",
|
||||
"fieldtype": "Currency",
|
||||
"label": "Margin Money"
|
||||
},
|
||||
{
|
||||
"fieldname": "charges",
|
||||
"fieldtype": "Currency",
|
||||
"label": "Charges Incurred"
|
||||
},
|
||||
{
|
||||
"fieldname": "fixed_deposit_number",
|
||||
"fieldtype": "Data",
|
||||
"label": "Fixed Deposit Number"
|
||||
},
|
||||
{
|
||||
"fieldname": "amended_from",
|
||||
"fieldtype": "Link",
|
||||
"label": "Amended From",
|
||||
"no_copy": 1,
|
||||
"options": "Bank Guarantee",
|
||||
"print_hide": 1,
|
||||
"read_only": 1
|
||||
}
|
||||
],
|
||||
"is_submittable": 1,
|
||||
"links": [],
|
||||
"modified": "2024-03-27 13:06:37.731207",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Bank Guarantee",
|
||||
"owner": "Administrator",
|
||||
"permissions": [
|
||||
{
|
||||
"create": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "Accounts User",
|
||||
"share": 1,
|
||||
"submit": 1,
|
||||
"write": 1
|
||||
},
|
||||
{
|
||||
"cancel": 1,
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "Accounts Manager",
|
||||
"share": 1,
|
||||
"submit": 1,
|
||||
"write": 1
|
||||
}
|
||||
],
|
||||
"quick_entry": 1,
|
||||
"search_fields": "customer",
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"title_field": "customer"
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
}
|
||||
@@ -48,11 +48,19 @@ class BankGuarantee(Document):
|
||||
|
||||
def on_submit(self):
|
||||
if not self.bank_guarantee_number:
|
||||
<<<<<<< HEAD
|
||||
frappe.throw(_("Enter the Bank Guarantee Number before submittting."))
|
||||
if not self.name_of_beneficiary:
|
||||
frappe.throw(_("Enter the name of the Beneficiary before submittting."))
|
||||
if not self.bank:
|
||||
frappe.throw(_("Enter the name of the bank or lending institution before submittting."))
|
||||
=======
|
||||
frappe.throw(_("Enter the Bank Guarantee Number before submitting."))
|
||||
if not self.name_of_beneficiary:
|
||||
frappe.throw(_("Enter the name of the Beneficiary before submitting."))
|
||||
if not self.bank:
|
||||
frappe.throw(_("Enter the name of the bank or lending institution before submitting."))
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
|
||||
@frappe.whitelist()
|
||||
|
||||
@@ -1,8 +1,17 @@
|
||||
# Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
import unittest
|
||||
|
||||
|
||||
class TestBankGuarantee(unittest.TestCase):
|
||||
=======
|
||||
import unittest
|
||||
|
||||
from frappe.tests import IntegrationTestCase
|
||||
|
||||
|
||||
class TestBankGuarantee(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pass
|
||||
|
||||
@@ -19,15 +19,10 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
||||
},
|
||||
|
||||
onload: function (frm) {
|
||||
if (!frm.doc.company) {
|
||||
frm.set_value("company", frappe.defaults.get_default("company"));
|
||||
}
|
||||
|
||||
// Set default filter dates
|
||||
let today = frappe.datetime.get_today();
|
||||
frm.doc.bank_statement_from_date = frappe.datetime.add_months(today, -1);
|
||||
frm.doc.bank_statement_to_date = today;
|
||||
|
||||
frm.trigger("bank_account");
|
||||
},
|
||||
|
||||
@@ -103,7 +98,7 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
||||
|
||||
make_reconciliation_tool(frm) {
|
||||
frm.get_field("reconciliation_tool_cards").$wrapper.empty();
|
||||
if (frm.doc.company && frm.doc.bank_account && frm.doc.bank_statement_to_date) {
|
||||
if (frm.doc.bank_account && frm.doc.bank_statement_to_date) {
|
||||
frm.trigger("get_cleared_balance").then(() => {
|
||||
if (
|
||||
frm.doc.bank_account &&
|
||||
@@ -119,13 +114,12 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
||||
},
|
||||
|
||||
get_account_opening_balance(frm) {
|
||||
if (frm.doc.company && frm.doc.bank_account && frm.doc.bank_statement_from_date) {
|
||||
if (frm.doc.bank_account && frm.doc.bank_statement_from_date) {
|
||||
frappe.call({
|
||||
method: "erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.get_account_balance",
|
||||
args: {
|
||||
bank_account: frm.doc.bank_account,
|
||||
till_date: frappe.datetime.add_days(frm.doc.bank_statement_from_date, -1),
|
||||
company: frm.doc.company,
|
||||
},
|
||||
callback: (response) => {
|
||||
frm.set_value("account_opening_balance", response.message);
|
||||
@@ -135,13 +129,12 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
||||
},
|
||||
|
||||
get_cleared_balance(frm) {
|
||||
if (frm.doc.company && frm.doc.bank_account && frm.doc.bank_statement_to_date) {
|
||||
if (frm.doc.bank_account && frm.doc.bank_statement_to_date) {
|
||||
return frappe.call({
|
||||
method: "erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.get_account_balance",
|
||||
args: {
|
||||
bank_account: frm.doc.bank_account,
|
||||
till_date: frm.doc.bank_statement_to_date,
|
||||
company: frm.doc.company,
|
||||
},
|
||||
callback: (response) => {
|
||||
frm.cleared_balance = response.message;
|
||||
|
||||
@@ -137,7 +137,14 @@
|
||||
}
|
||||
],
|
||||
"quick_entry": 1,
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC",
|
||||
"states": []
|
||||
}
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": []
|
||||
}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
@@ -8,12 +8,10 @@ import frappe
|
||||
from frappe import _
|
||||
from frappe.model.document import Document
|
||||
from frappe.query_builder.custom import ConstantColumn
|
||||
from frappe.query_builder.functions import Sum
|
||||
from frappe.utils import cint, flt
|
||||
|
||||
from erpnext import get_default_cost_center
|
||||
from erpnext.accounts.doctype.bank_transaction.bank_transaction import get_total_allocated_amount
|
||||
from erpnext.accounts.party import get_party_account
|
||||
from erpnext.accounts.report.bank_reconciliation_statement.bank_reconciliation_statement import (
|
||||
get_amounts_not_reflected_in_system,
|
||||
get_entries,
|
||||
@@ -80,17 +78,10 @@ def get_bank_transactions(bank_account, from_date=None, to_date=None):
|
||||
|
||||
|
||||
@frappe.whitelist()
|
||||
def get_account_balance(bank_account, till_date, company):
|
||||
def get_account_balance(bank_account, till_date):
|
||||
# returns account balance till the specified date
|
||||
account = frappe.db.get_value("Bank Account", bank_account, "account")
|
||||
filters = frappe._dict(
|
||||
{
|
||||
"account": account,
|
||||
"report_date": till_date,
|
||||
"include_pos_transactions": 1,
|
||||
"company": company,
|
||||
}
|
||||
)
|
||||
filters = frappe._dict({"account": account, "report_date": till_date, "include_pos_transactions": 1})
|
||||
data = get_entries(filters)
|
||||
|
||||
balance_as_per_system = get_balance_on(filters["account"], filters["report_date"])
|
||||
@@ -102,7 +93,11 @@ def get_account_balance(bank_account, till_date, company):
|
||||
|
||||
amounts_not_reflected_in_system = get_amounts_not_reflected_in_system(filters)
|
||||
|
||||
return flt(balance_as_per_system) - flt(total_debit) + flt(total_credit) + amounts_not_reflected_in_system
|
||||
bank_bal = (
|
||||
flt(balance_as_per_system) - flt(total_debit) + flt(total_credit) + amounts_not_reflected_in_system
|
||||
)
|
||||
|
||||
return bank_bal
|
||||
|
||||
|
||||
@frappe.whitelist()
|
||||
@@ -309,56 +304,54 @@ def create_payment_entry_bts(
|
||||
bank_transaction = frappe.db.get_values(
|
||||
"Bank Transaction",
|
||||
bank_transaction_name,
|
||||
fieldname=["name", "unallocated_amount", "deposit", "bank_account", "currency"],
|
||||
fieldname=["name", "unallocated_amount", "deposit", "bank_account"],
|
||||
as_dict=True,
|
||||
)[0]
|
||||
|
||||
paid_amount = bank_transaction.unallocated_amount
|
||||
payment_type = "Receive" if bank_transaction.deposit > 0.0 else "Pay"
|
||||
|
||||
bank_account = frappe.get_cached_value("Bank Account", bank_transaction.bank_account, "account")
|
||||
company = frappe.get_cached_value("Account", bank_account, "company")
|
||||
party_account = get_party_account(party_type, party, company)
|
||||
company_account = frappe.get_value("Bank Account", bank_transaction.bank_account, "account")
|
||||
company = frappe.get_value("Account", company_account, "company")
|
||||
payment_entry_dict = {
|
||||
"company": company,
|
||||
"payment_type": payment_type,
|
||||
"reference_no": reference_number,
|
||||
"reference_date": reference_date,
|
||||
"party_type": party_type,
|
||||
"party": party,
|
||||
"posting_date": posting_date,
|
||||
"paid_amount": paid_amount,
|
||||
"received_amount": paid_amount,
|
||||
}
|
||||
payment_entry = frappe.new_doc("Payment Entry")
|
||||
|
||||
bank_currency = bank_transaction.currency
|
||||
party_currency = frappe.get_cached_value("Account", party_account, "account_currency")
|
||||
payment_entry.update(payment_entry_dict)
|
||||
|
||||
exc_rate = get_exchange_rate(bank_currency, party_currency, posting_date)
|
||||
if mode_of_payment:
|
||||
payment_entry.mode_of_payment = mode_of_payment
|
||||
if project:
|
||||
payment_entry.project = project
|
||||
if cost_center:
|
||||
payment_entry.cost_center = cost_center
|
||||
if payment_type == "Receive":
|
||||
payment_entry.paid_to = company_account
|
||||
else:
|
||||
payment_entry.paid_from = company_account
|
||||
|
||||
amt_in_bank_acc_currency = bank_transaction.unallocated_amount
|
||||
amount_in_party_currency = bank_transaction.unallocated_amount * exc_rate
|
||||
|
||||
pe = frappe.new_doc("Payment Entry")
|
||||
pe.payment_type = payment_type
|
||||
pe.company = company
|
||||
pe.reference_no = reference_number
|
||||
pe.reference_date = reference_date
|
||||
pe.party_type = party_type
|
||||
pe.party = party
|
||||
pe.posting_date = posting_date
|
||||
pe.paid_from = party_account if payment_type == "Receive" else bank_account
|
||||
pe.paid_to = party_account if payment_type == "Pay" else bank_account
|
||||
pe.paid_from_account_currency = party_currency if payment_type == "Receive" else bank_currency
|
||||
pe.paid_to_account_currency = party_currency if payment_type == "Pay" else bank_currency
|
||||
pe.paid_amount = amount_in_party_currency if payment_type == "Receive" else amt_in_bank_acc_currency
|
||||
pe.received_amount = amount_in_party_currency if payment_type == "Pay" else amt_in_bank_acc_currency
|
||||
pe.mode_of_payment = mode_of_payment
|
||||
pe.project = project
|
||||
pe.cost_center = cost_center
|
||||
|
||||
pe.validate()
|
||||
payment_entry.validate()
|
||||
|
||||
if allow_edit:
|
||||
return pe
|
||||
return payment_entry
|
||||
|
||||
pe.insert()
|
||||
pe.submit()
|
||||
payment_entry.insert()
|
||||
|
||||
payment_entry.submit()
|
||||
vouchers = json.dumps(
|
||||
[
|
||||
{
|
||||
"payment_doctype": "Payment Entry",
|
||||
"payment_name": pe.name,
|
||||
"amount": amt_in_bank_acc_currency,
|
||||
"payment_name": payment_entry.name,
|
||||
"amount": paid_amount,
|
||||
}
|
||||
]
|
||||
)
|
||||
@@ -373,38 +366,11 @@ def auto_reconcile_vouchers(
|
||||
filter_by_reference_date=None,
|
||||
from_reference_date=None,
|
||||
to_reference_date=None,
|
||||
):
|
||||
bank_transactions = get_bank_transactions(bank_account)
|
||||
|
||||
if len(bank_transactions) > 10:
|
||||
frappe.enqueue(
|
||||
method="erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.start_auto_reconcile",
|
||||
queue="long",
|
||||
bank_transactions=bank_transactions,
|
||||
from_date=from_date,
|
||||
to_date=to_date,
|
||||
filter_by_reference_date=filter_by_reference_date,
|
||||
from_reference_date=from_reference_date,
|
||||
to_reference_date=to_reference_date,
|
||||
)
|
||||
frappe.msgprint(_("Auto Reconciliation has started in the background"))
|
||||
else:
|
||||
start_auto_reconcile(
|
||||
bank_transactions,
|
||||
from_date,
|
||||
to_date,
|
||||
filter_by_reference_date,
|
||||
from_reference_date,
|
||||
to_reference_date,
|
||||
)
|
||||
|
||||
|
||||
def start_auto_reconcile(
|
||||
bank_transactions, from_date, to_date, filter_by_reference_date, from_reference_date, to_reference_date
|
||||
):
|
||||
frappe.flags.auto_reconcile_vouchers = True
|
||||
|
||||
reconciled, partially_reconciled = set(), set()
|
||||
|
||||
bank_transactions = get_bank_transactions(bank_account)
|
||||
for transaction in bank_transactions:
|
||||
linked_payments = get_linked_payments(
|
||||
transaction.name,
|
||||
@@ -442,6 +408,7 @@ def start_auto_reconcile(
|
||||
frappe.msgprint(title=_("Auto Reconciliation"), msg=alert_message, indicator=indicator)
|
||||
|
||||
frappe.flags.auto_reconcile_vouchers = False
|
||||
return reconciled, partially_reconciled
|
||||
|
||||
|
||||
def get_auto_reconcile_message(partially_reconciled, reconciled):
|
||||
@@ -513,28 +480,17 @@ def get_linked_payments(
|
||||
def subtract_allocations(gl_account, vouchers):
|
||||
"Look up & subtract any existing Bank Transaction allocations"
|
||||
copied = []
|
||||
|
||||
voucher_docs = [(voucher.get("doctype"), voucher.get("name")) for voucher in vouchers]
|
||||
voucher_allocated_amounts = get_total_allocated_amount(voucher_docs)
|
||||
|
||||
for voucher in vouchers:
|
||||
if amount := get_allocated_amount(voucher_allocated_amounts, voucher, gl_account):
|
||||
rows = get_total_allocated_amount(voucher.get("doctype"), voucher.get("name"))
|
||||
filtered_row = list(filter(lambda row: row.get("gl_account") == gl_account, rows))
|
||||
|
||||
if amount := None if not filtered_row else filtered_row[0]["total"]:
|
||||
voucher["paid_amount"] -= amount
|
||||
|
||||
copied.append(voucher)
|
||||
return copied
|
||||
|
||||
|
||||
def get_allocated_amount(voucher_allocated_amounts, voucher, gl_account):
|
||||
if not (voucher_details := voucher_allocated_amounts.get((voucher.get("doctype"), voucher.get("name")))):
|
||||
return
|
||||
|
||||
if not (row := voucher_details.get(gl_account)):
|
||||
return
|
||||
|
||||
return row.get("total")
|
||||
|
||||
|
||||
def check_matching(
|
||||
bank_account,
|
||||
company,
|
||||
@@ -763,7 +719,7 @@ def get_pe_matching_query(
|
||||
(ref_rank + amount_rank + party_rank + 1).as_("rank"),
|
||||
ConstantColumn("Payment Entry").as_("doctype"),
|
||||
pe.name,
|
||||
pe.base_paid_amount_after_tax.as_("paid_amount"),
|
||||
pe.paid_amount_after_tax.as_("paid_amount"),
|
||||
pe.reference_no,
|
||||
pe.reference_date,
|
||||
pe.party,
|
||||
@@ -804,20 +760,26 @@ def get_je_matching_query(
|
||||
je = frappe.qb.DocType("Journal Entry")
|
||||
jea = frappe.qb.DocType("Journal Entry Account")
|
||||
|
||||
ref_condition = je.cheque_no == transaction.reference_number
|
||||
ref_rank = frappe.qb.terms.Case().when(ref_condition, 1).else_(0)
|
||||
|
||||
amount_field = f"{cr_or_dr}_in_account_currency"
|
||||
amount_equality = getattr(jea, amount_field) == transaction.unallocated_amount
|
||||
amount_rank = frappe.qb.terms.Case().when(amount_equality, 1).else_(0)
|
||||
|
||||
filter_by_date = je.posting_date.between(from_date, to_date)
|
||||
if cint(filter_by_reference_date):
|
||||
filter_by_date = je.cheque_date.between(from_reference_date, to_reference_date)
|
||||
|
||||
subquery = (
|
||||
query = (
|
||||
frappe.qb.from_(jea)
|
||||
.join(je)
|
||||
.on(jea.parent == je.name)
|
||||
.select(
|
||||
Sum(getattr(jea, amount_field)).as_("paid_amount"),
|
||||
(ref_rank + amount_rank + 1).as_("rank"),
|
||||
ConstantColumn("Journal Entry").as_("doctype"),
|
||||
je.name,
|
||||
getattr(jea, amount_field).as_("paid_amount"),
|
||||
je.cheque_no.as_("reference_no"),
|
||||
je.cheque_date.as_("reference_date"),
|
||||
je.pay_to_recd_from.as_("party"),
|
||||
@@ -829,26 +791,14 @@ def get_je_matching_query(
|
||||
.where(je.voucher_type != "Opening Entry")
|
||||
.where(je.clearance_date.isnull())
|
||||
.where(jea.account == common_filters.bank_account)
|
||||
.where(amount_equality if exact_match else getattr(jea, amount_field) > 0.0)
|
||||
.where(je.docstatus == 1)
|
||||
.where(filter_by_date)
|
||||
.groupby(je.name)
|
||||
.orderby(je.cheque_date if cint(filter_by_reference_date) else je.posting_date)
|
||||
)
|
||||
|
||||
if frappe.flags.auto_reconcile_vouchers is True:
|
||||
subquery = subquery.where(je.cheque_no == transaction.reference_number)
|
||||
|
||||
ref_rank = frappe.qb.terms.Case().when(subquery.reference_no == transaction.reference_number, 1).else_(0)
|
||||
amount_equality = subquery.paid_amount == transaction.unallocated_amount
|
||||
amount_rank = frappe.qb.terms.Case().when(amount_equality, 1).else_(0)
|
||||
|
||||
query = (
|
||||
frappe.qb.from_(subquery)
|
||||
.select(
|
||||
"*",
|
||||
(ref_rank + amount_rank + 1).as_("rank"),
|
||||
)
|
||||
.where(amount_equality if exact_match else subquery.paid_amount > 0.0)
|
||||
)
|
||||
query = query.where(ref_condition)
|
||||
|
||||
return query
|
||||
|
||||
|
||||
@@ -4,7 +4,11 @@
|
||||
|
||||
import frappe
|
||||
from frappe import qb
|
||||
<<<<<<< HEAD
|
||||
from frappe.tests.utils import FrappeTestCase
|
||||
=======
|
||||
from frappe.tests import IntegrationTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
from frappe.utils import add_days, today
|
||||
|
||||
from erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool import (
|
||||
@@ -15,7 +19,11 @@ from erpnext.accounts.doctype.payment_entry.test_payment_entry import create_pay
|
||||
from erpnext.accounts.test.accounts_mixin import AccountsTestMixin
|
||||
|
||||
|
||||
<<<<<<< HEAD
|
||||
class TestBankReconciliationTool(AccountsTestMixin, FrappeTestCase):
|
||||
=======
|
||||
class TestBankReconciliationTool(AccountsTestMixin, IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def setUp(self):
|
||||
self.create_company()
|
||||
self.create_customer()
|
||||
|
||||
@@ -2,6 +2,19 @@
|
||||
// For license information, please see license.txt
|
||||
|
||||
frappe.ui.form.on("Bank Statement Import", {
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
onload(frm) {
|
||||
frm.set_query("bank_account", function (doc) {
|
||||
return {
|
||||
filters: {
|
||||
company: doc.company,
|
||||
},
|
||||
};
|
||||
});
|
||||
},
|
||||
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
setup(frm) {
|
||||
frappe.realtime.on("data_import_refresh", ({ data_import }) => {
|
||||
frm.import_in_progress = false;
|
||||
|
||||
@@ -230,7 +230,15 @@
|
||||
"write": 1
|
||||
}
|
||||
],
|
||||
<<<<<<< HEAD
|
||||
"sort_field": "modified",
|
||||
"sort_order": "DESC",
|
||||
"track_changes": 1
|
||||
}
|
||||
=======
|
||||
"sort_field": "creation",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"track_changes": 1
|
||||
}
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
@@ -79,7 +79,12 @@ class BankStatementImport(DataImport):
|
||||
from frappe.utils.background_jobs import is_job_enqueued
|
||||
from frappe.utils.scheduler import is_scheduler_inactive
|
||||
|
||||
<<<<<<< HEAD
|
||||
if is_scheduler_inactive() and not frappe.flags.in_test:
|
||||
=======
|
||||
run_now = frappe.flags.in_test or frappe.conf.developer_mode
|
||||
if is_scheduler_inactive() and not run_now:
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
frappe.throw(_("Scheduler is inactive. Cannot import data."), title=_("Scheduler Inactive"))
|
||||
|
||||
job_id = f"bank_statement_import::{self.name}"
|
||||
@@ -96,7 +101,11 @@ class BankStatementImport(DataImport):
|
||||
google_sheets_url=self.google_sheets_url,
|
||||
bank=self.bank,
|
||||
template_options=self.template_options,
|
||||
<<<<<<< HEAD
|
||||
now=frappe.conf.developer_mode or frappe.flags.in_test,
|
||||
=======
|
||||
now=run_now,
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
)
|
||||
return True
|
||||
|
||||
@@ -277,7 +286,7 @@ def get_import_status(docname):
|
||||
|
||||
@frappe.whitelist()
|
||||
def get_import_logs(docname: str):
|
||||
frappe.has_permission("Bank Statement Import", throw=True)
|
||||
frappe.has_permission("Bank Statement Import")
|
||||
|
||||
return frappe.get_all(
|
||||
"Data Import Log",
|
||||
|
||||
@@ -1,9 +1,19 @@
|
||||
# Copyright (c) 2020, Frappe Technologies and Contributors
|
||||
# See license.txt
|
||||
<<<<<<< HEAD
|
||||
|
||||
# import frappe
|
||||
import unittest
|
||||
|
||||
|
||||
class TestBankStatementImport(unittest.TestCase):
|
||||
=======
|
||||
# import frappe
|
||||
import unittest
|
||||
|
||||
from frappe.tests import IntegrationTestCase
|
||||
|
||||
|
||||
class TestBankStatementImport(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
pass
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import frappe
|
||||
from frappe.utils import flt
|
||||
from rapidfuzz import fuzz, process
|
||||
from rapidfuzz.utils import default_process
|
||||
|
||||
|
||||
class AutoMatchParty:
|
||||
@@ -46,41 +45,45 @@ class AutoMatchbyAccountIBAN:
|
||||
if not (self.bank_party_account_number or self.bank_party_iban):
|
||||
return None
|
||||
|
||||
return self.match_account_in_party()
|
||||
result = self.match_account_in_party()
|
||||
return result
|
||||
|
||||
def match_account_in_party(self) -> tuple | None:
|
||||
"""
|
||||
Returns (Party Type, Party) if a matching account is found in Bank Account or Employee:
|
||||
1. Get party from a matching (iban/account no) Bank Account
|
||||
2. If not found, get party from Employee with matching bank account details (iban/account no)
|
||||
"""
|
||||
if not (self.bank_party_account_number or self.bank_party_iban):
|
||||
# Nothing to match
|
||||
return None
|
||||
"""Check if there is a IBAN/Account No. match in Customer/Supplier/Employee"""
|
||||
result = None
|
||||
parties = get_parties_in_order(self.deposit)
|
||||
or_filters = self.get_or_filters()
|
||||
|
||||
# Search for a matching Bank Account that has party set
|
||||
party_result = frappe.db.get_all(
|
||||
"Bank Account",
|
||||
or_filters=self.get_or_filters(),
|
||||
filters={"party_type": ("is", "set"), "party": ("is", "set")},
|
||||
fields=["party", "party_type"],
|
||||
limit_page_length=1,
|
||||
)
|
||||
if result := party_result[0] if party_result else None:
|
||||
return (result["party_type"], result["party"])
|
||||
for party in parties:
|
||||
party_result = frappe.db.get_all(
|
||||
"Bank Account", or_filters=or_filters, pluck="party", limit_page_length=1
|
||||
)
|
||||
|
||||
# If no party is found, search in Employee (since it has bank account details)
|
||||
if employee_result := frappe.db.get_all(
|
||||
"Employee", or_filters=self.get_or_filters("Employee"), pluck="name", limit_page_length=1
|
||||
):
|
||||
return ("Employee", employee_result[0])
|
||||
if party == "Employee" and not party_result:
|
||||
# Search in Bank Accounts first for Employee, and then Employee record
|
||||
if "bank_account_no" in or_filters:
|
||||
or_filters["bank_ac_no"] = or_filters.pop("bank_account_no")
|
||||
|
||||
def get_or_filters(self, party: str | None = None) -> dict:
|
||||
"""Return OR filters for Bank Account and IBAN"""
|
||||
party_result = frappe.db.get_all(
|
||||
party, or_filters=or_filters, pluck="name", limit_page_length=1
|
||||
)
|
||||
|
||||
if "bank_ac_no" in or_filters:
|
||||
or_filters["bank_account_no"] = or_filters.pop("bank_ac_no")
|
||||
|
||||
if party_result:
|
||||
result = (
|
||||
party,
|
||||
party_result[0],
|
||||
)
|
||||
break
|
||||
|
||||
return result
|
||||
|
||||
def get_or_filters(self) -> dict:
|
||||
or_filters = {}
|
||||
if self.bank_party_account_number:
|
||||
bank_ac_field = "bank_ac_no" if party == "Employee" else "bank_account_no"
|
||||
or_filters[bank_ac_field] = self.bank_party_account_number
|
||||
or_filters["bank_account_no"] = self.bank_party_account_number
|
||||
|
||||
if self.bank_party_iban:
|
||||
or_filters["iban"] = self.bank_party_iban
|
||||
@@ -100,7 +103,8 @@ class AutoMatchbyPartyNameDescription:
|
||||
if not (self.bank_party_name or self.description):
|
||||
return None
|
||||
|
||||
return self.match_party_name_desc_in_party()
|
||||
result = self.match_party_name_desc_in_party()
|
||||
return result
|
||||
|
||||
def match_party_name_desc_in_party(self) -> tuple | None:
|
||||
"""Fuzzy search party name and/or description against parties in the system"""
|
||||
@@ -109,8 +113,12 @@ class AutoMatchbyPartyNameDescription:
|
||||
|
||||
for party in parties:
|
||||
filters = {"status": "Active"} if party == "Employee" else {"disabled": 0}
|
||||
field = f"{party.lower()}_name"
|
||||
<<<<<<< HEAD
|
||||
names = frappe.get_all(party, filters=filters, pluck=party.lower() + "_name")
|
||||
=======
|
||||
field = party.lower() + "_name"
|
||||
names = frappe.get_all(party, filters=filters, fields=[f"{field} as party_name", "name"])
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
for field in ["bank_party_name", "description"]:
|
||||
if not self.get(field):
|
||||
@@ -129,15 +137,24 @@ class AutoMatchbyPartyNameDescription:
|
||||
|
||||
def fuzzy_search_and_return_result(self, party, names, field) -> tuple | None:
|
||||
skip = False
|
||||
<<<<<<< HEAD
|
||||
result = process.extract(query=self.get(field), choices=names, scorer=fuzz.token_set_ratio)
|
||||
=======
|
||||
result = process.extract(
|
||||
query=self.get(field),
|
||||
choices={row.get("name"): row.get("party_name") for row in names},
|
||||
scorer=fuzz.token_set_ratio,
|
||||
processor=default_process,
|
||||
)
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
party_name, skip = self.process_fuzzy_result(result)
|
||||
|
||||
return ((party, party_name), skip) if party_name else (None, skip)
|
||||
if not party_name:
|
||||
return None, skip
|
||||
|
||||
return (
|
||||
party,
|
||||
party_name,
|
||||
), skip
|
||||
|
||||
def process_fuzzy_result(self, result: list | None):
|
||||
"""
|
||||
@@ -146,30 +163,42 @@ class AutoMatchbyPartyNameDescription:
|
||||
|
||||
Returns: Result, Skip (whether or not to discontinue matching)
|
||||
"""
|
||||
<<<<<<< HEAD
|
||||
PARTY, SCORE, CUTOFF = 0, 1, 80
|
||||
=======
|
||||
SCORE, PARTY_ID, CUTOFF = 1, 2, 80
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
if not result or not len(result):
|
||||
return None, False
|
||||
|
||||
first_result = result[0]
|
||||
if len(result) == 1:
|
||||
<<<<<<< HEAD
|
||||
return (first_result[PARTY] if first_result[SCORE] > CUTOFF else None), True
|
||||
=======
|
||||
return (first_result[PARTY_ID] if first_result[SCORE] > CUTOFF else None), True
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
second_result = result[1]
|
||||
if first_result[SCORE] > CUTOFF:
|
||||
second_result = result[1]
|
||||
# If multiple matches with the same score, return None but discontinue matching
|
||||
# Matches were found but were too close to distinguish between
|
||||
if first_result[SCORE] == second_result[SCORE]:
|
||||
return None, True
|
||||
|
||||
<<<<<<< HEAD
|
||||
return first_result[PARTY], True
|
||||
=======
|
||||
return first_result[PARTY_ID], True
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
else:
|
||||
return None, False
|
||||
|
||||
|
||||
def get_parties_in_order(deposit: float) -> list:
|
||||
return (
|
||||
["Customer", "Supplier", "Employee"] # most -> least likely to pay us
|
||||
if flt(deposit) > 0
|
||||
else ["Supplier", "Employee", "Customer"] # most -> least likely to receive from us
|
||||
)
|
||||
parties = ["Supplier", "Employee", "Customer"] # most -> least likely to receive
|
||||
if flt(deposit) > 0:
|
||||
parties = ["Customer", "Supplier", "Employee"] # most -> least likely to pay
|
||||
|
||||
return parties
|
||||
|
||||
@@ -2,21 +2,7 @@
|
||||
// For license information, please see license.txt
|
||||
|
||||
frappe.ui.form.on("Bank Transaction", {
|
||||
setup: function (frm) {
|
||||
frm.set_query("party_type", function () {
|
||||
return {
|
||||
filters: {
|
||||
name: ["in", Object.keys(frappe.boot.party_account_types)],
|
||||
},
|
||||
};
|
||||
});
|
||||
|
||||
frm.set_query("bank_account", function () {
|
||||
return {
|
||||
filters: { is_company_account: 1 },
|
||||
};
|
||||
});
|
||||
|
||||
onload(frm) {
|
||||
frm.set_query("payment_document", "payment_entries", function () {
|
||||
const payment_doctypes = frm.events.get_payment_doctypes(frm);
|
||||
return {
|
||||
@@ -25,16 +11,7 @@ frappe.ui.form.on("Bank Transaction", {
|
||||
},
|
||||
};
|
||||
});
|
||||
|
||||
frm.set_query("payment_entry", "payment_entries", function () {
|
||||
return {
|
||||
filters: {
|
||||
docstatus: ["!=", 2],
|
||||
},
|
||||
};
|
||||
});
|
||||
},
|
||||
|
||||
refresh(frm) {
|
||||
if (!frm.is_dirty() && frm.doc.payment_entries.length > 0) {
|
||||
frm.add_custom_button(__("Unreconcile Transaction"), () => {
|
||||
@@ -42,17 +19,51 @@ frappe.ui.form.on("Bank Transaction", {
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
bank_account: function (frm) {
|
||||
set_bank_statement_filter(frm);
|
||||
},
|
||||
|
||||
setup: function (frm) {
|
||||
frm.set_query("party_type", function () {
|
||||
return {
|
||||
filters: {
|
||||
name: ["in", Object.keys(frappe.boot.party_account_types)],
|
||||
},
|
||||
};
|
||||
});
|
||||
},
|
||||
|
||||
get_payment_doctypes: function () {
|
||||
// get payment doctypes from all the apps
|
||||
return ["Payment Entry", "Journal Entry", "Sales Invoice", "Purchase Invoice", "Bank Transaction"];
|
||||
},
|
||||
});
|
||||
|
||||
frappe.ui.form.on("Bank Transaction Payments", {
|
||||
payment_entries_remove: function (frm, cdt, cdn) {
|
||||
update_clearance_date(frm, cdt, cdn);
|
||||
},
|
||||
});
|
||||
|
||||
const update_clearance_date = (frm, cdt, cdn) => {
|
||||
if (frm.doc.docstatus === 1) {
|
||||
frappe
|
||||
.xcall("erpnext.accounts.doctype.bank_transaction.bank_transaction.unclear_reference_payment", {
|
||||
doctype: cdt,
|
||||
docname: cdn,
|
||||
bt_name: frm.doc.name,
|
||||
})
|
||||
.then((e) => {
|
||||
if (e == "success") {
|
||||
frappe.show_alert({
|
||||
message: __("Document {0} successfully uncleared", [e]),
|
||||
indicator: "green",
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
function set_bank_statement_filter(frm) {
|
||||
frm.set_query("bank_statement", function () {
|
||||
return {
|
||||
|
||||
@@ -45,6 +45,7 @@
|
||||
"default": "ACC-BTN-.YYYY.-",
|
||||
"fieldname": "naming_series",
|
||||
"fieldtype": "Select",
|
||||
"hidden": 1,
|
||||
"label": "Series",
|
||||
"no_copy": 1,
|
||||
"options": "ACC-BTN-.YYYY.-",
|
||||
@@ -235,10 +236,9 @@
|
||||
"fieldtype": "Column Break"
|
||||
}
|
||||
],
|
||||
"grid_page_length": 50,
|
||||
"is_submittable": 1,
|
||||
"links": [],
|
||||
"modified": "2025-06-18 17:24:57.044666",
|
||||
"modified": "2023-11-18 18:32:47.203694",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Accounts",
|
||||
"name": "Bank Transaction",
|
||||
@@ -287,10 +287,9 @@
|
||||
"write": 1
|
||||
}
|
||||
],
|
||||
"row_format": "Dynamic",
|
||||
"sort_field": "date",
|
||||
"sort_order": "DESC",
|
||||
"states": [],
|
||||
"title_field": "bank_account",
|
||||
"track_changes": 1
|
||||
}
|
||||
}
|
||||
@@ -5,7 +5,7 @@ import frappe
|
||||
from frappe import _
|
||||
from frappe.model.docstatus import DocStatus
|
||||
from frappe.model.document import Document
|
||||
from frappe.utils import flt, getdate
|
||||
from frappe.utils import flt
|
||||
|
||||
|
||||
class BankTransaction(Document):
|
||||
@@ -84,16 +84,16 @@ class BankTransaction(Document):
|
||||
if not self.payment_entries:
|
||||
return
|
||||
|
||||
references = set()
|
||||
pe = []
|
||||
for row in self.payment_entries:
|
||||
reference = (row.payment_document, row.payment_entry)
|
||||
if reference in references:
|
||||
if reference in pe:
|
||||
frappe.throw(
|
||||
_("{0} {1} is allocated twice in this Bank Transaction").format(
|
||||
row.payment_document, row.payment_entry
|
||||
)
|
||||
)
|
||||
references.add(reference)
|
||||
pe.append(reference)
|
||||
|
||||
def update_allocated_amount(self):
|
||||
allocated_amount = (
|
||||
@@ -104,19 +104,6 @@ class BankTransaction(Document):
|
||||
self.allocated_amount = flt(allocated_amount, self.precision("allocated_amount"))
|
||||
self.unallocated_amount = flt(unallocated_amount, self.precision("unallocated_amount"))
|
||||
|
||||
def delink_old_payment_entries(self):
|
||||
if self.flags.updating_linked_bank_transaction:
|
||||
return
|
||||
|
||||
old_doc = self.get_doc_before_save()
|
||||
payment_entry_names = set(pe.name for pe in self.payment_entries)
|
||||
|
||||
for old_pe in old_doc.payment_entries:
|
||||
if old_pe.name in payment_entry_names:
|
||||
continue
|
||||
|
||||
self.delink_payment_entry(old_pe)
|
||||
|
||||
def before_submit(self):
|
||||
self.allocate_payment_entries()
|
||||
self.set_status()
|
||||
@@ -126,14 +113,13 @@ class BankTransaction(Document):
|
||||
|
||||
def before_update_after_submit(self):
|
||||
self.validate_duplicate_references()
|
||||
self.update_allocated_amount()
|
||||
self.delink_old_payment_entries()
|
||||
self.allocate_payment_entries()
|
||||
self.update_allocated_amount()
|
||||
self.set_status()
|
||||
|
||||
def on_cancel(self):
|
||||
for payment_entry in self.payment_entries:
|
||||
self.delink_payment_entry(payment_entry)
|
||||
self.clear_linked_payment_entry(payment_entry, for_cancel=True)
|
||||
|
||||
self.set_status()
|
||||
|
||||
@@ -166,55 +152,37 @@ class BankTransaction(Document):
|
||||
- 0 > a: Error: already over-allocated
|
||||
- clear means: set the latest transaction date as clearance date
|
||||
"""
|
||||
if self.flags.updating_linked_bank_transaction or not self.payment_entries:
|
||||
return
|
||||
|
||||
remaining_amount = self.unallocated_amount
|
||||
payment_entry_docs = [(pe.payment_document, pe.payment_entry) for pe in self.payment_entries]
|
||||
pe_bt_allocations = get_total_allocated_amount(payment_entry_docs)
|
||||
gl_entries = get_related_bank_gl_entries(payment_entry_docs)
|
||||
gl_bank_account = frappe.db.get_value("Bank Account", self.bank_account, "account")
|
||||
|
||||
for payment_entry in list(self.payment_entries):
|
||||
if payment_entry.allocated_amount != 0:
|
||||
continue
|
||||
|
||||
allocable_amount, should_clear, clearance_date = get_clearance_details(
|
||||
self,
|
||||
payment_entry,
|
||||
pe_bt_allocations.get((payment_entry.payment_document, payment_entry.payment_entry)) or {},
|
||||
gl_entries.get((payment_entry.payment_document, payment_entry.payment_entry)) or {},
|
||||
gl_bank_account,
|
||||
)
|
||||
|
||||
if allocable_amount < 0:
|
||||
frappe.throw(_("Voucher {0} is over-allocated by {1}").format(allocable_amount))
|
||||
|
||||
if remaining_amount <= 0:
|
||||
self.remove(payment_entry)
|
||||
continue
|
||||
|
||||
if allocable_amount == 0:
|
||||
if should_clear:
|
||||
self.clear_linked_payment_entry(payment_entry, clearance_date=clearance_date)
|
||||
self.remove(payment_entry)
|
||||
continue
|
||||
|
||||
should_clear = should_clear and allocable_amount <= remaining_amount
|
||||
payment_entry.allocated_amount = min(allocable_amount, remaining_amount)
|
||||
remaining_amount = flt(
|
||||
remaining_amount - payment_entry.allocated_amount,
|
||||
self.precision("unallocated_amount"),
|
||||
)
|
||||
|
||||
if payment_entry.payment_document == "Bank Transaction":
|
||||
self.update_linked_bank_transaction(
|
||||
payment_entry.payment_entry, payment_entry.allocated_amount
|
||||
to_remove = []
|
||||
for payment_entry in self.payment_entries:
|
||||
if payment_entry.allocated_amount == 0.0:
|
||||
unallocated_amount, should_clear, latest_transaction = get_clearance_details(
|
||||
self, payment_entry
|
||||
)
|
||||
elif should_clear:
|
||||
self.clear_linked_payment_entry(payment_entry, clearance_date=clearance_date)
|
||||
|
||||
self.update_allocated_amount()
|
||||
if 0.0 == unallocated_amount:
|
||||
if should_clear:
|
||||
latest_transaction.clear_linked_payment_entry(payment_entry)
|
||||
to_remove.append(payment_entry)
|
||||
|
||||
elif remaining_amount <= 0.0:
|
||||
to_remove.append(payment_entry)
|
||||
|
||||
elif 0.0 < unallocated_amount <= remaining_amount:
|
||||
payment_entry.allocated_amount = unallocated_amount
|
||||
remaining_amount -= unallocated_amount
|
||||
if should_clear:
|
||||
latest_transaction.clear_linked_payment_entry(payment_entry)
|
||||
|
||||
elif 0.0 < unallocated_amount:
|
||||
payment_entry.allocated_amount = remaining_amount
|
||||
remaining_amount = 0.0
|
||||
|
||||
elif 0.0 > unallocated_amount:
|
||||
frappe.throw(_("Voucher {0} is over-allocated by {1}").format(unallocated_amount))
|
||||
|
||||
for payment_entry in to_remove:
|
||||
self.remove(payment_entry)
|
||||
|
||||
@frappe.whitelist()
|
||||
def remove_payment_entries(self):
|
||||
@@ -225,64 +193,14 @@ class BankTransaction(Document):
|
||||
|
||||
def remove_payment_entry(self, payment_entry):
|
||||
"Clear payment entry and clearance"
|
||||
self.delink_payment_entry(payment_entry)
|
||||
self.clear_linked_payment_entry(payment_entry, for_cancel=True)
|
||||
self.remove(payment_entry)
|
||||
|
||||
def delink_payment_entry(self, payment_entry):
|
||||
if payment_entry.payment_document == "Bank Transaction":
|
||||
self.update_linked_bank_transaction(payment_entry.payment_entry, allocated_amount=None)
|
||||
else:
|
||||
self.clear_linked_payment_entry(payment_entry, clearance_date=None)
|
||||
|
||||
def clear_linked_payment_entry(self, payment_entry, clearance_date=None):
|
||||
doctype = payment_entry.payment_document
|
||||
docname = payment_entry.payment_entry
|
||||
|
||||
# might be a bank transaction
|
||||
if doctype not in get_doctypes_for_bank_reconciliation():
|
||||
return
|
||||
|
||||
if doctype == "Sales Invoice":
|
||||
frappe.db.set_value(
|
||||
"Sales Invoice Payment",
|
||||
dict(parenttype=doctype, parent=docname),
|
||||
"clearance_date",
|
||||
clearance_date,
|
||||
)
|
||||
return
|
||||
|
||||
frappe.db.set_value(doctype, docname, "clearance_date", clearance_date)
|
||||
|
||||
def update_linked_bank_transaction(self, bank_transaction_name, allocated_amount=None):
|
||||
"""For when a second bank transaction has fixed another, e.g. refund"""
|
||||
|
||||
bt = frappe.get_doc(self.doctype, bank_transaction_name)
|
||||
if allocated_amount:
|
||||
bt.append(
|
||||
"payment_entries",
|
||||
{
|
||||
"payment_document": self.doctype,
|
||||
"payment_entry": self.name,
|
||||
"allocated_amount": allocated_amount,
|
||||
},
|
||||
)
|
||||
|
||||
else:
|
||||
pe = next(
|
||||
(
|
||||
pe
|
||||
for pe in bt.payment_entries
|
||||
if pe.payment_document == self.doctype and pe.payment_entry == self.name
|
||||
),
|
||||
None,
|
||||
)
|
||||
if not pe:
|
||||
return
|
||||
|
||||
bt.flags.updating_linked_bank_transaction = True
|
||||
bt.remove(pe)
|
||||
|
||||
bt.save()
|
||||
def clear_linked_payment_entry(self, payment_entry, for_cancel=False):
|
||||
clearance_date = None if for_cancel else self.date
|
||||
set_voucher_clearance(
|
||||
payment_entry.payment_document, payment_entry.payment_entry, clearance_date, self
|
||||
)
|
||||
|
||||
def auto_set_party(self):
|
||||
from erpnext.accounts.doctype.bank_transaction.auto_match_party import AutoMatchParty
|
||||
@@ -314,147 +232,195 @@ def get_doctypes_for_bank_reconciliation():
|
||||
return frappe.get_hooks("bank_reconciliation_doctypes")
|
||||
|
||||
|
||||
def get_clearance_details(transaction, payment_entry, bt_allocations, gl_entries, gl_bank_account):
|
||||
def get_clearance_details(transaction, payment_entry):
|
||||
"""
|
||||
There should only be one bank gl entry for a voucher, except for JE.
|
||||
For JE, there can be multiple bank gl entries for the same account.
|
||||
In this case, the allocable_amount will be the sum of amounts of all gl entries of the account.
|
||||
There will be no gl entry for a Bank Transaction so return the unallocated amount.
|
||||
Should only clear the voucher if all bank gl entries are allocated.
|
||||
There should only be one bank gle for a voucher.
|
||||
Could be none for a Bank Transaction.
|
||||
But if a JE, could affect two banks.
|
||||
Should only clear the voucher if all bank gles are allocated.
|
||||
"""
|
||||
gl_bank_account = frappe.db.get_value("Bank Account", transaction.bank_account, "account")
|
||||
gles = get_related_bank_gl_entries(payment_entry.payment_document, payment_entry.payment_entry)
|
||||
bt_allocations = get_total_allocated_amount(payment_entry.payment_document, payment_entry.payment_entry)
|
||||
|
||||
transaction_date = getdate(transaction.date)
|
||||
|
||||
if payment_entry.payment_document == "Bank Transaction":
|
||||
bt = frappe.db.get_value(
|
||||
"Bank Transaction",
|
||||
payment_entry.payment_entry,
|
||||
("unallocated_amount", "bank_account"),
|
||||
as_dict=True,
|
||||
)
|
||||
|
||||
if bt.bank_account != gl_bank_account:
|
||||
frappe.throw(
|
||||
_("Bank Account {} in Bank Transaction {} is not matching with Bank Account {}").format(
|
||||
bt.bank_account, payment_entry.payment_entry, gl_bank_account
|
||||
unallocated_amount = min(
|
||||
transaction.unallocated_amount,
|
||||
get_paid_amount(payment_entry, transaction.currency, gl_bank_account),
|
||||
)
|
||||
unmatched_gles = len(gles)
|
||||
latest_transaction = transaction
|
||||
for gle in gles:
|
||||
if gle["gl_account"] == gl_bank_account:
|
||||
if gle["amount"] <= 0.0:
|
||||
frappe.throw(
|
||||
_("Voucher {0} value is broken: {1}").format(payment_entry.payment_entry, gle["amount"])
|
||||
)
|
||||
)
|
||||
|
||||
return abs(bt.unallocated_amount), True, transaction_date
|
||||
unmatched_gles -= 1
|
||||
unallocated_amount = gle["amount"]
|
||||
for a in bt_allocations:
|
||||
if a["gl_account"] == gle["gl_account"]:
|
||||
unallocated_amount = gle["amount"] - a["total"]
|
||||
if frappe.utils.getdate(transaction.date) < a["latest_date"]:
|
||||
latest_transaction = frappe.get_doc("Bank Transaction", a["latest_name"])
|
||||
else:
|
||||
# Must be a Journal Entry affecting more than one bank
|
||||
for a in bt_allocations:
|
||||
if a["gl_account"] == gle["gl_account"] and a["total"] == gle["amount"]:
|
||||
unmatched_gles -= 1
|
||||
|
||||
if gl_bank_account not in gl_entries:
|
||||
frappe.throw(
|
||||
_("{} {} is not affecting bank account {}").format(
|
||||
payment_entry.payment_document, payment_entry.payment_entry, gl_bank_account
|
||||
)
|
||||
)
|
||||
|
||||
allocable_amount = gl_entries.pop(gl_bank_account) or 0
|
||||
if allocable_amount <= 0.0:
|
||||
frappe.throw(
|
||||
_("Invalid amount in accounting entries of {} {} for Account {}: {}").format(
|
||||
payment_entry.payment_document, payment_entry.payment_entry, gl_bank_account, allocable_amount
|
||||
)
|
||||
)
|
||||
|
||||
matching_bt_allocaion = bt_allocations.pop(gl_bank_account, {})
|
||||
|
||||
allocable_amount = flt(
|
||||
allocable_amount - matching_bt_allocaion.get("total", 0), transaction.precision("unallocated_amount")
|
||||
)
|
||||
|
||||
should_clear = all(
|
||||
gl_entries[gle_account] == bt_allocations.get(gle_account, {}).get("total", 0)
|
||||
for gle_account in gl_entries
|
||||
)
|
||||
|
||||
bt_allocation_date = matching_bt_allocaion.get("latest_date", None)
|
||||
clearance_date = transaction_date if not bt_allocation_date else max(transaction_date, bt_allocation_date)
|
||||
|
||||
return allocable_amount, should_clear, clearance_date
|
||||
return unallocated_amount, unmatched_gles == 0, latest_transaction
|
||||
|
||||
|
||||
def get_related_bank_gl_entries(docs):
|
||||
def get_related_bank_gl_entries(doctype, docname):
|
||||
# nosemgrep: frappe-semgrep-rules.rules.frappe-using-db-sql
|
||||
if not docs:
|
||||
return {}
|
||||
|
||||
result = frappe.db.sql(
|
||||
return frappe.db.sql(
|
||||
"""
|
||||
SELECT
|
||||
gle.voucher_type AS doctype,
|
||||
gle.voucher_no AS docname,
|
||||
gle.account AS gl_account,
|
||||
SUM(ABS(gle.credit_in_account_currency - gle.debit_in_account_currency)) AS amount
|
||||
FROM
|
||||
`tabGL Entry` gle
|
||||
LEFT JOIN
|
||||
`tabAccount` ac ON ac.name = gle.account
|
||||
WHERE
|
||||
ac.account_type = 'Bank'
|
||||
AND (gle.voucher_type, gle.voucher_no) IN %(docs)s
|
||||
AND gle.is_cancelled = 0
|
||||
GROUP BY
|
||||
gle.voucher_type, gle.voucher_no, gle.account
|
||||
""",
|
||||
{"docs": docs},
|
||||
SELECT
|
||||
ABS(gle.credit_in_account_currency - gle.debit_in_account_currency) AS amount,
|
||||
gle.account AS gl_account
|
||||
FROM
|
||||
`tabGL Entry` gle
|
||||
LEFT JOIN
|
||||
`tabAccount` ac ON ac.name=gle.account
|
||||
WHERE
|
||||
ac.account_type = 'Bank'
|
||||
AND gle.voucher_type = %(doctype)s
|
||||
AND gle.voucher_no = %(docname)s
|
||||
AND is_cancelled = 0
|
||||
""",
|
||||
dict(doctype=doctype, docname=docname),
|
||||
as_dict=True,
|
||||
)
|
||||
|
||||
entries = {}
|
||||
for row in result:
|
||||
key = (row["doctype"], row["docname"])
|
||||
if key not in entries:
|
||||
entries[key] = {}
|
||||
entries[key][row["gl_account"]] = row["amount"]
|
||||
|
||||
return entries
|
||||
|
||||
|
||||
def get_total_allocated_amount(docs):
|
||||
def get_total_allocated_amount(doctype, docname):
|
||||
"""
|
||||
Gets the sum of allocations for a voucher on each bank GL account
|
||||
along with the latest bank transaction date
|
||||
along with the latest bank transaction name & date
|
||||
NOTE: query may also include just saved vouchers/payments but with zero allocated_amount
|
||||
"""
|
||||
if not docs:
|
||||
return {}
|
||||
|
||||
# nosemgrep: frappe-semgrep-rules.rules.frappe-using-db-sql
|
||||
result = frappe.db.sql(
|
||||
"""
|
||||
SELECT total, latest_date, gl_account, payment_document, payment_entry FROM (
|
||||
SELECT total, latest_name, latest_date, gl_account FROM (
|
||||
SELECT
|
||||
ROW_NUMBER() OVER w AS rownum,
|
||||
SUM(btp.allocated_amount) OVER(PARTITION BY ba.account, btp.payment_document, btp.payment_entry) AS total,
|
||||
SUM(btp.allocated_amount) OVER(PARTITION BY ba.account) AS total,
|
||||
FIRST_VALUE(bt.name) OVER w AS latest_name,
|
||||
FIRST_VALUE(bt.date) OVER w AS latest_date,
|
||||
ba.account AS gl_account,
|
||||
btp.payment_document,
|
||||
btp.payment_entry
|
||||
ba.account AS gl_account
|
||||
FROM
|
||||
`tabBank Transaction Payments` btp
|
||||
LEFT JOIN `tabBank Transaction` bt ON bt.name=btp.parent
|
||||
LEFT JOIN `tabBank Account` ba ON ba.name=bt.bank_account
|
||||
WHERE
|
||||
(btp.payment_document, btp.payment_entry) IN %(docs)s
|
||||
btp.payment_document = %(doctype)s
|
||||
AND btp.payment_entry = %(docname)s
|
||||
AND bt.docstatus = 1
|
||||
WINDOW w AS (PARTITION BY ba.account, btp.payment_document, btp.payment_entry ORDER BY bt.date DESC)
|
||||
WINDOW w AS (PARTITION BY ba.account ORDER BY bt.date desc)
|
||||
) temp
|
||||
WHERE
|
||||
rownum = 1
|
||||
""",
|
||||
dict(docs=docs),
|
||||
dict(doctype=doctype, docname=docname),
|
||||
as_dict=True,
|
||||
)
|
||||
|
||||
payment_allocation_details = {}
|
||||
for row in result:
|
||||
row["latest_date"] = getdate(row["latest_date"])
|
||||
payment_allocation_details.setdefault((row["payment_document"], row["payment_entry"]), {})[
|
||||
row["gl_account"]
|
||||
] = row
|
||||
# Why is this *sometimes* a byte string?
|
||||
if isinstance(row["latest_name"], bytes):
|
||||
row["latest_name"] = row["latest_name"].decode()
|
||||
row["latest_date"] = frappe.utils.getdate(row["latest_date"])
|
||||
return result
|
||||
|
||||
return payment_allocation_details
|
||||
|
||||
def get_paid_amount(payment_entry, currency, gl_bank_account):
|
||||
if payment_entry.payment_document in ["Payment Entry", "Sales Invoice", "Purchase Invoice"]:
|
||||
paid_amount_field = "paid_amount"
|
||||
if payment_entry.payment_document == "Payment Entry":
|
||||
doc = frappe.get_doc("Payment Entry", payment_entry.payment_entry)
|
||||
|
||||
if doc.payment_type == "Receive":
|
||||
paid_amount_field = (
|
||||
"received_amount" if doc.paid_to_account_currency == currency else "base_received_amount"
|
||||
)
|
||||
elif doc.payment_type == "Pay":
|
||||
paid_amount_field = (
|
||||
"paid_amount" if doc.paid_from_account_currency == currency else "base_paid_amount"
|
||||
)
|
||||
|
||||
return frappe.db.get_value(
|
||||
payment_entry.payment_document, payment_entry.payment_entry, paid_amount_field
|
||||
)
|
||||
|
||||
elif payment_entry.payment_document == "Journal Entry":
|
||||
return abs(
|
||||
frappe.db.get_value(
|
||||
"Journal Entry Account",
|
||||
{"parent": payment_entry.payment_entry, "account": gl_bank_account},
|
||||
"sum(debit_in_account_currency-credit_in_account_currency)",
|
||||
)
|
||||
or 0
|
||||
)
|
||||
|
||||
elif payment_entry.payment_document == "Expense Claim":
|
||||
return frappe.db.get_value(
|
||||
payment_entry.payment_document, payment_entry.payment_entry, "total_amount_reimbursed"
|
||||
)
|
||||
|
||||
elif payment_entry.payment_document == "Loan Disbursement":
|
||||
return frappe.db.get_value(
|
||||
payment_entry.payment_document, payment_entry.payment_entry, "disbursed_amount"
|
||||
)
|
||||
|
||||
elif payment_entry.payment_document == "Loan Repayment":
|
||||
return frappe.db.get_value(payment_entry.payment_document, payment_entry.payment_entry, "amount_paid")
|
||||
|
||||
elif payment_entry.payment_document == "Bank Transaction":
|
||||
dep, wth = frappe.db.get_value(
|
||||
"Bank Transaction", payment_entry.payment_entry, ("deposit", "withdrawal")
|
||||
)
|
||||
return abs(flt(wth) - flt(dep))
|
||||
|
||||
else:
|
||||
frappe.throw(
|
||||
f"Please reconcile {payment_entry.payment_document}: {payment_entry.payment_entry} manually"
|
||||
)
|
||||
|
||||
|
||||
def set_voucher_clearance(doctype, docname, clearance_date, self):
|
||||
if doctype in get_doctypes_for_bank_reconciliation():
|
||||
if (
|
||||
doctype == "Payment Entry"
|
||||
and frappe.db.get_value("Payment Entry", docname, "payment_type") == "Internal Transfer"
|
||||
and len(get_reconciled_bank_transactions(doctype, docname)) < 2
|
||||
):
|
||||
return
|
||||
|
||||
if doctype == "Sales Invoice":
|
||||
frappe.db.set_value(
|
||||
"Sales Invoice Payment",
|
||||
dict(parenttype=doctype, parent=docname),
|
||||
"clearance_date",
|
||||
clearance_date,
|
||||
)
|
||||
return
|
||||
|
||||
frappe.db.set_value(doctype, docname, "clearance_date", clearance_date)
|
||||
|
||||
elif doctype == "Bank Transaction":
|
||||
# For when a second bank transaction has fixed another, e.g. refund
|
||||
bt = frappe.get_doc(doctype, docname)
|
||||
if clearance_date:
|
||||
vouchers = [{"payment_doctype": "Bank Transaction", "payment_name": self.name}]
|
||||
bt.add_payment_entries(vouchers)
|
||||
bt.save()
|
||||
else:
|
||||
for pe in bt.payment_entries:
|
||||
if pe.payment_document == self.doctype and pe.payment_entry == self.name:
|
||||
bt.remove(pe)
|
||||
bt.save()
|
||||
break
|
||||
|
||||
|
||||
def get_reconciled_bank_transactions(doctype, docname):
|
||||
@@ -465,6 +431,13 @@ def get_reconciled_bank_transactions(doctype, docname):
|
||||
)
|
||||
|
||||
|
||||
@frappe.whitelist()
|
||||
def unclear_reference_payment(doctype, docname, bt_name):
|
||||
bt = frappe.get_doc("Bank Transaction", bt_name)
|
||||
set_voucher_clearance(doctype, docname, None, bt)
|
||||
return docname
|
||||
|
||||
|
||||
def remove_from_bank_transaction(doctype, docname):
|
||||
"""Remove a (cancelled) voucher from all Bank Transactions."""
|
||||
for bt_name in get_reconciled_bank_transactions(doctype, docname):
|
||||
|
||||
@@ -2,13 +2,30 @@
|
||||
# License: GNU General Public License v3. See license.txt
|
||||
|
||||
import frappe
|
||||
<<<<<<< HEAD
|
||||
from frappe.tests.utils import FrappeTestCase
|
||||
=======
|
||||
from frappe.tests import IntegrationTestCase, UnitTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
from frappe.utils import nowdate
|
||||
|
||||
from erpnext.accounts.doctype.bank_transaction.test_bank_transaction import create_bank_account
|
||||
|
||||
|
||||
<<<<<<< HEAD
|
||||
class TestAutoMatchParty(FrappeTestCase):
|
||||
=======
|
||||
class UnitTestBankTransaction(UnitTestCase):
|
||||
"""
|
||||
Unit tests for BankTransaction.
|
||||
Use this class for testing individual functions and methods.
|
||||
"""
|
||||
|
||||
pass
|
||||
|
||||
|
||||
class TestAutoMatchParty(IntegrationTestCase):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
create_bank_account()
|
||||
|
||||
@@ -6,21 +6,23 @@ import json
|
||||
import frappe
|
||||
from frappe import utils
|
||||
from frappe.model.docstatus import DocStatus
|
||||
<<<<<<< HEAD
|
||||
from frappe.tests.utils import FrappeTestCase
|
||||
=======
|
||||
from frappe.tests import IntegrationTestCase, UnitTestCase
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
|
||||
from erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool import (
|
||||
get_linked_payments,
|
||||
reconcile_vouchers,
|
||||
)
|
||||
from erpnext.accounts.doctype.mode_of_payment.test_mode_of_payment import (
|
||||
set_default_account_for_mode_of_payment,
|
||||
)
|
||||
from erpnext.accounts.doctype.payment_entry.test_payment_entry import get_payment_entry
|
||||
from erpnext.accounts.doctype.pos_profile.test_pos_profile import make_pos_profile
|
||||
from erpnext.accounts.doctype.purchase_invoice.test_purchase_invoice import make_purchase_invoice
|
||||
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
|
||||
from erpnext.tests.utils import if_lending_app_installed
|
||||
|
||||
<<<<<<< HEAD
|
||||
test_dependencies = ["Item", "Cost Center"]
|
||||
|
||||
|
||||
@@ -34,6 +36,22 @@ class TestBankTransaction(FrappeTestCase):
|
||||
]:
|
||||
frappe.db.delete(dt)
|
||||
clear_loan_transactions()
|
||||
=======
|
||||
EXTRA_TEST_RECORD_DEPENDENCIES = ["Item", "Cost Center"]
|
||||
|
||||
|
||||
class UnitTestBankTransaction(UnitTestCase):
|
||||
"""
|
||||
Unit tests for BankTransaction.
|
||||
Use this class for testing individual functions and methods.
|
||||
"""
|
||||
|
||||
pass
|
||||
|
||||
|
||||
class TestBankTransaction(IntegrationTestCase):
|
||||
def setUp(self):
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
make_pos_profile()
|
||||
|
||||
# generate and use a uniq hash identifier for 'Bank Account' and it's linked GL 'Account' to avoid validation error
|
||||
@@ -225,11 +243,14 @@ class TestBankTransaction(FrappeTestCase):
|
||||
self.assertEqual(linked_payments[0]["name"], repayment_entry.name)
|
||||
|
||||
|
||||
<<<<<<< HEAD
|
||||
@if_lending_app_installed
|
||||
def clear_loan_transactions():
|
||||
frappe.db.delete("Loan Repayment")
|
||||
|
||||
|
||||
=======
|
||||
>>>>>>> 94d7e5964b (fix: add doc.status to translation from POS)
|
||||
def create_bank_account(
|
||||
bank_name="Citi Bank", gl_account="_Test Bank - _TC", bank_account_name="Checking Account"
|
||||
):
|
||||
@@ -437,13 +458,15 @@ def add_vouchers(gl_account="_Test Bank - _TC"):
|
||||
except frappe.DuplicateEntryError:
|
||||
pass
|
||||
|
||||
mode_of_payment = frappe.get_doc({"doctype": "Mode of Payment", "name": "Wire Transfer"})
|
||||
mode_of_payment = frappe.get_doc({"doctype": "Mode of Payment", "name": "Cash"})
|
||||
|
||||
set_default_account_for_mode_of_payment(mode_of_payment, "_Test Company", gl_account)
|
||||
if not frappe.db.get_value("Mode of Payment Account", {"company": "_Test Company", "parent": "Cash"}):
|
||||
mode_of_payment.append("accounts", {"company": "_Test Company", "default_account": gl_account})
|
||||
mode_of_payment.save()
|
||||
|
||||
si = create_sales_invoice(customer="Fayva", qty=1, rate=109080, do_not_save=1)
|
||||
si.is_pos = 1
|
||||
si.append("payments", {"mode_of_payment": "Wire Transfer", "amount": 109080})
|
||||
si.append("payments", {"mode_of_payment": "Cash", "account": gl_account, "amount": 109080})
|
||||
si.insert()
|
||||
si.submit()
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user