Compare commits
1582 Commits
v15.6.1
...
skip_enque
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b189fc46b0 | ||
|
|
58e1548640 | ||
|
|
b660d98f20 | ||
|
|
dee49e6078 | ||
|
|
f4d69f16c0 | ||
|
|
c5b94df188 | ||
|
|
0b100782e2 | ||
|
|
ec74a5e566 | ||
|
|
2c16036ef3 | ||
|
|
1f4c86136f | ||
|
|
b0fcb014c1 | ||
|
|
65c8605b88 | ||
|
|
4c6d28a299 | ||
|
|
962b51d6d5 | ||
|
|
9702a65a0f | ||
|
|
d69c593f93 | ||
|
|
1e09f584d5 | ||
|
|
0d6afda6b8 | ||
|
|
ac1961b687 | ||
|
|
c0a1f298a1 | ||
|
|
55b9664115 | ||
|
|
68baa3612a | ||
|
|
01856a6e9d | ||
|
|
65a2f3d12c | ||
|
|
d0e0b66b2f | ||
|
|
4b38139b44 | ||
|
|
898c6e30eb | ||
|
|
cef6291311 | ||
|
|
a93d14b3f7 | ||
|
|
48da952fd7 | ||
|
|
e178ffc3c1 | ||
|
|
1eaa386657 | ||
|
|
171b8af3ee | ||
|
|
031465f5ec | ||
|
|
f44a841af7 | ||
|
|
28ac53a704 | ||
|
|
bdc0175fe3 | ||
|
|
e58c2dd43d | ||
|
|
092999f2a6 | ||
|
|
e52c4c8f22 | ||
|
|
d9a0494fc3 | ||
|
|
cb2529cec8 | ||
|
|
158112896e | ||
|
|
9d9b83362a | ||
|
|
9904a9868c | ||
|
|
34051bc04f | ||
|
|
8e2f9787c1 | ||
|
|
6379238893 | ||
|
|
031b99f373 | ||
|
|
51909077bd | ||
|
|
d0140412cd | ||
|
|
e7d707797a | ||
|
|
f2f5c1a0eb | ||
|
|
ceee93e0e8 | ||
|
|
ed95d41a51 | ||
|
|
eaac02655b | ||
|
|
72ac56b6c4 | ||
|
|
e017421708 | ||
|
|
13b05aa7fb | ||
|
|
a5232d9c10 | ||
|
|
8a5078b826 | ||
|
|
5b67631d40 | ||
|
|
0aa72f841d | ||
|
|
b8dac84a90 | ||
|
|
79c492cc4b | ||
|
|
a8eb5e5c85 | ||
|
|
863abc3ee5 | ||
|
|
93c2762f7b | ||
|
|
c067ac16a7 | ||
|
|
5e736f0d06 | ||
|
|
983f71975a | ||
|
|
b235f48067 | ||
|
|
9d3614597c | ||
|
|
3c19186654 | ||
|
|
646e9ca0dd | ||
|
|
3327599c9d | ||
|
|
dd70fb5f7e | ||
|
|
ac2b53bf15 | ||
|
|
5c47087f20 | ||
|
|
29f91a7919 | ||
|
|
f6fdfd2c01 | ||
|
|
24dcd64c16 | ||
|
|
9dcdd5b5ef | ||
|
|
fea20db262 | ||
|
|
043d9e3986 | ||
|
|
dde4d9e53c | ||
|
|
36a0569df2 | ||
|
|
f8ba560394 | ||
|
|
93170a56a9 | ||
|
|
6f5815e44f | ||
|
|
0c52eb913b | ||
|
|
519682bb0e | ||
|
|
694c17487d | ||
|
|
5b8b40c13b | ||
|
|
ceeb8fc9e5 | ||
|
|
b193fafe49 | ||
|
|
c310da7b29 | ||
|
|
d6b29d1cd7 | ||
|
|
303433c0ae | ||
|
|
20fa3da950 | ||
|
|
bc9c480246 | ||
|
|
8aa2b7c183 | ||
|
|
08caa7cfa1 | ||
|
|
5885978fc2 | ||
|
|
122373fcd3 | ||
|
|
1f01ff3487 | ||
|
|
c9e2f03a3a | ||
|
|
924b08e395 | ||
|
|
461fb183fc | ||
|
|
c9ff769d28 | ||
|
|
3658c4754f | ||
|
|
9c8d103d8a | ||
|
|
6d40844894 | ||
|
|
81dbfe189e | ||
|
|
75f8464724 | ||
|
|
e240ccd305 | ||
|
|
3c3c57c674 | ||
|
|
c42444ab3b | ||
|
|
bf6e32a960 | ||
|
|
9f6535472d | ||
|
|
7cb07425b1 | ||
|
|
4c9048fb39 | ||
|
|
f4222be027 | ||
|
|
44ed52c5cf | ||
|
|
8aaddb0f9e | ||
|
|
635174f1ce | ||
|
|
406793a6ff | ||
|
|
7566c1ee78 | ||
|
|
97c3e27c60 | ||
|
|
467c0898e9 | ||
|
|
26ec697a0b | ||
|
|
3294282880 | ||
|
|
a823f16dff | ||
|
|
339698d172 | ||
|
|
dd23ddcd6c | ||
|
|
20eff568b1 | ||
|
|
3634c4c284 | ||
|
|
2e0aaf3521 | ||
|
|
6249965605 | ||
|
|
a9f8af2fd1 | ||
|
|
6d43d46fbc | ||
|
|
4288713abe | ||
|
|
b03c683898 | ||
|
|
c5050c935b | ||
|
|
e2d16955dd | ||
|
|
5a3b133d65 | ||
|
|
146c5b3e16 | ||
|
|
c1e1fd8829 | ||
|
|
da184d709b | ||
|
|
864d7ae04c | ||
|
|
0b04d04da3 | ||
|
|
6707425baa | ||
|
|
6cfb8fe439 | ||
|
|
45b25e09c1 | ||
|
|
38e88db2c9 | ||
|
|
87df7ff717 | ||
|
|
4c061d61fa | ||
|
|
a73ba2c0d2 | ||
|
|
ecd83b12ab | ||
|
|
408ea0432b | ||
|
|
11f4cb914a | ||
|
|
66bf6e4041 | ||
|
|
f37f7ca5c3 | ||
|
|
85471533e9 | ||
|
|
4b24fcd221 | ||
|
|
68a23730f3 | ||
|
|
17f85de6fb | ||
|
|
8e7d47b3a7 | ||
|
|
133f8bd92a | ||
|
|
d4264f7ba1 | ||
|
|
fa1113f912 | ||
|
|
e8ae4ed61d | ||
|
|
a4cbfabe0e | ||
|
|
9cb83d2198 | ||
|
|
e25b4e24df | ||
|
|
4f23d88f62 | ||
|
|
0bbf45cd8b | ||
|
|
2ff06af154 | ||
|
|
9c0755d3de | ||
|
|
701671b2bd | ||
|
|
4d7d7dac01 | ||
|
|
f04676aaed | ||
|
|
0d260faa00 | ||
|
|
44538bd02a | ||
|
|
75230ece9a | ||
|
|
f99f7fd2cf | ||
|
|
cc83af0dd4 | ||
|
|
028d31a6f9 | ||
|
|
3f1d008741 | ||
|
|
0b3ecd24e2 | ||
|
|
506fefa186 | ||
|
|
a995e87567 | ||
|
|
fa4ea7c96d | ||
|
|
dc9115a586 | ||
|
|
f3bd53193d | ||
|
|
8a702a6338 | ||
|
|
8360339119 | ||
|
|
799794cafb | ||
|
|
2fb0499923 | ||
|
|
230a7d8d53 | ||
|
|
b1dfa2537b | ||
|
|
1a8f7f9403 | ||
|
|
d0df5df4a6 | ||
|
|
6239fd704b | ||
|
|
b124081065 | ||
|
|
4bef6707ec | ||
|
|
76023f1fdc | ||
|
|
f1f8f59bdb | ||
|
|
24ba26fef3 | ||
|
|
e6949d71f6 | ||
|
|
e3bd8d10b0 | ||
|
|
d80ca523a4 | ||
|
|
22291d32e6 | ||
|
|
5df5851798 | ||
|
|
1d1cb86c75 | ||
|
|
1c2a7801b7 | ||
|
|
55e66db315 | ||
|
|
094ecc1f62 | ||
|
|
2b1e0d3bd0 | ||
|
|
d97b6d38ef | ||
|
|
b966c06a4f | ||
|
|
2ee642fb2c | ||
|
|
4b1c851da1 | ||
|
|
39067c7614 | ||
|
|
aa1c69dd7a | ||
|
|
e5824fc3f1 | ||
|
|
d59caf08e6 | ||
|
|
186cc3d748 | ||
|
|
a2a8a8f2e0 | ||
|
|
17452b7693 | ||
|
|
8c85404191 | ||
|
|
159a123dc7 | ||
|
|
1568af2a7b | ||
|
|
1745371cd6 | ||
|
|
ecdc4c8e9b | ||
|
|
5cf0759b0c | ||
|
|
61a29eb5fb | ||
|
|
8bb83e267c | ||
|
|
781bdd2ec9 | ||
|
|
2d78dba66f | ||
|
|
2c8e4c1ab3 | ||
|
|
22a187c3be | ||
|
|
2f676ced5c | ||
|
|
e9251c3775 | ||
|
|
294f562fb9 | ||
|
|
81e82b0595 | ||
|
|
a8ebc94a36 | ||
|
|
33efe0d12d | ||
|
|
31a8c3bdc4 | ||
|
|
0549535603 | ||
|
|
50f54d983d | ||
|
|
146147316d | ||
|
|
ab9d6576d0 | ||
|
|
32ccf3524a | ||
|
|
d6d91257b6 | ||
|
|
40ce0c851d | ||
|
|
76b57a4338 | ||
|
|
0e5b4e5f07 | ||
|
|
fb330d1b5a | ||
|
|
9636458ae1 | ||
|
|
4671f65cbd | ||
|
|
9383f5da94 | ||
|
|
01650120d4 | ||
|
|
943dcb6dea | ||
|
|
3a26823c62 | ||
|
|
e55611497b | ||
|
|
798a0510e6 | ||
|
|
e38b46300c | ||
|
|
41f58476e1 | ||
|
|
56e5611337 | ||
|
|
2e509f69d4 | ||
|
|
ee14faaa39 | ||
|
|
ae4ebcd987 | ||
|
|
1bfbbfe393 | ||
|
|
1fa6233377 | ||
|
|
c1e869f040 | ||
|
|
3b671d5875 | ||
|
|
c5770f2ecc | ||
|
|
ff3ca50a4b | ||
|
|
cc96d2b50c | ||
|
|
4d614c1589 | ||
|
|
27d6c8b6d5 | ||
|
|
61ded697a7 | ||
|
|
5ce5c352e4 | ||
|
|
6e6c818084 | ||
|
|
b834ed10d6 | ||
|
|
25c2b79864 | ||
|
|
7a04f0f7ba | ||
|
|
b70f3de16b | ||
|
|
955098c4c0 | ||
|
|
675a0b810f | ||
|
|
d7e4a6be13 | ||
|
|
617d923f0d | ||
|
|
407045a1de | ||
|
|
d73e42fc41 | ||
|
|
9fafc83632 | ||
|
|
c81d597ca5 | ||
|
|
50cff656b4 | ||
|
|
d9a72c1e61 | ||
|
|
322cdbaccf | ||
|
|
a9a2ec81de | ||
|
|
93259cab1d | ||
|
|
7efb5a8cb5 | ||
|
|
c18ff5bd25 | ||
|
|
f7face43cd | ||
|
|
2caa2d677c | ||
|
|
6d87cfeb8d | ||
|
|
2693fcb446 | ||
|
|
7c6a5a0f23 | ||
|
|
1e15a3cc15 | ||
|
|
d78a1e7814 | ||
|
|
12affa70cf | ||
|
|
78483e2ee6 | ||
|
|
e9fe10c6f1 | ||
|
|
518b06c8eb | ||
|
|
27b557bef9 | ||
|
|
beff566c82 | ||
|
|
affca3a519 | ||
|
|
c077eda64e | ||
|
|
772f540bef | ||
|
|
951023f434 | ||
|
|
5e71d6ac4e | ||
|
|
7475233fa6 | ||
|
|
0c9572bb48 | ||
|
|
6b8f046fb4 | ||
|
|
1ff473b615 | ||
|
|
cfd1666181 | ||
|
|
0c6c650c08 | ||
|
|
31f586f716 | ||
|
|
6fea9d6dfe | ||
|
|
212d656d85 | ||
|
|
9a705169fd | ||
|
|
00a915b741 | ||
|
|
ae7be84d87 | ||
|
|
f8a9554bbd | ||
|
|
d86186ec47 | ||
|
|
3fd43cd6bb | ||
|
|
12a4f2761c | ||
|
|
e9dfb45fca | ||
|
|
b14886b227 | ||
|
|
2e49423d3f | ||
|
|
ddecbeba75 | ||
|
|
2e5d716408 | ||
|
|
bdca718103 | ||
|
|
8bdc760733 | ||
|
|
6f2fae1b61 | ||
|
|
91b913b5bb | ||
|
|
5cf47ae5f9 | ||
|
|
a673220feb | ||
|
|
4e182b89ce | ||
|
|
68c997aa06 | ||
|
|
866df9f1c7 | ||
|
|
079cd30b9c | ||
|
|
49cb11c1f3 | ||
|
|
efade9b9ae | ||
|
|
2a46799188 | ||
|
|
50d56db0c2 | ||
|
|
16404110a8 | ||
|
|
6a63a8997d | ||
|
|
88ff945e40 | ||
|
|
8f6c23cb53 | ||
|
|
4c197c8dbd | ||
|
|
f2891229ab | ||
|
|
2486b646a1 | ||
|
|
8fdc244e16 | ||
|
|
5be868c7f6 | ||
|
|
67d828dab3 | ||
|
|
7b37389115 | ||
|
|
0de4197c88 | ||
|
|
92649de5c6 | ||
|
|
3e59c66806 | ||
|
|
fc677811b7 | ||
|
|
19ff10dfeb | ||
|
|
4173203382 | ||
|
|
dbd4dae3d9 | ||
|
|
99b839d2b6 | ||
|
|
30cc65d2b7 | ||
|
|
722ee53fb1 | ||
|
|
6173b34b10 | ||
|
|
f7a3af7473 | ||
|
|
d491036f2d | ||
|
|
d2057588dd | ||
|
|
2bdfdeeb9a | ||
|
|
be074a2972 | ||
|
|
2b3cc5ba2d | ||
|
|
06f48c678b | ||
|
|
53b44ccf29 | ||
|
|
69db569ca5 | ||
|
|
7f8303a493 | ||
|
|
dfda5ad673 | ||
|
|
1e89c1c875 | ||
|
|
d1fb90edff | ||
|
|
4f215f1b70 | ||
|
|
3f383d81bd | ||
|
|
c0a1188067 | ||
|
|
ca02dfa652 | ||
|
|
7d3240ae3a | ||
|
|
93681cfa24 | ||
|
|
4f1e729b7c | ||
|
|
735576ab27 | ||
|
|
23199a3271 | ||
|
|
64cb1153de | ||
|
|
9fcd89d456 | ||
|
|
4a4c4ba21b | ||
|
|
030d35628d | ||
|
|
a552df8a9f | ||
|
|
b127aa308e | ||
|
|
02028becb3 | ||
|
|
764f3422a0 | ||
|
|
236c7e1e95 | ||
|
|
9f1ddeb4e4 | ||
|
|
b046d980ad | ||
|
|
806696a003 | ||
|
|
77b044f1a6 | ||
|
|
7a6a789199 | ||
|
|
252fae68df | ||
|
|
e5a5b6afc8 | ||
|
|
ffd38362d5 | ||
|
|
7a7a213285 | ||
|
|
34ec2f8a2b | ||
|
|
4832175341 | ||
|
|
3c7e7a76f0 | ||
|
|
3815f07c33 | ||
|
|
ebaa5d3add | ||
|
|
0d7dd93284 | ||
|
|
9b4e757b0b | ||
|
|
8de03ef836 | ||
|
|
bd6a4ca1d7 | ||
|
|
7d8aa469d7 | ||
|
|
b1aef01a1f | ||
|
|
c88ce55242 | ||
|
|
1a670ff266 | ||
|
|
1a686cb66d | ||
|
|
31592b8f3a | ||
|
|
f8675817e2 | ||
|
|
236b73565e | ||
|
|
72614fe9e1 | ||
|
|
60809ced85 | ||
|
|
aaf83da3e9 | ||
|
|
4c20a4710b | ||
|
|
52814724eb | ||
|
|
fc0d2aeeff | ||
|
|
7c2cb70387 | ||
|
|
ec0f17ca8b | ||
|
|
f8bbb0619c | ||
|
|
b17e632a85 | ||
|
|
13aae34e9c | ||
|
|
6d8949adea | ||
|
|
faab225126 | ||
|
|
63ffce58cc | ||
|
|
5d94f0bde5 | ||
|
|
b4393bc03d | ||
|
|
da0ad3bc00 | ||
|
|
9fc5c0cc58 | ||
|
|
ebc8230d45 | ||
|
|
e9526b112d | ||
|
|
a6afe50a92 | ||
|
|
273bc1b1e3 | ||
|
|
c40719caa5 | ||
|
|
b2d9380596 | ||
|
|
fcf4687c52 | ||
|
|
cbd443a78a | ||
|
|
6148fb024b | ||
|
|
9678d050a4 | ||
|
|
d468accb02 | ||
|
|
a50808a077 | ||
|
|
125847c69f | ||
|
|
4ca63c07f6 | ||
|
|
35067282cf | ||
|
|
c44eb432a5 | ||
|
|
871a1f4565 | ||
|
|
99b94af49f | ||
|
|
e9bc63aacf | ||
|
|
ba5a7c8cd8 | ||
|
|
527cfcd87f | ||
|
|
ef7aefeb45 | ||
|
|
45aea56198 | ||
|
|
daf954057f | ||
|
|
d7e6b83e64 | ||
|
|
80dc5a7b1c | ||
|
|
0f881bc90a | ||
|
|
6efa92de70 | ||
|
|
2adb710751 | ||
|
|
97f69986ff | ||
|
|
5df40661d2 | ||
|
|
889d67bcee | ||
|
|
8b91287034 | ||
|
|
1148ed1566 | ||
|
|
e3c44231ab | ||
|
|
188ff8cde7 | ||
|
|
3aa17fa0d6 | ||
|
|
4f3aeaefc1 | ||
|
|
120bfdf33d | ||
|
|
73625a2622 | ||
|
|
9f2b62dd1c | ||
|
|
60f52adc90 | ||
|
|
7eefedfb11 | ||
|
|
af80d253db | ||
|
|
ab939cc6e8 | ||
|
|
ca9413bc64 | ||
|
|
bfe42fdccb | ||
|
|
ce2dd28a25 | ||
|
|
96dcfba65a | ||
|
|
6e4d4a55cd | ||
|
|
3349dde5e2 | ||
|
|
4eefb445a7 | ||
|
|
ed927f102e | ||
|
|
82026f780d | ||
|
|
e5aeab7e7e | ||
|
|
32738637ce | ||
|
|
80f5026208 | ||
|
|
00619342e1 | ||
|
|
b719585a2f | ||
|
|
4970b5d5bc | ||
|
|
bdd382bdfd | ||
|
|
92a5cda61a | ||
|
|
60b26ad8b2 | ||
|
|
efe9f6656f | ||
|
|
22bd6a54b2 | ||
|
|
a36b6cb102 | ||
|
|
d91813c277 | ||
|
|
0ec17590ae | ||
|
|
2154502955 | ||
|
|
a4ddf93492 | ||
|
|
9c5a79209e | ||
|
|
5dc22e1811 | ||
|
|
ad8475cb8b | ||
|
|
ff60ec85b8 | ||
|
|
c1fe4bcc64 | ||
|
|
20576e0f47 | ||
|
|
20e0acc20a | ||
|
|
cfb3d87267 | ||
|
|
1cde804c77 | ||
|
|
1387b0ba7f | ||
|
|
2e03af7ac4 | ||
|
|
749c735627 | ||
|
|
aef87cced7 | ||
|
|
6bb2d9195f | ||
|
|
28ebc4cfee | ||
|
|
ad5906916d | ||
|
|
114f2b4326 | ||
|
|
a27a4db3de | ||
|
|
b4354cbc8d | ||
|
|
02fde73545 | ||
|
|
19975dcb7b | ||
|
|
641c3de0ca | ||
|
|
cf6b52e543 | ||
|
|
9500254861 | ||
|
|
13e5578bc6 | ||
|
|
24137ff54f | ||
|
|
9a13842751 | ||
|
|
13b4ddec63 | ||
|
|
39c8507dc2 | ||
|
|
0b1cc7fad1 | ||
|
|
8bc1efcf8b | ||
|
|
1a67d7d95f | ||
|
|
4dad4b50fb | ||
|
|
0f9734ae37 | ||
|
|
a43ee34bd5 | ||
|
|
e6f599b32d | ||
|
|
8cf6ff69c0 | ||
|
|
2249b7c793 | ||
|
|
591de1338b | ||
|
|
2c95cd206b | ||
|
|
8ee6dbc1e2 | ||
|
|
beb169cf75 | ||
|
|
b40d3b0a05 | ||
|
|
93ff84bf56 | ||
|
|
498c9c7955 | ||
|
|
073f2fa302 | ||
|
|
9339a8b57f | ||
|
|
fbeaf2b398 | ||
|
|
7c0e180fd9 | ||
|
|
1710e10b31 | ||
|
|
8ae7ca7f14 | ||
|
|
5fc29ac913 | ||
|
|
41d9225bd1 | ||
|
|
53f6cfb216 | ||
|
|
6827edb2c5 | ||
|
|
0b525f9d87 | ||
|
|
c7509d8ebf | ||
|
|
566876ae7a | ||
|
|
2820a0ac0a | ||
|
|
116ff8241c | ||
|
|
89623aba57 | ||
|
|
f567af49a6 | ||
|
|
1aecb578e6 | ||
|
|
a87bb21246 | ||
|
|
ec5c0deb0e | ||
|
|
3b14c59133 | ||
|
|
98e2b6575d | ||
|
|
9947bae60e | ||
|
|
402a1b91f9 | ||
|
|
3b07700ef6 | ||
|
|
d3aff000d9 | ||
|
|
c648090b5d | ||
|
|
d0687788b5 | ||
|
|
3c46abca6c | ||
|
|
cdd0acc672 | ||
|
|
c20241fcb5 | ||
|
|
ac81323fec | ||
|
|
6b5fa2c673 | ||
|
|
e4755778ae | ||
|
|
6c8f52b26f | ||
|
|
0c47396785 | ||
|
|
935622bde8 | ||
|
|
ea33f902e7 | ||
|
|
ea1624fba5 | ||
|
|
f31c6f52e8 | ||
|
|
3036a6afdc | ||
|
|
e67ed4fb2d | ||
|
|
f32a870a58 | ||
|
|
e69f9ddf8b | ||
|
|
2bcd032a44 | ||
|
|
33bffe8201 | ||
|
|
8039dc5194 | ||
|
|
2a195d457e | ||
|
|
951e8e3a73 | ||
|
|
268731aec4 | ||
|
|
7b3f9386d7 | ||
|
|
d9e2427aa8 | ||
|
|
eb0bc5c6ad | ||
|
|
fde6fadf4d | ||
|
|
432a14c84c | ||
|
|
813b7a96fb | ||
|
|
bbdf98a8f0 | ||
|
|
d96a777edd | ||
|
|
c67b0a3a64 | ||
|
|
7cc324e31e | ||
|
|
f057dc6867 | ||
|
|
e53931e27a | ||
|
|
6f9fe6a792 | ||
|
|
38c5ecf007 | ||
|
|
c1922ea5de | ||
|
|
54bcbd0bc6 | ||
|
|
9f27ac142b | ||
|
|
2ef0596df2 | ||
|
|
3ff562cb8a | ||
|
|
8fdf0ca2d3 | ||
|
|
01f507ebcb | ||
|
|
e1ba5878a3 | ||
|
|
6dceb25fb2 | ||
|
|
2178fdc65a | ||
|
|
eabf706f37 | ||
|
|
5b4c5d59d8 | ||
|
|
28626cd7c0 | ||
|
|
58343e5b7c | ||
|
|
b897225136 | ||
|
|
bb18ae82cf | ||
|
|
8e1f6c8149 | ||
|
|
74ceb6da5e | ||
|
|
e0ad52b500 | ||
|
|
8252d92e6a | ||
|
|
b15795392b | ||
|
|
274c65c451 | ||
|
|
1b4fbbb115 | ||
|
|
f95403d1dc | ||
|
|
53bf44d2b8 | ||
|
|
2d2ff7cf52 | ||
|
|
d32a407e08 | ||
|
|
5e0d017497 | ||
|
|
ce7d05aa1f | ||
|
|
ec07b42ea2 | ||
|
|
3b861798e6 | ||
|
|
135e19d0aa | ||
|
|
b498094a97 | ||
|
|
bb421c8b07 | ||
|
|
b5be17c6df | ||
|
|
2b93be1139 | ||
|
|
bd464197c4 | ||
|
|
62bbcbc7ef | ||
|
|
96530b9c0b | ||
|
|
0cbcc55d9a | ||
|
|
6b5c54bcbc | ||
|
|
c2dde04aa2 | ||
|
|
8d2c78867e | ||
|
|
c14986f9e6 | ||
|
|
62a6945bd2 | ||
|
|
be8bb235dc | ||
|
|
498bf15ecd | ||
|
|
210d7711b4 | ||
|
|
cf988434e9 | ||
|
|
466625213b | ||
|
|
9ba6ff67d5 | ||
|
|
eab22eb282 | ||
|
|
8548eae368 | ||
|
|
7e198ccb21 | ||
|
|
3d54fd8389 | ||
|
|
d319caa2ee | ||
|
|
d0ea598cdf | ||
|
|
f01f6d50b5 | ||
|
|
6de8c18f98 | ||
|
|
5923b48ede | ||
|
|
7d264696f3 | ||
|
|
b96c063c93 | ||
|
|
e9d36242ce | ||
|
|
2bad706dcf | ||
|
|
7fa3e82ac7 | ||
|
|
7ddbfa10c9 | ||
|
|
4bd437b59d | ||
|
|
fca8028e3c | ||
|
|
cd293a5173 | ||
|
|
b73507abe0 | ||
|
|
07b605a287 | ||
|
|
54383cfb55 | ||
|
|
5d33bbaff0 | ||
|
|
4cc3c1b765 | ||
|
|
4d56f725fe | ||
|
|
c34f09c503 | ||
|
|
fe43dab4d7 | ||
|
|
b69cdeb4a6 | ||
|
|
15dc5c7e99 | ||
|
|
e05bf9d32a | ||
|
|
3fb7886418 | ||
|
|
bae7c64964 | ||
|
|
68c0e188e8 | ||
|
|
e912e9597d | ||
|
|
610d4f5cb6 | ||
|
|
cdd5441435 | ||
|
|
60329ade9e | ||
|
|
f09e2130a1 | ||
|
|
0819675fce | ||
|
|
784b6dcfea | ||
|
|
245effcccd | ||
|
|
0d01bd8a5a | ||
|
|
57b6a98703 | ||
|
|
e1b0fffd0c | ||
|
|
c2f88f29dc | ||
|
|
277dade9f9 | ||
|
|
e2cf1ea73e | ||
|
|
df409d80e0 | ||
|
|
5b1571879c | ||
|
|
bb839b2924 | ||
|
|
5bc2035bd0 | ||
|
|
9e973476b2 | ||
|
|
5e2669f4b6 | ||
|
|
0f1be03faf | ||
|
|
351ee5b8fe | ||
|
|
e84c9f7c51 | ||
|
|
300aaa39fe | ||
|
|
7da9ffa3bd | ||
|
|
b21da472f6 | ||
|
|
4415212a2d | ||
|
|
6401908f41 | ||
|
|
beee98da6d | ||
|
|
60c33ac3e6 | ||
|
|
73ecf51a27 | ||
|
|
0d3a77dce9 | ||
|
|
1bc74bde29 | ||
|
|
12c40ef2e4 | ||
|
|
b250a21a2b | ||
|
|
4e28b5a199 | ||
|
|
739434b727 | ||
|
|
9ea963bfe9 | ||
|
|
f52d7c7665 | ||
|
|
6e5484ea03 | ||
|
|
d048644327 | ||
|
|
1a9e091d12 | ||
|
|
1b0d9643cd | ||
|
|
92bc962f60 | ||
|
|
a9576f0cf6 | ||
|
|
4f8a16848f | ||
|
|
bacf2b7431 | ||
|
|
34d8bc4701 | ||
|
|
510fdf7bf6 | ||
|
|
0346f47c1d | ||
|
|
026824880d | ||
|
|
3f9693b31f | ||
|
|
877cc7255d | ||
|
|
70abedc57a | ||
|
|
0c6de4ecb2 | ||
|
|
a517125d64 | ||
|
|
b7f283b2f0 | ||
|
|
cd37fd790b | ||
|
|
f983e09f92 | ||
|
|
3b4b2275de | ||
|
|
c86deceaba | ||
|
|
b5340c5ec0 | ||
|
|
10074e9980 | ||
|
|
bbee9b5637 | ||
|
|
915d864166 | ||
|
|
8555617295 | ||
|
|
b71b0d5997 | ||
|
|
37767738b0 | ||
|
|
a117ef3cb8 | ||
|
|
33b631e395 | ||
|
|
517bedeb7e | ||
|
|
0a95b38166 | ||
|
|
9b1c22250f | ||
|
|
43fed29514 | ||
|
|
4feecb69d8 | ||
|
|
12560e2407 | ||
|
|
0890b414b1 | ||
|
|
d54f8318fb | ||
|
|
fe77b9d633 | ||
|
|
47ee801d37 | ||
|
|
705ae7da14 | ||
|
|
7223106417 | ||
|
|
5a5758423e | ||
|
|
b09c9354fb | ||
|
|
d00f6672a8 | ||
|
|
06d6220a2a | ||
|
|
3011322b22 | ||
|
|
e560029736 | ||
|
|
b1ba210332 | ||
|
|
cb9114442b | ||
|
|
eb5bb9f9a9 | ||
|
|
87ba3b64f7 | ||
|
|
47f7b65058 | ||
|
|
161ae1edd1 | ||
|
|
d097ad6c19 | ||
|
|
a5d5223c0e | ||
|
|
1a1629196d | ||
|
|
d0ed8ef83b | ||
|
|
0773f66feb | ||
|
|
2dc49c834a | ||
|
|
787333896c | ||
|
|
283763dfb2 | ||
|
|
07175367d8 | ||
|
|
61219ca4ce | ||
|
|
c20995ec2f | ||
|
|
6a0a08b59c | ||
|
|
d370c60a6c | ||
|
|
a6ab53236e | ||
|
|
9a00edb031 | ||
|
|
f73685f4f6 | ||
|
|
ae353398d9 | ||
|
|
9983283f95 | ||
|
|
6d5bdc6c68 | ||
|
|
80e69210db | ||
|
|
793e3ad78e | ||
|
|
4057682c87 | ||
|
|
5e68b7e3a6 | ||
|
|
495b47db16 | ||
|
|
4aa960b744 | ||
|
|
dd6c192695 | ||
|
|
8772628912 | ||
|
|
a99d0a65b0 | ||
|
|
a09241e3c7 | ||
|
|
c7b961ffa2 | ||
|
|
32a608f948 | ||
|
|
8d79365e0d | ||
|
|
71e833c3f2 | ||
|
|
b5f3013005 | ||
|
|
39ef75e2d0 | ||
|
|
42813d38c3 | ||
|
|
55147781f3 | ||
|
|
c9fd182268 | ||
|
|
0743289925 | ||
|
|
4d75159247 | ||
|
|
baa1978128 | ||
|
|
259f313af7 | ||
|
|
863116f1cd | ||
|
|
5cb5e09dbb | ||
|
|
c61925598a | ||
|
|
fa1c7b663c | ||
|
|
a9a84cc7d4 | ||
|
|
ff967c45f7 | ||
|
|
9a5c422074 | ||
|
|
5a83a16e60 | ||
|
|
1704180f38 | ||
|
|
0cf9ff0a04 | ||
|
|
41ae2a2dc5 | ||
|
|
f7b2380ec1 | ||
|
|
5eeb650dfd | ||
|
|
a1b95606b1 | ||
|
|
726ac6bda1 | ||
|
|
d6201ce5c7 | ||
|
|
e7e23fbc96 | ||
|
|
e7544e9fc1 | ||
|
|
eaf86a6461 | ||
|
|
f53ba178a8 | ||
|
|
c68ad73c6e | ||
|
|
6851c5042f | ||
|
|
da96578afb | ||
|
|
27f05145ae | ||
|
|
1b3ba25220 | ||
|
|
13cba5068b | ||
|
|
db24e24882 | ||
|
|
e7984b3ef9 | ||
|
|
b562b4cf99 | ||
|
|
69d7a640ee | ||
|
|
fa2d33cb50 | ||
|
|
2588970d55 | ||
|
|
d4ac57704c | ||
|
|
15c90551b6 | ||
|
|
0acd0f50c5 | ||
|
|
acb6e8e120 | ||
|
|
ccff588563 | ||
|
|
780c4278e6 | ||
|
|
2d6506ecec | ||
|
|
a97b3db749 | ||
|
|
cc15f695b4 | ||
|
|
c41cbb3e29 | ||
|
|
6ad298adfc | ||
|
|
db9829e83f | ||
|
|
956c3c50a0 | ||
|
|
40c1acc961 | ||
|
|
7babfd4ac4 | ||
|
|
65df4b6aa8 | ||
|
|
2721ee3a8d | ||
|
|
137b5a6108 | ||
|
|
b023e5d6b3 | ||
|
|
89a0e9c245 | ||
|
|
89326bd657 | ||
|
|
a8949174c8 | ||
|
|
906ac093e3 | ||
|
|
8ddc26eb2e | ||
|
|
ca0c3eb184 | ||
|
|
0465c9aabb | ||
|
|
8e0a7a8dbc | ||
|
|
a045916aca | ||
|
|
be312cea4c | ||
|
|
9611e9bd7f | ||
|
|
08ed3cd313 | ||
|
|
231ab83562 | ||
|
|
f45dd740c5 | ||
|
|
0156339f34 | ||
|
|
f99bb61181 | ||
|
|
6a47a2ceaf | ||
|
|
525f656cc1 | ||
|
|
d34787cf6d | ||
|
|
9424bbc01c | ||
|
|
16c297c2ec | ||
|
|
8beec58670 | ||
|
|
bac811bd5e | ||
|
|
eb9ee3f79b | ||
|
|
5da3e532c9 | ||
|
|
b1d9f3132d | ||
|
|
aaa9036eca | ||
|
|
005c5a587f | ||
|
|
47c78a5a73 | ||
|
|
24ccb3eb78 | ||
|
|
a56b79cc72 | ||
|
|
84ee50e492 | ||
|
|
16b7401d4c | ||
|
|
1a5d56977e | ||
|
|
6812e91893 | ||
|
|
4ca84eadb6 | ||
|
|
27aba02d16 | ||
|
|
3d7ad71b22 | ||
|
|
e824cd012b | ||
|
|
8d5045ef4c | ||
|
|
083da7d8a4 | ||
|
|
00261094c8 | ||
|
|
9471d8fff9 | ||
|
|
ab6e92aae1 | ||
|
|
fb3421fcce | ||
|
|
c8693cdf37 | ||
|
|
3df1d75bdd | ||
|
|
fc12238fcc | ||
|
|
15fff84bb5 | ||
|
|
01aadbef85 | ||
|
|
ccdcb7dfcc | ||
|
|
94fabe0321 | ||
|
|
dd39da0b77 | ||
|
|
3688d9412e | ||
|
|
4918aeb4c6 | ||
|
|
d659d407a0 | ||
|
|
262cafc430 | ||
|
|
11190aac4c | ||
|
|
6d31563920 | ||
|
|
b6957ddac2 | ||
|
|
b2d8a44199 | ||
|
|
2815d196de | ||
|
|
64266c4d38 | ||
|
|
f4d418ea6d | ||
|
|
a008f5f611 | ||
|
|
74eab91042 | ||
|
|
9aeb3932d0 | ||
|
|
b6a7549407 | ||
|
|
9087e1443e | ||
|
|
5952cfa673 | ||
|
|
a1e0197a8b | ||
|
|
af7bc4f178 | ||
|
|
023bc36592 | ||
|
|
ceeb724acc | ||
|
|
5e9016ffab | ||
|
|
6bc40373f2 | ||
|
|
14c8c8c33d | ||
|
|
0925706d5e | ||
|
|
ca14ae8f1b | ||
|
|
90c6d4dc85 | ||
|
|
228aa1a244 | ||
|
|
993e2bfbf9 | ||
|
|
ea3071db66 | ||
|
|
395299803f | ||
|
|
5e2d21c033 | ||
|
|
c4c3090f46 | ||
|
|
6492019383 | ||
|
|
f6831fba13 | ||
|
|
16db6c2f47 | ||
|
|
bd3dc6482e | ||
|
|
f7b7b2b438 | ||
|
|
99fbd8ad18 | ||
|
|
9d20256366 | ||
|
|
85f2a6dd54 | ||
|
|
de2eba0d98 | ||
|
|
705ef4f5a3 | ||
|
|
b2dde55f2c | ||
|
|
d53b34c0ce | ||
|
|
a427029151 | ||
|
|
2de3e6ce6d | ||
|
|
03a38ed025 | ||
|
|
26503a205f | ||
|
|
5a25c80f2e | ||
|
|
4c8a8c3bcd | ||
|
|
decdbd2782 | ||
|
|
eb4c476490 | ||
|
|
68f5dd3e7b | ||
|
|
68aee8c144 | ||
|
|
b24e28953b | ||
|
|
9656412bba | ||
|
|
61280117eb | ||
|
|
961bdf0d24 | ||
|
|
080aa30407 | ||
|
|
eecf9cd1d8 | ||
|
|
e2a519464b | ||
|
|
60a81a563e | ||
|
|
3a66aefd2c | ||
|
|
54f7cf59fd | ||
|
|
ba10f7d04c | ||
|
|
691e3bb24f | ||
|
|
832734ff4c | ||
|
|
3d4156cc7d | ||
|
|
cc053ad894 | ||
|
|
ae294ee470 | ||
|
|
e4bdd3a28d | ||
|
|
63313eef6f | ||
|
|
1da9087cc4 | ||
|
|
de3795a7d4 | ||
|
|
cfd3230c75 | ||
|
|
e38b06bf2d | ||
|
|
7cb0b1b7c3 | ||
|
|
62b4a263f8 | ||
|
|
96b13c59c1 | ||
|
|
1423b38d50 | ||
|
|
ff27cccff4 | ||
|
|
abc7d30024 | ||
|
|
591f4ebdca | ||
|
|
ef8e4191cd | ||
|
|
cf97e3c21f | ||
|
|
2e8739fff7 | ||
|
|
3da0aa6a0b | ||
|
|
97be527ee9 | ||
|
|
cac3b4a0d8 | ||
|
|
96f31847b2 | ||
|
|
85f9f8d176 | ||
|
|
7b0cd03f88 | ||
|
|
68585f6f2b | ||
|
|
857f2b5a01 | ||
|
|
258148b615 | ||
|
|
7145b040f1 | ||
|
|
874766a82f | ||
|
|
096a2c8cd0 | ||
|
|
4a047fefb8 | ||
|
|
fddf341f44 | ||
|
|
fe5fc5bd3a | ||
|
|
0255e09285 | ||
|
|
2b0b15f4d1 | ||
|
|
8e4b591ea2 | ||
|
|
663bb8726c | ||
|
|
2add802d0d | ||
|
|
adfcdb3b65 | ||
|
|
9fadf5f426 | ||
|
|
3e6306348a | ||
|
|
458dd51af7 | ||
|
|
23b0b8ba36 | ||
|
|
592fc81260 | ||
|
|
c232acbe9b | ||
|
|
640dfab827 | ||
|
|
01044ca8e9 | ||
|
|
2633d7dca3 | ||
|
|
ecb533c4d1 | ||
|
|
5fc19dab54 | ||
|
|
58114e7b24 | ||
|
|
1763824e5f | ||
|
|
aee2e12f39 | ||
|
|
500573067a | ||
|
|
8052103197 | ||
|
|
78ab11f991 | ||
|
|
3263f2023c | ||
|
|
8f00481c5f | ||
|
|
9872e371a2 | ||
|
|
37b3ac7952 | ||
|
|
d891bd7fac | ||
|
|
d366a91d9e | ||
|
|
8c3713b649 | ||
|
|
729fc738af | ||
|
|
add238c892 | ||
|
|
ad3634be7c | ||
|
|
5a53a4b044 | ||
|
|
5a97fa6336 | ||
|
|
657bb9d682 | ||
|
|
b9f5a1c85d | ||
|
|
592ce45da7 | ||
|
|
d9b3b95854 | ||
|
|
5426b93387 | ||
|
|
284a40aa63 | ||
|
|
2989e36b1d | ||
|
|
d8245cef72 | ||
|
|
edf4514d8b | ||
|
|
477d9fa87e | ||
|
|
01f133f8c8 | ||
|
|
d32147f8fe | ||
|
|
86aeacf393 | ||
|
|
dd80d3b9b9 | ||
|
|
98cba5ed30 | ||
|
|
ca8a5b45ba | ||
|
|
9d6a06aec5 | ||
|
|
dd016e6ced | ||
|
|
0fe6dcd742 | ||
|
|
bcbe6c4a53 | ||
|
|
f09c5f32cf | ||
|
|
3ca7e442bc | ||
|
|
8ac647ece7 | ||
|
|
4307d3b5c9 | ||
|
|
aa17110bde | ||
|
|
3f6d805033 | ||
|
|
64b44a360a | ||
|
|
040cc8d22f | ||
|
|
3be345e605 | ||
|
|
e1cea25781 | ||
|
|
a2ede7d6d5 | ||
|
|
7e4dd33ab0 | ||
|
|
45d5cff47d | ||
|
|
745e3bfb73 | ||
|
|
762906f240 | ||
|
|
9ec6f1e1d6 | ||
|
|
628ea42b63 | ||
|
|
1efff268b0 | ||
|
|
b206b0583b | ||
|
|
816b1b6bd5 | ||
|
|
24fcd67f8b | ||
|
|
c99c805743 | ||
|
|
f258ab5e98 | ||
|
|
880a85d2af | ||
|
|
efd31a429c | ||
|
|
728cc9f725 | ||
|
|
52305e3000 | ||
|
|
1657337887 | ||
|
|
362f377f61 | ||
|
|
8bdb61cb87 | ||
|
|
67f43d37df | ||
|
|
3543f86c63 | ||
|
|
627165dc7c | ||
|
|
874774fe6c | ||
|
|
ee76af7681 | ||
|
|
f9713eeb56 | ||
|
|
0ca7527f7a | ||
|
|
2a41da94d4 | ||
|
|
73586fd9b2 | ||
|
|
9c889b37fb | ||
|
|
b11ae4b54c | ||
|
|
e3af1dc864 | ||
|
|
8b04c1d4f6 | ||
|
|
74f9e34182 | ||
|
|
1fddc30350 | ||
|
|
e2bb4e2baa | ||
|
|
383a4b132e | ||
|
|
9006c9b747 | ||
|
|
6518582ed3 | ||
|
|
5c308a4f9a | ||
|
|
ac91030b31 | ||
|
|
9680edfcc3 | ||
|
|
56e991b7f4 | ||
|
|
9903049c7a | ||
|
|
f34ffc2062 | ||
|
|
bfaa93b0ca | ||
|
|
f50d933a25 | ||
|
|
ce092bf23b | ||
|
|
fb06ad7330 | ||
|
|
80ab4eea8c | ||
|
|
83a13e22b7 | ||
|
|
ee0c64215d | ||
|
|
5ac8bd7f08 | ||
|
|
2f3fc12c08 | ||
|
|
331ad62f3c | ||
|
|
f6e93f084a | ||
|
|
7b2eacd4d8 | ||
|
|
a9bf906545 | ||
|
|
97090ff367 | ||
|
|
6c8b6de4c9 | ||
|
|
f91752cad2 | ||
|
|
cc60c328fe | ||
|
|
ff5b1b7ded | ||
|
|
a1ff7cab7e | ||
|
|
32f622ef80 | ||
|
|
969616ed09 | ||
|
|
ca62cde9aa | ||
|
|
3d1e3a9cde | ||
|
|
184848edf9 | ||
|
|
65ba5b3000 | ||
|
|
3a487bd33a | ||
|
|
56e92b702c | ||
|
|
45299fe4b3 | ||
|
|
434c2a1815 | ||
|
|
f31002636b | ||
|
|
b5dd0c8630 | ||
|
|
9c7b19e0b7 | ||
|
|
3a51a3f37e | ||
|
|
1662a4c9c3 | ||
|
|
a5a5341643 | ||
|
|
20c6e9fca2 | ||
|
|
5b3eba7bee | ||
|
|
8c6e341a71 | ||
|
|
545ef3c234 | ||
|
|
7842c9fba8 | ||
|
|
7e43d7b131 | ||
|
|
089da459f7 | ||
|
|
b27af6b5c8 | ||
|
|
c69fb80222 | ||
|
|
134201794a | ||
|
|
2df767f596 | ||
|
|
da80e4dbce | ||
|
|
5cc8603cff | ||
|
|
426c245032 | ||
|
|
9731b74ad3 | ||
|
|
ee29526bbe | ||
|
|
3e884d347a | ||
|
|
6e0362dee8 | ||
|
|
2499675ad1 | ||
|
|
908b21f7fd | ||
|
|
e93a19ffb5 | ||
|
|
3e77c0b564 | ||
|
|
e769e750ec | ||
|
|
c31ee8ea33 | ||
|
|
894ae1fe0f | ||
|
|
5fae2f6d57 | ||
|
|
ad5edbb1de | ||
|
|
780b827adc | ||
|
|
8e010ef063 | ||
|
|
09f9764bbd | ||
|
|
a59c942cd4 | ||
|
|
b097bb20d9 | ||
|
|
2f9e96e324 | ||
|
|
56b8d1b927 | ||
|
|
5b446d4575 | ||
|
|
9ae5c979e8 | ||
|
|
c2f0fadb6e | ||
|
|
ea7565889f | ||
|
|
4a111f7362 | ||
|
|
ffd171a26b | ||
|
|
95edd82638 | ||
|
|
e07c3aad6b | ||
|
|
a393a6b76c | ||
|
|
d380bf8179 | ||
|
|
8062d2be3b | ||
|
|
d17e37c581 | ||
|
|
6f432b8e45 | ||
|
|
94faa44697 | ||
|
|
9fde782403 | ||
|
|
ecc305dd59 | ||
|
|
6f6d5cb4cf | ||
|
|
8634abc021 | ||
|
|
a74e1f1600 | ||
|
|
59438ee8d4 | ||
|
|
4ed9927a30 | ||
|
|
ae508144cd | ||
|
|
a52a1b49af | ||
|
|
93295bf25b | ||
|
|
73639db910 | ||
|
|
c320288690 | ||
|
|
0aa1636d04 | ||
|
|
194d70f8a0 | ||
|
|
af35590549 | ||
|
|
a248b13cc3 | ||
|
|
b0dfc936a1 | ||
|
|
73090fa130 | ||
|
|
ade09bc709 | ||
|
|
8d9f391309 | ||
|
|
ebd74a4e5b | ||
|
|
c4f8f3613f | ||
|
|
e5a8ad54e2 | ||
|
|
815c616f18 | ||
|
|
1d8fcd66e6 | ||
|
|
6ca3b26820 | ||
|
|
18a2e6ecb2 | ||
|
|
922fffda1f | ||
|
|
1fc5844025 | ||
|
|
45b4bfc947 | ||
|
|
92f6d2c87c | ||
|
|
c2bda2c705 | ||
|
|
4b4b176fcf | ||
|
|
a27374fd8f | ||
|
|
56ac3424d2 | ||
|
|
696e2108ac | ||
|
|
89612f2605 | ||
|
|
a8216b9727 | ||
|
|
779260fb49 | ||
|
|
860b67e9c0 | ||
|
|
47ba357bea | ||
|
|
3502c01aa4 | ||
|
|
6e3e094c95 | ||
|
|
a89afb65d7 | ||
|
|
9a171db97f | ||
|
|
48567ef755 | ||
|
|
b57eba6eaf | ||
|
|
70d99eebc0 | ||
|
|
4783e4beee | ||
|
|
450c2470e9 | ||
|
|
09439334ca | ||
|
|
f9c88ea7bc | ||
|
|
33eedb97dc | ||
|
|
2984a86f37 | ||
|
|
5f5d75a0bb | ||
|
|
6f231e4c83 | ||
|
|
c750e4d7ef | ||
|
|
291a499124 | ||
|
|
67b36a0823 | ||
|
|
162c0497d1 | ||
|
|
416bd400bb | ||
|
|
ee60fa940c | ||
|
|
6210b24c64 | ||
|
|
68c6ad6036 | ||
|
|
10b9570429 | ||
|
|
11c8d9fcf1 | ||
|
|
61705047b0 | ||
|
|
ea4b6ff27b | ||
|
|
5ce395a60a | ||
|
|
ac79b8483f | ||
|
|
0135293127 | ||
|
|
adff287160 | ||
|
|
b651b36fff | ||
|
|
5a068410c6 | ||
|
|
ebb186c8df | ||
|
|
d582a73795 | ||
|
|
e845b63228 | ||
|
|
cfe0479dfb | ||
|
|
67e74d03ed | ||
|
|
8722318081 | ||
|
|
2d272fa51c | ||
|
|
15840d408b | ||
|
|
f9fc6c9c9d | ||
|
|
30c6b83a10 | ||
|
|
1754d027b3 | ||
|
|
a1f8595a6a | ||
|
|
5cce522ecd | ||
|
|
758ec720de | ||
|
|
6280031722 | ||
|
|
ff0343d2cc | ||
|
|
3d00d74fed | ||
|
|
30402033bc | ||
|
|
de445b32f5 | ||
|
|
34d3eb88b3 | ||
|
|
a9d91189b0 | ||
|
|
84f0d1ff1f | ||
|
|
98a8288da2 | ||
|
|
0e100cd451 | ||
|
|
e5a018f84c | ||
|
|
2b02ef0066 | ||
|
|
e5bc8fccb1 | ||
|
|
0c5bdbdcf3 | ||
|
|
a3191f1c8c | ||
|
|
787784e937 | ||
|
|
539ff03a7e | ||
|
|
e42a3e0084 | ||
|
|
8fbd4cea5b | ||
|
|
05f24ede96 | ||
|
|
54b323e557 | ||
|
|
9231706227 | ||
|
|
1f88b1ef84 | ||
|
|
10242235bc | ||
|
|
73b65ac82e | ||
|
|
f52916a2c3 | ||
|
|
98d6cdd53c | ||
|
|
e1a87a802d | ||
|
|
d9e284366d | ||
|
|
56e9a46c17 | ||
|
|
2ce6bbf291 | ||
|
|
568d5bfbe8 | ||
|
|
60435daba3 | ||
|
|
f14d1eb871 | ||
|
|
d4c0dbfacc | ||
|
|
469ae2c7f1 | ||
|
|
a9372c42cd | ||
|
|
edf67444ea | ||
|
|
4867ca353c | ||
|
|
4015723591 | ||
|
|
f70d779034 | ||
|
|
23beb46d15 | ||
|
|
e019d43d0b | ||
|
|
c37e374fdd | ||
|
|
cd1e016163 | ||
|
|
1f4b381748 | ||
|
|
fb9a80923b | ||
|
|
ed1c198897 | ||
|
|
1b808e1d7c | ||
|
|
639f427d6d | ||
|
|
539f0251d9 | ||
|
|
d91d9b02d4 | ||
|
|
0104897d69 | ||
|
|
5530a5b303 | ||
|
|
a9fceeb00f | ||
|
|
34e3538b55 | ||
|
|
851a234988 | ||
|
|
17893eff59 | ||
|
|
54e8ce1ac5 | ||
|
|
38e5e4a893 | ||
|
|
65cc804186 | ||
|
|
8fa677b8e8 | ||
|
|
6bd56d2d5f | ||
|
|
204face50d | ||
|
|
c5f5aa8208 | ||
|
|
3d9938221a | ||
|
|
f0a1f4ac7c | ||
|
|
ec1a7869f8 | ||
|
|
7e67d42d1d | ||
|
|
da9a7ff63d | ||
|
|
47f913abcb | ||
|
|
fc4199504f | ||
|
|
0fc14b72ca | ||
|
|
804ed0d26a | ||
|
|
028b3e2fbf | ||
|
|
e0a03789ae | ||
|
|
7a3e4a8a05 | ||
|
|
e16cc38b70 | ||
|
|
c43b30cf36 | ||
|
|
07a8024b45 | ||
|
|
b64147cce9 | ||
|
|
058bb95171 | ||
|
|
daf2ec063c | ||
|
|
77af247450 | ||
|
|
1fd888175f | ||
|
|
fb0ec74d08 | ||
|
|
eb73017798 | ||
|
|
139a68fd0f | ||
|
|
d758fc1b89 | ||
|
|
056b74b162 | ||
|
|
c78fdaae90 | ||
|
|
e752f8f0ef | ||
|
|
54a32adef3 | ||
|
|
ca69845238 | ||
|
|
d2fdda8bcd | ||
|
|
afc64ed9ee | ||
|
|
500435b856 | ||
|
|
a15484fe3d | ||
|
|
76c61c1b04 | ||
|
|
de58c67991 | ||
|
|
8a34a4ba68 | ||
|
|
208d5042ee | ||
|
|
ece7049390 | ||
|
|
e72afd0bd6 | ||
|
|
83db7c6a65 | ||
|
|
62384e9321 | ||
|
|
1081df3d7e | ||
|
|
3a8736374c | ||
|
|
f276fbba4f | ||
|
|
fd78f868e1 | ||
|
|
d99a56bc27 | ||
|
|
48c66b68ab | ||
|
|
8d9b90f3f5 | ||
|
|
4a86375e89 | ||
|
|
b60c57a97d | ||
|
|
8903c1bc6f | ||
|
|
e33fd450fd | ||
|
|
dc5d2c7406 | ||
|
|
1612d7ba3f | ||
|
|
681782121c | ||
|
|
35cf944cb7 | ||
|
|
4bbad7f448 | ||
|
|
74b6bfb9eb | ||
|
|
46ea868559 | ||
|
|
3290df5593 | ||
|
|
8e3b9ec879 | ||
|
|
787fc8737f | ||
|
|
fcfcf6957e | ||
|
|
8ffa2bfe25 | ||
|
|
d69b0d76dd | ||
|
|
2bcff4c7f2 | ||
|
|
d436a40739 | ||
|
|
5deba1b6f9 | ||
|
|
886102d462 | ||
|
|
7be578485e | ||
|
|
7c1b990c55 | ||
|
|
74a0d6408a | ||
|
|
92cbe580e6 | ||
|
|
d92eb0c603 | ||
|
|
11d956fa18 | ||
|
|
8e523961dc | ||
|
|
cdbe1c87d4 | ||
|
|
3f42128fff | ||
|
|
4dff2c7a0d | ||
|
|
547993f801 | ||
|
|
946228d783 | ||
|
|
23df4205f8 | ||
|
|
89f484282a | ||
|
|
9ef26e1df0 | ||
|
|
025acc0e48 | ||
|
|
6942ab1012 | ||
|
|
3bfb7b79f2 | ||
|
|
24788ddcc0 | ||
|
|
adf313a6d3 | ||
|
|
7f39318340 | ||
|
|
a432290a82 | ||
|
|
2b64e1ca8b | ||
|
|
514d5434a3 | ||
|
|
7e600a6494 | ||
|
|
17ebc1ea80 | ||
|
|
b099590b2c | ||
|
|
5323bb7bee | ||
|
|
55dbcee36a | ||
|
|
ec9434aae3 | ||
|
|
d1ec0a6093 | ||
|
|
5136fe196b | ||
|
|
4aa841786f | ||
|
|
98cc7434d2 | ||
|
|
35020a9423 | ||
|
|
1cc1c9aa38 | ||
|
|
9d392970f0 | ||
|
|
b0d440c34b | ||
|
|
21c3d9c371 | ||
|
|
dae66eab36 | ||
|
|
9474908449 | ||
|
|
eec4057e8d | ||
|
|
08bc77fb95 | ||
|
|
fff97b1cd2 | ||
|
|
2a7d1c4c8d | ||
|
|
0b674b608b | ||
|
|
14b009b093 | ||
|
|
530922848f | ||
|
|
79d51a0a0b | ||
|
|
85488cd0dc | ||
|
|
ce7ac29d06 | ||
|
|
4f363f5bf3 | ||
|
|
ff7108a3b1 | ||
|
|
77cc91d06b | ||
|
|
45395027d3 | ||
|
|
6d5ccde864 | ||
|
|
961d2d9926 | ||
|
|
75441017c6 | ||
|
|
ed2457bddf | ||
|
|
4471ad581e | ||
|
|
7ecc0d5a04 | ||
|
|
78fe567419 | ||
|
|
5ae9c2f62b | ||
|
|
705dadae8e | ||
|
|
40cdde8820 | ||
|
|
64497c9228 | ||
|
|
188175be84 | ||
|
|
2b4fa98941 | ||
|
|
36a996d704 | ||
|
|
7f1d916f04 | ||
|
|
e15546b42f | ||
|
|
8c61fe2ca5 | ||
|
|
7f865492d0 | ||
|
|
726fba61f3 | ||
|
|
0b85a525fb | ||
|
|
8b21ca2db9 | ||
|
|
fed8cf4196 | ||
|
|
528ed9c986 | ||
|
|
e2cccc4005 | ||
|
|
569d0961f2 | ||
|
|
de46fa8e66 | ||
|
|
bfa0c0981c | ||
|
|
c77c296b8b | ||
|
|
9ab55a5bd8 | ||
|
|
e4d657e6fd | ||
|
|
f4c8d63fe0 | ||
|
|
d94f45531a | ||
|
|
4d38bd8517 | ||
|
|
c99e7ca999 | ||
|
|
aba3065573 | ||
|
|
e95dce6d8d | ||
|
|
35d92abe73 | ||
|
|
28445058ef | ||
|
|
aab5737ff3 | ||
|
|
e97af14ff4 | ||
|
|
c809e61103 | ||
|
|
115f024260 | ||
|
|
952e8cf60c | ||
|
|
fcfdb9b566 | ||
|
|
ff1dc72d74 | ||
|
|
b3486b43c4 | ||
|
|
f705bf2efe | ||
|
|
6e1565c32c | ||
|
|
4ea43ebc5d | ||
|
|
f292a0cc4c | ||
|
|
4c5a83d6cf | ||
|
|
82774f89b1 | ||
|
|
19b220f39c | ||
|
|
725a7f90e9 |
@@ -9,6 +9,13 @@ trim_trailing_whitespace = true
|
|||||||
charset = utf-8
|
charset = utf-8
|
||||||
|
|
||||||
# python, js indentation settings
|
# python, js indentation settings
|
||||||
[{*.py,*.js}]
|
[{*.py,*.js,*.vue,*.css,*.scss,*.html}]
|
||||||
indent_style = tab
|
indent_style = tab
|
||||||
indent_size = 4
|
indent_size = 4
|
||||||
|
max_line_length = 110
|
||||||
|
|
||||||
|
# JSON files - mostly doctype schema files
|
||||||
|
[{*.json}]
|
||||||
|
insert_final_newline = false
|
||||||
|
indent_style = space
|
||||||
|
indent_size = 2
|
||||||
|
|||||||
@@ -124,6 +124,7 @@
|
|||||||
"beforeEach": true,
|
"beforeEach": true,
|
||||||
"onScan": true,
|
"onScan": true,
|
||||||
"extend_cscript": true,
|
"extend_cscript": true,
|
||||||
"localforage": true
|
"localforage": true,
|
||||||
|
"Plaid": true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -28,4 +28,10 @@ b147b85e6ac19a9220cd1e2958a6ebd99373283a
|
|||||||
494bd9ef78313436f0424b918f200dab8fc7c20b
|
494bd9ef78313436f0424b918f200dab8fc7c20b
|
||||||
|
|
||||||
# bulk format python code with black
|
# bulk format python code with black
|
||||||
baec607ff5905b1c67531096a9cf50ec7ff00a5d
|
baec607ff5905b1c67531096a9cf50ec7ff00a5d
|
||||||
|
|
||||||
|
# bulk refactor with sourcery
|
||||||
|
eb9ee3f79b94e594fc6dfa4f6514580e125eee8c
|
||||||
|
|
||||||
|
# js formatting
|
||||||
|
ec74a5e56617bbd76ac402451468fd4668af543d
|
||||||
|
|||||||
60
.github/helper/translation.py
vendored
Normal file
60
.github/helper/translation.py
vendored
Normal file
@@ -0,0 +1,60 @@
|
|||||||
|
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, 'r') 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 .
|
||||||
|
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}" -R frappe/erpnext
|
||||||
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}}"
|
||||||
38
.github/workflows/generate-pot-file.yml
vendored
Normal file
38
.github/workflows/generate-pot-file.yml
vendored
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
# 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:
|
||||||
|
regeneratee-pot-file:
|
||||||
|
name: Release
|
||||||
|
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 }}
|
||||||
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 }}
|
||||||
12
.github/workflows/linters.yml
vendored
12
.github/workflows/linters.yml
vendored
@@ -20,6 +20,18 @@ jobs:
|
|||||||
- name: Install and Run Pre-commit
|
- name: Install and Run Pre-commit
|
||||||
uses: pre-commit/action@v3.0.0
|
uses: pre-commit/action@v3.0.0
|
||||||
|
|
||||||
|
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
|
||||||
|
|
||||||
- name: Download Semgrep rules
|
- name: Download Semgrep rules
|
||||||
run: git clone --depth 1 https://github.com/frappe/semgrep-rules.git frappe-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
|
||||||
1
.github/workflows/patch.yml
vendored
1
.github/workflows/patch.yml
vendored
@@ -134,6 +134,7 @@ jobs:
|
|||||||
}
|
}
|
||||||
|
|
||||||
update_to_version 14
|
update_to_version 14
|
||||||
|
update_to_version 15
|
||||||
|
|
||||||
echo "Updating to latest version"
|
echo "Updating to latest version"
|
||||||
git -C "apps/frappe" checkout -q -f "${GITHUB_BASE_REF:-${GITHUB_REF##*/}}"
|
git -C "apps/frappe" checkout -q -f "${GITHUB_BASE_REF:-${GITHUB_REF##*/}}"
|
||||||
|
|||||||
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"
|
||||||
8
.github/workflows/release.yml
vendored
8
.github/workflows/release.yml
vendored
@@ -2,23 +2,21 @@ name: Generate Semantic Release
|
|||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
branches:
|
branches:
|
||||||
- version-15
|
- version-13
|
||||||
jobs:
|
jobs:
|
||||||
release:
|
release:
|
||||||
name: Release
|
name: Release
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- name: Checkout Entire Repository
|
- name: Checkout Entire Repository
|
||||||
uses: actions/checkout@v4
|
uses: actions/checkout@v2
|
||||||
with:
|
with:
|
||||||
fetch-depth: 0
|
fetch-depth: 0
|
||||||
persist-credentials: false
|
persist-credentials: false
|
||||||
|
|
||||||
- name: Setup Node.js
|
- name: Setup Node.js
|
||||||
uses: actions/setup-node@v2
|
uses: actions/setup-node@v2
|
||||||
with:
|
with:
|
||||||
node-version: 18
|
node-version: 20
|
||||||
|
|
||||||
- name: Setup dependencies
|
- name: Setup dependencies
|
||||||
run: |
|
run: |
|
||||||
npm install @semantic-release/git @semantic-release/exec --no-save
|
npm install @semantic-release/git @semantic-release/exec --no-save
|
||||||
|
|||||||
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"
|
||||||
34
.github/workflows/server-tests-mariadb.yml
vendored
34
.github/workflows/server-tests-mariadb.yml
vendored
@@ -31,6 +31,9 @@ jobs:
|
|||||||
test:
|
test:
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
timeout-minutes: 60
|
timeout-minutes: 60
|
||||||
|
env:
|
||||||
|
NODE_ENV: "production"
|
||||||
|
WITH_COVERAGE: ${{ github.event_name != 'pull_request' }}
|
||||||
|
|
||||||
strategy:
|
strategy:
|
||||||
fail-fast: false
|
fail-fast: false
|
||||||
@@ -120,9 +123,36 @@ jobs:
|
|||||||
run: 'cd ~/frappe-bench/ && bench --site test_site run-parallel-tests --app erpnext --total-builds 4 --build-number ${{ matrix.container }}'
|
run: 'cd ~/frappe-bench/ && bench --site test_site run-parallel-tests --app erpnext --total-builds 4 --build-number ${{ matrix.container }}'
|
||||||
env:
|
env:
|
||||||
TYPE: server
|
TYPE: server
|
||||||
CI_BUILD_ID: ${{ github.run_id }}
|
CAPTURE_COVERAGE: ${{ github.event_name != 'pull_request' }}
|
||||||
ORCHESTRATOR_URL: http://test-orchestrator.frappe.io
|
|
||||||
|
|
||||||
- name: Show bench output
|
- name: Show bench output
|
||||||
if: ${{ always() }}
|
if: ${{ always() }}
|
||||||
run: cat ~/frappe-bench/bench_start.log || true
|
run: cat ~/frappe-bench/bench_start.log || true
|
||||||
|
|
||||||
|
- 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@v2
|
||||||
|
|
||||||
|
- name: Download artifacts
|
||||||
|
uses: actions/download-artifact@v3
|
||||||
|
|
||||||
|
- name: Upload coverage data
|
||||||
|
uses: codecov/codecov-action@v2
|
||||||
|
with:
|
||||||
|
name: MariaDB
|
||||||
|
token: ${{ secrets.CODECOV_TOKEN }}
|
||||||
|
fail_ci_if_error: true
|
||||||
|
verbose: true
|
||||||
|
|||||||
1
.gitignore
vendored
1
.gitignore
vendored
@@ -2,7 +2,6 @@
|
|||||||
*.py~
|
*.py~
|
||||||
.DS_Store
|
.DS_Store
|
||||||
conf.py
|
conf.py
|
||||||
locale
|
|
||||||
latest_updates.json
|
latest_updates.json
|
||||||
.wnf-lang-status
|
.wnf-lang-status
|
||||||
*.egg-info
|
*.egg-info
|
||||||
|
|||||||
46
.mergify.yml
46
.mergify.yml
@@ -17,6 +17,7 @@ pull_request_rules:
|
|||||||
- base=version-12
|
- base=version-12
|
||||||
- base=version-14
|
- base=version-14
|
||||||
- base=version-15
|
- base=version-15
|
||||||
|
- base=version-16
|
||||||
actions:
|
actions:
|
||||||
close:
|
close:
|
||||||
comment:
|
comment:
|
||||||
@@ -24,16 +25,6 @@ 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.
|
@{{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
|
https://github.com/frappe/erpnext/wiki/Pull-Request-Checklist#which-branch
|
||||||
|
|
||||||
- name: Auto-close PRs on pre-release branch
|
|
||||||
conditions:
|
|
||||||
- base=version-13-pre-release
|
|
||||||
actions:
|
|
||||||
close:
|
|
||||||
comment:
|
|
||||||
message: |
|
|
||||||
@{{author}}, pre-release branch is not maintained anymore. Releases are directly done by merging hotfix branch to stable branches.
|
|
||||||
|
|
||||||
|
|
||||||
- name: backport to develop
|
- name: backport to develop
|
||||||
conditions:
|
conditions:
|
||||||
- label="backport develop"
|
- label="backport develop"
|
||||||
@@ -54,13 +45,13 @@ pull_request_rules:
|
|||||||
assignees:
|
assignees:
|
||||||
- "{{ author }}"
|
- "{{ author }}"
|
||||||
|
|
||||||
- name: backport to version-14-pre-release
|
- name: backport to version-15-hotfix
|
||||||
conditions:
|
conditions:
|
||||||
- label="backport version-14-pre-release"
|
- label="backport version-15-hotfix"
|
||||||
actions:
|
actions:
|
||||||
backport:
|
backport:
|
||||||
branches:
|
branches:
|
||||||
- version-14-pre-release
|
- version-15-hotfix
|
||||||
assignees:
|
assignees:
|
||||||
- "{{ author }}"
|
- "{{ author }}"
|
||||||
|
|
||||||
@@ -74,35 +65,6 @@ pull_request_rules:
|
|||||||
assignees:
|
assignees:
|
||||||
- "{{ author }}"
|
- "{{ author }}"
|
||||||
|
|
||||||
- name: backport to version-13-pre-release
|
|
||||||
conditions:
|
|
||||||
- label="backport version-13-pre-release"
|
|
||||||
actions:
|
|
||||||
backport:
|
|
||||||
branches:
|
|
||||||
- version-13-pre-release
|
|
||||||
assignees:
|
|
||||||
- "{{ author }}"
|
|
||||||
|
|
||||||
- name: backport to version-12-hotfix
|
|
||||||
conditions:
|
|
||||||
- label="backport version-12-hotfix"
|
|
||||||
actions:
|
|
||||||
backport:
|
|
||||||
branches:
|
|
||||||
- version-12-hotfix
|
|
||||||
assignees:
|
|
||||||
- "{{ author }}"
|
|
||||||
|
|
||||||
- name: backport to version-12-pre-release
|
|
||||||
conditions:
|
|
||||||
- label="backport version-12-pre-release"
|
|
||||||
actions:
|
|
||||||
backport:
|
|
||||||
branches:
|
|
||||||
- version-12-pre-release
|
|
||||||
assignees:
|
|
||||||
- "{{ author }}"
|
|
||||||
|
|
||||||
- name: Automatic merge on CI success and review
|
- name: Automatic merge on CI success and review
|
||||||
conditions:
|
conditions:
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ fail_fast: false
|
|||||||
|
|
||||||
repos:
|
repos:
|
||||||
- repo: https://github.com/pre-commit/pre-commit-hooks
|
- repo: https://github.com/pre-commit/pre-commit-hooks
|
||||||
rev: v4.0.1
|
rev: v4.3.0
|
||||||
hooks:
|
hooks:
|
||||||
- id: trailing-whitespace
|
- id: trailing-whitespace
|
||||||
files: "erpnext.*"
|
files: "erpnext.*"
|
||||||
@@ -15,6 +15,27 @@ repos:
|
|||||||
args: ['--branch', 'develop']
|
args: ['--branch', 'develop']
|
||||||
- id: check-merge-conflict
|
- id: check-merge-conflict
|
||||||
- id: check-ast
|
- id: check-ast
|
||||||
|
- id: check-json
|
||||||
|
- id: check-toml
|
||||||
|
- id: check-yaml
|
||||||
|
- id: debug-statements
|
||||||
|
|
||||||
|
- repo: https://github.com/pre-commit/mirrors-prettier
|
||||||
|
rev: v2.7.1
|
||||||
|
hooks:
|
||||||
|
- id: prettier
|
||||||
|
types_or: [javascript, vue, scss]
|
||||||
|
# Ignore any files that might contain jinja / bundles
|
||||||
|
exclude: |
|
||||||
|
(?x)^(
|
||||||
|
erpnext/public/dist/.*|
|
||||||
|
cypress/.*|
|
||||||
|
.*node_modules.*|
|
||||||
|
.*boilerplate.*|
|
||||||
|
erpnext/public/js/controllers/.*|
|
||||||
|
erpnext/templates/pages/order.js|
|
||||||
|
erpnext/templates/includes/.*
|
||||||
|
)$
|
||||||
|
|
||||||
- repo: https://github.com/pre-commit/mirrors-eslint
|
- repo: https://github.com/pre-commit/mirrors-eslint
|
||||||
rev: v8.44.0
|
rev: v8.44.0
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
{
|
{
|
||||||
"branches": ["version-15"],
|
"branches": ["version-13"],
|
||||||
"plugins": [
|
"plugins": [
|
||||||
"@semantic-release/commit-analyzer", {
|
"@semantic-release/commit-analyzer", {
|
||||||
"preset": "angular",
|
"preset": "angular",
|
||||||
@@ -21,4 +21,4 @@
|
|||||||
],
|
],
|
||||||
"@semantic-release/github"
|
"@semantic-release/github"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
@@ -7,8 +7,7 @@
|
|||||||
<p>ERP made simple</p>
|
<p>ERP made simple</p>
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
[](https://github.com/frappe/erpnext/actions/workflows/server-tests.yml)
|
[](https://github.com/frappe/erpnext/actions/workflows/server-tests-mariadb.yml)
|
||||||
[](https://github.com/erpnext/erpnext_ui_tests/actions/workflows/ui-tests.yml)
|
|
||||||
[](https://www.codetriage.com/frappe/erpnext)
|
[](https://www.codetriage.com/frappe/erpnext)
|
||||||
[](https://codecov.io/gh/frappe/erpnext)
|
[](https://codecov.io/gh/frappe/erpnext)
|
||||||
[](https://hub.docker.com/r/frappe/erpnext-worker)
|
[](https://hub.docker.com/r/frappe/erpnext-worker)
|
||||||
@@ -73,8 +72,6 @@ New passwords will be created for the ERPNext "Administrator" user, the MariaDB
|
|||||||
1. [Issue Guidelines](https://github.com/frappe/erpnext/wiki/Issue-Guidelines)
|
1. [Issue Guidelines](https://github.com/frappe/erpnext/wiki/Issue-Guidelines)
|
||||||
1. [Report Security Vulnerabilities](https://erpnext.com/security)
|
1. [Report Security Vulnerabilities](https://erpnext.com/security)
|
||||||
1. [Pull Request Requirements](https://github.com/frappe/erpnext/wiki/Contribution-Guidelines)
|
1. [Pull Request Requirements](https://github.com/frappe/erpnext/wiki/Contribution-Guidelines)
|
||||||
1. [Translations](https://translate.erpnext.com)
|
|
||||||
|
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|
||||||
|
|||||||
@@ -1,25 +1,13 @@
|
|||||||
module.exports = {
|
module.exports = {
|
||||||
parserPreset: 'conventional-changelog-conventionalcommits',
|
parserPreset: "conventional-changelog-conventionalcommits",
|
||||||
rules: {
|
rules: {
|
||||||
'subject-empty': [2, 'never'],
|
"subject-empty": [2, "never"],
|
||||||
'type-case': [2, 'always', 'lower-case'],
|
"type-case": [2, "always", "lower-case"],
|
||||||
'type-empty': [2, 'never'],
|
"type-empty": [2, "never"],
|
||||||
'type-enum': [
|
"type-enum": [
|
||||||
2,
|
2,
|
||||||
'always',
|
"always",
|
||||||
[
|
["build", "chore", "ci", "docs", "feat", "fix", "perf", "refactor", "revert", "style", "test"],
|
||||||
'build',
|
|
||||||
'chore',
|
|
||||||
'ci',
|
|
||||||
'docs',
|
|
||||||
'feat',
|
|
||||||
'fix',
|
|
||||||
'perf',
|
|
||||||
'refactor',
|
|
||||||
'revert',
|
|
||||||
'style',
|
|
||||||
'test',
|
|
||||||
],
|
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|||||||
4
crowdin.yml
Normal file
4
crowdin.yml
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
files:
|
||||||
|
- source: /erpnext/locale/main.pot
|
||||||
|
translation: /erpnext/locale/%two_letters_code%.po
|
||||||
|
pull_request_title: "chore: sync translations from crowdin"
|
||||||
@@ -3,7 +3,7 @@ import inspect
|
|||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
|
|
||||||
__version__ = "15.6.1"
|
__version__ = "16.0.0-dev"
|
||||||
|
|
||||||
|
|
||||||
def get_default_company(user=None):
|
def get_default_company(user=None):
|
||||||
@@ -13,7 +13,7 @@ def get_default_company(user=None):
|
|||||||
if not user:
|
if not user:
|
||||||
user = frappe.session.user
|
user = frappe.session.user
|
||||||
|
|
||||||
companies = get_user_default_as_list(user, "company")
|
companies = get_user_default_as_list("company", user)
|
||||||
if companies:
|
if companies:
|
||||||
default_company = companies[0]
|
default_company = companies[0]
|
||||||
else:
|
else:
|
||||||
@@ -36,7 +36,7 @@ def get_default_cost_center(company):
|
|||||||
|
|
||||||
if not frappe.flags.company_cost_center:
|
if not frappe.flags.company_cost_center:
|
||||||
frappe.flags.company_cost_center = {}
|
frappe.flags.company_cost_center = {}
|
||||||
if not company in frappe.flags.company_cost_center:
|
if company not in frappe.flags.company_cost_center:
|
||||||
frappe.flags.company_cost_center[company] = frappe.get_cached_value(
|
frappe.flags.company_cost_center[company] = frappe.get_cached_value(
|
||||||
"Company", company, "cost_center"
|
"Company", company, "cost_center"
|
||||||
)
|
)
|
||||||
@@ -47,7 +47,7 @@ def get_company_currency(company):
|
|||||||
"""Returns the default company currency"""
|
"""Returns the default company currency"""
|
||||||
if not frappe.flags.company_currency:
|
if not frappe.flags.company_currency:
|
||||||
frappe.flags.company_currency = {}
|
frappe.flags.company_currency = {}
|
||||||
if not company in frappe.flags.company_currency:
|
if company not in frappe.flags.company_currency:
|
||||||
frappe.flags.company_currency[company] = frappe.db.get_value(
|
frappe.flags.company_currency[company] = frappe.db.get_value(
|
||||||
"Company", company, "default_currency", cache=True
|
"Company", company, "default_currency", cache=True
|
||||||
)
|
)
|
||||||
@@ -81,7 +81,7 @@ def is_perpetual_inventory_enabled(company):
|
|||||||
if not hasattr(frappe.local, "enable_perpetual_inventory"):
|
if not hasattr(frappe.local, "enable_perpetual_inventory"):
|
||||||
frappe.local.enable_perpetual_inventory = {}
|
frappe.local.enable_perpetual_inventory = {}
|
||||||
|
|
||||||
if not company in frappe.local.enable_perpetual_inventory:
|
if company not in frappe.local.enable_perpetual_inventory:
|
||||||
frappe.local.enable_perpetual_inventory[company] = (
|
frappe.local.enable_perpetual_inventory[company] = (
|
||||||
frappe.get_cached_value("Company", company, "enable_perpetual_inventory") or 0
|
frappe.get_cached_value("Company", company, "enable_perpetual_inventory") or 0
|
||||||
)
|
)
|
||||||
@@ -96,7 +96,7 @@ def get_default_finance_book(company=None):
|
|||||||
if not hasattr(frappe.local, "default_finance_book"):
|
if not hasattr(frappe.local, "default_finance_book"):
|
||||||
frappe.local.default_finance_book = {}
|
frappe.local.default_finance_book = {}
|
||||||
|
|
||||||
if not company in frappe.local.default_finance_book:
|
if company not in frappe.local.default_finance_book:
|
||||||
frappe.local.default_finance_book[company] = frappe.get_cached_value(
|
frappe.local.default_finance_book[company] = frappe.get_cached_value(
|
||||||
"Company", company, "default_finance_book"
|
"Company", company, "default_finance_book"
|
||||||
)
|
)
|
||||||
@@ -108,7 +108,7 @@ def get_party_account_type(party_type):
|
|||||||
if not hasattr(frappe.local, "party_account_types"):
|
if not hasattr(frappe.local, "party_account_types"):
|
||||||
frappe.local.party_account_types = {}
|
frappe.local.party_account_types = {}
|
||||||
|
|
||||||
if not party_type in frappe.local.party_account_types:
|
if party_type not in frappe.local.party_account_types:
|
||||||
frappe.local.party_account_types[party_type] = (
|
frappe.local.party_account_types[party_type] = (
|
||||||
frappe.db.get_value("Party Type", party_type, "account_type") or ""
|
frappe.db.get_value("Party Type", party_type, "account_type") or ""
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
frappe.provide('frappe.dashboards.chart_sources');
|
frappe.provide("frappe.dashboards.chart_sources");
|
||||||
|
|
||||||
frappe.dashboards.chart_sources["Account Balance Timeline"] = {
|
frappe.dashboards.chart_sources["Account Balance Timeline"] = {
|
||||||
method: "erpnext.accounts.dashboard_chart_source.account_balance_timeline.account_balance_timeline.get",
|
method: "erpnext.accounts.dashboard_chart_source.account_balance_timeline.account_balance_timeline.get",
|
||||||
@@ -9,14 +9,14 @@ frappe.dashboards.chart_sources["Account Balance Timeline"] = {
|
|||||||
fieldtype: "Link",
|
fieldtype: "Link",
|
||||||
options: "Company",
|
options: "Company",
|
||||||
default: frappe.defaults.get_user_default("Company"),
|
default: frappe.defaults.get_user_default("Company"),
|
||||||
reqd: 1
|
reqd: 1,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
fieldname: "account",
|
fieldname: "account",
|
||||||
label: __("Account"),
|
label: __("Account"),
|
||||||
fieldtype: "Link",
|
fieldtype: "Link",
|
||||||
options: "Account",
|
options: "Account",
|
||||||
reqd: 1
|
reqd: 1,
|
||||||
},
|
},
|
||||||
]
|
],
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -232,7 +232,7 @@ def calculate_monthly_amount(
|
|||||||
if amount + already_booked_amount_in_account_currency > item.net_amount:
|
if amount + already_booked_amount_in_account_currency > item.net_amount:
|
||||||
amount = item.net_amount - already_booked_amount_in_account_currency
|
amount = item.net_amount - already_booked_amount_in_account_currency
|
||||||
|
|
||||||
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:
|
||||||
partial_month = flt(date_diff(end_date, start_date)) / flt(
|
partial_month = flt(date_diff(end_date, start_date)) / flt(
|
||||||
date_diff(get_last_day(end_date), get_first_day(start_date))
|
date_diff(get_last_day(end_date), get_first_day(start_date))
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -26,19 +26,14 @@ frappe.ui.form.on("Account", {
|
|||||||
frm.toggle_enable(["is_group", "company"], false);
|
frm.toggle_enable(["is_group", "company"], false);
|
||||||
|
|
||||||
if (cint(frm.doc.is_group) == 0) {
|
if (cint(frm.doc.is_group) == 0) {
|
||||||
frm.toggle_display(
|
frm.toggle_display("freeze_account", frm.doc.__onload && frm.doc.__onload.can_freeze_account);
|
||||||
"freeze_account",
|
|
||||||
frm.doc.__onload && frm.doc.__onload.can_freeze_account
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// read-only for root accounts
|
// read-only for root accounts
|
||||||
if (!frm.is_new()) {
|
if (!frm.is_new()) {
|
||||||
if (!frm.doc.parent_account) {
|
if (!frm.doc.parent_account) {
|
||||||
frm.set_read_only();
|
frm.set_read_only();
|
||||||
frm.set_intro(
|
frm.set_intro(__("This is a root account and cannot be edited."));
|
||||||
__("This is a root account and cannot be edited.")
|
|
||||||
);
|
|
||||||
} else {
|
} else {
|
||||||
// credit days and type if customer or supplier
|
// credit days and type if customer or supplier
|
||||||
frm.set_intro(null);
|
frm.set_intro(null);
|
||||||
@@ -80,27 +75,33 @@ frappe.ui.form.on("Account", {
|
|||||||
);
|
);
|
||||||
|
|
||||||
if (frm.doc.is_group == 1) {
|
if (frm.doc.is_group == 1) {
|
||||||
frm.add_custom_button(__('Convert to Non-Group'), function () {
|
frm.add_custom_button(
|
||||||
return frappe.call({
|
__("Convert to Non-Group"),
|
||||||
doc: frm.doc,
|
function () {
|
||||||
method: 'convert_group_to_ledger',
|
return frappe.call({
|
||||||
callback: function() {
|
doc: frm.doc,
|
||||||
frm.refresh();
|
method: "convert_group_to_ledger",
|
||||||
}
|
callback: function () {
|
||||||
});
|
frm.refresh();
|
||||||
}, __('Actions'));
|
},
|
||||||
|
});
|
||||||
} else if (cint(frm.doc.is_group) == 0
|
},
|
||||||
&& frappe.boot.user.can_read.indexOf("GL Entry") !== -1) {
|
__("Actions")
|
||||||
frm.add_custom_button(__('General Ledger'), function () {
|
);
|
||||||
frappe.route_options = {
|
} else if (cint(frm.doc.is_group) == 0 && frappe.boot.user.can_read.indexOf("GL Entry") !== -1) {
|
||||||
"account": frm.doc.name,
|
frm.add_custom_button(
|
||||||
"from_date": erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[1],
|
__("General Ledger"),
|
||||||
"to_date": erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[2],
|
function () {
|
||||||
"company": frm.doc.company
|
frappe.route_options = {
|
||||||
};
|
account: frm.doc.name,
|
||||||
frappe.set_route("query-report", "General Ledger");
|
from_date: erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[1],
|
||||||
}, __('View'));
|
to_date: erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[2],
|
||||||
|
company: frm.doc.company,
|
||||||
|
};
|
||||||
|
frappe.set_route("query-report", "General Ledger");
|
||||||
|
},
|
||||||
|
__("View")
|
||||||
|
);
|
||||||
|
|
||||||
frm.add_custom_button(
|
frm.add_custom_button(
|
||||||
__("Convert to Group"),
|
__("Convert to Group"),
|
||||||
@@ -193,14 +194,8 @@ frappe.ui.form.on("Account", {
|
|||||||
if (r.message) {
|
if (r.message) {
|
||||||
frappe.set_route("Form", "Account", r.message);
|
frappe.set_route("Form", "Account", r.message);
|
||||||
} else {
|
} else {
|
||||||
frm.set_value(
|
frm.set_value("account_number", data.account_number);
|
||||||
"account_number",
|
frm.set_value("account_name", data.account_name);
|
||||||
data.account_number
|
|
||||||
);
|
|
||||||
frm.set_value(
|
|
||||||
"account_name",
|
|
||||||
data.account_name
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
d.hide();
|
d.hide();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -108,6 +108,7 @@
|
|||||||
"fieldname": "parent_account",
|
"fieldname": "parent_account",
|
||||||
"fieldtype": "Link",
|
"fieldtype": "Link",
|
||||||
"ignore_user_permissions": 1,
|
"ignore_user_permissions": 1,
|
||||||
|
"in_preview": 1,
|
||||||
"label": "Parent Account",
|
"label": "Parent Account",
|
||||||
"oldfieldname": "parent_account",
|
"oldfieldname": "parent_account",
|
||||||
"oldfieldtype": "Link",
|
"oldfieldtype": "Link",
|
||||||
@@ -192,7 +193,7 @@
|
|||||||
"idx": 1,
|
"idx": 1,
|
||||||
"is_tree": 1,
|
"is_tree": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2023-07-20 18:18:44.405723",
|
"modified": "2024-01-10 04:57:33.681676",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Account",
|
"name": "Account",
|
||||||
@@ -249,8 +250,9 @@
|
|||||||
],
|
],
|
||||||
"search_fields": "account_number",
|
"search_fields": "account_number",
|
||||||
"show_name_in_global_search": 1,
|
"show_name_in_global_search": 1,
|
||||||
|
"show_preview_popup": 1,
|
||||||
"sort_field": "modified",
|
"sort_field": "modified",
|
||||||
"sort_order": "ASC",
|
"sort_order": "ASC",
|
||||||
"states": [],
|
"states": [],
|
||||||
"track_changes": 1
|
"track_changes": 1
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -91,8 +91,8 @@ class Account(NestedSet):
|
|||||||
super(Account, self).on_update()
|
super(Account, self).on_update()
|
||||||
|
|
||||||
def onload(self):
|
def onload(self):
|
||||||
frozen_accounts_modifier = frappe.db.get_value(
|
frozen_accounts_modifier = frappe.db.get_single_value(
|
||||||
"Accounts Settings", "Accounts Settings", "frozen_accounts_modifier"
|
"Accounts Settings", "frozen_accounts_modifier"
|
||||||
)
|
)
|
||||||
if not frozen_accounts_modifier or frozen_accounts_modifier in frappe.get_roles():
|
if not frozen_accounts_modifier or frozen_accounts_modifier in frappe.get_roles():
|
||||||
self.set_onload("can_freeze_account", True)
|
self.set_onload("can_freeze_account", True)
|
||||||
@@ -118,6 +118,7 @@ class Account(NestedSet):
|
|||||||
self.validate_balance_must_be_debit_or_credit()
|
self.validate_balance_must_be_debit_or_credit()
|
||||||
self.validate_account_currency()
|
self.validate_account_currency()
|
||||||
self.validate_root_company_and_sync_account_to_children()
|
self.validate_root_company_and_sync_account_to_children()
|
||||||
|
self.validate_receivable_payable_account_type()
|
||||||
|
|
||||||
def validate_parent_child_account_type(self):
|
def validate_parent_child_account_type(self):
|
||||||
if self.parent_account:
|
if self.parent_account:
|
||||||
@@ -188,6 +189,24 @@ class Account(NestedSet):
|
|||||||
"Balance Sheet" if self.root_type in ("Asset", "Liability", "Equity") else "Profit and Loss"
|
"Balance Sheet" if self.root_type in ("Asset", "Liability", "Equity") else "Profit and Loss"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def validate_receivable_payable_account_type(self):
|
||||||
|
doc_before_save = self.get_doc_before_save()
|
||||||
|
receivable_payable_types = ["Receivable", "Payable"]
|
||||||
|
if (
|
||||||
|
doc_before_save
|
||||||
|
and doc_before_save.account_type in receivable_payable_types
|
||||||
|
and doc_before_save.account_type != self.account_type
|
||||||
|
):
|
||||||
|
# check for ledger entries
|
||||||
|
if frappe.db.get_all("GL Entry", filters={"account": self.name, "is_cancelled": 0}, limit=1):
|
||||||
|
msg = _(
|
||||||
|
"There are ledger entries against this account. Changing {0} to non-{1} in live system will cause incorrect output in 'Accounts {2}' report"
|
||||||
|
).format(
|
||||||
|
frappe.bold("Account Type"), doc_before_save.account_type, doc_before_save.account_type
|
||||||
|
)
|
||||||
|
frappe.msgprint(msg)
|
||||||
|
self.add_comment("Comment", msg)
|
||||||
|
|
||||||
def validate_root_details(self):
|
def validate_root_details(self):
|
||||||
doc_before_save = self.get_doc_before_save()
|
doc_before_save = self.get_doc_before_save()
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
frappe.provide("frappe.treeview_settings")
|
frappe.provide("frappe.treeview_settings");
|
||||||
|
|
||||||
frappe.treeview_settings["Account"] = {
|
frappe.treeview_settings["Account"] = {
|
||||||
breadcrumb: "Accounts",
|
breadcrumb: "Accounts",
|
||||||
@@ -7,12 +7,12 @@ frappe.treeview_settings["Account"] = {
|
|||||||
filters: [
|
filters: [
|
||||||
{
|
{
|
||||||
fieldname: "company",
|
fieldname: "company",
|
||||||
fieldtype:"Select",
|
fieldtype: "Select",
|
||||||
options: erpnext.utils.get_tree_options("company"),
|
options: erpnext.utils.get_tree_options("company"),
|
||||||
label: __("Company"),
|
label: __("Company"),
|
||||||
default: erpnext.utils.get_tree_default("company"),
|
default: erpnext.utils.get_tree_default("company"),
|
||||||
on_change: function() {
|
on_change: function () {
|
||||||
var me = frappe.treeview_settings['Account'].treeview;
|
var me = frappe.treeview_settings["Account"].treeview;
|
||||||
var company = me.page.fields_dict.company.get_value();
|
var company = me.page.fields_dict.company.get_value();
|
||||||
if (!company) {
|
if (!company) {
|
||||||
frappe.throw(__("Please set a Company"));
|
frappe.throw(__("Please set a Company"));
|
||||||
@@ -22,30 +22,36 @@ frappe.treeview_settings["Account"] = {
|
|||||||
args: {
|
args: {
|
||||||
company: company,
|
company: company,
|
||||||
},
|
},
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
if(r.message) {
|
if (r.message) {
|
||||||
let root_company = r.message.length ? r.message[0] : "";
|
let root_company = r.message.length ? r.message[0] : "";
|
||||||
me.page.fields_dict.root_company.set_value(root_company);
|
me.page.fields_dict.root_company.set_value(root_company);
|
||||||
|
|
||||||
frappe.db.get_value("Company", {"name": company}, "allow_account_creation_against_child_company", (r) => {
|
frappe.db.get_value(
|
||||||
frappe.flags.ignore_root_company_validation = r.allow_account_creation_against_child_company;
|
"Company",
|
||||||
});
|
{ name: company },
|
||||||
|
"allow_account_creation_against_child_company",
|
||||||
|
(r) => {
|
||||||
|
frappe.flags.ignore_root_company_validation =
|
||||||
|
r.allow_account_creation_against_child_company;
|
||||||
|
}
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
}
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
fieldname: "root_company",
|
fieldname: "root_company",
|
||||||
fieldtype:"Data",
|
fieldtype: "Data",
|
||||||
label: __("Root Company"),
|
label: __("Root Company"),
|
||||||
hidden: true,
|
hidden: true,
|
||||||
disable_onchange: true
|
disable_onchange: true,
|
||||||
}
|
},
|
||||||
],
|
],
|
||||||
root_label: "Accounts",
|
root_label: "Accounts",
|
||||||
get_tree_nodes: 'erpnext.accounts.utils.get_children',
|
get_tree_nodes: "erpnext.accounts.utils.get_children",
|
||||||
on_get_node: function(nodes, deep=false) {
|
on_get_node: function (nodes, deep = false) {
|
||||||
if (frappe.boot.user.can_read.indexOf("GL Entry") == -1) return;
|
if (frappe.boot.user.can_read.indexOf("GL Entry") == -1) return;
|
||||||
|
|
||||||
let accounts = [];
|
let accounts = [];
|
||||||
@@ -57,151 +63,231 @@ frappe.treeview_settings["Account"] = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
frappe.db.get_single_value("Accounts Settings", "show_balance_in_coa").then((value) => {
|
frappe.db.get_single_value("Accounts Settings", "show_balance_in_coa").then((value) => {
|
||||||
if(value) {
|
if (value) {
|
||||||
|
|
||||||
const get_balances = frappe.call({
|
const get_balances = frappe.call({
|
||||||
method: 'erpnext.accounts.utils.get_account_balances',
|
method: "erpnext.accounts.utils.get_account_balances",
|
||||||
args: {
|
args: {
|
||||||
accounts: accounts,
|
accounts: accounts,
|
||||||
company: cur_tree.args.company
|
company: cur_tree.args.company,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
get_balances.then(r => {
|
get_balances.then((r) => {
|
||||||
if (!r.message || r.message.length == 0) return;
|
if (!r.message || r.message.length == 0) return;
|
||||||
|
|
||||||
for (let account of r.message) {
|
for (let account of r.message) {
|
||||||
|
|
||||||
const node = cur_tree.nodes && cur_tree.nodes[account.value];
|
const node = cur_tree.nodes && cur_tree.nodes[account.value];
|
||||||
if (!node || node.is_root) continue;
|
if (!node || node.is_root) continue;
|
||||||
|
|
||||||
// show Dr if positive since balance is calculated as debit - credit else show Cr
|
// show Dr if positive since balance is calculated as debit - credit else show Cr
|
||||||
const balance = account.balance_in_account_currency || account.balance;
|
const balance = account.balance_in_account_currency || account.balance;
|
||||||
const dr_or_cr = balance > 0 ? "Dr": "Cr";
|
const dr_or_cr = balance > 0 ? __("Dr") : __("Cr");
|
||||||
const format = (value, currency) => format_currency(Math.abs(value), currency);
|
const format = (value, currency) => format_currency(Math.abs(value), currency);
|
||||||
|
|
||||||
if (account.balance!==undefined) {
|
if (account.balance !== undefined) {
|
||||||
node.parent && node.parent.find('.balance-area').remove();
|
node.parent && node.parent.find(".balance-area").remove();
|
||||||
$('<span class="balance-area pull-right">'
|
$(
|
||||||
+ (account.balance_in_account_currency ?
|
'<span class="balance-area pull-right">' +
|
||||||
(format(account.balance_in_account_currency, account.account_currency) + " / ") : "")
|
(account.balance_in_account_currency
|
||||||
+ format(account.balance, account.company_currency)
|
? format(
|
||||||
+ " " + dr_or_cr
|
account.balance_in_account_currency,
|
||||||
+ '</span>').insertBefore(node.$ul);
|
account.account_currency
|
||||||
|
) + " / "
|
||||||
|
: "") +
|
||||||
|
format(account.balance, account.company_currency) +
|
||||||
|
" " +
|
||||||
|
dr_or_cr +
|
||||||
|
"</span>"
|
||||||
|
).insertBefore(node.$ul);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
add_tree_node: 'erpnext.accounts.utils.add_ac',
|
add_tree_node: "erpnext.accounts.utils.add_ac",
|
||||||
menu_items:[
|
menu_items: [
|
||||||
{
|
{
|
||||||
label: __('New Company'),
|
label: __("New Company"),
|
||||||
action: function() { frappe.new_doc("Company", true) },
|
action: function () {
|
||||||
condition: 'frappe.boot.user.can_create.indexOf("Company") !== -1'
|
frappe.new_doc("Company", true);
|
||||||
}
|
},
|
||||||
|
condition: 'frappe.boot.user.can_create.indexOf("Company") !== -1',
|
||||||
|
},
|
||||||
],
|
],
|
||||||
fields: [
|
fields: [
|
||||||
{fieldtype:'Data', fieldname:'account_name', label:__('New Account Name'), reqd:true,
|
{
|
||||||
description: __("Name of new Account. Note: Please don't create accounts for Customers and Suppliers")},
|
fieldtype: "Data",
|
||||||
{fieldtype:'Data', fieldname:'account_number', label:__('Account Number'),
|
fieldname: "account_name",
|
||||||
description: __("Number of new Account, it will be included in the account name as a prefix")},
|
label: __("New Account Name"),
|
||||||
{fieldtype:'Check', fieldname:'is_group', label:__('Is Group'),
|
reqd: true,
|
||||||
description: __('Further accounts can be made under Groups, but entries can be made against non-Groups')},
|
description: __(
|
||||||
{fieldtype:'Select', fieldname:'root_type', label:__('Root Type'),
|
"Name of new Account. Note: Please don't create accounts for Customers and Suppliers"
|
||||||
options: ['Asset', 'Liability', 'Equity', 'Income', 'Expense'].join('\n'),
|
),
|
||||||
depends_on: 'eval:doc.is_group && !doc.parent_account'},
|
},
|
||||||
{fieldtype:'Select', fieldname:'account_type', label:__('Account Type'),
|
{
|
||||||
options: frappe.get_meta("Account").fields.filter(d => d.fieldname=='account_type')[0].options,
|
fieldtype: "Data",
|
||||||
description: __("Optional. This setting will be used to filter in various transactions.")
|
fieldname: "account_number",
|
||||||
|
label: __("Account Number"),
|
||||||
|
description: __("Number of new Account, it will be included in the account name as a prefix"),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
fieldtype: "Check",
|
||||||
|
fieldname: "is_group",
|
||||||
|
label: __("Is Group"),
|
||||||
|
description: __(
|
||||||
|
"Further accounts can be made under Groups, but entries can be made against non-Groups"
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
fieldtype: "Select",
|
||||||
|
fieldname: "root_type",
|
||||||
|
label: __("Root Type"),
|
||||||
|
options: ["Asset", "Liability", "Equity", "Income", "Expense"].join("\n"),
|
||||||
|
depends_on: "eval:doc.is_group && !doc.parent_account",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
fieldtype: "Select",
|
||||||
|
fieldname: "account_type",
|
||||||
|
label: __("Account Type"),
|
||||||
|
options: frappe.get_meta("Account").fields.filter((d) => d.fieldname == "account_type")[0]
|
||||||
|
.options,
|
||||||
|
description: __("Optional. This setting will be used to filter in various transactions."),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
fieldtype: "Float",
|
||||||
|
fieldname: "tax_rate",
|
||||||
|
label: __("Tax Rate"),
|
||||||
|
depends_on: 'eval:doc.is_group==0&&doc.account_type=="Tax"',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
fieldtype: "Link",
|
||||||
|
fieldname: "account_currency",
|
||||||
|
label: __("Currency"),
|
||||||
|
options: "Currency",
|
||||||
|
description: __("Optional. Sets company's default currency, if not specified."),
|
||||||
},
|
},
|
||||||
{fieldtype:'Float', fieldname:'tax_rate', label:__('Tax Rate'),
|
|
||||||
depends_on: 'eval:doc.is_group==0&&doc.account_type=="Tax"'},
|
|
||||||
{fieldtype:'Link', fieldname:'account_currency', label:__('Currency'), options:"Currency",
|
|
||||||
description: __("Optional. Sets company's default currency, if not specified.")}
|
|
||||||
],
|
],
|
||||||
ignore_fields:["parent_account"],
|
ignore_fields: ["parent_account"],
|
||||||
onload: function(treeview) {
|
onload: function (treeview) {
|
||||||
frappe.treeview_settings['Account'].treeview = {};
|
frappe.treeview_settings["Account"].treeview = {};
|
||||||
$.extend(frappe.treeview_settings['Account'].treeview, treeview);
|
$.extend(frappe.treeview_settings["Account"].treeview, treeview);
|
||||||
function get_company() {
|
function get_company() {
|
||||||
return treeview.page.fields_dict.company.get_value();
|
return treeview.page.fields_dict.company.get_value();
|
||||||
}
|
}
|
||||||
|
|
||||||
// tools
|
// tools
|
||||||
treeview.page.add_inner_button(__("Chart of Cost Centers"), function() {
|
treeview.page.add_inner_button(
|
||||||
frappe.set_route('Tree', 'Cost Center', {company: get_company()});
|
__("Chart of Cost Centers"),
|
||||||
}, __('View'));
|
function () {
|
||||||
|
frappe.set_route("Tree", "Cost Center", { company: get_company() });
|
||||||
|
},
|
||||||
|
__("View")
|
||||||
|
);
|
||||||
|
|
||||||
treeview.page.add_inner_button(__("Opening Invoice Creation Tool"), function() {
|
treeview.page.add_inner_button(
|
||||||
frappe.set_route('Form', 'Opening Invoice Creation Tool', {company: get_company()});
|
__("Opening Invoice Creation Tool"),
|
||||||
}, __('View'));
|
function () {
|
||||||
|
frappe.set_route("Form", "Opening Invoice Creation Tool", { company: get_company() });
|
||||||
|
},
|
||||||
|
__("View")
|
||||||
|
);
|
||||||
|
|
||||||
treeview.page.add_inner_button(__("Period Closing Voucher"), function() {
|
treeview.page.add_inner_button(
|
||||||
frappe.set_route('List', 'Period Closing Voucher', {company: get_company()});
|
__("Period Closing Voucher"),
|
||||||
}, __('View'));
|
function () {
|
||||||
|
frappe.set_route("List", "Period Closing Voucher", { company: get_company() });
|
||||||
|
},
|
||||||
|
__("View")
|
||||||
|
);
|
||||||
|
|
||||||
|
treeview.page.add_inner_button(
|
||||||
treeview.page.add_inner_button(__("Journal Entry"), function() {
|
__("Journal Entry"),
|
||||||
frappe.new_doc('Journal Entry', {company: get_company()});
|
function () {
|
||||||
}, __('Create'));
|
frappe.new_doc("Journal Entry", { company: get_company() });
|
||||||
treeview.page.add_inner_button(__("Company"), function() {
|
},
|
||||||
frappe.new_doc('Company');
|
__("Create")
|
||||||
}, __('Create'));
|
);
|
||||||
|
treeview.page.add_inner_button(
|
||||||
|
__("Company"),
|
||||||
|
function () {
|
||||||
|
frappe.new_doc("Company");
|
||||||
|
},
|
||||||
|
__("Create")
|
||||||
|
);
|
||||||
|
|
||||||
// financial statements
|
// financial statements
|
||||||
for (let report of ['Trial Balance', 'General Ledger', 'Balance Sheet',
|
for (let report of [
|
||||||
'Profit and Loss Statement', 'Cash Flow Statement', 'Accounts Payable', 'Accounts Receivable']) {
|
"Trial Balance",
|
||||||
treeview.page.add_inner_button(__(report), function() {
|
"General Ledger",
|
||||||
frappe.set_route('query-report', report, {company: get_company()});
|
"Balance Sheet",
|
||||||
}, __('Financial Statements'));
|
"Profit and Loss Statement",
|
||||||
|
"Cash Flow Statement",
|
||||||
|
"Accounts Payable",
|
||||||
|
"Accounts Receivable",
|
||||||
|
]) {
|
||||||
|
treeview.page.add_inner_button(
|
||||||
|
__(report),
|
||||||
|
function () {
|
||||||
|
frappe.set_route("query-report", report, { company: get_company() });
|
||||||
|
},
|
||||||
|
__("Financial Statements")
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
},
|
},
|
||||||
post_render: function(treeview) {
|
post_render: function (treeview) {
|
||||||
frappe.treeview_settings['Account'].treeview["tree"] = treeview.tree;
|
frappe.treeview_settings["Account"].treeview["tree"] = treeview.tree;
|
||||||
treeview.page.set_primary_action(__("New"), function() {
|
treeview.page.set_primary_action(
|
||||||
let root_company = treeview.page.fields_dict.root_company.get_value();
|
__("New"),
|
||||||
|
function () {
|
||||||
|
let root_company = treeview.page.fields_dict.root_company.get_value();
|
||||||
|
|
||||||
if(root_company) {
|
if (root_company) {
|
||||||
frappe.throw(__("Please add the account to root level Company - {0}"), [root_company]);
|
frappe.throw(__("Please add the account to root level Company - {0}"), [root_company]);
|
||||||
} else {
|
} else {
|
||||||
treeview.new_node();
|
treeview.new_node();
|
||||||
}
|
}
|
||||||
}, "add");
|
},
|
||||||
|
"add"
|
||||||
|
);
|
||||||
},
|
},
|
||||||
toolbar: [
|
toolbar: [
|
||||||
{
|
{
|
||||||
label:__("Add Child"),
|
label: __("Add Child"),
|
||||||
condition: function(node) {
|
condition: function (node) {
|
||||||
return frappe.boot.user.can_create.indexOf("Account") !== -1
|
return (
|
||||||
&& (!frappe.treeview_settings['Account'].treeview.page.fields_dict.root_company.get_value()
|
frappe.boot.user.can_create.indexOf("Account") !== -1 &&
|
||||||
|| frappe.flags.ignore_root_company_validation)
|
(!frappe.treeview_settings[
|
||||||
&& node.expandable && !node.hide_add;
|
"Account"
|
||||||
|
].treeview.page.fields_dict.root_company.get_value() ||
|
||||||
|
frappe.flags.ignore_root_company_validation) &&
|
||||||
|
node.expandable &&
|
||||||
|
!node.hide_add
|
||||||
|
);
|
||||||
},
|
},
|
||||||
click: function() {
|
click: function () {
|
||||||
var me = frappe.views.trees['Account'];
|
var me = frappe.views.trees["Account"];
|
||||||
me.new_node();
|
me.new_node();
|
||||||
},
|
},
|
||||||
btnClass: "hidden-xs"
|
btnClass: "hidden-xs",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
condition: function(node) {
|
condition: function (node) {
|
||||||
return !node.root && frappe.boot.user.can_read.indexOf("GL Entry") !== -1
|
return !node.root && frappe.boot.user.can_read.indexOf("GL Entry") !== -1;
|
||||||
},
|
},
|
||||||
label: __("View Ledger"),
|
label: __("View Ledger"),
|
||||||
click: function(node, btn) {
|
click: function (node, btn) {
|
||||||
frappe.route_options = {
|
frappe.route_options = {
|
||||||
"account": node.label,
|
account: node.label,
|
||||||
"from_date": erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[1],
|
from_date: erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[1],
|
||||||
"to_date": erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[2],
|
to_date: erpnext.utils.get_fiscal_year(frappe.datetime.get_today(), true)[2],
|
||||||
"company": frappe.treeview_settings['Account'].treeview.page.fields_dict.company.get_value()
|
company:
|
||||||
|
frappe.treeview_settings["Account"].treeview.page.fields_dict.company.get_value(),
|
||||||
};
|
};
|
||||||
frappe.set_route("query-report", "General Ledger");
|
frappe.set_route("query-report", "General Ledger");
|
||||||
},
|
},
|
||||||
btnClass: "hidden-xs"
|
btnClass: "hidden-xs",
|
||||||
}
|
},
|
||||||
],
|
],
|
||||||
extend_toolbar: true
|
extend_toolbar: true,
|
||||||
}
|
};
|
||||||
|
|||||||
@@ -74,7 +74,7 @@ def create_charts(
|
|||||||
# after all accounts are already inserted.
|
# after all accounts are already inserted.
|
||||||
frappe.local.flags.ignore_update_nsm = True
|
frappe.local.flags.ignore_update_nsm = True
|
||||||
_import_accounts(chart, None, None, root_account=True)
|
_import_accounts(chart, None, None, root_account=True)
|
||||||
rebuild_tree("Account", "parent_account")
|
rebuild_tree("Account")
|
||||||
frappe.local.flags.ignore_update_nsm = False
|
frappe.local.flags.ignore_update_nsm = False
|
||||||
|
|
||||||
|
|
||||||
@@ -231,6 +231,8 @@ def build_account_tree(tree, parent, all_accounts):
|
|||||||
tree[child.account_name]["account_type"] = child.account_type
|
tree[child.account_name]["account_type"] = child.account_type
|
||||||
if child.tax_rate:
|
if child.tax_rate:
|
||||||
tree[child.account_name]["tax_rate"] = child.tax_rate
|
tree[child.account_name]["tax_rate"] = child.tax_rate
|
||||||
|
if child.account_currency:
|
||||||
|
tree[child.account_name]["account_currency"] = child.account_currency
|
||||||
if not parent:
|
if not parent:
|
||||||
tree[child.account_name]["root_type"] = child.root_type
|
tree[child.account_name]["root_type"] = child.root_type
|
||||||
|
|
||||||
|
|||||||
@@ -26,7 +26,7 @@
|
|||||||
"0360 Bauliche Investitionen in fremden (gepachteten) Betriebs- und Geschäftsgebäuden": {"account_type": "Fixed Asset"},
|
"0360 Bauliche Investitionen in fremden (gepachteten) Betriebs- und Geschäftsgebäuden": {"account_type": "Fixed Asset"},
|
||||||
"0370 Bauliche Investitionen in fremden (gepachteten) Wohn- und Sozialgebäuden": {"account_type": "Fixed Asset"},
|
"0370 Bauliche Investitionen in fremden (gepachteten) Wohn- und Sozialgebäuden": {"account_type": "Fixed Asset"},
|
||||||
"0390 Kumulierte Abschreibungen zu Grundstücken ": {"account_type": "Fixed Asset"},
|
"0390 Kumulierte Abschreibungen zu Grundstücken ": {"account_type": "Fixed Asset"},
|
||||||
"0400 Maschinen und Geräte ": {"account_type": "Fixed Asset"},
|
"0400 Maschinen und Geräte ": {"account_type": "Fixed Asset"},
|
||||||
"0500 Maschinenwerkzeuge ": {"account_type": "Fixed Asset"},
|
"0500 Maschinenwerkzeuge ": {"account_type": "Fixed Asset"},
|
||||||
"0510 Allgemeine Werkzeuge und Handwerkzeuge ": {"account_type": "Fixed Asset"},
|
"0510 Allgemeine Werkzeuge und Handwerkzeuge ": {"account_type": "Fixed Asset"},
|
||||||
"0520 Prototypen, Formen, Modelle ": {"account_type": "Fixed Asset"},
|
"0520 Prototypen, Formen, Modelle ": {"account_type": "Fixed Asset"},
|
||||||
@@ -65,42 +65,41 @@
|
|||||||
"0980 Geleistete Anzahlungen auf Finanzanlagen ": {"account_type": "Fixed Asset"},
|
"0980 Geleistete Anzahlungen auf Finanzanlagen ": {"account_type": "Fixed Asset"},
|
||||||
"0990 Kumulierte Abschreibungen zu Finanzanlagen ": {"account_type": "Fixed Asset"},
|
"0990 Kumulierte Abschreibungen zu Finanzanlagen ": {"account_type": "Fixed Asset"},
|
||||||
"root_type": "Asset"
|
"root_type": "Asset"
|
||||||
},
|
},
|
||||||
"Klasse 1 Aktiva: Vorr\u00e4te": {
|
"Klasse 1 Aktiva: Vorr\u00e4te": {
|
||||||
"1000 Bezugsverrechnung": {"account_type": "Stock"},
|
"1000 Bezugsverrechnung": {"account_type": "Stock"},
|
||||||
"1100 Rohstoffe": {"account_type": "Stock"},
|
"1100 Rohstoffe": {"account_type": "Stock"},
|
||||||
"1200 Bezogene Teile": {"account_type": "Stock"},
|
"1200 Bezogene Teile": {"account_type": "Stock"},
|
||||||
"1300 Hilfsstoffe": {"account_type": "Stock"},
|
"1300 Hilfsstoffe": {"account_type": "Stock"},
|
||||||
"1350 Betriebsstoffe": {"account_type": "Stock"},
|
"1350 Betriebsstoffe": {"account_type": "Stock"},
|
||||||
"1360 Vorrat Energietraeger": {"account_type": "Stock"},
|
"1360 Vorrat Energietraeger": {"account_type": "Stock"},
|
||||||
"1400 Unfertige Erzeugnisse": {"account_type": "Stock"},
|
"1400 Unfertige Erzeugnisse": {"account_type": "Stock"},
|
||||||
"1500 Fertige Erzeugnisse": {"account_type": "Stock"},
|
"1500 Fertige Erzeugnisse": {"account_type": "Stock"},
|
||||||
"1600 Handelswarenvorrat": {"account_type": "Stock Received But Not Billed"},
|
"1600 Handelswarenvorrat": {"account_type": "Stock Received But Not Billed"},
|
||||||
"1700 Noch nicht abrechenbare Leistungen": {"account_type": "Stock"},
|
"1700 Noch nicht abrechenbare Leistungen": {"account_type": "Stock"},
|
||||||
"1900 Wertberichtigungen": {"account_type": "Stock"},
|
|
||||||
"1800 Geleistete Anzahlungen": {"account_type": "Stock"},
|
"1800 Geleistete Anzahlungen": {"account_type": "Stock"},
|
||||||
"1900 Wertberichtigungen": {"account_type": "Stock"},
|
"1900 Wertberichtigungen": {"account_type": "Stock"},
|
||||||
"root_type": "Asset"
|
"root_type": "Asset"
|
||||||
},
|
},
|
||||||
"Klasse 3 Passiva: Verbindlichkeiten": {
|
"Klasse 3 Passiva: Verbindlichkeiten": {
|
||||||
"3000 Allgemeine Verbindlichkeiten (Schuld)": {"account_type": "Payable"},
|
"3000 Allgemeine Verbindlichkeiten (Schuld)": {"account_type": "Payable"},
|
||||||
"3010 R\u00fcckstellungen f\u00fcr Pensionen": {"account_type": "Payable"},
|
"3010 R\u00fcckstellungen f\u00fcr Pensionen": {"account_type": "Payable"},
|
||||||
"3020 Steuerr\u00fcckstellungen": {"account_type": "Tax"},
|
"3020 Steuerr\u00fcckstellungen": {"account_type": "Tax"},
|
||||||
"3041 Sonstige R\u00fcckstellungen": {"account_type": "Payable"},
|
"3041 Sonstige R\u00fcckstellungen": {"account_type": "Payable"},
|
||||||
"3110 Verbindlichkeiten gegen\u00fcber Bank": {"account_type": "Payable"},
|
"3110 Verbindlichkeiten gegen\u00fcber Bank": {"account_type": "Payable"},
|
||||||
"3150 Verbindlichkeiten Darlehen": {"account_type": "Payable"},
|
"3150 Verbindlichkeiten Darlehen": {"account_type": "Payable"},
|
||||||
"3185 Verbindlichkeiten Kreditkarte": {"account_type": "Payable"},
|
"3185 Verbindlichkeiten Kreditkarte": {"account_type": "Payable"},
|
||||||
"3380 Verbindlichkeiten aus der Annahme gezogener Wechsel u. d. Ausstellungen eigener Wechsel": {
|
"3380 Verbindlichkeiten aus der Annahme gezogener Wechsel u. d. Ausstellungen eigener Wechsel": {
|
||||||
"account_type": "Payable"
|
"account_type": "Payable"
|
||||||
},
|
},
|
||||||
"3400 Verbindlichkeiten gegen\u00fc. verb. Untern., Verbindl. gegen\u00fc. Untern., mit denen eine Beteiligungsverh\u00e4lnis besteht": {},
|
"3400 Verbindlichkeiten gegen\u00fc. verb. Untern., Verbindl. gegen\u00fc. Untern., mit denen eine Beteiligungsverh\u00e4lnis besteht": {},
|
||||||
"3460 Verbindlichkeiten gegenueber Gesellschaftern": {"account_type": "Payable"},
|
"3460 Verbindlichkeiten gegenueber Gesellschaftern": {"account_type": "Payable"},
|
||||||
"3470 Einlagen stiller Gesellschafter": {"account_type": "Payable"},
|
"3470 Einlagen stiller Gesellschafter": {"account_type": "Payable"},
|
||||||
"3585 Verbindlichkeiten Lohnsteuer": {"account_type": "Tax"},
|
"3585 Verbindlichkeiten Lohnsteuer": {"account_type": "Tax"},
|
||||||
"3590 Verbindlichkeiten Kommunalabgaben": {"account_type": "Tax"},
|
"3590 Verbindlichkeiten Kommunalabgaben": {"account_type": "Tax"},
|
||||||
"3595 Verbindlichkeiten Dienstgeberbeitrag": {"account_type": "Tax"},
|
"3595 Verbindlichkeiten Dienstgeberbeitrag": {"account_type": "Tax"},
|
||||||
"3600 Verbindlichkeiten Sozialversicherung": {"account_type": "Payable"},
|
"3600 Verbindlichkeiten Sozialversicherung": {"account_type": "Payable"},
|
||||||
"3640 Verbindlichkeiten Loehne und Gehaelter": {"account_type": "Payable"},
|
"3640 Verbindlichkeiten Loehne und Gehaelter": {"account_type": "Payable"},
|
||||||
"3700 Sonstige Verbindlichkeiten": {"account_type": "Payable"},
|
"3700 Sonstige Verbindlichkeiten": {"account_type": "Payable"},
|
||||||
"3900 Passive Rechnungsabgrenzungsposten": {"account_type": "Payable"},
|
"3900 Passive Rechnungsabgrenzungsposten": {"account_type": "Payable"},
|
||||||
"3100 Anleihen (einschlie\u00dflich konvertibler)": {"account_type": "Payable"},
|
"3100 Anleihen (einschlie\u00dflich konvertibler)": {"account_type": "Payable"},
|
||||||
@@ -119,13 +118,13 @@
|
|||||||
},
|
},
|
||||||
"3515 Umsatzsteuer Inland 10%": {
|
"3515 Umsatzsteuer Inland 10%": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"3520 Umsatzsteuer aus i.g. Erwerb 20%": {
|
"3520 Umsatzsteuer aus i.g. Erwerb 20%": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"3525 Umsatzsteuer aus i.g. Erwerb 10%": {
|
"3525 Umsatzsteuer aus i.g. Erwerb 10%": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"3560 Umsatzsteuer-Evidenzkonto f\u00fcr erhaltene Anzahlungen auf Bestellungen": {},
|
"3560 Umsatzsteuer-Evidenzkonto f\u00fcr erhaltene Anzahlungen auf Bestellungen": {},
|
||||||
"3360 Verbindlichkeiten aus Lieferungen u. Leistungen EU": {
|
"3360 Verbindlichkeiten aus Lieferungen u. Leistungen EU": {
|
||||||
"account_type": "Payable"
|
"account_type": "Payable"
|
||||||
@@ -141,7 +140,7 @@
|
|||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"root_type": "Liability"
|
"root_type": "Liability"
|
||||||
},
|
},
|
||||||
"Klasse 2 Aktiva: Umlaufverm\u00f6gen, Rechnungsabgrenzungen": {
|
"Klasse 2 Aktiva: Umlaufverm\u00f6gen, Rechnungsabgrenzungen": {
|
||||||
"2030 Forderungen aus Lieferungen und Leistungen Inland (0% USt, umsatzsteuerfrei)": {
|
"2030 Forderungen aus Lieferungen und Leistungen Inland (0% USt, umsatzsteuerfrei)": {
|
||||||
"account_type": "Receivable"
|
"account_type": "Receivable"
|
||||||
@@ -154,7 +153,7 @@
|
|||||||
},
|
},
|
||||||
"2040 Forderungen aus Lieferungen und Leistungen Inland (sonstiger USt-Satz)": {
|
"2040 Forderungen aus Lieferungen und Leistungen Inland (sonstiger USt-Satz)": {
|
||||||
"account_type": "Receivable"
|
"account_type": "Receivable"
|
||||||
},
|
},
|
||||||
"2100 Forderungen aus Lieferungen und Leistungen EU": {
|
"2100 Forderungen aus Lieferungen und Leistungen EU": {
|
||||||
"account_type": "Receivable"
|
"account_type": "Receivable"
|
||||||
},
|
},
|
||||||
@@ -192,7 +191,7 @@
|
|||||||
"account_type": "Receivable"
|
"account_type": "Receivable"
|
||||||
},
|
},
|
||||||
"2570 Einfuhrumsatzsteuer (bezahlt)": {"account_type": "Tax"},
|
"2570 Einfuhrumsatzsteuer (bezahlt)": {"account_type": "Tax"},
|
||||||
|
|
||||||
"2460 Eingeforderte aber noch nicht eingezahlte Einlagen": {
|
"2460 Eingeforderte aber noch nicht eingezahlte Einlagen": {
|
||||||
"account_type": "Receivable"
|
"account_type": "Receivable"
|
||||||
},
|
},
|
||||||
@@ -243,10 +242,10 @@
|
|||||||
},
|
},
|
||||||
"2800 Guthaben bei Bank": {
|
"2800 Guthaben bei Bank": {
|
||||||
"account_type": "Bank"
|
"account_type": "Bank"
|
||||||
},
|
},
|
||||||
"2801 Guthaben bei Bank - Sparkonto": {
|
"2801 Guthaben bei Bank - Sparkonto": {
|
||||||
"account_type": "Bank"
|
"account_type": "Bank"
|
||||||
},
|
},
|
||||||
"2810 Guthaben bei Paypal": {
|
"2810 Guthaben bei Paypal": {
|
||||||
"account_type": "Bank"
|
"account_type": "Bank"
|
||||||
},
|
},
|
||||||
@@ -264,19 +263,19 @@
|
|||||||
},
|
},
|
||||||
"2895 Schwebende Geldbewegugen": {
|
"2895 Schwebende Geldbewegugen": {
|
||||||
"account_type": "Bank"
|
"account_type": "Bank"
|
||||||
},
|
},
|
||||||
"2513 Vorsteuer Inland 5%": {
|
"2513 Vorsteuer Inland 5%": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"2515 Vorsteuer Inland 20%": {
|
"2515 Vorsteuer Inland 20%": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"2520 Vorsteuer aus innergemeinschaftlichem Erwerb 10%": {
|
"2520 Vorsteuer aus innergemeinschaftlichem Erwerb 10%": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"2525 Vorsteuer aus innergemeinschaftlichem Erwerb 20%": {
|
"2525 Vorsteuer aus innergemeinschaftlichem Erwerb 20%": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
"2530 Vorsteuer \u00a719/Art 19 ( reverse charge ) ": {
|
"2530 Vorsteuer \u00a719/Art 19 ( reverse charge ) ": {
|
||||||
"account_type": "Tax"
|
"account_type": "Tax"
|
||||||
},
|
},
|
||||||
@@ -286,16 +285,16 @@
|
|||||||
"root_type": "Asset"
|
"root_type": "Asset"
|
||||||
},
|
},
|
||||||
"Klasse 4: Betriebliche Erträge": {
|
"Klasse 4: Betriebliche Erträge": {
|
||||||
"4000 Erlöse 20 %": {"account_type": "Income Account"},
|
"4000 Erlöse 20 %": {"account_type": "Income Account"},
|
||||||
"4020 Erl\u00f6se 0 % steuerbefreit": {"account_type": "Income Account"},
|
"4020 Erl\u00f6se 0 % steuerbefreit": {"account_type": "Income Account"},
|
||||||
"4010 Erl\u00f6se 10 %": {"account_type": "Income Account"},
|
"4010 Erl\u00f6se 10 %": {"account_type": "Income Account"},
|
||||||
"4030 Erl\u00f6se 13 %": {"account_type": "Income Account"},
|
"4030 Erl\u00f6se 13 %": {"account_type": "Income Account"},
|
||||||
"4040 Erl\u00f6se 0 % innergemeinschaftliche Lieferungen": {"account_type": "Income Account"},
|
"4040 Erl\u00f6se 0 % innergemeinschaftliche Lieferungen": {"account_type": "Income Account"},
|
||||||
"4400 Erl\u00f6sreduktion 0 % steuerbefreit": {"account_type": "Expense Account"},
|
"4400 Erl\u00f6sreduktion 0 % steuerbefreit": {"account_type": "Expense Account"},
|
||||||
"4410 Erl\u00f6sreduktion 10 %": {"account_type": "Expense Account"},
|
"4410 Erl\u00f6sreduktion 10 %": {"account_type": "Expense Account"},
|
||||||
"4420 Erl\u00f6sreduktion 20 %": {"account_type": "Expense Account"},
|
"4420 Erl\u00f6sreduktion 20 %": {"account_type": "Expense Account"},
|
||||||
"4430 Erl\u00f6sreduktion 13 %": {"account_type": "Expense Account"},
|
"4430 Erl\u00f6sreduktion 13 %": {"account_type": "Expense Account"},
|
||||||
"4440 Erl\u00f6sreduktion 0 % innergemeinschaftliche Lieferungen": {"account_type": "Expense Account"},
|
"4440 Erl\u00f6sreduktion 0 % innergemeinschaftliche Lieferungen": {"account_type": "Expense Account"},
|
||||||
"4500 Ver\u00e4nderungen des Bestandes an fertigen und unfertigen Erzeugn. sowie an noch nicht abrechenbaren Leistungen": {"account_type": "Income Account"},
|
"4500 Ver\u00e4nderungen des Bestandes an fertigen und unfertigen Erzeugn. sowie an noch nicht abrechenbaren Leistungen": {"account_type": "Income Account"},
|
||||||
"4580 Aktivierte Eigenleistungen": {"account_type": "Income Account"},
|
"4580 Aktivierte Eigenleistungen": {"account_type": "Income Account"},
|
||||||
"4600 Erl\u00f6se aus dem Abgang vom Anlageverm\u00f6gen, ausgen. Finanzanlagen": {"account_type": "Income Account"},
|
"4600 Erl\u00f6se aus dem Abgang vom Anlageverm\u00f6gen, ausgen. Finanzanlagen": {"account_type": "Income Account"},
|
||||||
@@ -304,15 +303,15 @@
|
|||||||
"4700 Ertr\u00e4ge aus der Aufl\u00f6sung von R\u00fcckstellungen": {"account_type": "Income Account"},
|
"4700 Ertr\u00e4ge aus der Aufl\u00f6sung von R\u00fcckstellungen": {"account_type": "Income Account"},
|
||||||
"4800 \u00dcbrige betriebliche Ertr\u00e4ge": {"account_type": "Income Account"},
|
"4800 \u00dcbrige betriebliche Ertr\u00e4ge": {"account_type": "Income Account"},
|
||||||
"root_type": "Income"
|
"root_type": "Income"
|
||||||
},
|
},
|
||||||
"Klasse 5: Aufwand f\u00fcr Material und Leistungen": {
|
"Klasse 5: Aufwand f\u00fcr Material und Leistungen": {
|
||||||
"5000 Einkauf Partnerleistungen": {"account_type": "Cost of Goods Sold"},
|
"5000 Einkauf Partnerleistungen": {"account_type": "Cost of Goods Sold"},
|
||||||
"5100 Verbrauch an Rohstoffen": {"account_type": "Cost of Goods Sold"},
|
"5100 Verbrauch an Rohstoffen": {"account_type": "Cost of Goods Sold"},
|
||||||
"5200 Verbrauch von bezogenen Fertig- und Einzelteilen": {"account_type": "Cost of Goods Sold"},
|
"5200 Verbrauch von bezogenen Fertig- und Einzelteilen": {"account_type": "Cost of Goods Sold"},
|
||||||
"5300 Verbrauch von Hilfsstoffen": {"account_type": "Cost of Goods Sold"},
|
"5300 Verbrauch von Hilfsstoffen": {"account_type": "Cost of Goods Sold"},
|
||||||
"5340 Verbrauch Verpackungsmaterial": {"account_type": "Cost of Goods Sold"},
|
"5340 Verbrauch Verpackungsmaterial": {"account_type": "Cost of Goods Sold"},
|
||||||
"5470 Verbrauch von Kleinmaterial": {"account_type": "Cost of Goods Sold"},
|
"5470 Verbrauch von Kleinmaterial": {"account_type": "Cost of Goods Sold"},
|
||||||
"5450 Verbrauch von Reinigungsmaterial": {"account_type": "Cost of Goods Sold"},
|
"5450 Verbrauch von Reinigungsmaterial": {"account_type": "Cost of Goods Sold"},
|
||||||
"5400 Verbrauch von Betriebsstoffen": {"account_type": "Cost of Goods Sold"},
|
"5400 Verbrauch von Betriebsstoffen": {"account_type": "Cost of Goods Sold"},
|
||||||
"5500 Verbrauch von Werkzeugen und anderen Erzeugungshilfsmittel": {"account_type": "Cost of Goods Sold"},
|
"5500 Verbrauch von Werkzeugen und anderen Erzeugungshilfsmittel": {"account_type": "Cost of Goods Sold"},
|
||||||
"5600 Verbrauch von Brenn- und Treibstoffen, Energie und Wasser": {"account_type": "Cost of Goods Sold"},
|
"5600 Verbrauch von Brenn- und Treibstoffen, Energie und Wasser": {"account_type": "Cost of Goods Sold"},
|
||||||
@@ -340,7 +339,7 @@
|
|||||||
"6700 Sonstige Sozialaufwendungen": {"account_type": "Payable"},
|
"6700 Sonstige Sozialaufwendungen": {"account_type": "Payable"},
|
||||||
"6900 Aufwandsstellenrechnung Personal": {"account_type": "Payable"},
|
"6900 Aufwandsstellenrechnung Personal": {"account_type": "Payable"},
|
||||||
"root_type": "Expense"
|
"root_type": "Expense"
|
||||||
},
|
},
|
||||||
"Klasse 7: Abschreibungen und sonstige betriebliche Aufwendungen": {
|
"Klasse 7: Abschreibungen und sonstige betriebliche Aufwendungen": {
|
||||||
"7010 Abschreibungen auf das Anlageverm\u00f6gen (ausgenommen Finanzanlagen)": {"account_type": "Depreciation"},
|
"7010 Abschreibungen auf das Anlageverm\u00f6gen (ausgenommen Finanzanlagen)": {"account_type": "Depreciation"},
|
||||||
"7100 Sonstige Steuern und Geb\u00fchren": {"account_type": "Tax"},
|
"7100 Sonstige Steuern und Geb\u00fchren": {"account_type": "Tax"},
|
||||||
@@ -349,7 +348,7 @@
|
|||||||
"7310 Fahrrad - Aufwand": {"account_type": "Expense Account"},
|
"7310 Fahrrad - Aufwand": {"account_type": "Expense Account"},
|
||||||
"7320 Kfz - Aufwand": {"account_type": "Expense Account"},
|
"7320 Kfz - Aufwand": {"account_type": "Expense Account"},
|
||||||
"7330 LKW - Aufwand": {"account_type": "Expense Account"},
|
"7330 LKW - Aufwand": {"account_type": "Expense Account"},
|
||||||
"7340 Lastenrad - Aufwand": {"account_type": "Expense Account"},
|
"7340 Lastenrad - Aufwand": {"account_type": "Expense Account"},
|
||||||
"7350 Reise- und Fahraufwand": {"account_type": "Expense Account"},
|
"7350 Reise- und Fahraufwand": {"account_type": "Expense Account"},
|
||||||
"7360 Tag- und N\u00e4chtigungsgelder": {"account_type": "Expense Account"},
|
"7360 Tag- und N\u00e4chtigungsgelder": {"account_type": "Expense Account"},
|
||||||
"7380 Nachrichtenaufwand": {"account_type": "Expense Account"},
|
"7380 Nachrichtenaufwand": {"account_type": "Expense Account"},
|
||||||
@@ -409,7 +408,7 @@
|
|||||||
"8990 Gewinnabfuhr bzw. Verlust\u00fcberrechnung aus Ergebnisabf\u00fchrungsvertr\u00e4gen": {"account_type": "Expense Account"},
|
"8990 Gewinnabfuhr bzw. Verlust\u00fcberrechnung aus Ergebnisabf\u00fchrungsvertr\u00e4gen": {"account_type": "Expense Account"},
|
||||||
"8350 nicht ausgenutzte Lieferantenskonti": {"account_type": "Expense Account"},
|
"8350 nicht ausgenutzte Lieferantenskonti": {"account_type": "Expense Account"},
|
||||||
"root_type": "Income"
|
"root_type": "Income"
|
||||||
},
|
},
|
||||||
"Klasse 9 Passiva: Eigenkapital, R\u00fccklagen, stille Einlagen, Abschlusskonten": {
|
"Klasse 9 Passiva: Eigenkapital, R\u00fccklagen, stille Einlagen, Abschlusskonten": {
|
||||||
"9000 Gezeichnetes bzw. gewidmetes Kapital": {
|
"9000 Gezeichnetes bzw. gewidmetes Kapital": {
|
||||||
"account_type": "Equity"
|
"account_type": "Equity"
|
||||||
@@ -435,5 +434,5 @@
|
|||||||
},
|
},
|
||||||
"root_type": "Equity"
|
"root_type": "Equity"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -56,7 +56,9 @@
|
|||||||
"Constru\u00e7\u00f5es em Andamento de Im\u00f3veis Destinados \u00e0 Venda": {},
|
"Constru\u00e7\u00f5es em Andamento de Im\u00f3veis Destinados \u00e0 Venda": {},
|
||||||
"Estoques Destinados \u00e0 Doa\u00e7\u00e3o": {},
|
"Estoques Destinados \u00e0 Doa\u00e7\u00e3o": {},
|
||||||
"Im\u00f3veis Destinados \u00e0 Venda": {},
|
"Im\u00f3veis Destinados \u00e0 Venda": {},
|
||||||
"Insumos (materiais diretos)": {},
|
"Insumos (materiais diretos)": {
|
||||||
|
"account_type": "Stock"
|
||||||
|
},
|
||||||
"Insumos Agropecu\u00e1rios": {},
|
"Insumos Agropecu\u00e1rios": {},
|
||||||
"Mercadorias para Revenda": {},
|
"Mercadorias para Revenda": {},
|
||||||
"Outras 11": {},
|
"Outras 11": {},
|
||||||
@@ -146,6 +148,65 @@
|
|||||||
"root_type": "Asset"
|
"root_type": "Asset"
|
||||||
},
|
},
|
||||||
"CUSTOS DE PRODU\u00c7\u00c3O": {
|
"CUSTOS DE PRODU\u00c7\u00c3O": {
|
||||||
|
"CUSTO DOS PRODUTOS E SERVI\u00c7OS VENDIDOS": {
|
||||||
|
"CUSTO DOS PRODUTOS VENDIDOS": {
|
||||||
|
"CUSTO DOS PRODUTOS VENDIDOS PARA AS DEMAIS ATIVIDADES": {
|
||||||
|
"Custos dos Produtos Vendidos em Geral": {
|
||||||
|
"account_type": "Cost of Goods Sold"
|
||||||
|
},
|
||||||
|
"Outros Custos 4": {},
|
||||||
|
"account_type": "Cost of Goods Sold"
|
||||||
|
},
|
||||||
|
"CUSTO DOS PRODUTOS VENDIDOS PARA ASSIST\u00caNCIA SOCIAL": {
|
||||||
|
"Custos dos Produtos para Assist\u00eancia Social - Gratuidades": {},
|
||||||
|
"Custos dos Produtos para Assist\u00eancia Social - Vendidos": {},
|
||||||
|
"Outras": {}
|
||||||
|
},
|
||||||
|
"CUSTO DOS PRODUTOS VENDIDOS PARA EDUCA\u00c7\u00c3O": {
|
||||||
|
"Custos dos Produtos para Educa\u00e7\u00e3o - Gratuidades": {},
|
||||||
|
"Custos dos Produtos para Educa\u00e7\u00e3o - Vendidos": {},
|
||||||
|
"Outros Custos 6": {}
|
||||||
|
},
|
||||||
|
"CUSTO DOS PRODUTOS VENDIDOS PARA SA\u00daDE": {
|
||||||
|
"Custos dos Produtos para Sa\u00fade - Gratuidades": {},
|
||||||
|
"Custos dos Produtos para Sa\u00fade \u2013 Vendidos": {},
|
||||||
|
"Outros Custos 5": {}
|
||||||
|
},
|
||||||
|
"account_type": "Cost of Goods Sold"
|
||||||
|
},
|
||||||
|
"CUSTO DOS SERVI\u00c7OS PRESTADOS": {
|
||||||
|
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA AS DEMAIS ATIVIDADES": {
|
||||||
|
"Custo dos Servi\u00e7os Prestados em Geral": {},
|
||||||
|
"Outros Custos": {}
|
||||||
|
},
|
||||||
|
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA ASSIST\u00caNCIA SOCIAL": {
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios/Contratos/Parcerias": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es 1": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es/Subven\u00e7\u00f5es Vinculadas 1": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Gratuidade 1": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Pacientes Particulares": {},
|
||||||
|
"Outros Custos 2": {}
|
||||||
|
},
|
||||||
|
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA EDUCA\u00c7\u00c3O": {
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Alunos N\u00e3o Bolsistas": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios/Contratos/Parcerias (Exceto PROUNI)": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es/Subven\u00e7\u00f5es Vinculadas": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Gratuidade": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados ao PROUNI": {},
|
||||||
|
"Outros Custos 1": {}
|
||||||
|
},
|
||||||
|
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA SA\u00daDE": {
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios SUS": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios/Contratos/Parcerias 1": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es 2": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es/Subven\u00e7\u00f5es Vinculadas 2": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Gratuidade 2": {},
|
||||||
|
"Custo dos Servi\u00e7os Prestados a Pacientes Particulares 1": {},
|
||||||
|
"Outros Custos 3": {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"CUSTO DOS BENS E SERVI\u00c7OS PRODUZIDOS": {
|
"CUSTO DOS BENS E SERVI\u00c7OS PRODUZIDOS": {
|
||||||
"CUSTO DOS PRODUTOS DE FABRICA\u00c7\u00c3O PR\u00d3PRIA PRODUZIDOS": {
|
"CUSTO DOS PRODUTOS DE FABRICA\u00c7\u00c3O PR\u00d3PRIA PRODUZIDOS": {
|
||||||
"Alimenta\u00e7\u00e3o do Trabalhador": {},
|
"Alimenta\u00e7\u00e3o do Trabalhador": {},
|
||||||
@@ -621,7 +682,9 @@
|
|||||||
"Receita das Unidades Imobili\u00e1rias Vendidas": {},
|
"Receita das Unidades Imobili\u00e1rias Vendidas": {},
|
||||||
"Receita de Exporta\u00e7\u00e3o Direta de Mercadorias e Produtos": {},
|
"Receita de Exporta\u00e7\u00e3o Direta de Mercadorias e Produtos": {},
|
||||||
"Receita de Exporta\u00e7\u00e3o de Servi\u00e7os": {},
|
"Receita de Exporta\u00e7\u00e3o de Servi\u00e7os": {},
|
||||||
"Receita de Loca\u00e7\u00e3o de Bens M\u00f3veis e Im\u00f3veis": {},
|
"Receita de Loca\u00e7\u00e3o de Bens M\u00f3veis e Im\u00f3veis": {
|
||||||
|
"account_type": "Income Account"
|
||||||
|
},
|
||||||
"Receita de Vendas de Mercadorias e Produtos a Comercial Exportadora com Fim Espec\u00edfico de Exporta\u00e7\u00e3o": {}
|
"Receita de Vendas de Mercadorias e Produtos a Comercial Exportadora com Fim Espec\u00edfico de Exporta\u00e7\u00e3o": {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -645,65 +708,6 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"RESULTADO OPERACIONAL": {
|
"RESULTADO OPERACIONAL": {
|
||||||
"CUSTO DOS PRODUTOS E SERVI\u00c7OS VENDIDOS": {
|
|
||||||
"CUSTO DOS PRODUTOS VENDIDOS": {
|
|
||||||
"CUSTO DOS PRODUTOS VENDIDOS PARA AS DEMAIS ATIVIDADES": {
|
|
||||||
"Custos dos Produtos Vendidos em Geral": {
|
|
||||||
"account_type": "Cost of Goods Sold"
|
|
||||||
},
|
|
||||||
"Outros Custos 4": {},
|
|
||||||
"account_type": "Cost of Goods Sold"
|
|
||||||
},
|
|
||||||
"CUSTO DOS PRODUTOS VENDIDOS PARA ASSIST\u00caNCIA SOCIAL": {
|
|
||||||
"Custos dos Produtos para Assist\u00eancia Social - Gratuidades": {},
|
|
||||||
"Custos dos Produtos para Assist\u00eancia Social - Vendidos": {},
|
|
||||||
"Outras": {}
|
|
||||||
},
|
|
||||||
"CUSTO DOS PRODUTOS VENDIDOS PARA EDUCA\u00c7\u00c3O": {
|
|
||||||
"Custos dos Produtos para Educa\u00e7\u00e3o - Gratuidades": {},
|
|
||||||
"Custos dos Produtos para Educa\u00e7\u00e3o - Vendidos": {},
|
|
||||||
"Outros Custos 6": {}
|
|
||||||
},
|
|
||||||
"CUSTO DOS PRODUTOS VENDIDOS PARA SA\u00daDE": {
|
|
||||||
"Custos dos Produtos para Sa\u00fade - Gratuidades": {},
|
|
||||||
"Custos dos Produtos para Sa\u00fade \u2013 Vendidos": {},
|
|
||||||
"Outros Custos 5": {}
|
|
||||||
},
|
|
||||||
"account_type": "Cost of Goods Sold"
|
|
||||||
},
|
|
||||||
"CUSTO DOS SERVI\u00c7OS PRESTADOS": {
|
|
||||||
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA AS DEMAIS ATIVIDADES": {
|
|
||||||
"Custo dos Servi\u00e7os Prestados em Geral": {},
|
|
||||||
"Outros Custos": {}
|
|
||||||
},
|
|
||||||
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA ASSIST\u00caNCIA SOCIAL": {
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios/Contratos/Parcerias": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es 1": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es/Subven\u00e7\u00f5es Vinculadas 1": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Gratuidade 1": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Pacientes Particulares": {},
|
|
||||||
"Outros Custos 2": {}
|
|
||||||
},
|
|
||||||
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA EDUCA\u00c7\u00c3O": {
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Alunos N\u00e3o Bolsistas": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios/Contratos/Parcerias (Exceto PROUNI)": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es/Subven\u00e7\u00f5es Vinculadas": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Gratuidade": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados ao PROUNI": {},
|
|
||||||
"Outros Custos 1": {}
|
|
||||||
},
|
|
||||||
"CUSTO DOS SERVI\u00c7OS PRESTADOS PARA SA\u00daDE": {
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios SUS": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Conv\u00eanios/Contratos/Parcerias 1": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es 2": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Doa\u00e7\u00f5es/Subven\u00e7\u00f5es Vinculadas 2": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Gratuidade 2": {},
|
|
||||||
"Custo dos Servi\u00e7os Prestados a Pacientes Particulares 1": {},
|
|
||||||
"Outros Custos 3": {}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"DESPESAS OPERACIONAIS": {
|
"DESPESAS OPERACIONAIS": {
|
||||||
"DESPESAS OPERACIONAIS 1": {
|
"DESPESAS OPERACIONAIS 1": {
|
||||||
"DESPESAS OPERACIONAIS 2": {
|
"DESPESAS OPERACIONAIS 2": {
|
||||||
|
|||||||
@@ -33,7 +33,9 @@
|
|||||||
},
|
},
|
||||||
"Stocks": {
|
"Stocks": {
|
||||||
"Mati\u00e8res premi\u00e8res": {},
|
"Mati\u00e8res premi\u00e8res": {},
|
||||||
"Stock de produits fini": {},
|
"Stock de produits fini": {
|
||||||
|
"account_type": "Stock"
|
||||||
|
},
|
||||||
"Stock exp\u00e9di\u00e9 non-factur\u00e9": {},
|
"Stock exp\u00e9di\u00e9 non-factur\u00e9": {},
|
||||||
"Travaux en cours": {},
|
"Travaux en cours": {},
|
||||||
"account_type": "Stock"
|
"account_type": "Stock"
|
||||||
@@ -395,9 +397,11 @@
|
|||||||
},
|
},
|
||||||
"Produits": {
|
"Produits": {
|
||||||
"Revenus de ventes": {
|
"Revenus de ventes": {
|
||||||
" Escomptes de volume sur ventes": {},
|
"Escomptes de volume sur ventes": {},
|
||||||
"Autres produits d'exploitation": {},
|
"Autres produits d'exploitation": {},
|
||||||
"Ventes": {},
|
"Ventes": {
|
||||||
|
"account_type": "Income Account"
|
||||||
|
},
|
||||||
"Ventes avec des provinces harmonis\u00e9es": {},
|
"Ventes avec des provinces harmonis\u00e9es": {},
|
||||||
"Ventes avec des provinces non-harmonis\u00e9es": {},
|
"Ventes avec des provinces non-harmonis\u00e9es": {},
|
||||||
"Ventes \u00e0 l'\u00e9tranger": {}
|
"Ventes \u00e0 l'\u00e9tranger": {}
|
||||||
|
|||||||
@@ -53,8 +53,13 @@
|
|||||||
},
|
},
|
||||||
"II. Forderungen und sonstige Vermögensgegenstände": {
|
"II. Forderungen und sonstige Vermögensgegenstände": {
|
||||||
"is_group": 1,
|
"is_group": 1,
|
||||||
"Ford. a. Lieferungen und Leistungen": {
|
"Forderungen aus Lieferungen und Leistungen mit Kontokorrent": {
|
||||||
"account_number": "1400",
|
"account_number": "1400",
|
||||||
|
"account_type": "Receivable",
|
||||||
|
"is_group": 1
|
||||||
|
},
|
||||||
|
"Forderungen aus Lieferungen und Leistungen ohne Kontokorrent": {
|
||||||
|
"account_number": "1410",
|
||||||
"account_type": "Receivable"
|
"account_type": "Receivable"
|
||||||
},
|
},
|
||||||
"Durchlaufende Posten": {
|
"Durchlaufende Posten": {
|
||||||
@@ -180,8 +185,13 @@
|
|||||||
},
|
},
|
||||||
"IV. Verbindlichkeiten aus Lieferungen und Leistungen": {
|
"IV. Verbindlichkeiten aus Lieferungen und Leistungen": {
|
||||||
"is_group": 1,
|
"is_group": 1,
|
||||||
"Verbindlichkeiten aus Lieferungen u. Leistungen": {
|
"Verbindlichkeiten aus Lieferungen und Leistungen mit Kontokorrent": {
|
||||||
"account_number": "1600",
|
"account_number": "1600",
|
||||||
|
"account_type": "Payable",
|
||||||
|
"is_group": 1
|
||||||
|
},
|
||||||
|
"Verbindlichkeiten aus Lieferungen und Leistungen ohne Kontokorrent": {
|
||||||
|
"account_number": "1610",
|
||||||
"account_type": "Payable"
|
"account_type": "Payable"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,4 +1,6 @@
|
|||||||
{
|
{
|
||||||
|
"country_code": "hu",
|
||||||
|
"name": "Hungary - Chart of Accounts for Microenterprises",
|
||||||
"tree": {
|
"tree": {
|
||||||
"SZ\u00c1MLAOSZT\u00c1LY BEFEKTETETT ESZK\u00d6Z\u00d6K": {
|
"SZ\u00c1MLAOSZT\u00c1LY BEFEKTETETT ESZK\u00d6Z\u00d6K": {
|
||||||
"account_number": 1,
|
"account_number": 1,
|
||||||
@@ -1651,4 +1653,4 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -36,16 +36,16 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"Fixed Assets": {
|
"Fixed Assets": {
|
||||||
"Capital Equipments": {
|
"Capital Equipment": {
|
||||||
"account_type": "Fixed Asset"
|
"account_type": "Fixed Asset"
|
||||||
},
|
},
|
||||||
"Electronic Equipments": {
|
"Electronic Equipment": {
|
||||||
"account_type": "Fixed Asset"
|
"account_type": "Fixed Asset"
|
||||||
},
|
},
|
||||||
"Furnitures and Fixtures": {
|
"Furniture and Fixtures": {
|
||||||
"account_type": "Fixed Asset"
|
"account_type": "Fixed Asset"
|
||||||
},
|
},
|
||||||
"Office Equipments": {
|
"Office Equipment": {
|
||||||
"account_type": "Fixed Asset"
|
"account_type": "Fixed Asset"
|
||||||
},
|
},
|
||||||
"Plants and Machineries": {
|
"Plants and Machineries": {
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"country_code": "ni",
|
"country_code": "ni",
|
||||||
"name": "Nicaragua - Catalogo de Cuentas",
|
"name": "Nicaragua - Catálogo de Cuentas",
|
||||||
"tree": {
|
"tree": {
|
||||||
"Activo": {
|
"Activo": {
|
||||||
"Activo Corriente": {
|
"Activo Corriente": {
|
||||||
@@ -491,4 +491,4 @@
|
|||||||
"root_type": "Liability"
|
"root_type": "Liability"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,13 +23,13 @@ def get():
|
|||||||
_("Tax Assets"): {"is_group": 1},
|
_("Tax Assets"): {"is_group": 1},
|
||||||
},
|
},
|
||||||
_("Fixed Assets"): {
|
_("Fixed Assets"): {
|
||||||
_("Capital Equipments"): {"account_type": "Fixed Asset"},
|
_("Capital Equipment"): {"account_type": "Fixed Asset"},
|
||||||
_("Electronic Equipments"): {"account_type": "Fixed Asset"},
|
_("Electronic Equipment"): {"account_type": "Fixed Asset"},
|
||||||
_("Furnitures and Fixtures"): {"account_type": "Fixed Asset"},
|
_("Furniture and Fixtures"): {"account_type": "Fixed Asset"},
|
||||||
_("Office Equipments"): {"account_type": "Fixed Asset"},
|
_("Office Equipment"): {"account_type": "Fixed Asset"},
|
||||||
_("Plants and Machineries"): {"account_type": "Fixed Asset"},
|
_("Plants and Machineries"): {"account_type": "Fixed Asset"},
|
||||||
_("Buildings"): {"account_type": "Fixed Asset"},
|
_("Buildings"): {"account_type": "Fixed Asset"},
|
||||||
_("Softwares"): {"account_type": "Fixed Asset"},
|
_("Software"): {"account_type": "Fixed Asset"},
|
||||||
_("Accumulated Depreciation"): {"account_type": "Accumulated Depreciation"},
|
_("Accumulated Depreciation"): {"account_type": "Accumulated Depreciation"},
|
||||||
_("CWIP Account"): {
|
_("CWIP Account"): {
|
||||||
"account_type": "Capital Work in Progress",
|
"account_type": "Capital Work in Progress",
|
||||||
|
|||||||
@@ -36,13 +36,13 @@ def get():
|
|||||||
"account_number": "1100-1600",
|
"account_number": "1100-1600",
|
||||||
},
|
},
|
||||||
_("Fixed Assets"): {
|
_("Fixed Assets"): {
|
||||||
_("Capital Equipments"): {"account_type": "Fixed Asset", "account_number": "1710"},
|
_("Capital Equipment"): {"account_type": "Fixed Asset", "account_number": "1710"},
|
||||||
_("Electronic Equipments"): {"account_type": "Fixed Asset", "account_number": "1720"},
|
_("Electronic Equipment"): {"account_type": "Fixed Asset", "account_number": "1720"},
|
||||||
_("Furnitures and Fixtures"): {"account_type": "Fixed Asset", "account_number": "1730"},
|
_("Furniture and Fixtures"): {"account_type": "Fixed Asset", "account_number": "1730"},
|
||||||
_("Office Equipments"): {"account_type": "Fixed Asset", "account_number": "1740"},
|
_("Office Equipment"): {"account_type": "Fixed Asset", "account_number": "1740"},
|
||||||
_("Plants and Machineries"): {"account_type": "Fixed Asset", "account_number": "1750"},
|
_("Plants and Machineries"): {"account_type": "Fixed Asset", "account_number": "1750"},
|
||||||
_("Buildings"): {"account_type": "Fixed Asset", "account_number": "1760"},
|
_("Buildings"): {"account_type": "Fixed Asset", "account_number": "1760"},
|
||||||
_("Softwares"): {"account_type": "Fixed Asset", "account_number": "1770"},
|
_("Software"): {"account_type": "Fixed Asset", "account_number": "1770"},
|
||||||
_("Accumulated Depreciation"): {
|
_("Accumulated Depreciation"): {
|
||||||
"account_type": "Accumulated Depreciation",
|
"account_type": "Accumulated Depreciation",
|
||||||
"account_number": "1780",
|
"account_number": "1780",
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import unittest
|
|||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
from frappe.test_runner import make_test_records
|
from frappe.test_runner import make_test_records
|
||||||
|
from frappe.utils import nowdate
|
||||||
|
|
||||||
from erpnext.accounts.doctype.account.account import (
|
from erpnext.accounts.doctype.account.account import (
|
||||||
InvalidAccountMergeError,
|
InvalidAccountMergeError,
|
||||||
@@ -119,7 +120,7 @@ class TestAccount(unittest.TestCase):
|
|||||||
InvalidAccountMergeError,
|
InvalidAccountMergeError,
|
||||||
merge_account,
|
merge_account,
|
||||||
"Capital Stock - _TC",
|
"Capital Stock - _TC",
|
||||||
"Softwares - _TC",
|
"Software - _TC",
|
||||||
)
|
)
|
||||||
|
|
||||||
# Raise error as currency doesn't match
|
# Raise error as currency doesn't match
|
||||||
@@ -324,6 +325,19 @@ class TestAccount(unittest.TestCase):
|
|||||||
acc.account_currency = "USD"
|
acc.account_currency = "USD"
|
||||||
self.assertRaises(frappe.ValidationError, acc.save)
|
self.assertRaises(frappe.ValidationError, acc.save)
|
||||||
|
|
||||||
|
def test_account_balance(self):
|
||||||
|
from erpnext.accounts.utils import get_balance_on
|
||||||
|
|
||||||
|
if not frappe.db.exists("Account", "Test Percent Account %5 - _TC"):
|
||||||
|
acc = frappe.new_doc("Account")
|
||||||
|
acc.account_name = "Test Percent Account %5"
|
||||||
|
acc.parent_account = "Tax Assets - _TC"
|
||||||
|
acc.company = "_Test Company"
|
||||||
|
acc.insert()
|
||||||
|
|
||||||
|
balance = get_balance_on(account="Test Percent Account %5 - _TC", date=nowdate())
|
||||||
|
self.assertEqual(balance, 0)
|
||||||
|
|
||||||
|
|
||||||
def _make_test_records(verbose=None):
|
def _make_test_records(verbose=None):
|
||||||
from frappe.test_runner import make_test_objects
|
from frappe.test_runner import make_test_objects
|
||||||
|
|||||||
@@ -1,74 +1,86 @@
|
|||||||
// Copyright (c) 2019, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2019, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Accounting Dimension', {
|
frappe.ui.form.on("Accounting Dimension", {
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
frm.set_query('document_type', () => {
|
frm.set_query("document_type", () => {
|
||||||
let invalid_doctypes = frappe.model.core_doctypes_list;
|
let invalid_doctypes = frappe.model.core_doctypes_list;
|
||||||
invalid_doctypes.push('Accounting Dimension', 'Project',
|
invalid_doctypes.push(
|
||||||
'Cost Center', 'Accounting Dimension Detail', 'Company');
|
"Accounting Dimension",
|
||||||
|
"Project",
|
||||||
|
"Cost Center",
|
||||||
|
"Accounting Dimension Detail",
|
||||||
|
"Company"
|
||||||
|
);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
name: ['not in', invalid_doctypes]
|
name: ["not in", invalid_doctypes],
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
frm.set_query("offsetting_account", "dimension_defaults", function(doc, cdt, cdn) {
|
frm.set_query("offsetting_account", "dimension_defaults", function (doc, cdt, cdn) {
|
||||||
let d = locals[cdt][cdn];
|
let d = locals[cdt][cdn];
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
company: d.company,
|
company: d.company,
|
||||||
root_type: ["in", ["Asset", "Liability"]],
|
root_type: ["in", ["Asset", "Liability"]],
|
||||||
is_group: 0
|
is_group: 0,
|
||||||
}
|
},
|
||||||
}
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
if (!frm.is_new()) {
|
if (!frm.is_new()) {
|
||||||
frm.add_custom_button(__('Show {0}', [frm.doc.document_type]), function () {
|
frm.add_custom_button(__("Show {0}", [frm.doc.document_type]), function () {
|
||||||
frappe.set_route("List", frm.doc.document_type);
|
frappe.set_route("List", frm.doc.document_type);
|
||||||
});
|
});
|
||||||
|
|
||||||
let button = frm.doc.disabled ? "Enable" : "Disable";
|
let button = frm.doc.disabled ? "Enable" : "Disable";
|
||||||
|
|
||||||
frm.add_custom_button(__(button), function() {
|
frm.add_custom_button(__(button), function () {
|
||||||
|
frm.set_value("disabled", 1 - frm.doc.disabled);
|
||||||
frm.set_value('disabled', 1 - frm.doc.disabled);
|
|
||||||
|
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "erpnext.accounts.doctype.accounting_dimension.accounting_dimension.disable_dimension",
|
method: "erpnext.accounts.doctype.accounting_dimension.accounting_dimension.disable_dimension",
|
||||||
args: {
|
args: {
|
||||||
doc: frm.doc
|
doc: frm.doc,
|
||||||
},
|
},
|
||||||
freeze: true,
|
freeze: true,
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
let message = frm.doc.disabled ? "Dimension Disabled" : "Dimension Enabled";
|
let message = frm.doc.disabled ? "Dimension Disabled" : "Dimension Enabled";
|
||||||
frm.save();
|
frm.save();
|
||||||
frappe.show_alert({message:__(message), indicator:'green'});
|
frappe.show_alert({ message: __(message), indicator: "green" });
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
document_type: function(frm) {
|
document_type: function (frm) {
|
||||||
|
frm.set_value("label", frm.doc.document_type);
|
||||||
|
frm.set_value("fieldname", frappe.model.scrub(frm.doc.document_type));
|
||||||
|
|
||||||
frm.set_value('label', frm.doc.document_type);
|
frappe.db.get_value(
|
||||||
frm.set_value('fieldname', frappe.model.scrub(frm.doc.document_type));
|
"Accounting Dimension",
|
||||||
|
{ document_type: frm.doc.document_type },
|
||||||
frappe.db.get_value('Accounting Dimension', {'document_type': frm.doc.document_type}, 'document_type', (r) => {
|
"document_type",
|
||||||
if (r && r.document_type) {
|
(r) => {
|
||||||
frm.set_df_property('document_type', 'description', "Document type is already set as dimension");
|
if (r && r.document_type) {
|
||||||
|
frm.set_df_property(
|
||||||
|
"document_type",
|
||||||
|
"description",
|
||||||
|
"Document type is already set as dimension"
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
});
|
);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
frappe.ui.form.on('Accounting Dimension Detail', {
|
frappe.ui.form.on("Accounting Dimension Detail", {
|
||||||
dimension_defaults_add: function(frm, cdt, cdn) {
|
dimension_defaults_add: function (frm, cdt, cdn) {
|
||||||
let row = locals[cdt][cdn];
|
let row = locals[cdt][cdn];
|
||||||
row.reference_document = frm.doc.document_type;
|
row.reference_document = frm.doc.document_type;
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -11,6 +11,10 @@ from frappe.model import core_doctypes_list
|
|||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
from frappe.utils import cstr
|
from frappe.utils import cstr
|
||||||
|
|
||||||
|
from erpnext.accounts.doctype.repost_accounting_ledger.repost_accounting_ledger import (
|
||||||
|
get_allowed_types_from_settings,
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class AccountingDimension(Document):
|
class AccountingDimension(Document):
|
||||||
# begin: auto-generated types
|
# begin: auto-generated types
|
||||||
@@ -106,6 +110,7 @@ def make_dimension_in_accounting_doctypes(doc, doclist=None):
|
|||||||
|
|
||||||
doc_count = len(get_accounting_dimensions())
|
doc_count = len(get_accounting_dimensions())
|
||||||
count = 0
|
count = 0
|
||||||
|
repostable_doctypes = get_allowed_types_from_settings()
|
||||||
|
|
||||||
for doctype in doclist:
|
for doctype in doclist:
|
||||||
|
|
||||||
@@ -121,6 +126,7 @@ def make_dimension_in_accounting_doctypes(doc, doclist=None):
|
|||||||
"options": doc.document_type,
|
"options": doc.document_type,
|
||||||
"insert_after": insert_after_field,
|
"insert_after": insert_after_field,
|
||||||
"owner": "Administrator",
|
"owner": "Administrator",
|
||||||
|
"allow_on_submit": 1 if doctype in repostable_doctypes else 0,
|
||||||
}
|
}
|
||||||
|
|
||||||
meta = frappe.get_meta(doctype, cached=False)
|
meta = frappe.get_meta(doctype, cached=False)
|
||||||
|
|||||||
@@ -1,10 +1,9 @@
|
|||||||
// Copyright (c) 2020, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2020, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Accounting Dimension Filter', {
|
frappe.ui.form.on("Accounting Dimension Filter", {
|
||||||
refresh: function(frm, cdt, cdn) {
|
refresh: function (frm, cdt, cdn) {
|
||||||
let help_content =
|
let help_content = `<table class="table table-bordered" style="background-color: var(--scrollbar-track-color);">
|
||||||
`<table class="table table-bordered" style="background-color: var(--scrollbar-track-color);">
|
|
||||||
<tr><td>
|
<tr><td>
|
||||||
<p>
|
<p>
|
||||||
<i class="fa fa-hand-right"></i>
|
<i class="fa fa-hand-right"></i>
|
||||||
@@ -13,77 +12,80 @@ frappe.ui.form.on('Accounting Dimension Filter', {
|
|||||||
</td></tr>
|
</td></tr>
|
||||||
</table>`;
|
</table>`;
|
||||||
|
|
||||||
frm.set_df_property('dimension_filter_help', 'options', help_content);
|
frm.set_df_property("dimension_filter_help", "options", help_content);
|
||||||
},
|
},
|
||||||
onload: function(frm) {
|
onload: function (frm) {
|
||||||
frm.set_query('applicable_on_account', 'accounts', function() {
|
frm.set_query("applicable_on_account", "accounts", function () {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
'company': frm.doc.company
|
company: frm.doc.company,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
frappe.db.get_list('Accounting Dimension',
|
frappe.db.get_list("Accounting Dimension", { fields: ["document_type"] }).then((res) => {
|
||||||
{fields: ['document_type']}).then((res) => {
|
let options = ["Cost Center", "Project"];
|
||||||
let options = ['Cost Center', 'Project'];
|
|
||||||
|
|
||||||
res.forEach((dimension) => {
|
res.forEach((dimension) => {
|
||||||
options.push(dimension.document_type);
|
options.push(dimension.document_type);
|
||||||
});
|
});
|
||||||
|
|
||||||
frm.set_df_property('accounting_dimension', 'options', options);
|
frm.set_df_property("accounting_dimension", "options", options);
|
||||||
});
|
});
|
||||||
|
|
||||||
frm.trigger('setup_filters');
|
frm.trigger("setup_filters");
|
||||||
},
|
},
|
||||||
|
|
||||||
setup_filters: function(frm) {
|
setup_filters: function (frm) {
|
||||||
let filters = {};
|
let filters = {};
|
||||||
|
|
||||||
if (frm.doc.accounting_dimension) {
|
if (frm.doc.accounting_dimension) {
|
||||||
frappe.model.with_doctype(frm.doc.accounting_dimension, function() {
|
frappe.model.with_doctype(frm.doc.accounting_dimension, function () {
|
||||||
if (frappe.model.is_tree(frm.doc.accounting_dimension)) {
|
if (frappe.model.is_tree(frm.doc.accounting_dimension)) {
|
||||||
filters['is_group'] = 0;
|
filters["is_group"] = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (frappe.meta.has_field(frm.doc.accounting_dimension, 'company')) {
|
if (frappe.meta.has_field(frm.doc.accounting_dimension, "company")) {
|
||||||
filters['company'] = frm.doc.company;
|
filters["company"] = frm.doc.company;
|
||||||
}
|
}
|
||||||
|
|
||||||
frm.set_query('dimension_value', 'dimensions', function() {
|
frm.set_query("dimension_value", "dimensions", function () {
|
||||||
return {
|
return {
|
||||||
filters: filters
|
filters: filters,
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
accounting_dimension: function(frm) {
|
accounting_dimension: function (frm) {
|
||||||
frm.clear_table("dimensions");
|
frm.clear_table("dimensions");
|
||||||
let row = frm.add_child("dimensions");
|
let row = frm.add_child("dimensions");
|
||||||
row.accounting_dimension = frm.doc.accounting_dimension;
|
row.accounting_dimension = frm.doc.accounting_dimension;
|
||||||
frm.fields_dict["dimensions"].grid.update_docfield_property("dimension_value", "label", frm.doc.accounting_dimension);
|
frm.fields_dict["dimensions"].grid.update_docfield_property(
|
||||||
|
"dimension_value",
|
||||||
|
"label",
|
||||||
|
frm.doc.accounting_dimension
|
||||||
|
);
|
||||||
frm.refresh_field("dimensions");
|
frm.refresh_field("dimensions");
|
||||||
frm.trigger('setup_filters');
|
frm.trigger("setup_filters");
|
||||||
},
|
},
|
||||||
apply_restriction_on_values: function(frm) {
|
apply_restriction_on_values: function (frm) {
|
||||||
/** If restriction on values is not applied, we should set "allow_or_restrict" to "Restrict" with an empty allowed dimension table.
|
/** If restriction on values is not applied, we should set "allow_or_restrict" to "Restrict" with an empty allowed dimension table.
|
||||||
* Hence it's not "restricted" on any value.
|
* Hence it's not "restricted" on any value.
|
||||||
*/
|
*/
|
||||||
if (!frm.doc.apply_restriction_on_values) {
|
if (!frm.doc.apply_restriction_on_values) {
|
||||||
frm.set_value("allow_or_restrict", "Restrict");
|
frm.set_value("allow_or_restrict", "Restrict");
|
||||||
frm.clear_table("dimensions");
|
frm.clear_table("dimensions");
|
||||||
frm.refresh_field("dimensions");
|
frm.refresh_field("dimensions");
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
frappe.ui.form.on('Allowed Dimension', {
|
frappe.ui.form.on("Allowed Dimension", {
|
||||||
dimensions_add: function(frm, cdt, cdn) {
|
dimensions_add: function (frm, cdt, cdn) {
|
||||||
let row = locals[cdt][cdn];
|
let row = locals[cdt][cdn];
|
||||||
row.accounting_dimension = frm.doc.accounting_dimension;
|
row.accounting_dimension = frm.doc.accounting_dimension;
|
||||||
frm.refresh_field("dimensions");
|
frm.refresh_field("dimensions");
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,30 +1,33 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Accounting Period', {
|
frappe.ui.form.on("Accounting Period", {
|
||||||
onload: function(frm) {
|
onload: function (frm) {
|
||||||
if(frm.doc.closed_documents.length === 0 || (frm.doc.closed_documents.length === 1 && frm.doc.closed_documents[0].document_type == undefined)) {
|
if (
|
||||||
|
frm.doc.closed_documents.length === 0 ||
|
||||||
|
(frm.doc.closed_documents.length === 1 && frm.doc.closed_documents[0].document_type == undefined)
|
||||||
|
) {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "get_doctypes_for_closing",
|
method: "get_doctypes_for_closing",
|
||||||
doc:frm.doc,
|
doc: frm.doc,
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
if(r.message) {
|
if (r.message) {
|
||||||
cur_frm.clear_table("closed_documents");
|
cur_frm.clear_table("closed_documents");
|
||||||
r.message.forEach(function(element) {
|
r.message.forEach(function (element) {
|
||||||
var c = frm.add_child("closed_documents");
|
var c = frm.add_child("closed_documents");
|
||||||
c.document_type = element.document_type;
|
c.document_type = element.document_type;
|
||||||
c.closed = element.closed;
|
c.closed = element.closed;
|
||||||
});
|
});
|
||||||
refresh_field("closed_documents");
|
refresh_field("closed_documents");
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
frm.set_query("document_type", "closed_documents", () => {
|
frm.set_query("document_type", "closed_documents", () => {
|
||||||
return {
|
return {
|
||||||
query: "erpnext.controllers.queries.get_doctypes_for_closing",
|
query: "erpnext.controllers.queries.get_doctypes_for_closing",
|
||||||
}
|
};
|
||||||
});
|
});
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,8 +1,6 @@
|
|||||||
// Copyright (c) 2016, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2016, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Accounts Settings', {
|
frappe.ui.form.on("Accounts Settings", {
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {},
|
||||||
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,7 +1,6 @@
|
|||||||
{
|
{
|
||||||
"actions": [],
|
"actions": [],
|
||||||
"creation": "2013-06-24 15:49:57",
|
"creation": "2013-06-24 15:49:57",
|
||||||
"description": "Settings for Accounts",
|
|
||||||
"doctype": "DocType",
|
"doctype": "DocType",
|
||||||
"document_type": "Other",
|
"document_type": "Other",
|
||||||
"editable_grid": 1,
|
"editable_grid": 1,
|
||||||
@@ -462,7 +461,7 @@
|
|||||||
"index_web_pages_for_search": 1,
|
"index_web_pages_for_search": 1,
|
||||||
"issingle": 1,
|
"issingle": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2023-11-20 09:37:47.650347",
|
"modified": "2024-01-30 14:04:26.553554",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Accounts Settings",
|
"name": "Accounts Settings",
|
||||||
|
|||||||
@@ -1,8 +1,11 @@
|
|||||||
|
frappe.ui.form.on("Accounts Settings", {
|
||||||
frappe.ui.form.on('Accounts Settings', {
|
refresh: function (frm) {
|
||||||
refresh: function(frm) {
|
|
||||||
frm.set_df_property("acc_frozen_upto", "label", "Books Closed Through");
|
frm.set_df_property("acc_frozen_upto", "label", "Books Closed Through");
|
||||||
frm.set_df_property("frozen_accounts_modifier", "label", "Role Allowed to Close Books & Make Changes to Closed Periods");
|
frm.set_df_property(
|
||||||
|
"frozen_accounts_modifier",
|
||||||
|
"label",
|
||||||
|
"Role Allowed to Close Books & Make Changes to Closed Periods"
|
||||||
|
);
|
||||||
frm.set_df_property("credit_controller", "label", "Credit Manager");
|
frm.set_df_property("credit_controller", "label", "Credit Manager");
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -11,6 +11,7 @@
|
|||||||
{
|
{
|
||||||
"fieldname": "company",
|
"fieldname": "company",
|
||||||
"fieldtype": "Link",
|
"fieldtype": "Link",
|
||||||
|
"ignore_user_permissions": 1,
|
||||||
"in_list_view": 1,
|
"in_list_view": 1,
|
||||||
"label": "Company",
|
"label": "Company",
|
||||||
"options": "Company",
|
"options": "Company",
|
||||||
@@ -19,7 +20,7 @@
|
|||||||
],
|
],
|
||||||
"istable": 1,
|
"istable": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2020-05-01 12:32:34.044911",
|
"modified": "2024-01-03 11:13:02.669632",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Allowed To Transact With",
|
"name": "Allowed To Transact With",
|
||||||
@@ -28,5 +29,6 @@
|
|||||||
"quick_entry": 1,
|
"quick_entry": 1,
|
||||||
"sort_field": "modified",
|
"sort_field": "modified",
|
||||||
"sort_order": "DESC",
|
"sort_order": "DESC",
|
||||||
|
"states": [],
|
||||||
"track_changes": 1
|
"track_changes": 1
|
||||||
}
|
}
|
||||||
@@ -1,38 +1,36 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
frappe.provide('erpnext.integrations');
|
frappe.provide("erpnext.integrations");
|
||||||
|
|
||||||
frappe.ui.form.on('Bank', {
|
frappe.ui.form.on("Bank", {
|
||||||
onload: function(frm) {
|
onload: function (frm) {
|
||||||
add_fields_to_mapping_table(frm);
|
add_fields_to_mapping_table(frm);
|
||||||
},
|
},
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
add_fields_to_mapping_table(frm);
|
add_fields_to_mapping_table(frm);
|
||||||
frm.toggle_display(['address_html','contact_html'], !frm.doc.__islocal);
|
frm.toggle_display(["address_html", "contact_html"], !frm.doc.__islocal);
|
||||||
|
|
||||||
if (frm.doc.__islocal) {
|
if (frm.doc.__islocal) {
|
||||||
frm.set_df_property('address_and_contact', 'hidden', 1);
|
frm.set_df_property("address_and_contact", "hidden", 1);
|
||||||
frappe.contacts.clear_address_and_contact(frm);
|
frappe.contacts.clear_address_and_contact(frm);
|
||||||
}
|
} else {
|
||||||
else {
|
frm.set_df_property("address_and_contact", "hidden", 0);
|
||||||
frm.set_df_property('address_and_contact', 'hidden', 0);
|
|
||||||
frappe.contacts.render_address_and_contact(frm);
|
frappe.contacts.render_address_and_contact(frm);
|
||||||
}
|
}
|
||||||
if (frm.doc.plaid_access_token) {
|
if (frm.doc.plaid_access_token) {
|
||||||
frm.add_custom_button(__('Refresh Plaid Link'), () => {
|
frm.add_custom_button(__("Refresh Plaid Link"), () => {
|
||||||
new erpnext.integrations.refreshPlaidLink(frm.doc.plaid_access_token);
|
new erpnext.integrations.refreshPlaidLink(frm.doc.plaid_access_token);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
let add_fields_to_mapping_table = function (frm) {
|
let add_fields_to_mapping_table = function (frm) {
|
||||||
let options = [];
|
let options = [];
|
||||||
|
|
||||||
frappe.model.with_doctype("Bank Transaction", function() {
|
frappe.model.with_doctype("Bank Transaction", function () {
|
||||||
let meta = frappe.get_meta("Bank Transaction");
|
let meta = frappe.get_meta("Bank Transaction");
|
||||||
meta.fields.forEach(value => {
|
meta.fields.forEach((value) => {
|
||||||
if (!["Section Break", "Column Break"].includes(value.fieldtype)) {
|
if (!["Section Break", "Column Break"].includes(value.fieldtype)) {
|
||||||
options.push(value.fieldname);
|
options.push(value.fieldname);
|
||||||
}
|
}
|
||||||
@@ -40,30 +38,32 @@ let add_fields_to_mapping_table = function (frm) {
|
|||||||
});
|
});
|
||||||
|
|
||||||
frm.fields_dict.bank_transaction_mapping.grid.update_docfield_property(
|
frm.fields_dict.bank_transaction_mapping.grid.update_docfield_property(
|
||||||
'bank_transaction_field', 'options', options
|
"bank_transaction_field",
|
||||||
|
"options",
|
||||||
|
options
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
erpnext.integrations.refreshPlaidLink = class refreshPlaidLink {
|
erpnext.integrations.refreshPlaidLink = class refreshPlaidLink {
|
||||||
constructor(access_token) {
|
constructor(access_token) {
|
||||||
this.access_token = access_token;
|
this.access_token = access_token;
|
||||||
this.plaidUrl = 'https://cdn.plaid.com/link/v2/stable/link-initialize.js';
|
this.plaidUrl = "https://cdn.plaid.com/link/v2/stable/link-initialize.js";
|
||||||
this.init_config();
|
this.init_config();
|
||||||
}
|
}
|
||||||
|
|
||||||
async init_config() {
|
async init_config() {
|
||||||
this.plaid_env = await frappe.db.get_single_value('Plaid Settings', 'plaid_env');
|
this.plaid_env = await frappe.db.get_single_value("Plaid Settings", "plaid_env");
|
||||||
this.token = await this.get_link_token_for_update();
|
this.token = await this.get_link_token_for_update();
|
||||||
this.init_plaid();
|
this.init_plaid();
|
||||||
}
|
}
|
||||||
|
|
||||||
async get_link_token_for_update() {
|
async get_link_token_for_update() {
|
||||||
const token = frappe.xcall(
|
const token = frappe.xcall(
|
||||||
'erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.get_link_token_for_update',
|
"erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.get_link_token_for_update",
|
||||||
{ access_token: this.access_token }
|
{ access_token: this.access_token }
|
||||||
)
|
);
|
||||||
if (!token) {
|
if (!token) {
|
||||||
frappe.throw(__('Cannot retrieve link token for update. Check Error Log for more information'));
|
frappe.throw(__("Cannot retrieve link token for update. Check Error Log for more information"));
|
||||||
}
|
}
|
||||||
return token;
|
return token;
|
||||||
}
|
}
|
||||||
@@ -90,35 +90,45 @@ erpnext.integrations.refreshPlaidLink = class refreshPlaidLink {
|
|||||||
resolve();
|
resolve();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const el = document.createElement('script');
|
const el = document.createElement("script");
|
||||||
el.type = 'text/javascript';
|
el.type = "text/javascript";
|
||||||
el.async = true;
|
el.async = true;
|
||||||
el.src = src;
|
el.src = src;
|
||||||
el.addEventListener('load', resolve);
|
el.addEventListener("load", resolve);
|
||||||
el.addEventListener('error', reject);
|
el.addEventListener("error", reject);
|
||||||
el.addEventListener('abort', reject);
|
el.addEventListener("abort", reject);
|
||||||
document.head.appendChild(el);
|
document.head.appendChild(el);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
onScriptLoaded(me) {
|
onScriptLoaded(me) {
|
||||||
me.linkHandler = Plaid.create({ // eslint-disable-line no-undef
|
me.linkHandler = Plaid.create({
|
||||||
|
// eslint-disable-line no-undef
|
||||||
env: me.plaid_env,
|
env: me.plaid_env,
|
||||||
token: me.token,
|
token: me.token,
|
||||||
onSuccess: me.plaid_success
|
onSuccess: me.plaid_success,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
onScriptError(error) {
|
onScriptError(error) {
|
||||||
frappe.msgprint(__("There was an issue connecting to Plaid's authentication server. Check browser console for more information"));
|
frappe.msgprint(
|
||||||
|
__(
|
||||||
|
"There was an issue connecting to Plaid's authentication server. Check browser console for more information"
|
||||||
|
)
|
||||||
|
);
|
||||||
console.log(error);
|
console.log(error);
|
||||||
}
|
}
|
||||||
|
|
||||||
plaid_success(token, response) {
|
plaid_success(token, response) {
|
||||||
frappe.xcall('erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.update_bank_account_ids', {
|
frappe
|
||||||
response: response,
|
.xcall(
|
||||||
}).then(() => {
|
"erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.update_bank_account_ids",
|
||||||
frappe.show_alert({ message: __('Plaid Link Updated'), indicator: 'green' });
|
{
|
||||||
});
|
response: response,
|
||||||
|
}
|
||||||
|
)
|
||||||
|
.then(() => {
|
||||||
|
frappe.show_alert({ message: __("Plaid Link Updated"), indicator: "green" });
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,45 +1,49 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Bank Account', {
|
frappe.ui.form.on("Bank Account", {
|
||||||
setup: function(frm) {
|
setup: function (frm) {
|
||||||
frm.set_query("account", function() {
|
frm.set_query("account", function () {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
'account_type': 'Bank',
|
account_type: "Bank",
|
||||||
'company': frm.doc.company,
|
company: frm.doc.company,
|
||||||
'is_group': 0
|
is_group: 0,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
frm.set_query("party_type", function() {
|
frm.set_query("party_type", function () {
|
||||||
return {
|
return {
|
||||||
query: "erpnext.setup.doctype.party_type.party_type.get_party_type",
|
query: "erpnext.setup.doctype.party_type.party_type.get_party_type",
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
frappe.dynamic_link = { doc: frm.doc, fieldname: 'name', doctype: 'Bank Account' }
|
frappe.dynamic_link = { doc: frm.doc, fieldname: "name", doctype: "Bank Account" };
|
||||||
|
|
||||||
frm.toggle_display(['address_html','contact_html'], !frm.doc.__islocal);
|
frm.toggle_display(["address_html", "contact_html"], !frm.doc.__islocal);
|
||||||
|
|
||||||
if (frm.doc.__islocal) {
|
if (frm.doc.__islocal) {
|
||||||
frappe.contacts.clear_address_and_contact(frm);
|
frappe.contacts.clear_address_and_contact(frm);
|
||||||
}
|
} else {
|
||||||
else {
|
|
||||||
frappe.contacts.render_address_and_contact(frm);
|
frappe.contacts.render_address_and_contact(frm);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (frm.doc.integration_id) {
|
if (frm.doc.integration_id) {
|
||||||
frm.add_custom_button(__("Unlink external integrations"), function() {
|
frm.add_custom_button(__("Unlink external integrations"), function () {
|
||||||
frappe.confirm(__("This action will unlink this account from any external service integrating ERPNext with your bank accounts. It cannot be undone. Are you certain ?"), function() {
|
frappe.confirm(
|
||||||
frm.set_value("integration_id", "");
|
__(
|
||||||
});
|
"This action will unlink this account from any external service integrating ERPNext with your bank accounts. It cannot be undone. Are you certain ?"
|
||||||
|
),
|
||||||
|
function () {
|
||||||
|
frm.set_value("integration_id", "");
|
||||||
|
}
|
||||||
|
);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
is_company_account: function(frm) {
|
is_company_account: function (frm) {
|
||||||
frm.set_df_property('account', 'reqd', frm.doc.is_company_account);
|
frm.set_df_property("account", "reqd", frm.doc.is_company_account);
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ from frappe.contacts.address_and_contact import (
|
|||||||
load_address_and_contact,
|
load_address_and_contact,
|
||||||
)
|
)
|
||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
|
from frappe.utils import comma_and, get_link_to_form
|
||||||
|
|
||||||
|
|
||||||
class BankAccount(Document):
|
class BankAccount(Document):
|
||||||
@@ -52,10 +53,23 @@ class BankAccount(Document):
|
|||||||
def validate(self):
|
def validate(self):
|
||||||
self.validate_company()
|
self.validate_company()
|
||||||
self.validate_iban()
|
self.validate_iban()
|
||||||
|
self.validate_account()
|
||||||
|
|
||||||
|
def validate_account(self):
|
||||||
|
if self.account:
|
||||||
|
if accounts := frappe.db.get_all(
|
||||||
|
"Bank Account", filters={"account": self.account, "name": ["!=", self.name]}, as_list=1
|
||||||
|
):
|
||||||
|
frappe.throw(
|
||||||
|
_("'{0}' account is already used by {1}. Use another account.").format(
|
||||||
|
frappe.bold(self.account),
|
||||||
|
frappe.bold(comma_and([get_link_to_form(self.doctype, x[0]) for x in accounts])),
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
def validate_company(self):
|
def validate_company(self):
|
||||||
if self.is_company_account and not self.company:
|
if self.is_company_account and not self.company:
|
||||||
frappe.throw(_("Company is manadatory for company account"))
|
frappe.throw(_("Company is mandatory for company account"))
|
||||||
|
|
||||||
def validate_iban(self):
|
def validate_iban(self):
|
||||||
"""
|
"""
|
||||||
|
|||||||
@@ -1,8 +1,6 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Bank Account Subtype', {
|
frappe.ui.form.on("Bank Account Subtype", {
|
||||||
refresh: function() {
|
refresh: function () {},
|
||||||
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,8 +1,7 @@
|
|||||||
// Copyright (c) 2020, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2020, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Bank Account Type', {
|
frappe.ui.form.on("Bank Account Type", {
|
||||||
// refresh: function(frm) {
|
// refresh: function(frm) {
|
||||||
|
|
||||||
// }
|
// }
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -2,80 +2,76 @@
|
|||||||
// License: GNU General Public License v3. See license.txt
|
// License: GNU General Public License v3. See license.txt
|
||||||
|
|
||||||
frappe.ui.form.on("Bank Clearance", {
|
frappe.ui.form.on("Bank Clearance", {
|
||||||
setup: function(frm) {
|
setup: function (frm) {
|
||||||
frm.add_fetch("account", "account_currency", "account_currency");
|
frm.add_fetch("account", "account_currency", "account_currency");
|
||||||
|
|
||||||
frm.set_query("account", function() {
|
frm.set_query("account", function () {
|
||||||
return {
|
return {
|
||||||
"filters": {
|
filters: {
|
||||||
"account_type": ["in",["Bank","Cash"]],
|
account_type: ["in", ["Bank", "Cash"]],
|
||||||
"is_group": 0,
|
is_group: 0,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
frm.set_query("bank_account", function () {
|
frm.set_query("bank_account", function () {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
'is_company_account': 1
|
is_company_account: 1,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
onload: function(frm) {
|
onload: function (frm) {
|
||||||
|
let default_bank_account = frappe.defaults.get_user_default("Company")
|
||||||
let default_bank_account = frappe.defaults.get_user_default("Company")?
|
? locals[":Company"][frappe.defaults.get_user_default("Company")]["default_bank_account"]
|
||||||
locals[":Company"][frappe.defaults.get_user_default("Company")]["default_bank_account"]: "";
|
: "";
|
||||||
frm.set_value("account", default_bank_account);
|
frm.set_value("account", default_bank_account);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
frm.set_value("from_date", frappe.datetime.month_start());
|
frm.set_value("from_date", frappe.datetime.month_start());
|
||||||
frm.set_value("to_date", frappe.datetime.month_end());
|
frm.set_value("to_date", frappe.datetime.month_end());
|
||||||
},
|
},
|
||||||
|
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
frm.disable_save();
|
frm.disable_save();
|
||||||
frm.add_custom_button(__('Get Payment Entries'), () =>
|
frm.add_custom_button(__("Get Payment Entries"), () => frm.trigger("get_payment_entries"));
|
||||||
frm.trigger("get_payment_entries")
|
|
||||||
);
|
|
||||||
|
|
||||||
frm.change_custom_button_type(__('Get Payment Entries'), null, 'primary');
|
frm.change_custom_button_type(__("Get Payment Entries"), null, "primary");
|
||||||
},
|
},
|
||||||
|
|
||||||
update_clearance_date: function(frm) {
|
update_clearance_date: function (frm) {
|
||||||
return frappe.call({
|
return frappe.call({
|
||||||
method: "update_clearance_date",
|
method: "update_clearance_date",
|
||||||
doc: frm.doc,
|
doc: frm.doc,
|
||||||
callback: function(r, rt) {
|
callback: function (r, rt) {
|
||||||
frm.refresh_field("payment_entries");
|
frm.refresh_field("payment_entries");
|
||||||
frm.refresh_fields();
|
frm.refresh_fields();
|
||||||
|
|
||||||
if (!frm.doc.payment_entries.length) {
|
if (!frm.doc.payment_entries.length) {
|
||||||
frm.change_custom_button_type(__('Get Payment Entries'), null, 'primary');
|
frm.change_custom_button_type(__("Get Payment Entries"), null, "primary");
|
||||||
frm.change_custom_button_type(__('Update Clearance Date'), null, 'default');
|
frm.change_custom_button_type(__("Update Clearance Date"), null, "default");
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
get_payment_entries: function(frm) {
|
get_payment_entries: function (frm) {
|
||||||
return frappe.call({
|
return frappe.call({
|
||||||
method: "get_payment_entries",
|
method: "get_payment_entries",
|
||||||
doc: frm.doc,
|
doc: frm.doc,
|
||||||
callback: function(r, rt) {
|
callback: function (r, rt) {
|
||||||
frm.refresh_field("payment_entries");
|
frm.refresh_field("payment_entries");
|
||||||
|
|
||||||
if (frm.doc.payment_entries.length) {
|
if (frm.doc.payment_entries.length) {
|
||||||
frm.add_custom_button(__('Update Clearance Date'), () =>
|
frm.add_custom_button(__("Update Clearance Date"), () =>
|
||||||
frm.trigger("update_clearance_date")
|
frm.trigger("update_clearance_date")
|
||||||
);
|
);
|
||||||
|
|
||||||
frm.change_custom_button_type(__('Get Payment Entries'), null, 'default');
|
frm.change_custom_button_type(__("Get Payment Entries"), null, "default");
|
||||||
frm.change_custom_button_type(__('Update Clearance Date'), null, 'primary');
|
frm.change_custom_button_type(__("Update Clearance Date"), null, "primary");
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -5,7 +5,9 @@
|
|||||||
import frappe
|
import frappe
|
||||||
from frappe import _, msgprint
|
from frappe import _, msgprint
|
||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
|
from frappe.query_builder.custom import ConstantColumn
|
||||||
from frappe.utils import flt, fmt_money, getdate
|
from frappe.utils import flt, fmt_money, getdate
|
||||||
|
from pypika import Order
|
||||||
|
|
||||||
import erpnext
|
import erpnext
|
||||||
|
|
||||||
@@ -179,39 +181,62 @@ def get_payment_entries_for_bank_clearance(
|
|||||||
|
|
||||||
pos_sales_invoices, pos_purchase_invoices = [], []
|
pos_sales_invoices, pos_purchase_invoices = [], []
|
||||||
if include_pos_transactions:
|
if include_pos_transactions:
|
||||||
pos_sales_invoices = frappe.db.sql(
|
si_payment = frappe.qb.DocType("Sales Invoice Payment")
|
||||||
"""
|
si = frappe.qb.DocType("Sales Invoice")
|
||||||
select
|
acc = frappe.qb.DocType("Account")
|
||||||
"Sales Invoice Payment" as payment_document, sip.name as payment_entry, sip.amount as debit,
|
|
||||||
si.posting_date, si.customer as against_account, sip.clearance_date,
|
|
||||||
account.account_currency, 0 as credit
|
|
||||||
from `tabSales Invoice Payment` sip, `tabSales Invoice` si, `tabAccount` account
|
|
||||||
where
|
|
||||||
sip.account=%(account)s and si.docstatus=1 and sip.parent = si.name
|
|
||||||
and account.name = sip.account and si.posting_date >= %(from)s and si.posting_date <= %(to)s
|
|
||||||
order by
|
|
||||||
si.posting_date ASC, si.name DESC
|
|
||||||
""",
|
|
||||||
{"account": account, "from": from_date, "to": to_date},
|
|
||||||
as_dict=1,
|
|
||||||
)
|
|
||||||
|
|
||||||
pos_purchase_invoices = frappe.db.sql(
|
pos_sales_invoices = (
|
||||||
"""
|
frappe.qb.from_(si_payment)
|
||||||
select
|
.inner_join(si)
|
||||||
"Purchase Invoice" as payment_document, pi.name as payment_entry, pi.paid_amount as credit,
|
.on(si_payment.parent == si.name)
|
||||||
pi.posting_date, pi.supplier as against_account, pi.clearance_date,
|
.inner_join(acc)
|
||||||
account.account_currency, 0 as debit
|
.on(si_payment.account == acc.name)
|
||||||
from `tabPurchase Invoice` pi, `tabAccount` account
|
.select(
|
||||||
where
|
ConstantColumn("Sales Invoice").as_("payment_document"),
|
||||||
pi.cash_bank_account=%(account)s and pi.docstatus=1 and account.name = pi.cash_bank_account
|
si.name.as_("payment_entry"),
|
||||||
and pi.posting_date >= %(from)s and pi.posting_date <= %(to)s
|
si_payment.reference_no.as_("cheque_number"),
|
||||||
order by
|
si_payment.amount.as_("debit"),
|
||||||
pi.posting_date ASC, pi.name DESC
|
si.posting_date,
|
||||||
""",
|
si.customer.as_("against_account"),
|
||||||
{"account": account, "from": from_date, "to": to_date},
|
si_payment.clearance_date,
|
||||||
as_dict=1,
|
acc.account_currency,
|
||||||
)
|
ConstantColumn(0).as_("credit"),
|
||||||
|
)
|
||||||
|
.where(
|
||||||
|
(si.docstatus == 1)
|
||||||
|
& (si_payment.account == account)
|
||||||
|
& (si.posting_date >= from_date)
|
||||||
|
& (si.posting_date <= to_date)
|
||||||
|
)
|
||||||
|
.orderby(si.posting_date)
|
||||||
|
.orderby(si.name, order=Order.desc)
|
||||||
|
).run(as_dict=True)
|
||||||
|
|
||||||
|
pi = frappe.qb.DocType("Purchase Invoice")
|
||||||
|
|
||||||
|
pos_purchase_invoices = (
|
||||||
|
frappe.qb.from_(pi)
|
||||||
|
.inner_join(acc)
|
||||||
|
.on(pi.cash_bank_account == acc.name)
|
||||||
|
.select(
|
||||||
|
ConstantColumn("Purchase Invoice").as_("payment_document"),
|
||||||
|
pi.name.as_("payment_entry"),
|
||||||
|
pi.paid_amount.as_("credit"),
|
||||||
|
pi.posting_date,
|
||||||
|
pi.supplier.as_("against_account"),
|
||||||
|
pi.clearance_date,
|
||||||
|
acc.account_currency,
|
||||||
|
ConstantColumn(0).as_("debit"),
|
||||||
|
)
|
||||||
|
.where(
|
||||||
|
(pi.docstatus == 1)
|
||||||
|
& (pi.cash_bank_account == account)
|
||||||
|
& (pi.posting_date >= from_date)
|
||||||
|
& (pi.posting_date <= to_date)
|
||||||
|
)
|
||||||
|
.orderby(pi.posting_date)
|
||||||
|
.orderby(pi.name, order=Order.desc)
|
||||||
|
).run(as_dict=True)
|
||||||
|
|
||||||
entries = (
|
entries = (
|
||||||
list(payment_entries)
|
list(payment_entries)
|
||||||
|
|||||||
@@ -1,39 +1,39 @@
|
|||||||
// Copyright (c) 2016, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2016, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
cur_frm.add_fetch('bank_account','account','account');
|
cur_frm.add_fetch("bank_account", "account", "account");
|
||||||
cur_frm.add_fetch('bank_account','bank_account_no','bank_account_no');
|
cur_frm.add_fetch("bank_account", "bank_account_no", "bank_account_no");
|
||||||
cur_frm.add_fetch('bank_account','iban','iban');
|
cur_frm.add_fetch("bank_account", "iban", "iban");
|
||||||
cur_frm.add_fetch('bank_account','branch_code','branch_code');
|
cur_frm.add_fetch("bank_account", "branch_code", "branch_code");
|
||||||
cur_frm.add_fetch('bank','swift_number','swift_number');
|
cur_frm.add_fetch("bank", "swift_number", "swift_number");
|
||||||
|
|
||||||
frappe.ui.form.on('Bank Guarantee', {
|
frappe.ui.form.on("Bank Guarantee", {
|
||||||
setup: function(frm) {
|
setup: function (frm) {
|
||||||
frm.set_query("bank", function() {
|
frm.set_query("bank", function () {
|
||||||
return {
|
|
||||||
filters: {
|
|
||||||
company: frm.doc.company
|
|
||||||
}
|
|
||||||
};
|
|
||||||
});
|
|
||||||
frm.set_query("bank_account", function() {
|
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
bank: frm.doc.bank
|
},
|
||||||
}
|
};
|
||||||
}
|
|
||||||
});
|
});
|
||||||
frm.set_query("project", function() {
|
frm.set_query("bank_account", function () {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
customer: frm.doc.customer
|
company: frm.doc.company,
|
||||||
}
|
bank: frm.doc.bank,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
});
|
||||||
|
frm.set_query("project", function () {
|
||||||
|
return {
|
||||||
|
filters: {
|
||||||
|
customer: frm.doc.customer,
|
||||||
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
bg_type: function(frm) {
|
bg_type: function (frm) {
|
||||||
if (frm.doc.bg_type == "Receiving") {
|
if (frm.doc.bg_type == "Receiving") {
|
||||||
frm.set_value("reference_doctype", "Sales Order");
|
frm.set_value("reference_doctype", "Sales Order");
|
||||||
} else if (frm.doc.bg_type == "Providing") {
|
} else if (frm.doc.bg_type == "Providing") {
|
||||||
@@ -41,34 +41,33 @@ frappe.ui.form.on('Bank Guarantee', {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
reference_docname: function(frm) {
|
reference_docname: function (frm) {
|
||||||
if (frm.doc.reference_docname && frm.doc.reference_doctype) {
|
if (frm.doc.reference_docname && frm.doc.reference_doctype) {
|
||||||
let party_field = frm.doc.reference_doctype == "Sales Order" ? "customer" : "supplier";
|
let party_field = frm.doc.reference_doctype == "Sales Order" ? "customer" : "supplier";
|
||||||
|
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "erpnext.accounts.doctype.bank_guarantee.bank_guarantee.get_voucher_details",
|
method: "erpnext.accounts.doctype.bank_guarantee.bank_guarantee.get_voucher_details",
|
||||||
args: {
|
args: {
|
||||||
"bank_guarantee_type": frm.doc.bg_type,
|
bank_guarantee_type: frm.doc.bg_type,
|
||||||
"reference_name": frm.doc.reference_docname
|
reference_name: frm.doc.reference_docname,
|
||||||
},
|
},
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
if (r.message) {
|
if (r.message) {
|
||||||
if (r.message[party_field]) frm.set_value(party_field, r.message[party_field]);
|
if (r.message[party_field]) frm.set_value(party_field, r.message[party_field]);
|
||||||
if (r.message.project) frm.set_value("project", r.message.project);
|
if (r.message.project) frm.set_value("project", r.message.project);
|
||||||
if (r.message.grand_total) frm.set_value("amount", r.message.grand_total);
|
if (r.message.grand_total) frm.set_value("amount", r.message.grand_total);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
start_date: function(frm) {
|
start_date: function (frm) {
|
||||||
var end_date = frappe.datetime.add_days(cur_frm.doc.start_date, cur_frm.doc.validity - 1);
|
var end_date = frappe.datetime.add_days(cur_frm.doc.start_date, cur_frm.doc.validity - 1);
|
||||||
cur_frm.set_value("end_date", end_date);
|
cur_frm.set_value("end_date", end_date);
|
||||||
},
|
},
|
||||||
validity: function(frm) {
|
validity: function (frm) {
|
||||||
var end_date = frappe.datetime.add_days(cur_frm.doc.start_date, cur_frm.doc.validity - 1);
|
var end_date = frappe.datetime.add_days(cur_frm.doc.start_date, cur_frm.doc.validity - 1);
|
||||||
cur_frm.set_value("end_date", end_date);
|
cur_frm.set_value("end_date", end_date);
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -48,11 +48,11 @@ class BankGuarantee(Document):
|
|||||||
|
|
||||||
def on_submit(self):
|
def on_submit(self):
|
||||||
if not self.bank_guarantee_number:
|
if not self.bank_guarantee_number:
|
||||||
frappe.throw(_("Enter the Bank Guarantee Number before submittting."))
|
frappe.throw(_("Enter the Bank Guarantee Number before submitting."))
|
||||||
if not self.name_of_beneficiary:
|
if not self.name_of_beneficiary:
|
||||||
frappe.throw(_("Enter the name of the Beneficiary before submittting."))
|
frappe.throw(_("Enter the name of the Beneficiary before submitting."))
|
||||||
if not self.bank:
|
if not self.bank:
|
||||||
frappe.throw(_("Enter the name of the bank or lending institution before submittting."))
|
frappe.throw(_("Enter the name of the bank or lending institution before submitting."))
|
||||||
|
|
||||||
|
|
||||||
@frappe.whitelist()
|
@frappe.whitelist()
|
||||||
|
|||||||
@@ -8,21 +8,22 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
|||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
'is_company_account': 1
|
is_company_account: 1,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
let no_bank_transactions_text =
|
let no_bank_transactions_text = `<div class="text-muted text-center">${__(
|
||||||
`<div class="text-muted text-center">${__("No Matching Bank Transactions Found")}</div>`
|
"No Matching Bank Transactions Found"
|
||||||
|
)}</div>`;
|
||||||
set_field_options("no_bank_transactions", no_bank_transactions_text);
|
set_field_options("no_bank_transactions", no_bank_transactions_text);
|
||||||
},
|
},
|
||||||
|
|
||||||
onload: function (frm) {
|
onload: function (frm) {
|
||||||
// Set default filter dates
|
// Set default filter dates
|
||||||
let today = frappe.datetime.get_today()
|
let today = frappe.datetime.get_today();
|
||||||
frm.doc.bank_statement_from_date = frappe.datetime.add_months(today, -1);
|
frm.doc.bank_statement_from_date = frappe.datetime.add_months(today, -1);
|
||||||
frm.doc.bank_statement_to_date = today;
|
frm.doc.bank_statement_to_date = today;
|
||||||
frm.trigger('bank_account');
|
frm.trigger("bank_account");
|
||||||
},
|
},
|
||||||
|
|
||||||
filter_by_reference_date: function (frm) {
|
filter_by_reference_date: function (frm) {
|
||||||
@@ -37,34 +38,27 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
|||||||
|
|
||||||
refresh: function (frm) {
|
refresh: function (frm) {
|
||||||
frm.disable_save();
|
frm.disable_save();
|
||||||
frappe.require("bank-reconciliation-tool.bundle.js", () =>
|
frappe.require("bank-reconciliation-tool.bundle.js", () => frm.trigger("make_reconciliation_tool"));
|
||||||
frm.trigger("make_reconciliation_tool")
|
|
||||||
);
|
|
||||||
|
|
||||||
frm.add_custom_button(__("Upload Bank Statement"), () =>
|
frm.add_custom_button(__("Upload Bank Statement"), () =>
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method:
|
method: "erpnext.accounts.doctype.bank_statement_import.bank_statement_import.upload_bank_statement",
|
||||||
"erpnext.accounts.doctype.bank_statement_import.bank_statement_import.upload_bank_statement",
|
args: {
|
||||||
args: {
|
dt: frm.doc.doctype,
|
||||||
dt: frm.doc.doctype,
|
dn: frm.doc.name,
|
||||||
dn: frm.doc.name,
|
company: frm.doc.company,
|
||||||
company: frm.doc.company,
|
bank_account: frm.doc.bank_account,
|
||||||
bank_account: frm.doc.bank_account,
|
},
|
||||||
},
|
callback: function (r) {
|
||||||
callback: function (r) {
|
if (!r.exc) {
|
||||||
if (!r.exc) {
|
var doc = frappe.model.sync(r.message);
|
||||||
var doc = frappe.model.sync(r.message);
|
frappe.set_route("Form", doc[0].doctype, doc[0].name);
|
||||||
frappe.set_route(
|
}
|
||||||
"Form",
|
},
|
||||||
doc[0].doctype,
|
})
|
||||||
doc[0].name
|
|
||||||
);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
})
|
|
||||||
);
|
);
|
||||||
|
|
||||||
frm.add_custom_button(__('Auto Reconcile'), function() {
|
frm.add_custom_button(__("Auto Reconcile"), function () {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.auto_reconcile_vouchers",
|
method: "erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.auto_reconcile_vouchers",
|
||||||
args: {
|
args: {
|
||||||
@@ -75,33 +69,22 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
|||||||
from_reference_date: frm.doc.from_reference_date,
|
from_reference_date: frm.doc.from_reference_date,
|
||||||
to_reference_date: frm.doc.to_reference_date,
|
to_reference_date: frm.doc.to_reference_date,
|
||||||
},
|
},
|
||||||
})
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
frm.add_custom_button(__('Get Unreconciled Entries'), function() {
|
frm.add_custom_button(__("Get Unreconciled Entries"), function () {
|
||||||
frm.trigger("make_reconciliation_tool");
|
frm.trigger("make_reconciliation_tool");
|
||||||
});
|
});
|
||||||
frm.change_custom_button_type(__('Get Unreconciled Entries'), null, 'primary');
|
frm.change_custom_button_type(__("Get Unreconciled Entries"), null, "primary");
|
||||||
|
|
||||||
},
|
},
|
||||||
|
|
||||||
bank_account: function (frm) {
|
bank_account: function (frm) {
|
||||||
frappe.db.get_value(
|
frappe.db.get_value("Bank Account", frm.doc.bank_account, "account", (r) => {
|
||||||
"Bank Account",
|
frappe.db.get_value("Account", r.account, "account_currency", (r) => {
|
||||||
frm.doc.bank_account,
|
frm.doc.account_currency = r.account_currency;
|
||||||
"account",
|
frm.trigger("render_chart");
|
||||||
(r) => {
|
});
|
||||||
frappe.db.get_value(
|
});
|
||||||
"Account",
|
|
||||||
r.account,
|
|
||||||
"account_currency",
|
|
||||||
(r) => {
|
|
||||||
frm.doc.account_currency = r.account_currency;
|
|
||||||
frm.trigger("render_chart");
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
);
|
|
||||||
frm.trigger("get_account_opening_balance");
|
frm.trigger("get_account_opening_balance");
|
||||||
},
|
},
|
||||||
|
|
||||||
@@ -120,11 +103,7 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
|||||||
) {
|
) {
|
||||||
frm.trigger("render_chart");
|
frm.trigger("render_chart");
|
||||||
frm.trigger("render");
|
frm.trigger("render");
|
||||||
frappe.utils.scroll_to(
|
frappe.utils.scroll_to(frm.get_field("reconciliation_tool_cards").$wrapper, true, 30);
|
||||||
frm.get_field("reconciliation_tool_cards").$wrapper,
|
|
||||||
true,
|
|
||||||
30
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -133,11 +112,10 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
|||||||
get_account_opening_balance(frm) {
|
get_account_opening_balance(frm) {
|
||||||
if (frm.doc.bank_account && frm.doc.bank_statement_from_date) {
|
if (frm.doc.bank_account && frm.doc.bank_statement_from_date) {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method:
|
method: "erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.get_account_balance",
|
||||||
"erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.get_account_balance",
|
|
||||||
args: {
|
args: {
|
||||||
bank_account: frm.doc.bank_account,
|
bank_account: frm.doc.bank_account,
|
||||||
till_date: frm.doc.bank_statement_from_date,
|
till_date: frappe.datetime.add_days(frm.doc.bank_statement_from_date, -1),
|
||||||
},
|
},
|
||||||
callback: (response) => {
|
callback: (response) => {
|
||||||
frm.set_value("account_opening_balance", response.message);
|
frm.set_value("account_opening_balance", response.message);
|
||||||
@@ -149,8 +127,7 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
|||||||
get_cleared_balance(frm) {
|
get_cleared_balance(frm) {
|
||||||
if (frm.doc.bank_account && frm.doc.bank_statement_to_date) {
|
if (frm.doc.bank_account && frm.doc.bank_statement_to_date) {
|
||||||
return frappe.call({
|
return frappe.call({
|
||||||
method:
|
method: "erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.get_account_balance",
|
||||||
"erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool.get_account_balance",
|
|
||||||
args: {
|
args: {
|
||||||
bank_account: frm.doc.bank_account,
|
bank_account: frm.doc.bank_account,
|
||||||
till_date: frm.doc.bank_statement_to_date,
|
till_date: frm.doc.bank_statement_to_date,
|
||||||
@@ -163,41 +140,30 @@ frappe.ui.form.on("Bank Reconciliation Tool", {
|
|||||||
},
|
},
|
||||||
|
|
||||||
render_chart(frm) {
|
render_chart(frm) {
|
||||||
frm.cards_manager = new erpnext.accounts.bank_reconciliation.NumberCardManager(
|
frm.cards_manager = new erpnext.accounts.bank_reconciliation.NumberCardManager({
|
||||||
{
|
$reconciliation_tool_cards: frm.get_field("reconciliation_tool_cards").$wrapper,
|
||||||
$reconciliation_tool_cards: frm.get_field(
|
bank_statement_closing_balance: frm.doc.bank_statement_closing_balance,
|
||||||
"reconciliation_tool_cards"
|
cleared_balance: frm.cleared_balance,
|
||||||
).$wrapper,
|
currency: frm.doc.account_currency,
|
||||||
bank_statement_closing_balance:
|
});
|
||||||
frm.doc.bank_statement_closing_balance,
|
|
||||||
cleared_balance: frm.cleared_balance,
|
|
||||||
currency: frm.doc.account_currency,
|
|
||||||
}
|
|
||||||
);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
render(frm) {
|
render(frm) {
|
||||||
if (frm.doc.bank_account) {
|
if (frm.doc.bank_account) {
|
||||||
frm.bank_reconciliation_data_table_manager = new erpnext.accounts.bank_reconciliation.DataTableManager(
|
frm.bank_reconciliation_data_table_manager =
|
||||||
{
|
new erpnext.accounts.bank_reconciliation.DataTableManager({
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
bank_account: frm.doc.bank_account,
|
bank_account: frm.doc.bank_account,
|
||||||
$reconciliation_tool_dt: frm.get_field(
|
$reconciliation_tool_dt: frm.get_field("reconciliation_tool_dt").$wrapper,
|
||||||
"reconciliation_tool_dt"
|
$no_bank_transactions: frm.get_field("no_bank_transactions").$wrapper,
|
||||||
).$wrapper,
|
|
||||||
$no_bank_transactions: frm.get_field(
|
|
||||||
"no_bank_transactions"
|
|
||||||
).$wrapper,
|
|
||||||
bank_statement_from_date: frm.doc.bank_statement_from_date,
|
bank_statement_from_date: frm.doc.bank_statement_from_date,
|
||||||
bank_statement_to_date: frm.doc.bank_statement_to_date,
|
bank_statement_to_date: frm.doc.bank_statement_to_date,
|
||||||
filter_by_reference_date: frm.doc.filter_by_reference_date,
|
filter_by_reference_date: frm.doc.filter_by_reference_date,
|
||||||
from_reference_date: frm.doc.from_reference_date,
|
from_reference_date: frm.doc.from_reference_date,
|
||||||
to_reference_date: frm.doc.to_reference_date,
|
to_reference_date: frm.doc.to_reference_date,
|
||||||
bank_statement_closing_balance:
|
bank_statement_closing_balance: frm.doc.bank_statement_closing_balance,
|
||||||
frm.doc.bank_statement_closing_balance,
|
|
||||||
cards_manager: frm.cards_manager,
|
cards_manager: frm.cards_manager,
|
||||||
}
|
});
|
||||||
);
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -18,6 +18,7 @@ from erpnext.accounts.report.bank_reconciliation_statement.bank_reconciliation_s
|
|||||||
get_entries,
|
get_entries,
|
||||||
)
|
)
|
||||||
from erpnext.accounts.utils import get_account_currency, get_balance_on
|
from erpnext.accounts.utils import get_account_currency, get_balance_on
|
||||||
|
from erpnext.setup.utils import get_exchange_rate
|
||||||
|
|
||||||
|
|
||||||
class BankReconciliationTool(Document):
|
class BankReconciliationTool(Document):
|
||||||
@@ -150,7 +151,7 @@ def create_journal_entry_bts(
|
|||||||
bank_transaction = frappe.db.get_values(
|
bank_transaction = frappe.db.get_values(
|
||||||
"Bank Transaction",
|
"Bank Transaction",
|
||||||
bank_transaction_name,
|
bank_transaction_name,
|
||||||
fieldname=["name", "deposit", "withdrawal", "bank_account"],
|
fieldname=["name", "deposit", "withdrawal", "bank_account", "currency"],
|
||||||
as_dict=True,
|
as_dict=True,
|
||||||
)[0]
|
)[0]
|
||||||
company_account = frappe.get_value("Bank Account", bank_transaction.bank_account, "account")
|
company_account = frappe.get_value("Bank Account", bank_transaction.bank_account, "account")
|
||||||
@@ -164,29 +165,94 @@ def create_journal_entry_bts(
|
|||||||
)
|
)
|
||||||
|
|
||||||
company = frappe.get_value("Account", company_account, "company")
|
company = frappe.get_value("Account", company_account, "company")
|
||||||
|
company_default_currency = frappe.get_cached_value("Company", company, "default_currency")
|
||||||
|
company_account_currency = frappe.get_cached_value("Account", company_account, "account_currency")
|
||||||
|
second_account_currency = frappe.get_cached_value("Account", second_account, "account_currency")
|
||||||
|
|
||||||
|
# determine if multi-currency Journal or not
|
||||||
|
is_multi_currency = (
|
||||||
|
True
|
||||||
|
if company_default_currency != company_account_currency
|
||||||
|
or company_default_currency != second_account_currency
|
||||||
|
or company_default_currency != bank_transaction.currency
|
||||||
|
else False
|
||||||
|
)
|
||||||
|
|
||||||
accounts = []
|
accounts = []
|
||||||
# Multi Currency?
|
second_account_dict = {
|
||||||
accounts.append(
|
"account": second_account,
|
||||||
{
|
"account_currency": second_account_currency,
|
||||||
"account": second_account,
|
"credit_in_account_currency": bank_transaction.deposit,
|
||||||
"credit_in_account_currency": bank_transaction.deposit,
|
"debit_in_account_currency": bank_transaction.withdrawal,
|
||||||
"debit_in_account_currency": bank_transaction.withdrawal,
|
"party_type": party_type,
|
||||||
"party_type": party_type,
|
"party": party,
|
||||||
"party": party,
|
"cost_center": get_default_cost_center(company),
|
||||||
"cost_center": get_default_cost_center(company),
|
}
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
accounts.append(
|
company_account_dict = {
|
||||||
{
|
"account": company_account,
|
||||||
"account": company_account,
|
"account_currency": company_account_currency,
|
||||||
"bank_account": bank_transaction.bank_account,
|
"bank_account": bank_transaction.bank_account,
|
||||||
"credit_in_account_currency": bank_transaction.withdrawal,
|
"credit_in_account_currency": bank_transaction.withdrawal,
|
||||||
"debit_in_account_currency": bank_transaction.deposit,
|
"debit_in_account_currency": bank_transaction.deposit,
|
||||||
"cost_center": get_default_cost_center(company),
|
"cost_center": get_default_cost_center(company),
|
||||||
}
|
}
|
||||||
)
|
|
||||||
|
# convert transaction amount to company currency
|
||||||
|
if is_multi_currency:
|
||||||
|
exc_rate = get_exchange_rate(bank_transaction.currency, company_default_currency, posting_date)
|
||||||
|
withdrawal_in_company_currency = flt(exc_rate * abs(bank_transaction.withdrawal))
|
||||||
|
deposit_in_company_currency = flt(exc_rate * abs(bank_transaction.deposit))
|
||||||
|
else:
|
||||||
|
withdrawal_in_company_currency = bank_transaction.withdrawal
|
||||||
|
deposit_in_company_currency = bank_transaction.deposit
|
||||||
|
|
||||||
|
# if second account is of foreign currency, convert and set debit and credit fields.
|
||||||
|
if second_account_currency != company_default_currency:
|
||||||
|
exc_rate = get_exchange_rate(second_account_currency, company_default_currency, posting_date)
|
||||||
|
second_account_dict.update(
|
||||||
|
{
|
||||||
|
"exchange_rate": exc_rate,
|
||||||
|
"credit": deposit_in_company_currency,
|
||||||
|
"debit": withdrawal_in_company_currency,
|
||||||
|
"credit_in_account_currency": flt(deposit_in_company_currency / exc_rate) or 0,
|
||||||
|
"debit_in_account_currency": flt(withdrawal_in_company_currency / exc_rate) or 0,
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
second_account_dict.update(
|
||||||
|
{
|
||||||
|
"exchange_rate": 1,
|
||||||
|
"credit": deposit_in_company_currency,
|
||||||
|
"debit": withdrawal_in_company_currency,
|
||||||
|
"credit_in_account_currency": deposit_in_company_currency,
|
||||||
|
"debit_in_account_currency": withdrawal_in_company_currency,
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
# if company account is of foreign currency, convert and set debit and credit fields.
|
||||||
|
if company_account_currency != company_default_currency:
|
||||||
|
exc_rate = get_exchange_rate(company_account_currency, company_default_currency, posting_date)
|
||||||
|
company_account_dict.update(
|
||||||
|
{
|
||||||
|
"exchange_rate": exc_rate,
|
||||||
|
"credit": withdrawal_in_company_currency,
|
||||||
|
"debit": deposit_in_company_currency,
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
company_account_dict.update(
|
||||||
|
{
|
||||||
|
"exchange_rate": 1,
|
||||||
|
"credit": withdrawal_in_company_currency,
|
||||||
|
"debit": deposit_in_company_currency,
|
||||||
|
"credit_in_account_currency": withdrawal_in_company_currency,
|
||||||
|
"debit_in_account_currency": deposit_in_company_currency,
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
accounts.append(second_account_dict)
|
||||||
|
accounts.append(company_account_dict)
|
||||||
|
|
||||||
journal_entry_dict = {
|
journal_entry_dict = {
|
||||||
"voucher_type": entry_type,
|
"voucher_type": entry_type,
|
||||||
@@ -196,6 +262,9 @@ def create_journal_entry_bts(
|
|||||||
"cheque_no": reference_number,
|
"cheque_no": reference_number,
|
||||||
"mode_of_payment": mode_of_payment,
|
"mode_of_payment": mode_of_payment,
|
||||||
}
|
}
|
||||||
|
if is_multi_currency:
|
||||||
|
journal_entry_dict.update({"multi_currency": True})
|
||||||
|
|
||||||
journal_entry = frappe.new_doc("Journal Entry")
|
journal_entry = frappe.new_doc("Journal Entry")
|
||||||
journal_entry.update(journal_entry_dict)
|
journal_entry.update(journal_entry_dict)
|
||||||
journal_entry.set("accounts", accounts)
|
journal_entry.set("accounts", accounts)
|
||||||
@@ -375,6 +444,10 @@ def reconcile_vouchers(bank_transaction_name, vouchers):
|
|||||||
vouchers = json.loads(vouchers)
|
vouchers = json.loads(vouchers)
|
||||||
transaction = frappe.get_doc("Bank Transaction", bank_transaction_name)
|
transaction = frappe.get_doc("Bank Transaction", bank_transaction_name)
|
||||||
transaction.add_payment_entries(vouchers)
|
transaction.add_payment_entries(vouchers)
|
||||||
|
transaction.validate_duplicate_references()
|
||||||
|
transaction.allocate_payment_entries()
|
||||||
|
transaction.update_allocated_amount()
|
||||||
|
transaction.set_status()
|
||||||
transaction.save()
|
transaction.save()
|
||||||
|
|
||||||
return transaction
|
return transaction
|
||||||
|
|||||||
@@ -76,6 +76,7 @@ class TestBankReconciliationTool(AccountsTestMixin, FrappeTestCase):
|
|||||||
"deposit": 100,
|
"deposit": 100,
|
||||||
"bank_account": self.bank_account,
|
"bank_account": self.bank_account,
|
||||||
"reference_number": "123",
|
"reference_number": "123",
|
||||||
|
"currency": "INR",
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
.save()
|
.save()
|
||||||
|
|||||||
@@ -2,16 +2,24 @@
|
|||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on("Bank Statement Import", {
|
frappe.ui.form.on("Bank Statement Import", {
|
||||||
|
onload(frm) {
|
||||||
|
frm.set_query("bank_account", function (doc) {
|
||||||
|
return {
|
||||||
|
filters: {
|
||||||
|
company: doc.company,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
setup(frm) {
|
setup(frm) {
|
||||||
frappe.realtime.on("data_import_refresh", ({ data_import }) => {
|
frappe.realtime.on("data_import_refresh", ({ data_import }) => {
|
||||||
frm.import_in_progress = false;
|
frm.import_in_progress = false;
|
||||||
if (data_import !== frm.doc.name) return;
|
if (data_import !== frm.doc.name) return;
|
||||||
frappe.model.clear_doc("Bank Statement Import", frm.doc.name);
|
frappe.model.clear_doc("Bank Statement Import", frm.doc.name);
|
||||||
frappe.model
|
frappe.model.with_doc("Bank Statement Import", frm.doc.name).then(() => {
|
||||||
.with_doc("Bank Statement Import", frm.doc.name)
|
frm.refresh();
|
||||||
.then(() => {
|
});
|
||||||
frm.refresh();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
frappe.realtime.on("data_import_progress", (data) => {
|
frappe.realtime.on("data_import_progress", (data) => {
|
||||||
frm.import_in_progress = true;
|
frm.import_in_progress = true;
|
||||||
@@ -38,20 +46,9 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
: __("Updating {0} of {1}, {2}", message_args);
|
: __("Updating {0} of {1}, {2}", message_args);
|
||||||
}
|
}
|
||||||
if (data.skipping) {
|
if (data.skipping) {
|
||||||
message = __(
|
message = __("Skipping {0} of {1}, {2}", [data.current, data.total, eta_message]);
|
||||||
"Skipping {0} of {1}, {2}",
|
|
||||||
[
|
|
||||||
data.current,
|
|
||||||
data.total,
|
|
||||||
eta_message,
|
|
||||||
]
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
frm.dashboard.show_progress(
|
frm.dashboard.show_progress(__("Import Progress"), percent, message);
|
||||||
__("Import Progress"),
|
|
||||||
percent,
|
|
||||||
message
|
|
||||||
);
|
|
||||||
frm.page.set_indicator(__("In Progress"), "orange");
|
frm.page.set_indicator(__("In Progress"), "orange");
|
||||||
|
|
||||||
// hide progress when complete
|
// hide progress when complete
|
||||||
@@ -93,15 +90,12 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
frm.trigger("show_report_error_button");
|
frm.trigger("show_report_error_button");
|
||||||
|
|
||||||
if (frm.doc.status === "Partial Success") {
|
if (frm.doc.status === "Partial Success") {
|
||||||
frm.add_custom_button(__("Export Errored Rows"), () =>
|
frm.add_custom_button(__("Export Errored Rows"), () => frm.trigger("export_errored_rows"));
|
||||||
frm.trigger("export_errored_rows")
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (frm.doc.status.includes("Success")) {
|
if (frm.doc.status.includes("Success")) {
|
||||||
frm.add_custom_button(
|
frm.add_custom_button(__("Go to {0} List", [__(frm.doc.reference_doctype)]), () =>
|
||||||
__("Go to {0} List", [__(frm.doc.reference_doctype)]),
|
frappe.set_route("List", frm.doc.reference_doctype)
|
||||||
() => frappe.set_route("List", frm.doc.reference_doctype)
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -118,13 +112,8 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
frm.disable_save();
|
frm.disable_save();
|
||||||
if (frm.doc.status !== "Success") {
|
if (frm.doc.status !== "Success") {
|
||||||
if (!frm.is_new() && frm.has_import_file()) {
|
if (!frm.is_new() && frm.has_import_file()) {
|
||||||
let label =
|
let label = frm.doc.status === "Pending" ? __("Start Import") : __("Retry");
|
||||||
frm.doc.status === "Pending"
|
frm.page.set_primary_action(label, () => frm.events.start_import(frm));
|
||||||
? __("Start Import")
|
|
||||||
: __("Retry");
|
|
||||||
frm.page.set_primary_action(label, () =>
|
|
||||||
frm.events.start_import(frm)
|
|
||||||
);
|
|
||||||
} else {
|
} else {
|
||||||
frm.page.set_primary_action(__("Save"), () => frm.save());
|
frm.page.set_primary_action(__("Save"), () => frm.save());
|
||||||
}
|
}
|
||||||
@@ -166,24 +155,24 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
message =
|
message =
|
||||||
successful_records.length > 1
|
successful_records.length > 1
|
||||||
? __(
|
? __(
|
||||||
"Successfully imported {0} records out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
"Successfully imported {0} records out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
||||||
message_args
|
message_args
|
||||||
)
|
)
|
||||||
: __(
|
: __(
|
||||||
"Successfully imported {0} record out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
"Successfully imported {0} record out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
||||||
message_args
|
message_args
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
message =
|
message =
|
||||||
successful_records.length > 1
|
successful_records.length > 1
|
||||||
? __(
|
? __(
|
||||||
"Successfully updated {0} records out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
"Successfully updated {0} records out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
||||||
message_args
|
message_args
|
||||||
)
|
)
|
||||||
: __(
|
: __(
|
||||||
"Successfully updated {0} record out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
"Successfully updated {0} record out of {1}. Click on Export Errored Rows, fix the errors and import again.",
|
||||||
message_args
|
message_args
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
frm.dashboard.set_headline(message);
|
frm.dashboard.set_headline(message);
|
||||||
@@ -226,8 +215,7 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
},
|
},
|
||||||
|
|
||||||
download_template() {
|
download_template() {
|
||||||
let method =
|
let method = "/api/method/frappe.core.doctype.data_import.data_import.download_template";
|
||||||
"/api/method/frappe.core.doctype.data_import.data_import.download_template";
|
|
||||||
|
|
||||||
open_url_post(method, {
|
open_url_post(method, {
|
||||||
doctype: "Bank Transaction",
|
doctype: "Bank Transaction",
|
||||||
@@ -240,7 +228,7 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
"description",
|
"description",
|
||||||
"reference_number",
|
"reference_number",
|
||||||
"bank_account",
|
"bank_account",
|
||||||
"currency"
|
"currency",
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
@@ -311,10 +299,7 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
show_import_preview(frm, preview_data) {
|
show_import_preview(frm, preview_data) {
|
||||||
let import_log = JSON.parse(frm.doc.statement_import_log || "[]");
|
let import_log = JSON.parse(frm.doc.statement_import_log || "[]");
|
||||||
|
|
||||||
if (
|
if (frm.import_preview && frm.import_preview.doctype === frm.doc.reference_doctype) {
|
||||||
frm.import_preview &&
|
|
||||||
frm.import_preview.doctype === frm.doc.reference_doctype
|
|
||||||
) {
|
|
||||||
frm.import_preview.preview_data = preview_data;
|
frm.import_preview.preview_data = preview_data;
|
||||||
frm.import_preview.import_log = import_log;
|
frm.import_preview.import_log = import_log;
|
||||||
frm.import_preview.refresh();
|
frm.import_preview.refresh();
|
||||||
@@ -330,19 +315,10 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
frm,
|
frm,
|
||||||
events: {
|
events: {
|
||||||
remap_column(changed_map) {
|
remap_column(changed_map) {
|
||||||
let template_options = JSON.parse(
|
let template_options = JSON.parse(frm.doc.template_options || "{}");
|
||||||
frm.doc.template_options || "{}"
|
template_options.column_to_field_map = template_options.column_to_field_map || {};
|
||||||
);
|
Object.assign(template_options.column_to_field_map, changed_map);
|
||||||
template_options.column_to_field_map =
|
frm.set_value("template_options", JSON.stringify(template_options));
|
||||||
template_options.column_to_field_map || {};
|
|
||||||
Object.assign(
|
|
||||||
template_options.column_to_field_map,
|
|
||||||
changed_map
|
|
||||||
);
|
|
||||||
frm.set_value(
|
|
||||||
"template_options",
|
|
||||||
JSON.stringify(template_options)
|
|
||||||
);
|
|
||||||
frm.save().then(() => frm.trigger("import_file"));
|
frm.save().then(() => frm.trigger("import_file"));
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@@ -376,8 +352,7 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
let other_warnings = [];
|
let other_warnings = [];
|
||||||
for (let warning of warnings) {
|
for (let warning of warnings) {
|
||||||
if (warning.row) {
|
if (warning.row) {
|
||||||
warnings_by_row[warning.row] =
|
warnings_by_row[warning.row] = warnings_by_row[warning.row] || [];
|
||||||
warnings_by_row[warning.row] || [];
|
|
||||||
warnings_by_row[warning.row].push(warning);
|
warnings_by_row[warning.row].push(warning);
|
||||||
} else {
|
} else {
|
||||||
other_warnings.push(warning);
|
other_warnings.push(warning);
|
||||||
@@ -392,9 +367,7 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
if (w.field) {
|
if (w.field) {
|
||||||
let label =
|
let label =
|
||||||
w.field.label +
|
w.field.label +
|
||||||
(w.field.parent !== frm.doc.reference_doctype
|
(w.field.parent !== frm.doc.reference_doctype ? ` (${w.field.parent})` : "");
|
||||||
? ` (${w.field.parent})`
|
|
||||||
: "");
|
|
||||||
return `<li>${label}: ${w.message}</li>`;
|
return `<li>${label}: ${w.message}</li>`;
|
||||||
}
|
}
|
||||||
return `<li>${w.message}</li>`;
|
return `<li>${w.message}</li>`;
|
||||||
@@ -413,10 +386,9 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
.map((warning) => {
|
.map((warning) => {
|
||||||
let header = "";
|
let header = "";
|
||||||
if (warning.col) {
|
if (warning.col) {
|
||||||
let column_number = `<span class="text-uppercase">${__(
|
let column_number = `<span class="text-uppercase">${__("Column {0}", [
|
||||||
"Column {0}",
|
warning.col,
|
||||||
[warning.col]
|
])}</span>`;
|
||||||
)}</span>`;
|
|
||||||
let column_header = columns[warning.col].header_title;
|
let column_header = columns[warning.col].header_title;
|
||||||
header = `${column_number} (${column_header})`;
|
header = `${column_number} (${column_header})`;
|
||||||
}
|
}
|
||||||
@@ -455,36 +427,28 @@ frappe.ui.form.on("Bank Statement Import", {
|
|||||||
let html = "";
|
let html = "";
|
||||||
if (log.success) {
|
if (log.success) {
|
||||||
if (frm.doc.import_type === "Insert New Records") {
|
if (frm.doc.import_type === "Insert New Records") {
|
||||||
html = __(
|
html = __("Successfully imported {0}", [
|
||||||
"Successfully imported {0}", [
|
`<span class="underline">${frappe.utils.get_form_link(
|
||||||
`<span class="underline">${frappe.utils.get_form_link(
|
frm.doc.reference_doctype,
|
||||||
frm.doc.reference_doctype,
|
log.docname,
|
||||||
log.docname,
|
true
|
||||||
true
|
)}<span>`,
|
||||||
)}<span>`,
|
]);
|
||||||
]
|
|
||||||
);
|
|
||||||
} else {
|
} else {
|
||||||
html = __(
|
html = __("Successfully updated {0}", [
|
||||||
"Successfully updated {0}", [
|
`<span class="underline">${frappe.utils.get_form_link(
|
||||||
`<span class="underline">${frappe.utils.get_form_link(
|
frm.doc.reference_doctype,
|
||||||
frm.doc.reference_doctype,
|
log.docname,
|
||||||
log.docname,
|
true
|
||||||
true
|
)}<span>`,
|
||||||
)}<span>`,
|
]);
|
||||||
]
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
let messages = log.messages
|
let messages = log.messages
|
||||||
.map(JSON.parse)
|
.map(JSON.parse)
|
||||||
.map((m) => {
|
.map((m) => {
|
||||||
let title = m.title
|
let title = m.title ? `<strong>${m.title}</strong>` : "";
|
||||||
? `<strong>${m.title}</strong>`
|
let message = m.message ? `<div>${m.message}</div>` : "";
|
||||||
: "";
|
|
||||||
let message = m.message
|
|
||||||
? `<div>${m.message}</div>`
|
|
||||||
: "";
|
|
||||||
return title + message;
|
return title + message;
|
||||||
})
|
})
|
||||||
.join("");
|
.join("");
|
||||||
|
|||||||
@@ -80,7 +80,8 @@ class BankStatementImport(DataImport):
|
|||||||
from frappe.utils.background_jobs import is_job_enqueued
|
from frappe.utils.background_jobs import is_job_enqueued
|
||||||
from frappe.utils.scheduler import is_scheduler_inactive
|
from frappe.utils.scheduler import is_scheduler_inactive
|
||||||
|
|
||||||
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:
|
||||||
frappe.throw(_("Scheduler is inactive. Cannot import data."), title=_("Scheduler Inactive"))
|
frappe.throw(_("Scheduler is inactive. Cannot import data."), title=_("Scheduler Inactive"))
|
||||||
|
|
||||||
job_id = f"bank_statement_import::{self.name}"
|
job_id = f"bank_statement_import::{self.name}"
|
||||||
@@ -97,7 +98,7 @@ class BankStatementImport(DataImport):
|
|||||||
google_sheets_url=self.google_sheets_url,
|
google_sheets_url=self.google_sheets_url,
|
||||||
bank=self.bank,
|
bank=self.bank,
|
||||||
template_options=self.template_options,
|
template_options=self.template_options,
|
||||||
now=frappe.conf.developer_mode or frappe.flags.in_test,
|
now=run_now,
|
||||||
)
|
)
|
||||||
return True
|
return True
|
||||||
|
|
||||||
|
|||||||
@@ -1,36 +1,34 @@
|
|||||||
let imports_in_progress = [];
|
let imports_in_progress = [];
|
||||||
|
|
||||||
frappe.listview_settings['Bank Statement Import'] = {
|
frappe.listview_settings["Bank Statement Import"] = {
|
||||||
onload(listview) {
|
onload(listview) {
|
||||||
frappe.realtime.on('data_import_progress', data => {
|
frappe.realtime.on("data_import_progress", (data) => {
|
||||||
if (!imports_in_progress.includes(data.data_import)) {
|
if (!imports_in_progress.includes(data.data_import)) {
|
||||||
imports_in_progress.push(data.data_import);
|
imports_in_progress.push(data.data_import);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
frappe.realtime.on('data_import_refresh', data => {
|
frappe.realtime.on("data_import_refresh", (data) => {
|
||||||
imports_in_progress = imports_in_progress.filter(
|
imports_in_progress = imports_in_progress.filter((d) => d !== data.data_import);
|
||||||
d => d !== data.data_import
|
|
||||||
);
|
|
||||||
listview.refresh();
|
listview.refresh();
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
get_indicator: function(doc) {
|
get_indicator: function (doc) {
|
||||||
var colors = {
|
var colors = {
|
||||||
'Pending': 'orange',
|
Pending: "orange",
|
||||||
'Not Started': 'orange',
|
"Not Started": "orange",
|
||||||
'Partial Success': 'orange',
|
"Partial Success": "orange",
|
||||||
'Success': 'green',
|
Success: "green",
|
||||||
'In Progress': 'orange',
|
"In Progress": "orange",
|
||||||
'Error': 'red'
|
Error: "red",
|
||||||
};
|
};
|
||||||
let status = doc.status;
|
let status = doc.status;
|
||||||
if (imports_in_progress.includes(doc.name)) {
|
if (imports_in_progress.includes(doc.name)) {
|
||||||
status = 'In Progress';
|
status = "In Progress";
|
||||||
}
|
}
|
||||||
if (status == 'Pending') {
|
if (status == "Pending") {
|
||||||
status = 'Not Started';
|
status = "Not Started";
|
||||||
}
|
}
|
||||||
return [__(status), colors[status], 'status,=,' + doc.status];
|
return [__(status), colors[status], "status,=," + doc.status];
|
||||||
},
|
},
|
||||||
hide_name_column: true
|
hide_name_column: true,
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -112,7 +112,8 @@ class AutoMatchbyPartyNameDescription:
|
|||||||
|
|
||||||
for party in parties:
|
for party in parties:
|
||||||
filters = {"status": "Active"} if party == "Employee" else {"disabled": 0}
|
filters = {"status": "Active"} if party == "Employee" else {"disabled": 0}
|
||||||
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"])
|
||||||
|
|
||||||
for field in ["bank_party_name", "description"]:
|
for field in ["bank_party_name", "description"]:
|
||||||
if not self.get(field):
|
if not self.get(field):
|
||||||
@@ -131,7 +132,11 @@ class AutoMatchbyPartyNameDescription:
|
|||||||
|
|
||||||
def fuzzy_search_and_return_result(self, party, names, field) -> Union[Tuple, None]:
|
def fuzzy_search_and_return_result(self, party, names, field) -> Union[Tuple, None]:
|
||||||
skip = False
|
skip = False
|
||||||
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,
|
||||||
|
)
|
||||||
party_name, skip = self.process_fuzzy_result(result)
|
party_name, skip = self.process_fuzzy_result(result)
|
||||||
|
|
||||||
if not party_name:
|
if not party_name:
|
||||||
@@ -149,14 +154,14 @@ class AutoMatchbyPartyNameDescription:
|
|||||||
|
|
||||||
Returns: Result, Skip (whether or not to discontinue matching)
|
Returns: Result, Skip (whether or not to discontinue matching)
|
||||||
"""
|
"""
|
||||||
PARTY, SCORE, CUTOFF = 0, 1, 80
|
SCORE, PARTY_ID, CUTOFF = 1, 2, 80
|
||||||
|
|
||||||
if not result or not len(result):
|
if not result or not len(result):
|
||||||
return None, False
|
return None, False
|
||||||
|
|
||||||
first_result = result[0]
|
first_result = result[0]
|
||||||
if len(result) == 1:
|
if len(result) == 1:
|
||||||
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
|
||||||
|
|
||||||
second_result = result[1]
|
second_result = result[1]
|
||||||
if first_result[SCORE] > CUTOFF:
|
if first_result[SCORE] > CUTOFF:
|
||||||
@@ -165,7 +170,7 @@ class AutoMatchbyPartyNameDescription:
|
|||||||
if first_result[SCORE] == second_result[SCORE]:
|
if first_result[SCORE] == second_result[SCORE]:
|
||||||
return None, True
|
return None, True
|
||||||
|
|
||||||
return first_result[PARTY], True
|
return first_result[PARTY_ID], True
|
||||||
else:
|
else:
|
||||||
return None, False
|
return None, False
|
||||||
|
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
frappe.ui.form.on("Bank Transaction", {
|
frappe.ui.form.on("Bank Transaction", {
|
||||||
onload(frm) {
|
onload(frm) {
|
||||||
frm.set_query("payment_document", "payment_entries", function() {
|
frm.set_query("payment_document", "payment_entries", function () {
|
||||||
const payment_doctypes = frm.events.get_payment_doctypes(frm);
|
const payment_doctypes = frm.events.get_payment_doctypes(frm);
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
@@ -23,7 +23,7 @@ frappe.ui.form.on("Bank Transaction", {
|
|||||||
set_bank_statement_filter(frm);
|
set_bank_statement_filter(frm);
|
||||||
},
|
},
|
||||||
|
|
||||||
setup: function(frm) {
|
setup: function (frm) {
|
||||||
frm.set_query("party_type", function () {
|
frm.set_query("party_type", function () {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
@@ -33,16 +33,10 @@ frappe.ui.form.on("Bank Transaction", {
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
get_payment_doctypes: function() {
|
get_payment_doctypes: function () {
|
||||||
// get payment doctypes from all the apps
|
// get payment doctypes from all the apps
|
||||||
return [
|
return ["Payment Entry", "Journal Entry", "Sales Invoice", "Purchase Invoice", "Bank Transaction"];
|
||||||
"Payment Entry",
|
},
|
||||||
"Journal Entry",
|
|
||||||
"Sales Invoice",
|
|
||||||
"Purchase Invoice",
|
|
||||||
"Bank Transaction",
|
|
||||||
];
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|
||||||
frappe.ui.form.on("Bank Transaction Payments", {
|
frappe.ui.form.on("Bank Transaction Payments", {
|
||||||
@@ -54,10 +48,11 @@ frappe.ui.form.on("Bank Transaction Payments", {
|
|||||||
const update_clearance_date = (frm, cdt, cdn) => {
|
const update_clearance_date = (frm, cdt, cdn) => {
|
||||||
if (frm.doc.docstatus === 1) {
|
if (frm.doc.docstatus === 1) {
|
||||||
frappe
|
frappe
|
||||||
.xcall(
|
.xcall("erpnext.accounts.doctype.bank_transaction.bank_transaction.unclear_reference_payment", {
|
||||||
"erpnext.accounts.doctype.bank_transaction.bank_transaction.unclear_reference_payment",
|
doctype: cdt,
|
||||||
{ doctype: cdt, docname: cdn, bt_name: frm.doc.name }
|
docname: cdn,
|
||||||
)
|
bt_name: frm.doc.name,
|
||||||
|
})
|
||||||
.then((e) => {
|
.then((e) => {
|
||||||
if (e == "success") {
|
if (e == "success") {
|
||||||
frappe.show_alert({
|
frappe.show_alert({
|
||||||
|
|||||||
@@ -3,12 +3,12 @@
|
|||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
from frappe import _
|
from frappe import _
|
||||||
|
from frappe.model.docstatus import DocStatus
|
||||||
|
from frappe.model.document import Document
|
||||||
from frappe.utils import flt
|
from frappe.utils import flt
|
||||||
|
|
||||||
from erpnext.controllers.status_updater import StatusUpdater
|
|
||||||
|
|
||||||
|
class BankTransaction(Document):
|
||||||
class BankTransaction(StatusUpdater):
|
|
||||||
# begin: auto-generated types
|
# begin: auto-generated types
|
||||||
# This code is auto-generated. Do not modify anything in this block.
|
# This code is auto-generated. Do not modify anything in this block.
|
||||||
|
|
||||||
@@ -49,6 +49,33 @@ class BankTransaction(StatusUpdater):
|
|||||||
|
|
||||||
def validate(self):
|
def validate(self):
|
||||||
self.validate_duplicate_references()
|
self.validate_duplicate_references()
|
||||||
|
self.validate_currency()
|
||||||
|
|
||||||
|
def validate_currency(self):
|
||||||
|
"""
|
||||||
|
Bank Transaction should be on the same currency as the Bank Account.
|
||||||
|
"""
|
||||||
|
if self.currency and self.bank_account:
|
||||||
|
account = frappe.get_cached_value("Bank Account", self.bank_account, "account")
|
||||||
|
account_currency = frappe.get_cached_value("Account", account, "account_currency")
|
||||||
|
|
||||||
|
if self.currency != account_currency:
|
||||||
|
frappe.throw(
|
||||||
|
_(
|
||||||
|
"Transaction currency: {0} cannot be different from Bank Account({1}) currency: {2}"
|
||||||
|
).format(
|
||||||
|
frappe.bold(self.currency), frappe.bold(self.bank_account), frappe.bold(account_currency)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
def set_status(self):
|
||||||
|
if self.docstatus == 2:
|
||||||
|
self.db_set("status", "Cancelled")
|
||||||
|
elif self.docstatus == 1:
|
||||||
|
if self.unallocated_amount > 0:
|
||||||
|
self.db_set("status", "Unreconciled")
|
||||||
|
elif self.unallocated_amount <= 0:
|
||||||
|
self.db_set("status", "Reconciled")
|
||||||
|
|
||||||
def validate_duplicate_references(self):
|
def validate_duplicate_references(self):
|
||||||
"""Make sure the same voucher is not allocated twice within the same Bank Transaction"""
|
"""Make sure the same voucher is not allocated twice within the same Bank Transaction"""
|
||||||
@@ -67,10 +94,13 @@ class BankTransaction(StatusUpdater):
|
|||||||
pe.append(reference)
|
pe.append(reference)
|
||||||
|
|
||||||
def update_allocated_amount(self):
|
def update_allocated_amount(self):
|
||||||
self.allocated_amount = (
|
allocated_amount = (
|
||||||
sum(p.allocated_amount for p in self.payment_entries) if self.payment_entries else 0.0
|
sum(p.allocated_amount for p in self.payment_entries) if self.payment_entries else 0.0
|
||||||
)
|
)
|
||||||
self.unallocated_amount = abs(flt(self.withdrawal) - flt(self.deposit)) - self.allocated_amount
|
unallocated_amount = abs(flt(self.withdrawal) - flt(self.deposit)) - allocated_amount
|
||||||
|
|
||||||
|
self.allocated_amount = flt(allocated_amount, self.precision("allocated_amount"))
|
||||||
|
self.unallocated_amount = flt(unallocated_amount, self.precision("unallocated_amount"))
|
||||||
|
|
||||||
def before_submit(self):
|
def before_submit(self):
|
||||||
self.allocate_payment_entries()
|
self.allocate_payment_entries()
|
||||||
@@ -83,12 +113,13 @@ class BankTransaction(StatusUpdater):
|
|||||||
self.validate_duplicate_references()
|
self.validate_duplicate_references()
|
||||||
self.allocate_payment_entries()
|
self.allocate_payment_entries()
|
||||||
self.update_allocated_amount()
|
self.update_allocated_amount()
|
||||||
|
self.set_status()
|
||||||
|
|
||||||
def on_cancel(self):
|
def on_cancel(self):
|
||||||
for payment_entry in self.payment_entries:
|
for payment_entry in self.payment_entries:
|
||||||
self.clear_linked_payment_entry(payment_entry, for_cancel=True)
|
self.clear_linked_payment_entry(payment_entry, for_cancel=True)
|
||||||
|
|
||||||
self.set_status(update=True)
|
self.set_status()
|
||||||
|
|
||||||
def add_payment_entries(self, vouchers):
|
def add_payment_entries(self, vouchers):
|
||||||
"Add the vouchers with zero allocation. Save() will perform the allocations and clearance"
|
"Add the vouchers with zero allocation. Save() will perform the allocations and clearance"
|
||||||
@@ -366,15 +397,17 @@ def set_voucher_clearance(doctype, docname, clearance_date, self):
|
|||||||
and len(get_reconciled_bank_transactions(doctype, docname)) < 2
|
and len(get_reconciled_bank_transactions(doctype, docname)) < 2
|
||||||
):
|
):
|
||||||
return
|
return
|
||||||
frappe.db.set_value(doctype, docname, "clearance_date", clearance_date)
|
|
||||||
|
|
||||||
elif doctype == "Sales Invoice":
|
if doctype == "Sales Invoice":
|
||||||
frappe.db.set_value(
|
frappe.db.set_value(
|
||||||
"Sales Invoice Payment",
|
"Sales Invoice Payment",
|
||||||
dict(parenttype=doctype, parent=docname),
|
dict(parenttype=doctype, parent=docname),
|
||||||
"clearance_date",
|
"clearance_date",
|
||||||
clearance_date,
|
clearance_date,
|
||||||
)
|
)
|
||||||
|
return
|
||||||
|
|
||||||
|
frappe.db.set_value(doctype, docname, "clearance_date", clearance_date)
|
||||||
|
|
||||||
elif doctype == "Bank Transaction":
|
elif doctype == "Bank Transaction":
|
||||||
# For when a second bank transaction has fixed another, e.g. refund
|
# For when a second bank transaction has fixed another, e.g. refund
|
||||||
@@ -404,3 +437,21 @@ def unclear_reference_payment(doctype, docname, bt_name):
|
|||||||
bt = frappe.get_doc("Bank Transaction", bt_name)
|
bt = frappe.get_doc("Bank Transaction", bt_name)
|
||||||
set_voucher_clearance(doctype, docname, None, bt)
|
set_voucher_clearance(doctype, docname, None, bt)
|
||||||
return docname
|
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):
|
||||||
|
bt = frappe.get_doc("Bank Transaction", bt_name)
|
||||||
|
if bt.docstatus == DocStatus.cancelled():
|
||||||
|
continue
|
||||||
|
|
||||||
|
modified = False
|
||||||
|
|
||||||
|
for pe in bt.payment_entries:
|
||||||
|
if pe.payment_document == doctype and pe.payment_entry == docname:
|
||||||
|
bt.remove(pe)
|
||||||
|
modified = True
|
||||||
|
|
||||||
|
if modified:
|
||||||
|
bt.save()
|
||||||
|
|||||||
@@ -1,15 +1,15 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and Contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and Contributors
|
||||||
// License: GNU General Public License v3. See license.txt
|
// License: GNU General Public License v3. See license.txt
|
||||||
|
|
||||||
frappe.listview_settings['Bank Transaction'] = {
|
frappe.listview_settings["Bank Transaction"] = {
|
||||||
add_fields: ["unallocated_amount"],
|
add_fields: ["unallocated_amount"],
|
||||||
get_indicator: function(doc) {
|
get_indicator: function (doc) {
|
||||||
if(doc.docstatus == 2) {
|
if (doc.docstatus == 2) {
|
||||||
return [__("Cancelled"), "red", "docstatus,=,2"];
|
return [__("Cancelled"), "red", "docstatus,=,2"];
|
||||||
} else if(flt(doc.unallocated_amount)<=0) {
|
} else if (flt(doc.unallocated_amount) <= 0) {
|
||||||
return [__("Reconciled"), "green", "unallocated_amount,=,0"];
|
return [__("Reconciled"), "green", "unallocated_amount,=,0"];
|
||||||
} else if(flt(doc.unallocated_amount)>0) {
|
} else if (flt(doc.unallocated_amount) > 0) {
|
||||||
return [__("Unreconciled"), "orange", "unallocated_amount,>,0"];
|
return [__("Unreconciled"), "orange", "unallocated_amount,>,0"];
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -2,10 +2,10 @@
|
|||||||
# See license.txt
|
# See license.txt
|
||||||
|
|
||||||
import json
|
import json
|
||||||
import unittest
|
|
||||||
|
|
||||||
import frappe
|
import frappe
|
||||||
from frappe import utils
|
from frappe import utils
|
||||||
|
from frappe.model.docstatus import DocStatus
|
||||||
from frappe.tests.utils import FrappeTestCase
|
from frappe.tests.utils import FrappeTestCase
|
||||||
|
|
||||||
from erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool import (
|
from erpnext.accounts.doctype.bank_reconciliation_tool.bank_reconciliation_tool import (
|
||||||
@@ -32,8 +32,16 @@ class TestBankTransaction(FrappeTestCase):
|
|||||||
frappe.db.delete(dt)
|
frappe.db.delete(dt)
|
||||||
clear_loan_transactions()
|
clear_loan_transactions()
|
||||||
make_pos_profile()
|
make_pos_profile()
|
||||||
add_transactions()
|
|
||||||
add_vouchers()
|
# generate and use a uniq hash identifier for 'Bank Account' and it's linked GL 'Account' to avoid validation error
|
||||||
|
uniq_identifier = frappe.generate_hash(length=10)
|
||||||
|
gl_account = create_gl_account("_Test Bank " + uniq_identifier)
|
||||||
|
bank_account = create_bank_account(
|
||||||
|
gl_account=gl_account, bank_account_name="Checking Account " + uniq_identifier
|
||||||
|
)
|
||||||
|
|
||||||
|
add_transactions(bank_account=bank_account)
|
||||||
|
add_vouchers(gl_account=gl_account)
|
||||||
|
|
||||||
# This test checks if ERPNext is able to provide a linked payment for a bank transaction based on the amount of the bank transaction.
|
# This test checks if ERPNext is able to provide a linked payment for a bank transaction based on the amount of the bank transaction.
|
||||||
def test_linked_payments(self):
|
def test_linked_payments(self):
|
||||||
@@ -81,6 +89,29 @@ class TestBankTransaction(FrappeTestCase):
|
|||||||
clearance_date = frappe.db.get_value("Payment Entry", payment.name, "clearance_date")
|
clearance_date = frappe.db.get_value("Payment Entry", payment.name, "clearance_date")
|
||||||
self.assertFalse(clearance_date)
|
self.assertFalse(clearance_date)
|
||||||
|
|
||||||
|
def test_cancel_voucher(self):
|
||||||
|
bank_transaction = frappe.get_doc(
|
||||||
|
"Bank Transaction",
|
||||||
|
dict(description="1512567 BG/000003025 OPSKATTUZWXXX AT776000000098709849 Herr G"),
|
||||||
|
)
|
||||||
|
payment = frappe.get_doc("Payment Entry", dict(party="Mr G", paid_amount=1700))
|
||||||
|
vouchers = json.dumps(
|
||||||
|
[
|
||||||
|
{
|
||||||
|
"payment_doctype": "Payment Entry",
|
||||||
|
"payment_name": payment.name,
|
||||||
|
"amount": bank_transaction.unallocated_amount,
|
||||||
|
}
|
||||||
|
]
|
||||||
|
)
|
||||||
|
reconcile_vouchers(bank_transaction.name, vouchers)
|
||||||
|
payment.reload()
|
||||||
|
payment.cancel()
|
||||||
|
bank_transaction.reload()
|
||||||
|
self.assertEqual(bank_transaction.docstatus, DocStatus.submitted())
|
||||||
|
self.assertEqual(bank_transaction.unallocated_amount, 1700)
|
||||||
|
self.assertEqual(bank_transaction.payment_entries, [])
|
||||||
|
|
||||||
# Check if ERPNext can correctly filter a linked payments based on the debit/credit amount
|
# Check if ERPNext can correctly filter a linked payments based on the debit/credit amount
|
||||||
def test_debit_credit_output(self):
|
def test_debit_credit_output(self):
|
||||||
bank_transaction = frappe.get_doc(
|
bank_transaction = frappe.get_doc(
|
||||||
@@ -196,7 +227,9 @@ def clear_loan_transactions():
|
|||||||
frappe.db.delete("Loan Repayment")
|
frappe.db.delete("Loan Repayment")
|
||||||
|
|
||||||
|
|
||||||
def create_bank_account(bank_name="Citi Bank", account_name="_Test Bank - _TC"):
|
def create_bank_account(
|
||||||
|
bank_name="Citi Bank", gl_account="_Test Bank - _TC", bank_account_name="Checking Account"
|
||||||
|
):
|
||||||
try:
|
try:
|
||||||
frappe.get_doc(
|
frappe.get_doc(
|
||||||
{
|
{
|
||||||
@@ -208,21 +241,35 @@ def create_bank_account(bank_name="Citi Bank", account_name="_Test Bank - _TC"):
|
|||||||
pass
|
pass
|
||||||
|
|
||||||
try:
|
try:
|
||||||
frappe.get_doc(
|
bank_account = frappe.get_doc(
|
||||||
{
|
{
|
||||||
"doctype": "Bank Account",
|
"doctype": "Bank Account",
|
||||||
"account_name": "Checking Account",
|
"account_name": bank_account_name,
|
||||||
"bank": bank_name,
|
"bank": bank_name,
|
||||||
"account": account_name,
|
"account": gl_account,
|
||||||
}
|
}
|
||||||
).insert(ignore_if_duplicate=True)
|
).insert(ignore_if_duplicate=True)
|
||||||
except frappe.DuplicateEntryError:
|
except frappe.DuplicateEntryError:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
return bank_account.name
|
||||||
|
|
||||||
def add_transactions():
|
|
||||||
create_bank_account()
|
|
||||||
|
|
||||||
|
def create_gl_account(gl_account_name="_Test Bank - _TC"):
|
||||||
|
gl_account = frappe.get_doc(
|
||||||
|
{
|
||||||
|
"doctype": "Account",
|
||||||
|
"company": "_Test Company",
|
||||||
|
"parent_account": "Current Assets - _TC",
|
||||||
|
"account_type": "Bank",
|
||||||
|
"is_group": 0,
|
||||||
|
"account_name": gl_account_name,
|
||||||
|
}
|
||||||
|
).insert()
|
||||||
|
return gl_account.name
|
||||||
|
|
||||||
|
|
||||||
|
def add_transactions(bank_account="_Test Bank - _TC"):
|
||||||
doc = frappe.get_doc(
|
doc = frappe.get_doc(
|
||||||
{
|
{
|
||||||
"doctype": "Bank Transaction",
|
"doctype": "Bank Transaction",
|
||||||
@@ -230,7 +277,7 @@ def add_transactions():
|
|||||||
"date": "2018-10-23",
|
"date": "2018-10-23",
|
||||||
"deposit": 1200,
|
"deposit": 1200,
|
||||||
"currency": "INR",
|
"currency": "INR",
|
||||||
"bank_account": "Checking Account - Citi Bank",
|
"bank_account": bank_account,
|
||||||
}
|
}
|
||||||
).insert()
|
).insert()
|
||||||
doc.submit()
|
doc.submit()
|
||||||
@@ -242,7 +289,7 @@ def add_transactions():
|
|||||||
"date": "2018-10-23",
|
"date": "2018-10-23",
|
||||||
"deposit": 1700,
|
"deposit": 1700,
|
||||||
"currency": "INR",
|
"currency": "INR",
|
||||||
"bank_account": "Checking Account - Citi Bank",
|
"bank_account": bank_account,
|
||||||
}
|
}
|
||||||
).insert()
|
).insert()
|
||||||
doc.submit()
|
doc.submit()
|
||||||
@@ -254,7 +301,7 @@ def add_transactions():
|
|||||||
"date": "2018-10-26",
|
"date": "2018-10-26",
|
||||||
"withdrawal": 690,
|
"withdrawal": 690,
|
||||||
"currency": "INR",
|
"currency": "INR",
|
||||||
"bank_account": "Checking Account - Citi Bank",
|
"bank_account": bank_account,
|
||||||
}
|
}
|
||||||
).insert()
|
).insert()
|
||||||
doc.submit()
|
doc.submit()
|
||||||
@@ -266,7 +313,7 @@ def add_transactions():
|
|||||||
"date": "2018-10-27",
|
"date": "2018-10-27",
|
||||||
"deposit": 3900,
|
"deposit": 3900,
|
||||||
"currency": "INR",
|
"currency": "INR",
|
||||||
"bank_account": "Checking Account - Citi Bank",
|
"bank_account": bank_account,
|
||||||
}
|
}
|
||||||
).insert()
|
).insert()
|
||||||
doc.submit()
|
doc.submit()
|
||||||
@@ -278,13 +325,13 @@ def add_transactions():
|
|||||||
"date": "2018-10-27",
|
"date": "2018-10-27",
|
||||||
"withdrawal": 109080,
|
"withdrawal": 109080,
|
||||||
"currency": "INR",
|
"currency": "INR",
|
||||||
"bank_account": "Checking Account - Citi Bank",
|
"bank_account": bank_account,
|
||||||
}
|
}
|
||||||
).insert()
|
).insert()
|
||||||
doc.submit()
|
doc.submit()
|
||||||
|
|
||||||
|
|
||||||
def add_vouchers():
|
def add_vouchers(gl_account="_Test Bank - _TC"):
|
||||||
try:
|
try:
|
||||||
frappe.get_doc(
|
frappe.get_doc(
|
||||||
{
|
{
|
||||||
@@ -300,7 +347,7 @@ def add_vouchers():
|
|||||||
|
|
||||||
pi = make_purchase_invoice(supplier="Conrad Electronic", qty=1, rate=690)
|
pi = make_purchase_invoice(supplier="Conrad Electronic", qty=1, rate=690)
|
||||||
|
|
||||||
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account="_Test Bank - _TC")
|
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account=gl_account)
|
||||||
pe.reference_no = "Conrad Oct 18"
|
pe.reference_no = "Conrad Oct 18"
|
||||||
pe.reference_date = "2018-10-24"
|
pe.reference_date = "2018-10-24"
|
||||||
pe.insert()
|
pe.insert()
|
||||||
@@ -319,14 +366,14 @@ def add_vouchers():
|
|||||||
pass
|
pass
|
||||||
|
|
||||||
pi = make_purchase_invoice(supplier="Mr G", qty=1, rate=1200)
|
pi = make_purchase_invoice(supplier="Mr G", qty=1, rate=1200)
|
||||||
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account="_Test Bank - _TC")
|
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account=gl_account)
|
||||||
pe.reference_no = "Herr G Oct 18"
|
pe.reference_no = "Herr G Oct 18"
|
||||||
pe.reference_date = "2018-10-24"
|
pe.reference_date = "2018-10-24"
|
||||||
pe.insert()
|
pe.insert()
|
||||||
pe.submit()
|
pe.submit()
|
||||||
|
|
||||||
pi = make_purchase_invoice(supplier="Mr G", qty=1, rate=1700)
|
pi = make_purchase_invoice(supplier="Mr G", qty=1, rate=1700)
|
||||||
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account="_Test Bank - _TC")
|
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account=gl_account)
|
||||||
pe.reference_no = "Herr G Nov 18"
|
pe.reference_no = "Herr G Nov 18"
|
||||||
pe.reference_date = "2018-11-01"
|
pe.reference_date = "2018-11-01"
|
||||||
pe.insert()
|
pe.insert()
|
||||||
@@ -357,10 +404,10 @@ def add_vouchers():
|
|||||||
pass
|
pass
|
||||||
|
|
||||||
pi = make_purchase_invoice(supplier="Poore Simon's", qty=1, rate=3900, is_paid=1, do_not_save=1)
|
pi = make_purchase_invoice(supplier="Poore Simon's", qty=1, rate=3900, is_paid=1, do_not_save=1)
|
||||||
pi.cash_bank_account = "_Test Bank - _TC"
|
pi.cash_bank_account = gl_account
|
||||||
pi.insert()
|
pi.insert()
|
||||||
pi.submit()
|
pi.submit()
|
||||||
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account="_Test Bank - _TC")
|
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account=gl_account)
|
||||||
pe.reference_no = "Poore Simon's Oct 18"
|
pe.reference_no = "Poore Simon's Oct 18"
|
||||||
pe.reference_date = "2018-10-28"
|
pe.reference_date = "2018-10-28"
|
||||||
pe.paid_amount = 690
|
pe.paid_amount = 690
|
||||||
@@ -369,7 +416,7 @@ def add_vouchers():
|
|||||||
pe.submit()
|
pe.submit()
|
||||||
|
|
||||||
si = create_sales_invoice(customer="Poore Simon's", qty=1, rate=3900)
|
si = create_sales_invoice(customer="Poore Simon's", qty=1, rate=3900)
|
||||||
pe = get_payment_entry("Sales Invoice", si.name, bank_account="_Test Bank - _TC")
|
pe = get_payment_entry("Sales Invoice", si.name, bank_account=gl_account)
|
||||||
pe.reference_no = "Poore Simon's Oct 18"
|
pe.reference_no = "Poore Simon's Oct 18"
|
||||||
pe.reference_date = "2018-10-28"
|
pe.reference_date = "2018-10-28"
|
||||||
pe.insert()
|
pe.insert()
|
||||||
@@ -392,16 +439,12 @@ def add_vouchers():
|
|||||||
if not frappe.db.get_value(
|
if not frappe.db.get_value(
|
||||||
"Mode of Payment Account", {"company": "_Test Company", "parent": "Cash"}
|
"Mode of Payment Account", {"company": "_Test Company", "parent": "Cash"}
|
||||||
):
|
):
|
||||||
mode_of_payment.append(
|
mode_of_payment.append("accounts", {"company": "_Test Company", "default_account": gl_account})
|
||||||
"accounts", {"company": "_Test Company", "default_account": "_Test Bank - _TC"}
|
|
||||||
)
|
|
||||||
mode_of_payment.save()
|
mode_of_payment.save()
|
||||||
|
|
||||||
si = create_sales_invoice(customer="Fayva", qty=1, rate=109080, do_not_save=1)
|
si = create_sales_invoice(customer="Fayva", qty=1, rate=109080, do_not_save=1)
|
||||||
si.is_pos = 1
|
si.is_pos = 1
|
||||||
si.append(
|
si.append("payments", {"mode_of_payment": "Cash", "account": gl_account, "amount": 109080})
|
||||||
"payments", {"mode_of_payment": "Cash", "account": "_Test Bank - _TC", "amount": 109080}
|
|
||||||
)
|
|
||||||
si.insert()
|
si.insert()
|
||||||
si.submit()
|
si.submit()
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,100 @@
|
|||||||
|
// Copyright (c) 2023, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
|
// For license information, please see license.txt
|
||||||
|
|
||||||
|
frappe.ui.form.on("Bisect Accounting Statements", {
|
||||||
|
onload(frm) {
|
||||||
|
frm.trigger("render_heatmap");
|
||||||
|
},
|
||||||
|
refresh(frm) {
|
||||||
|
frm.add_custom_button(__("Bisect Left"), () => {
|
||||||
|
frm.trigger("bisect_left");
|
||||||
|
});
|
||||||
|
|
||||||
|
frm.add_custom_button(__("Bisect Right"), () => {
|
||||||
|
frm.trigger("bisect_right");
|
||||||
|
});
|
||||||
|
|
||||||
|
frm.add_custom_button(__("Up"), () => {
|
||||||
|
frm.trigger("move_up");
|
||||||
|
});
|
||||||
|
frm.add_custom_button(__("Build Tree"), () => {
|
||||||
|
frm.trigger("build_tree");
|
||||||
|
});
|
||||||
|
},
|
||||||
|
render_heatmap(frm) {
|
||||||
|
let bisect_heatmap = frm.get_field("bisect_heatmap").$wrapper;
|
||||||
|
bisect_heatmap.addClass("bisect_heatmap_location");
|
||||||
|
|
||||||
|
// milliseconds in a day
|
||||||
|
let msiad = 24 * 60 * 60 * 1000;
|
||||||
|
let datapoints = {};
|
||||||
|
let fr_dt = new Date(frm.doc.from_date).getTime();
|
||||||
|
let to_dt = new Date(frm.doc.to_date).getTime();
|
||||||
|
let bisect_start = new Date(frm.doc.current_from_date).getTime();
|
||||||
|
let bisect_end = new Date(frm.doc.current_to_date).getTime();
|
||||||
|
|
||||||
|
for (let x = fr_dt; x <= to_dt; x += msiad) {
|
||||||
|
let epoch_in_seconds = x / 1000;
|
||||||
|
if (bisect_start <= x && x <= bisect_end) {
|
||||||
|
datapoints[epoch_in_seconds] = 1.0;
|
||||||
|
} else {
|
||||||
|
datapoints[epoch_in_seconds] = 0.0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
new frappe.Chart(".bisect_heatmap_location", {
|
||||||
|
type: "heatmap",
|
||||||
|
data: {
|
||||||
|
dataPoints: datapoints,
|
||||||
|
start: new Date(frm.doc.from_date),
|
||||||
|
end: new Date(frm.doc.to_date),
|
||||||
|
},
|
||||||
|
countLabel: "Bisecting",
|
||||||
|
discreteDomains: 1,
|
||||||
|
});
|
||||||
|
},
|
||||||
|
bisect_left(frm) {
|
||||||
|
frm.call({
|
||||||
|
doc: frm.doc,
|
||||||
|
method: "bisect_left",
|
||||||
|
freeze: true,
|
||||||
|
freeze_message: __("Bisecting Left ..."),
|
||||||
|
callback: (r) => {
|
||||||
|
frm.trigger("render_heatmap");
|
||||||
|
},
|
||||||
|
});
|
||||||
|
},
|
||||||
|
bisect_right(frm) {
|
||||||
|
frm.call({
|
||||||
|
doc: frm.doc,
|
||||||
|
freeze: true,
|
||||||
|
freeze_message: __("Bisecting Right ..."),
|
||||||
|
method: "bisect_right",
|
||||||
|
callback: (r) => {
|
||||||
|
frm.trigger("render_heatmap");
|
||||||
|
},
|
||||||
|
});
|
||||||
|
},
|
||||||
|
move_up(frm) {
|
||||||
|
frm.call({
|
||||||
|
doc: frm.doc,
|
||||||
|
freeze: true,
|
||||||
|
freeze_message: __("Moving up in tree ..."),
|
||||||
|
method: "move_up",
|
||||||
|
callback: (r) => {
|
||||||
|
frm.trigger("render_heatmap");
|
||||||
|
},
|
||||||
|
});
|
||||||
|
},
|
||||||
|
build_tree(frm) {
|
||||||
|
frm.call({
|
||||||
|
doc: frm.doc,
|
||||||
|
freeze: true,
|
||||||
|
freeze_message: __("Rebuilding BTree for period ..."),
|
||||||
|
method: "build_tree",
|
||||||
|
callback: (r) => {
|
||||||
|
frm.trigger("render_heatmap");
|
||||||
|
},
|
||||||
|
});
|
||||||
|
},
|
||||||
|
});
|
||||||
@@ -0,0 +1,194 @@
|
|||||||
|
{
|
||||||
|
"actions": [],
|
||||||
|
"allow_rename": 1,
|
||||||
|
"creation": "2023-09-15 21:28:28.054773",
|
||||||
|
"default_view": "List",
|
||||||
|
"doctype": "DocType",
|
||||||
|
"editable_grid": 1,
|
||||||
|
"engine": "InnoDB",
|
||||||
|
"field_order": [
|
||||||
|
"section_break_cvfg",
|
||||||
|
"company",
|
||||||
|
"column_break_hcam",
|
||||||
|
"from_date",
|
||||||
|
"column_break_qxbi",
|
||||||
|
"to_date",
|
||||||
|
"column_break_iwny",
|
||||||
|
"algorithm",
|
||||||
|
"section_break_8ph9",
|
||||||
|
"current_node",
|
||||||
|
"section_break_ngid",
|
||||||
|
"bisect_heatmap",
|
||||||
|
"section_break_hmsy",
|
||||||
|
"bisecting_from",
|
||||||
|
"current_from_date",
|
||||||
|
"column_break_uqyd",
|
||||||
|
"bisecting_to",
|
||||||
|
"current_to_date",
|
||||||
|
"section_break_hbyo",
|
||||||
|
"heading_cppb",
|
||||||
|
"p_l_summary",
|
||||||
|
"column_break_aivo",
|
||||||
|
"balance_sheet_summary",
|
||||||
|
"b_s_summary",
|
||||||
|
"column_break_gvwx",
|
||||||
|
"difference_heading",
|
||||||
|
"difference"
|
||||||
|
],
|
||||||
|
"fields": [
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_qxbi",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "from_date",
|
||||||
|
"fieldtype": "Datetime",
|
||||||
|
"label": "From Date"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "to_date",
|
||||||
|
"fieldtype": "Datetime",
|
||||||
|
"label": "To Date"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"default": "BFS",
|
||||||
|
"fieldname": "algorithm",
|
||||||
|
"fieldtype": "Select",
|
||||||
|
"label": "Algorithm",
|
||||||
|
"options": "BFS\nDFS"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_iwny",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "current_node",
|
||||||
|
"fieldtype": "Link",
|
||||||
|
"label": "Current Node",
|
||||||
|
"options": "Bisect Nodes"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "section_break_hmsy",
|
||||||
|
"fieldtype": "Section Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "current_from_date",
|
||||||
|
"fieldtype": "Datetime",
|
||||||
|
"read_only": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "current_to_date",
|
||||||
|
"fieldtype": "Datetime",
|
||||||
|
"read_only": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_uqyd",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "section_break_hbyo",
|
||||||
|
"fieldtype": "Section Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "p_l_summary",
|
||||||
|
"fieldtype": "Float",
|
||||||
|
"read_only": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "b_s_summary",
|
||||||
|
"fieldtype": "Float",
|
||||||
|
"read_only": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "difference",
|
||||||
|
"fieldtype": "Float",
|
||||||
|
"read_only": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_aivo",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_gvwx",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "company",
|
||||||
|
"fieldtype": "Link",
|
||||||
|
"label": "Company",
|
||||||
|
"options": "Company"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_hcam",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "section_break_ngid",
|
||||||
|
"fieldtype": "Section Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "section_break_8ph9",
|
||||||
|
"fieldtype": "Section Break",
|
||||||
|
"hidden": 1
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "bisect_heatmap",
|
||||||
|
"fieldtype": "HTML",
|
||||||
|
"label": "Heatmap"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "heading_cppb",
|
||||||
|
"fieldtype": "Heading",
|
||||||
|
"label": "Profit and Loss Summary"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "balance_sheet_summary",
|
||||||
|
"fieldtype": "Heading",
|
||||||
|
"label": "Balance Sheet Summary"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "difference_heading",
|
||||||
|
"fieldtype": "Heading",
|
||||||
|
"label": "Difference"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "bisecting_from",
|
||||||
|
"fieldtype": "Heading",
|
||||||
|
"label": "Bisecting From"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "bisecting_to",
|
||||||
|
"fieldtype": "Heading",
|
||||||
|
"label": "Bisecting To"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "section_break_cvfg",
|
||||||
|
"fieldtype": "Section Break"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"hide_toolbar": 1,
|
||||||
|
"index_web_pages_for_search": 1,
|
||||||
|
"issingle": 1,
|
||||||
|
"links": [],
|
||||||
|
"modified": "2023-12-01 16:49:54.073890",
|
||||||
|
"modified_by": "Administrator",
|
||||||
|
"module": "Accounts",
|
||||||
|
"name": "Bisect Accounting Statements",
|
||||||
|
"owner": "Administrator",
|
||||||
|
"permissions": [
|
||||||
|
{
|
||||||
|
"create": 1,
|
||||||
|
"delete": 1,
|
||||||
|
"email": 1,
|
||||||
|
"print": 1,
|
||||||
|
"read": 1,
|
||||||
|
"role": "Administrator",
|
||||||
|
"share": 1,
|
||||||
|
"write": 1
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"read_only": 1,
|
||||||
|
"sort_field": "modified",
|
||||||
|
"sort_order": "DESC",
|
||||||
|
"states": []
|
||||||
|
}
|
||||||
@@ -0,0 +1,227 @@
|
|||||||
|
# Copyright (c) 2023, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
|
# For license information, please see license.txt
|
||||||
|
|
||||||
|
import datetime
|
||||||
|
from collections import deque
|
||||||
|
from math import floor
|
||||||
|
|
||||||
|
import frappe
|
||||||
|
from dateutil.relativedelta import relativedelta
|
||||||
|
from frappe import _
|
||||||
|
from frappe.model.document import Document
|
||||||
|
from frappe.utils import getdate
|
||||||
|
from frappe.utils.data import guess_date_format
|
||||||
|
|
||||||
|
|
||||||
|
class BisectAccountingStatements(Document):
|
||||||
|
# begin: auto-generated types
|
||||||
|
# This code is auto-generated. Do not modify anything in this block.
|
||||||
|
|
||||||
|
from typing import TYPE_CHECKING
|
||||||
|
|
||||||
|
if TYPE_CHECKING:
|
||||||
|
from frappe.types import DF
|
||||||
|
|
||||||
|
algorithm: DF.Literal["BFS", "DFS"]
|
||||||
|
b_s_summary: DF.Float
|
||||||
|
company: DF.Link | None
|
||||||
|
current_from_date: DF.Datetime | None
|
||||||
|
current_node: DF.Link | None
|
||||||
|
current_to_date: DF.Datetime | None
|
||||||
|
difference: DF.Float
|
||||||
|
from_date: DF.Datetime | None
|
||||||
|
p_l_summary: DF.Float
|
||||||
|
to_date: DF.Datetime | None
|
||||||
|
# end: auto-generated types
|
||||||
|
|
||||||
|
def validate(self):
|
||||||
|
self.validate_dates()
|
||||||
|
|
||||||
|
def validate_dates(self):
|
||||||
|
if getdate(self.from_date) > getdate(self.to_date):
|
||||||
|
frappe.throw(
|
||||||
|
_("From Date: {0} cannot be greater than To date: {1}").format(
|
||||||
|
frappe.bold(self.from_date), frappe.bold(self.to_date)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
def bfs(self, from_date: datetime, to_date: datetime):
|
||||||
|
# Make Root node
|
||||||
|
node = frappe.new_doc("Bisect Nodes")
|
||||||
|
node.root = None
|
||||||
|
node.period_from_date = from_date
|
||||||
|
node.period_to_date = to_date
|
||||||
|
node.insert()
|
||||||
|
|
||||||
|
period_queue = deque([node])
|
||||||
|
while period_queue:
|
||||||
|
cur_node = period_queue.popleft()
|
||||||
|
delta = cur_node.period_to_date - cur_node.period_from_date
|
||||||
|
if delta.days == 0:
|
||||||
|
continue
|
||||||
|
else:
|
||||||
|
cur_floor = floor(delta.days / 2)
|
||||||
|
next_to_date = cur_node.period_from_date + relativedelta(days=+cur_floor)
|
||||||
|
left_node = frappe.new_doc("Bisect Nodes")
|
||||||
|
left_node.period_from_date = cur_node.period_from_date
|
||||||
|
left_node.period_to_date = next_to_date
|
||||||
|
left_node.root = cur_node.name
|
||||||
|
left_node.generated = False
|
||||||
|
left_node.insert()
|
||||||
|
cur_node.left_child = left_node.name
|
||||||
|
period_queue.append(left_node)
|
||||||
|
|
||||||
|
next_from_date = cur_node.period_from_date + relativedelta(days=+(cur_floor + 1))
|
||||||
|
right_node = frappe.new_doc("Bisect Nodes")
|
||||||
|
right_node.period_from_date = next_from_date
|
||||||
|
right_node.period_to_date = cur_node.period_to_date
|
||||||
|
right_node.root = cur_node.name
|
||||||
|
right_node.generated = False
|
||||||
|
right_node.insert()
|
||||||
|
cur_node.right_child = right_node.name
|
||||||
|
period_queue.append(right_node)
|
||||||
|
|
||||||
|
cur_node.save()
|
||||||
|
|
||||||
|
def dfs(self, from_date: datetime, to_date: datetime):
|
||||||
|
# Make Root node
|
||||||
|
node = frappe.new_doc("Bisect Nodes")
|
||||||
|
node.root = None
|
||||||
|
node.period_from_date = from_date
|
||||||
|
node.period_to_date = to_date
|
||||||
|
node.insert()
|
||||||
|
|
||||||
|
period_stack = [node]
|
||||||
|
while period_stack:
|
||||||
|
cur_node = period_stack.pop()
|
||||||
|
delta = cur_node.period_to_date - cur_node.period_from_date
|
||||||
|
if delta.days == 0:
|
||||||
|
continue
|
||||||
|
else:
|
||||||
|
cur_floor = floor(delta.days / 2)
|
||||||
|
next_to_date = cur_node.period_from_date + relativedelta(days=+cur_floor)
|
||||||
|
left_node = frappe.new_doc("Bisect Nodes")
|
||||||
|
left_node.period_from_date = cur_node.period_from_date
|
||||||
|
left_node.period_to_date = next_to_date
|
||||||
|
left_node.root = cur_node.name
|
||||||
|
left_node.generated = False
|
||||||
|
left_node.insert()
|
||||||
|
cur_node.left_child = left_node.name
|
||||||
|
period_stack.append(left_node)
|
||||||
|
|
||||||
|
next_from_date = cur_node.period_from_date + relativedelta(days=+(cur_floor + 1))
|
||||||
|
right_node = frappe.new_doc("Bisect Nodes")
|
||||||
|
right_node.period_from_date = next_from_date
|
||||||
|
right_node.period_to_date = cur_node.period_to_date
|
||||||
|
right_node.root = cur_node.name
|
||||||
|
right_node.generated = False
|
||||||
|
right_node.insert()
|
||||||
|
cur_node.right_child = right_node.name
|
||||||
|
period_stack.append(right_node)
|
||||||
|
|
||||||
|
cur_node.save()
|
||||||
|
|
||||||
|
@frappe.whitelist()
|
||||||
|
def build_tree(self):
|
||||||
|
frappe.db.delete("Bisect Nodes")
|
||||||
|
|
||||||
|
# Convert str to datetime format
|
||||||
|
dt_format = guess_date_format(self.from_date)
|
||||||
|
from_date = datetime.datetime.strptime(self.from_date, dt_format)
|
||||||
|
to_date = datetime.datetime.strptime(self.to_date, dt_format)
|
||||||
|
|
||||||
|
if self.algorithm == "BFS":
|
||||||
|
self.bfs(from_date, to_date)
|
||||||
|
|
||||||
|
if self.algorithm == "DFS":
|
||||||
|
self.dfs(from_date, to_date)
|
||||||
|
|
||||||
|
# set root as current node
|
||||||
|
root = frappe.db.get_all("Bisect Nodes", filters={"root": ["is", "not set"]})[0]
|
||||||
|
self.current_node = root.name
|
||||||
|
self.current_from_date = self.from_date
|
||||||
|
self.current_to_date = self.to_date
|
||||||
|
|
||||||
|
self.get_report_summary()
|
||||||
|
self.save()
|
||||||
|
|
||||||
|
def get_report_summary(self):
|
||||||
|
filters = {
|
||||||
|
"company": self.company,
|
||||||
|
"filter_based_on": "Date Range",
|
||||||
|
"period_start_date": self.current_from_date,
|
||||||
|
"period_end_date": self.current_to_date,
|
||||||
|
"periodicity": "Yearly",
|
||||||
|
}
|
||||||
|
pl_summary = frappe.get_doc("Report", "Profit and Loss Statement")
|
||||||
|
self.p_l_summary = pl_summary.execute_script_report(filters=filters)[5]
|
||||||
|
bs_summary = frappe.get_doc("Report", "Balance Sheet")
|
||||||
|
self.b_s_summary = bs_summary.execute_script_report(filters=filters)[5]
|
||||||
|
self.difference = abs(self.p_l_summary - self.b_s_summary)
|
||||||
|
|
||||||
|
def update_node(self):
|
||||||
|
current_node = frappe.get_doc("Bisect Nodes", self.current_node)
|
||||||
|
current_node.balance_sheet_summary = self.b_s_summary
|
||||||
|
current_node.profit_loss_summary = self.p_l_summary
|
||||||
|
current_node.difference = self.difference
|
||||||
|
current_node.generated = True
|
||||||
|
current_node.save()
|
||||||
|
|
||||||
|
def current_node_has_summary_info(self):
|
||||||
|
"Assertion method"
|
||||||
|
return frappe.db.get_value("Bisect Nodes", self.current_node, "generated")
|
||||||
|
|
||||||
|
def fetch_summary_info_from_current_node(self):
|
||||||
|
current_node = frappe.get_doc("Bisect Nodes", self.current_node)
|
||||||
|
self.p_l_summary = current_node.balance_sheet_summary
|
||||||
|
self.b_s_summary = current_node.profit_loss_summary
|
||||||
|
self.difference = abs(self.p_l_summary - self.b_s_summary)
|
||||||
|
|
||||||
|
def fetch_or_calculate(self):
|
||||||
|
if self.current_node_has_summary_info():
|
||||||
|
self.fetch_summary_info_from_current_node()
|
||||||
|
else:
|
||||||
|
self.get_report_summary()
|
||||||
|
self.update_node()
|
||||||
|
|
||||||
|
@frappe.whitelist()
|
||||||
|
def bisect_left(self):
|
||||||
|
if self.current_node is not None:
|
||||||
|
cur_node = frappe.get_doc("Bisect Nodes", self.current_node)
|
||||||
|
if cur_node.left_child is not None:
|
||||||
|
lft_node = frappe.get_doc("Bisect Nodes", cur_node.left_child)
|
||||||
|
self.current_node = cur_node.left_child
|
||||||
|
self.current_from_date = lft_node.period_from_date
|
||||||
|
self.current_to_date = lft_node.period_to_date
|
||||||
|
self.fetch_or_calculate()
|
||||||
|
self.save()
|
||||||
|
else:
|
||||||
|
frappe.msgprint(_("No more children on Left"))
|
||||||
|
|
||||||
|
@frappe.whitelist()
|
||||||
|
def bisect_right(self):
|
||||||
|
if self.current_node is not None:
|
||||||
|
cur_node = frappe.get_doc("Bisect Nodes", self.current_node)
|
||||||
|
if cur_node.right_child is not None:
|
||||||
|
rgt_node = frappe.get_doc("Bisect Nodes", cur_node.right_child)
|
||||||
|
self.current_node = cur_node.right_child
|
||||||
|
self.current_from_date = rgt_node.period_from_date
|
||||||
|
self.current_to_date = rgt_node.period_to_date
|
||||||
|
self.fetch_or_calculate()
|
||||||
|
self.save()
|
||||||
|
else:
|
||||||
|
frappe.msgprint(_("No more children on Right"))
|
||||||
|
|
||||||
|
@frappe.whitelist()
|
||||||
|
def move_up(self):
|
||||||
|
if self.current_node is not None:
|
||||||
|
cur_node = frappe.get_doc("Bisect Nodes", self.current_node)
|
||||||
|
if cur_node.root is not None:
|
||||||
|
root = frappe.get_doc("Bisect Nodes", cur_node.root)
|
||||||
|
self.current_node = cur_node.root
|
||||||
|
self.current_from_date = root.period_from_date
|
||||||
|
self.current_to_date = root.period_to_date
|
||||||
|
self.fetch_or_calculate()
|
||||||
|
self.save()
|
||||||
|
else:
|
||||||
|
frappe.msgprint(_("Reached Root"))
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
# Copyright (c) 2023, Frappe Technologies Pvt. Ltd. and Contributors
|
||||||
|
# See license.txt
|
||||||
|
|
||||||
|
# import frappe
|
||||||
|
from frappe.tests.utils import FrappeTestCase
|
||||||
|
|
||||||
|
|
||||||
|
class TestBisectAccountingStatements(FrappeTestCase):
|
||||||
|
pass
|
||||||
8
erpnext/accounts/doctype/bisect_nodes/bisect_nodes.js
Normal file
8
erpnext/accounts/doctype/bisect_nodes/bisect_nodes.js
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
// Copyright (c) 2023, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
|
// For license information, please see license.txt
|
||||||
|
|
||||||
|
// frappe.ui.form.on("Bisect Nodes", {
|
||||||
|
// refresh(frm) {
|
||||||
|
|
||||||
|
// },
|
||||||
|
// });
|
||||||
97
erpnext/accounts/doctype/bisect_nodes/bisect_nodes.json
Normal file
97
erpnext/accounts/doctype/bisect_nodes/bisect_nodes.json
Normal file
@@ -0,0 +1,97 @@
|
|||||||
|
{
|
||||||
|
"actions": [],
|
||||||
|
"autoname": "autoincrement",
|
||||||
|
"creation": "2023-09-27 14:56:38.112462",
|
||||||
|
"default_view": "List",
|
||||||
|
"doctype": "DocType",
|
||||||
|
"editable_grid": 1,
|
||||||
|
"engine": "InnoDB",
|
||||||
|
"field_order": [
|
||||||
|
"root",
|
||||||
|
"left_child",
|
||||||
|
"right_child",
|
||||||
|
"period_from_date",
|
||||||
|
"period_to_date",
|
||||||
|
"difference",
|
||||||
|
"balance_sheet_summary",
|
||||||
|
"profit_loss_summary",
|
||||||
|
"generated"
|
||||||
|
],
|
||||||
|
"fields": [
|
||||||
|
{
|
||||||
|
"fieldname": "root",
|
||||||
|
"fieldtype": "Link",
|
||||||
|
"label": "Root",
|
||||||
|
"options": "Bisect Nodes"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "left_child",
|
||||||
|
"fieldtype": "Link",
|
||||||
|
"label": "Left Child",
|
||||||
|
"options": "Bisect Nodes"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "right_child",
|
||||||
|
"fieldtype": "Link",
|
||||||
|
"label": "Right Child",
|
||||||
|
"options": "Bisect Nodes"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "period_from_date",
|
||||||
|
"fieldtype": "Datetime",
|
||||||
|
"label": "Period_from_date"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "period_to_date",
|
||||||
|
"fieldtype": "Datetime",
|
||||||
|
"label": "Period To Date"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "difference",
|
||||||
|
"fieldtype": "Float",
|
||||||
|
"label": "Difference"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "balance_sheet_summary",
|
||||||
|
"fieldtype": "Float",
|
||||||
|
"label": "Balance Sheet Summary"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "profit_loss_summary",
|
||||||
|
"fieldtype": "Float",
|
||||||
|
"label": "Profit and Loss Summary"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"default": "0",
|
||||||
|
"fieldname": "generated",
|
||||||
|
"fieldtype": "Check",
|
||||||
|
"label": "Generated"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"index_web_pages_for_search": 1,
|
||||||
|
"links": [],
|
||||||
|
"modified": "2023-12-01 17:46:12.437996",
|
||||||
|
"modified_by": "Administrator",
|
||||||
|
"module": "Accounts",
|
||||||
|
"name": "Bisect Nodes",
|
||||||
|
"naming_rule": "Autoincrement",
|
||||||
|
"owner": "Administrator",
|
||||||
|
"permissions": [
|
||||||
|
{
|
||||||
|
"create": 1,
|
||||||
|
"delete": 1,
|
||||||
|
"email": 1,
|
||||||
|
"export": 1,
|
||||||
|
"print": 1,
|
||||||
|
"read": 1,
|
||||||
|
"report": 1,
|
||||||
|
"role": "Administrator",
|
||||||
|
"share": 1,
|
||||||
|
"write": 1
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"read_only": 1,
|
||||||
|
"sort_field": "modified",
|
||||||
|
"sort_order": "DESC",
|
||||||
|
"states": []
|
||||||
|
}
|
||||||
29
erpnext/accounts/doctype/bisect_nodes/bisect_nodes.py
Normal file
29
erpnext/accounts/doctype/bisect_nodes/bisect_nodes.py
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
# Copyright (c) 2023, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
|
# For license information, please see license.txt
|
||||||
|
|
||||||
|
# import frappe
|
||||||
|
from frappe.model.document import Document
|
||||||
|
|
||||||
|
|
||||||
|
class BisectNodes(Document):
|
||||||
|
# begin: auto-generated types
|
||||||
|
# This code is auto-generated. Do not modify anything in this block.
|
||||||
|
|
||||||
|
from typing import TYPE_CHECKING
|
||||||
|
|
||||||
|
if TYPE_CHECKING:
|
||||||
|
from frappe.types import DF
|
||||||
|
|
||||||
|
balance_sheet_summary: DF.Float
|
||||||
|
difference: DF.Float
|
||||||
|
generated: DF.Check
|
||||||
|
left_child: DF.Link | None
|
||||||
|
name: DF.Int | None
|
||||||
|
period_from_date: DF.Datetime | None
|
||||||
|
period_to_date: DF.Datetime | None
|
||||||
|
profit_loss_summary: DF.Float
|
||||||
|
right_child: DF.Link | None
|
||||||
|
root: DF.Link | None
|
||||||
|
# end: auto-generated types
|
||||||
|
|
||||||
|
pass
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
# Copyright (c) 2023, Frappe Technologies Pvt. Ltd. and Contributors
|
||||||
|
# See license.txt
|
||||||
|
|
||||||
|
# import frappe
|
||||||
|
from frappe.tests.utils import FrappeTestCase
|
||||||
|
|
||||||
|
|
||||||
|
class TestBisectNodes(FrappeTestCase):
|
||||||
|
pass
|
||||||
@@ -2,48 +2,48 @@
|
|||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
frappe.provide("erpnext.accounts.dimensions");
|
frappe.provide("erpnext.accounts.dimensions");
|
||||||
|
|
||||||
frappe.ui.form.on('Budget', {
|
frappe.ui.form.on("Budget", {
|
||||||
onload: function(frm) {
|
onload: function (frm) {
|
||||||
frm.set_query("account", "accounts", function() {
|
frm.set_query("account", "accounts", function () {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
report_type: "Profit and Loss",
|
report_type: "Profit and Loss",
|
||||||
is_group: 0
|
is_group: 0,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
frm.set_query("monthly_distribution", function() {
|
frm.set_query("monthly_distribution", function () {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
fiscal_year: frm.doc.fiscal_year
|
fiscal_year: frm.doc.fiscal_year,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
erpnext.accounts.dimensions.setup_dimension_filters(frm, frm.doctype);
|
erpnext.accounts.dimensions.setup_dimension_filters(frm, frm.doctype);
|
||||||
},
|
},
|
||||||
|
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
frm.trigger("toggle_reqd_fields")
|
frm.trigger("toggle_reqd_fields");
|
||||||
},
|
},
|
||||||
|
|
||||||
budget_against: function(frm) {
|
budget_against: function (frm) {
|
||||||
frm.trigger("set_null_value")
|
frm.trigger("set_null_value");
|
||||||
frm.trigger("toggle_reqd_fields")
|
frm.trigger("toggle_reqd_fields");
|
||||||
},
|
},
|
||||||
|
|
||||||
set_null_value: function(frm) {
|
set_null_value: function (frm) {
|
||||||
if(frm.doc.budget_against == 'Cost Center') {
|
if (frm.doc.budget_against == "Cost Center") {
|
||||||
frm.set_value('project', null)
|
frm.set_value("project", null);
|
||||||
} else {
|
} else {
|
||||||
frm.set_value('cost_center', null)
|
frm.set_value("cost_center", null);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
toggle_reqd_fields: function(frm) {
|
toggle_reqd_fields: function (frm) {
|
||||||
frm.toggle_reqd("cost_center", frm.doc.budget_against=="Cost Center");
|
frm.toggle_reqd("cost_center", frm.doc.budget_against == "Cost Center");
|
||||||
frm.toggle_reqd("project", frm.doc.budget_against=="Project");
|
frm.toggle_reqd("project", frm.doc.budget_against == "Project");
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,11 +1,10 @@
|
|||||||
// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
||||||
// License: GNU General Public License v3. See license.txt
|
// License: GNU General Public License v3. See license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Cashier Closing', {
|
frappe.ui.form.on("Cashier Closing", {
|
||||||
|
setup: function (frm) {
|
||||||
setup: function(frm){
|
|
||||||
if (frm.doc.user == "" || frm.doc.user == null) {
|
if (frm.doc.user == "" || frm.doc.user == null) {
|
||||||
frm.doc.user = frappe.session.user;
|
frm.doc.user = frappe.session.user;
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,457 +1,152 @@
|
|||||||
{
|
{
|
||||||
"allow_copy": 0,
|
"actions": [],
|
||||||
"allow_events_in_timeline": 0,
|
|
||||||
"allow_guest_to_view": 0,
|
|
||||||
"allow_import": 0,
|
|
||||||
"allow_rename": 0,
|
|
||||||
"autoname": "naming_series:",
|
"autoname": "naming_series:",
|
||||||
"beta": 0,
|
|
||||||
"creation": "2018-06-18 16:51:49.994750",
|
"creation": "2018-06-18 16:51:49.994750",
|
||||||
"custom": 0,
|
|
||||||
"docstatus": 0,
|
|
||||||
"doctype": "DocType",
|
"doctype": "DocType",
|
||||||
"document_type": "",
|
|
||||||
"editable_grid": 1,
|
"editable_grid": 1,
|
||||||
"engine": "InnoDB",
|
"engine": "InnoDB",
|
||||||
|
"field_order": [
|
||||||
|
"naming_series",
|
||||||
|
"user",
|
||||||
|
"date",
|
||||||
|
"from_time",
|
||||||
|
"time",
|
||||||
|
"expense",
|
||||||
|
"custody",
|
||||||
|
"returns",
|
||||||
|
"outstanding_amount",
|
||||||
|
"payments",
|
||||||
|
"net_amount",
|
||||||
|
"amended_from"
|
||||||
|
],
|
||||||
"fields": [
|
"fields": [
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "POS-CLO-",
|
"default": "POS-CLO-",
|
||||||
"fieldname": "naming_series",
|
"fieldname": "naming_series",
|
||||||
"fieldtype": "Select",
|
"fieldtype": "Select",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 1,
|
"in_global_search": 1,
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 1,
|
"in_standard_filter": 1,
|
||||||
"label": "Series",
|
"label": "Series",
|
||||||
"length": 0,
|
|
||||||
"no_copy": 0,
|
|
||||||
"options": "POS-CLO-",
|
"options": "POS-CLO-",
|
||||||
"permlevel": 0,
|
"read_only": 1
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 1,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"fieldname": "user",
|
"fieldname": "user",
|
||||||
"fieldtype": "Link",
|
"fieldtype": "Link",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 1,
|
"in_list_view": 1,
|
||||||
"in_standard_filter": 1,
|
"in_standard_filter": 1,
|
||||||
"label": "User",
|
"label": "User",
|
||||||
"length": 0,
|
|
||||||
"no_copy": 0,
|
|
||||||
"options": "User",
|
"options": "User",
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 1,
|
"read_only": 1,
|
||||||
"remember_last_selected_value": 0,
|
"reqd": 1
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 1,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "Today",
|
"default": "Today",
|
||||||
"fieldname": "date",
|
"fieldname": "date",
|
||||||
"fieldtype": "Date",
|
"fieldtype": "Date",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 1,
|
"in_standard_filter": 1,
|
||||||
"label": "Date",
|
"label": "Date",
|
||||||
"length": 0,
|
"read_only": 1
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 1,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"fieldname": "from_time",
|
"fieldname": "from_time",
|
||||||
"fieldtype": "Time",
|
"fieldtype": "Time",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 1,
|
"in_standard_filter": 1,
|
||||||
"label": "From Time",
|
"label": "From Time",
|
||||||
"length": 0,
|
"reqd": 1
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 0,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 1,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "",
|
|
||||||
"fieldname": "time",
|
"fieldname": "time",
|
||||||
"fieldtype": "Time",
|
"fieldtype": "Time",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 1,
|
"in_standard_filter": 1,
|
||||||
"label": "To Time",
|
"label": "To Time",
|
||||||
"length": 0,
|
"reqd": 1
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 0,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 1,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "0.00",
|
"default": "0.00",
|
||||||
"fieldname": "expense",
|
"fieldname": "expense",
|
||||||
"fieldtype": "Float",
|
"fieldtype": "Float",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
"label": "Expense"
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 0,
|
|
||||||
"label": "Expense",
|
|
||||||
"length": 0,
|
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 0,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "0.00",
|
"default": "0.00",
|
||||||
"fieldname": "custody",
|
"fieldname": "custody",
|
||||||
"fieldtype": "Float",
|
"fieldtype": "Float",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
"label": "Custody"
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 0,
|
|
||||||
"label": "Custody",
|
|
||||||
"length": 0,
|
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 0,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "0.00",
|
"default": "0.00",
|
||||||
"fieldname": "returns",
|
"fieldname": "returns",
|
||||||
"fieldtype": "Float",
|
"fieldtype": "Float",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 0,
|
|
||||||
"label": "Returns",
|
"label": "Returns",
|
||||||
"length": 0,
|
"precision": "2"
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "2",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 0,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "0.00",
|
"default": "0.00",
|
||||||
"fieldname": "outstanding_amount",
|
"fieldname": "outstanding_amount",
|
||||||
"fieldtype": "Float",
|
"fieldtype": "Float",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 0,
|
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 0,
|
|
||||||
"label": "Outstanding Amount",
|
"label": "Outstanding Amount",
|
||||||
"length": 0,
|
"read_only": 1
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 1,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"default": "0.0",
|
|
||||||
"fieldname": "payments",
|
"fieldname": "payments",
|
||||||
"fieldtype": "Table",
|
"fieldtype": "Table",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 0,
|
|
||||||
"label": "Payments",
|
"label": "Payments",
|
||||||
"length": 0,
|
"options": "Cashier Closing Payments"
|
||||||
"no_copy": 0,
|
|
||||||
"options": "Cashier Closing Payments",
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 0,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"fieldname": "net_amount",
|
"fieldname": "net_amount",
|
||||||
"fieldtype": "Float",
|
"fieldtype": "Float",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 1,
|
"in_filter": 1,
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 1,
|
"in_list_view": 1,
|
||||||
"in_standard_filter": 1,
|
"in_standard_filter": 1,
|
||||||
"label": "Net Amount",
|
"label": "Net Amount",
|
||||||
"length": 0,
|
"read_only": 1
|
||||||
"no_copy": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"precision": "",
|
|
||||||
"print_hide": 0,
|
|
||||||
"print_hide_if_no_value": 0,
|
|
||||||
"read_only": 1,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"allow_bulk_edit": 0,
|
|
||||||
"allow_in_quick_entry": 0,
|
|
||||||
"allow_on_submit": 0,
|
|
||||||
"bold": 0,
|
|
||||||
"collapsible": 0,
|
|
||||||
"columns": 0,
|
|
||||||
"fieldname": "amended_from",
|
"fieldname": "amended_from",
|
||||||
"fieldtype": "Link",
|
"fieldtype": "Link",
|
||||||
"hidden": 0,
|
|
||||||
"ignore_user_permissions": 0,
|
|
||||||
"ignore_xss_filter": 0,
|
|
||||||
"in_filter": 0,
|
|
||||||
"in_global_search": 0,
|
|
||||||
"in_list_view": 0,
|
|
||||||
"in_standard_filter": 0,
|
|
||||||
"label": "Amended From",
|
"label": "Amended From",
|
||||||
"length": 0,
|
|
||||||
"no_copy": 1,
|
"no_copy": 1,
|
||||||
"options": "Cashier Closing",
|
"options": "Cashier Closing",
|
||||||
"permlevel": 0,
|
|
||||||
"print_hide": 1,
|
"print_hide": 1,
|
||||||
"print_hide_if_no_value": 0,
|
"read_only": 1
|
||||||
"read_only": 1,
|
|
||||||
"remember_last_selected_value": 0,
|
|
||||||
"report_hide": 0,
|
|
||||||
"reqd": 0,
|
|
||||||
"search_index": 0,
|
|
||||||
"set_only_once": 0,
|
|
||||||
"translatable": 0,
|
|
||||||
"unique": 0
|
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"has_web_view": 0,
|
|
||||||
"hide_heading": 0,
|
|
||||||
"hide_toolbar": 0,
|
|
||||||
"idx": 0,
|
|
||||||
"image_view": 0,
|
|
||||||
"in_create": 0,
|
|
||||||
"is_submittable": 1,
|
"is_submittable": 1,
|
||||||
"issingle": 0,
|
"links": [],
|
||||||
"istable": 0,
|
"modified": "2023-12-28 13:15:46.858427",
|
||||||
"max_attachments": 0,
|
|
||||||
"modified": "2019-02-19 08:35:24.157327",
|
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Cashier Closing",
|
"name": "Cashier Closing",
|
||||||
"name_case": "",
|
"naming_rule": "By \"Naming Series\" field",
|
||||||
"owner": "Administrator",
|
"owner": "Administrator",
|
||||||
"permissions": [
|
"permissions": [
|
||||||
{
|
{
|
||||||
"amend": 0,
|
|
||||||
"cancel": 0,
|
|
||||||
"create": 1,
|
"create": 1,
|
||||||
"delete": 1,
|
"delete": 1,
|
||||||
"email": 1,
|
"email": 1,
|
||||||
"export": 1,
|
"export": 1,
|
||||||
"if_owner": 0,
|
|
||||||
"import": 0,
|
|
||||||
"permlevel": 0,
|
|
||||||
"print": 1,
|
"print": 1,
|
||||||
"read": 1,
|
"read": 1,
|
||||||
"report": 1,
|
"report": 1,
|
||||||
"role": "System Manager",
|
"role": "System Manager",
|
||||||
"set_user_permissions": 0,
|
|
||||||
"share": 1,
|
"share": 1,
|
||||||
"submit": 1,
|
"submit": 1,
|
||||||
"write": 1
|
"write": 1
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"quick_entry": 0,
|
|
||||||
"read_only": 0,
|
|
||||||
"read_only_onload": 0,
|
|
||||||
"show_name_in_global_search": 0,
|
|
||||||
"sort_field": "modified",
|
"sort_field": "modified",
|
||||||
"sort_order": "DESC",
|
"sort_order": "DESC",
|
||||||
"track_changes": 1,
|
"states": [],
|
||||||
"track_seen": 0,
|
"track_changes": 1
|
||||||
"track_views": 0
|
}
|
||||||
}
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
frappe.ui.form.on('Chart of Accounts Importer', {
|
frappe.ui.form.on("Chart of Accounts Importer", {
|
||||||
onload: function (frm) {
|
onload: function (frm) {
|
||||||
frm.set_value("company", "");
|
frm.set_value("company", "");
|
||||||
frm.set_value("import_file", "");
|
frm.set_value("import_file", "");
|
||||||
@@ -8,31 +8,34 @@ frappe.ui.form.on('Chart of Accounts Importer', {
|
|||||||
frm.disable_save();
|
frm.disable_save();
|
||||||
|
|
||||||
// make company mandatory
|
// make company mandatory
|
||||||
frm.set_df_property('company', 'reqd', frm.doc.company ? 0 : 1);
|
frm.set_df_property("company", "reqd", frm.doc.company ? 0 : 1);
|
||||||
frm.set_df_property('import_file_section', 'hidden', frm.doc.company ? 0 : 1);
|
frm.set_df_property("import_file_section", "hidden", frm.doc.company ? 0 : 1);
|
||||||
|
|
||||||
if (frm.doc.import_file) {
|
if (frm.doc.import_file) {
|
||||||
frappe.run_serially([
|
frappe.run_serially([
|
||||||
() => generate_tree_preview(frm),
|
() => generate_tree_preview(frm),
|
||||||
() => create_import_button(frm),
|
() => create_import_button(frm),
|
||||||
() => frm.set_df_property('chart_preview', 'hidden', 0)
|
() => frm.set_df_property("chart_preview", "hidden", 0),
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
frm.set_df_property('chart_preview', 'hidden',
|
frm.set_df_property(
|
||||||
$(frm.fields_dict['chart_tree'].wrapper).html()!="" ? 0 : 1);
|
"chart_preview",
|
||||||
|
"hidden",
|
||||||
|
$(frm.fields_dict["chart_tree"].wrapper).html() != "" ? 0 : 1
|
||||||
|
);
|
||||||
},
|
},
|
||||||
|
|
||||||
download_template: function(frm) {
|
download_template: function (frm) {
|
||||||
var d = new frappe.ui.Dialog({
|
var d = new frappe.ui.Dialog({
|
||||||
title: __("Download Template"),
|
title: __("Download Template"),
|
||||||
fields: [
|
fields: [
|
||||||
{
|
{
|
||||||
label : "File Type",
|
label: "File Type",
|
||||||
fieldname: "file_type",
|
fieldname: "file_type",
|
||||||
fieldtype: "Select",
|
fieldtype: "Select",
|
||||||
reqd: 1,
|
reqd: 1,
|
||||||
options: ["Excel", "CSV"]
|
options: ["Excel", "CSV"],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "Template Type",
|
label: "Template Type",
|
||||||
@@ -41,21 +44,27 @@ frappe.ui.form.on('Chart of Accounts Importer', {
|
|||||||
reqd: 1,
|
reqd: 1,
|
||||||
options: ["Sample Template", "Blank Template"],
|
options: ["Sample Template", "Blank Template"],
|
||||||
change: () => {
|
change: () => {
|
||||||
let template_type = d.get_value('template_type');
|
let template_type = d.get_value("template_type");
|
||||||
|
|
||||||
if (template_type === "Sample Template") {
|
if (template_type === "Sample Template") {
|
||||||
d.set_df_property('template_type', 'description',
|
d.set_df_property(
|
||||||
|
"template_type",
|
||||||
|
"description",
|
||||||
`The Sample Template contains all the required accounts pre filled in the template.
|
`The Sample Template contains all the required accounts pre filled in the template.
|
||||||
You can add more accounts or change existing accounts in the template as per your choice.`);
|
You can add more accounts or change existing accounts in the template as per your choice.`
|
||||||
|
);
|
||||||
} else {
|
} else {
|
||||||
d.set_df_property('template_type', 'description',
|
d.set_df_property(
|
||||||
|
"template_type",
|
||||||
|
"description",
|
||||||
`The Blank Template contains just the account type and root type required to build the Chart
|
`The Blank Template contains just the account type and root type required to build the Chart
|
||||||
of Accounts. Please enter the account names and add more rows as per your requirement.`);
|
of Accounts. Please enter the account names and add more rows as per your requirement.`
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label : "Company",
|
label: "Company",
|
||||||
fieldname: "company",
|
fieldname: "company",
|
||||||
fieldtype: "Link",
|
fieldtype: "Link",
|
||||||
reqd: 1,
|
reqd: 1,
|
||||||
@@ -63,25 +72,25 @@ frappe.ui.form.on('Chart of Accounts Importer', {
|
|||||||
default: frm.doc.company,
|
default: frm.doc.company,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
primary_action: function() {
|
primary_action: function () {
|
||||||
let data = d.get_values();
|
let data = d.get_values();
|
||||||
|
|
||||||
if (!data.template_type) {
|
if (!data.template_type) {
|
||||||
frappe.throw(__('Please select <b>Template Type</b> to download template'));
|
frappe.throw(__("Please select <b>Template Type</b> to download template"));
|
||||||
}
|
}
|
||||||
|
|
||||||
open_url_post(
|
open_url_post(
|
||||||
'/api/method/erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.download_template',
|
"/api/method/erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.download_template",
|
||||||
{
|
{
|
||||||
file_type: data.file_type,
|
file_type: data.file_type,
|
||||||
template_type: data.template_type,
|
template_type: data.template_type,
|
||||||
company: data.company
|
company: data.company,
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
d.hide();
|
d.hide();
|
||||||
},
|
},
|
||||||
primary_action_label: __('Download')
|
primary_action_label: __("Download"),
|
||||||
});
|
});
|
||||||
d.show();
|
d.show();
|
||||||
},
|
},
|
||||||
@@ -89,7 +98,7 @@ frappe.ui.form.on('Chart of Accounts Importer', {
|
|||||||
import_file: function (frm) {
|
import_file: function (frm) {
|
||||||
if (!frm.doc.import_file) {
|
if (!frm.doc.import_file) {
|
||||||
frm.page.set_indicator("");
|
frm.page.set_indicator("");
|
||||||
$(frm.fields_dict['chart_tree'].wrapper).empty(); // empty wrapper on removing file
|
$(frm.fields_dict["chart_tree"].wrapper).empty(); // empty wrapper on removing file
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
@@ -99,89 +108,97 @@ frappe.ui.form.on('Chart of Accounts Importer', {
|
|||||||
frappe.call({
|
frappe.call({
|
||||||
method: "erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.validate_company",
|
method: "erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.validate_company",
|
||||||
args: {
|
args: {
|
||||||
company: frm.doc.company
|
company: frm.doc.company,
|
||||||
},
|
},
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
if(r.message===false) {
|
if (r.message === false) {
|
||||||
frm.set_value("company", "");
|
frm.set_value("company", "");
|
||||||
frappe.throw(__("Transactions against the Company already exist! Chart of Accounts can only be imported for a Company with no transactions."));
|
frappe.throw(
|
||||||
|
__(
|
||||||
|
"Transactions against the Company already exist! Chart of Accounts can only be imported for a Company with no transactions."
|
||||||
|
)
|
||||||
|
);
|
||||||
} else {
|
} else {
|
||||||
frm.trigger("refresh");
|
frm.trigger("refresh");
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
var create_import_button = function(frm) {
|
var create_import_button = function (frm) {
|
||||||
frm.page.set_primary_action(__("Import"), function () {
|
frm.page
|
||||||
|
.set_primary_action(__("Import"), function () {
|
||||||
|
return frappe.call({
|
||||||
|
method: "erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.import_coa",
|
||||||
|
args: {
|
||||||
|
file_name: frm.doc.import_file,
|
||||||
|
company: frm.doc.company,
|
||||||
|
},
|
||||||
|
freeze: true,
|
||||||
|
freeze_message: __("Creating Accounts..."),
|
||||||
|
callback: function (r) {
|
||||||
|
if (!r.exc) {
|
||||||
|
clearInterval(frm.page["interval"]);
|
||||||
|
frm.page.set_indicator(__("Import Successful"), "blue");
|
||||||
|
create_reset_button(frm);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
});
|
||||||
|
})
|
||||||
|
.addClass("btn btn-primary");
|
||||||
|
};
|
||||||
|
|
||||||
|
var create_reset_button = function (frm) {
|
||||||
|
frm.page
|
||||||
|
.set_primary_action(__("Reset"), function () {
|
||||||
|
frm.page.clear_primary_action();
|
||||||
|
delete frm.page["show_import_button"];
|
||||||
|
frm.reload_doc();
|
||||||
|
})
|
||||||
|
.addClass("btn btn-primary");
|
||||||
|
};
|
||||||
|
|
||||||
|
var validate_coa = function (frm) {
|
||||||
|
if (frm.doc.import_file) {
|
||||||
|
let parent = __("All Accounts");
|
||||||
return frappe.call({
|
return frappe.call({
|
||||||
method: "erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.import_coa",
|
method: "erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.get_coa",
|
||||||
args: {
|
args: {
|
||||||
file_name: frm.doc.import_file,
|
|
||||||
company: frm.doc.company
|
|
||||||
},
|
|
||||||
freeze: true,
|
|
||||||
freeze_message: __("Creating Accounts..."),
|
|
||||||
callback: function(r) {
|
|
||||||
if (!r.exc) {
|
|
||||||
clearInterval(frm.page["interval"]);
|
|
||||||
frm.page.set_indicator(__('Import Successful'), 'blue');
|
|
||||||
create_reset_button(frm);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}).addClass('btn btn-primary');
|
|
||||||
};
|
|
||||||
|
|
||||||
var create_reset_button = function(frm) {
|
|
||||||
frm.page.set_primary_action(__("Reset"), function () {
|
|
||||||
frm.page.clear_primary_action();
|
|
||||||
delete frm.page["show_import_button"];
|
|
||||||
frm.reload_doc();
|
|
||||||
}).addClass('btn btn-primary');
|
|
||||||
};
|
|
||||||
|
|
||||||
var validate_coa = function(frm) {
|
|
||||||
if (frm.doc.import_file) {
|
|
||||||
let parent = __('All Accounts');
|
|
||||||
return frappe.call({
|
|
||||||
'method': 'erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.get_coa',
|
|
||||||
'args': {
|
|
||||||
file_name: frm.doc.import_file,
|
file_name: frm.doc.import_file,
|
||||||
parent: parent,
|
parent: parent,
|
||||||
doctype: 'Chart of Accounts Importer',
|
doctype: "Chart of Accounts Importer",
|
||||||
file_type: frm.doc.file_type,
|
file_type: frm.doc.file_type,
|
||||||
for_validate: 1
|
for_validate: 1,
|
||||||
},
|
},
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
if (r.message['show_import_button']) {
|
if (r.message["show_import_button"]) {
|
||||||
frm.page['show_import_button'] = Boolean(r.message['show_import_button']);
|
frm.page["show_import_button"] = Boolean(r.message["show_import_button"]);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
var generate_tree_preview = function(frm) {
|
var generate_tree_preview = function (frm) {
|
||||||
let parent = __('All Accounts');
|
let parent = __("All Accounts");
|
||||||
$(frm.fields_dict['chart_tree'].wrapper).empty(); // empty wrapper to load new data
|
$(frm.fields_dict["chart_tree"].wrapper).empty(); // empty wrapper to load new data
|
||||||
|
|
||||||
// generate tree structure based on the csv data
|
// generate tree structure based on the csv data
|
||||||
return new frappe.ui.Tree({
|
return new frappe.ui.Tree({
|
||||||
parent: $(frm.fields_dict['chart_tree'].wrapper),
|
parent: $(frm.fields_dict["chart_tree"].wrapper),
|
||||||
label: parent,
|
label: parent,
|
||||||
expandable: true,
|
expandable: true,
|
||||||
method: 'erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.get_coa',
|
method: "erpnext.accounts.doctype.chart_of_accounts_importer.chart_of_accounts_importer.get_coa",
|
||||||
args: {
|
args: {
|
||||||
file_name: frm.doc.import_file,
|
file_name: frm.doc.import_file,
|
||||||
parent: parent,
|
parent: parent,
|
||||||
doctype: 'Chart of Accounts Importer',
|
doctype: "Chart of Accounts Importer",
|
||||||
file_type: frm.doc.file_type
|
file_type: frm.doc.file_type,
|
||||||
},
|
},
|
||||||
onclick: function(node) {
|
onclick: function (node) {
|
||||||
parent = node.value;
|
parent = node.value;
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -3,18 +3,20 @@
|
|||||||
|
|
||||||
frappe.provide("erpnext.cheque_print");
|
frappe.provide("erpnext.cheque_print");
|
||||||
|
|
||||||
frappe.ui.form.on('Cheque Print Template', {
|
frappe.ui.form.on("Cheque Print Template", {
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
if(!frm.doc.__islocal) {
|
if (!frm.doc.__islocal) {
|
||||||
frm.add_custom_button(frm.doc.has_print_format?__("Update Print Format"):__("Create Print Format"),
|
frm.add_custom_button(
|
||||||
function() {
|
frm.doc.has_print_format ? __("Update Print Format") : __("Create Print Format"),
|
||||||
|
function () {
|
||||||
erpnext.cheque_print.view_cheque_print(frm);
|
erpnext.cheque_print.view_cheque_print(frm);
|
||||||
}).addClass("btn-primary");
|
}
|
||||||
|
).addClass("btn-primary");
|
||||||
|
|
||||||
$(frm.fields_dict.cheque_print_preview.wrapper).empty()
|
$(frm.fields_dict.cheque_print_preview.wrapper).empty();
|
||||||
|
|
||||||
|
var template =
|
||||||
var template = '<div style="position: relative; overflow-x: scroll;">\
|
'<div style="position: relative; overflow-x: scroll;">\
|
||||||
<div id="cheque_preview" style="width: {{ cheque_width }}cm; \
|
<div id="cheque_preview" style="width: {{ cheque_width }}cm; \
|
||||||
height: {{ cheque_height }}cm;\
|
height: {{ cheque_height }}cm;\
|
||||||
background-repeat: no-repeat;\
|
background-repeat: no-repeat;\
|
||||||
@@ -48,30 +50,30 @@ frappe.ui.form.on('Cheque Print Template', {
|
|||||||
</div>\
|
</div>\
|
||||||
</div>';
|
</div>';
|
||||||
|
|
||||||
$(frappe.render(template, frm.doc)).appendTo(frm.fields_dict.cheque_print_preview.wrapper)
|
$(frappe.render(template, frm.doc)).appendTo(frm.fields_dict.cheque_print_preview.wrapper);
|
||||||
|
|
||||||
if (frm.doc.scanned_cheque) {
|
if (frm.doc.scanned_cheque) {
|
||||||
$(frm.fields_dict.cheque_print_preview.wrapper).find("#cheque_preview").css('background-image', 'url(' + frm.doc.scanned_cheque + ')');
|
$(frm.fields_dict.cheque_print_preview.wrapper)
|
||||||
|
.find("#cheque_preview")
|
||||||
|
.css("background-image", "url(" + frm.doc.scanned_cheque + ")");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
erpnext.cheque_print.view_cheque_print = function (frm) {
|
||||||
erpnext.cheque_print.view_cheque_print = function(frm) {
|
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "erpnext.accounts.doctype.cheque_print_template.cheque_print_template.create_or_update_cheque_print_format",
|
method: "erpnext.accounts.doctype.cheque_print_template.cheque_print_template.create_or_update_cheque_print_format",
|
||||||
args:{
|
args: {
|
||||||
"template_name": frm.doc.name
|
template_name: frm.doc.name,
|
||||||
},
|
},
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
if (!r.exe && !frm.doc.has_print_format) {
|
if (!r.exe && !frm.doc.has_print_format) {
|
||||||
var doc = frappe.model.sync(r.message);
|
var doc = frappe.model.sync(r.message);
|
||||||
frappe.set_route("Form", r.message.doctype, r.message.name);
|
frappe.set_route("Form", r.message.doctype, r.message.name);
|
||||||
|
} else {
|
||||||
|
frappe.msgprint(__("Print settings updated in respective print format"));
|
||||||
}
|
}
|
||||||
else {
|
},
|
||||||
frappe.msgprint(__("Print settings updated in respective print format"))
|
});
|
||||||
}
|
};
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -3,75 +3,80 @@
|
|||||||
|
|
||||||
frappe.provide("erpnext.accounts");
|
frappe.provide("erpnext.accounts");
|
||||||
|
|
||||||
|
frappe.ui.form.on("Cost Center", {
|
||||||
|
onload: function (frm) {
|
||||||
frappe.ui.form.on('Cost Center', {
|
frm.set_query("parent_cost_center", function () {
|
||||||
onload: function(frm) {
|
|
||||||
frm.set_query("parent_cost_center", function() {
|
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
is_group: 1
|
is_group: 1,
|
||||||
}
|
},
|
||||||
}
|
};
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
if (!frm.is_new()) {
|
if (!frm.is_new()) {
|
||||||
frm.add_custom_button(__('Update Cost Center Name / Number'), function () {
|
frm.add_custom_button(__("Update Cost Center Name / Number"), function () {
|
||||||
frm.trigger("update_cost_center_number");
|
frm.trigger("update_cost_center_number");
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
let intro_txt = '';
|
let intro_txt = "";
|
||||||
let doc = frm.doc;
|
let doc = frm.doc;
|
||||||
frm.toggle_display('cost_center_name', doc.__islocal);
|
frm.toggle_display("cost_center_name", doc.__islocal);
|
||||||
frm.toggle_enable(['is_group', 'company'], doc.__islocal);
|
frm.toggle_enable(["is_group", "company"], doc.__islocal);
|
||||||
|
|
||||||
if(!doc.__islocal && doc.is_group==1) {
|
if (!doc.__islocal && doc.is_group == 1) {
|
||||||
intro_txt += __('Note: This Cost Center is a Group. Cannot make accounting entries against groups.');
|
intro_txt += __(
|
||||||
|
"Note: This Cost Center is a Group. Cannot make accounting entries against groups."
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
frm.events.hide_unhide_group_ledger(frm);
|
frm.events.hide_unhide_group_ledger(frm);
|
||||||
|
|
||||||
frm.toggle_display('sb1', doc.is_group==0);
|
frm.toggle_display("sb1", doc.is_group == 0);
|
||||||
frm.set_intro(intro_txt);
|
frm.set_intro(intro_txt);
|
||||||
|
|
||||||
if(!frm.doc.__islocal) {
|
if (!frm.doc.__islocal) {
|
||||||
frm.add_custom_button(__('Chart of Cost Centers'),
|
frm.add_custom_button(__("Chart of Cost Centers"), function () {
|
||||||
function() { frappe.set_route("Tree", "Cost Center"); });
|
frappe.set_route("Tree", "Cost Center");
|
||||||
|
});
|
||||||
|
|
||||||
frm.add_custom_button(__('Budget'),
|
frm.add_custom_button(__("Budget"), function () {
|
||||||
function() { frappe.set_route("List", "Budget", {'cost_center': frm.doc.name}); });
|
frappe.set_route("List", "Budget", { cost_center: frm.doc.name });
|
||||||
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
update_cost_center_number: function(frm) {
|
update_cost_center_number: function (frm) {
|
||||||
var d = new frappe.ui.Dialog({
|
var d = new frappe.ui.Dialog({
|
||||||
title: __('Update Cost Center Name / Number'),
|
title: __("Update Cost Center Name / Number"),
|
||||||
fields: [
|
fields: [
|
||||||
{
|
{
|
||||||
"label": "Cost Center Name",
|
label: "Cost Center Name",
|
||||||
"fieldname": "cost_center_name",
|
fieldname: "cost_center_name",
|
||||||
"fieldtype": "Data",
|
fieldtype: "Data",
|
||||||
"reqd": 1,
|
reqd: 1,
|
||||||
"default": frm.doc.cost_center_name
|
default: frm.doc.cost_center_name,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"label": "Cost Center Number",
|
label: "Cost Center Number",
|
||||||
"fieldname": "cost_center_number",
|
fieldname: "cost_center_number",
|
||||||
"fieldtype": "Data",
|
fieldtype: "Data",
|
||||||
"default": frm.doc.cost_center_number
|
default: frm.doc.cost_center_number,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"label": __("Merge with existing"),
|
label: __("Merge with existing"),
|
||||||
"fieldname": "merge",
|
fieldname: "merge",
|
||||||
"fieldtype": "Check",
|
fieldtype: "Check",
|
||||||
"default": 0
|
default: 0,
|
||||||
}
|
},
|
||||||
],
|
],
|
||||||
primary_action: function() {
|
primary_action: function () {
|
||||||
let data = d.get_values();
|
let data = d.get_values();
|
||||||
if(data.cost_center_name === frm.doc.cost_center_name && data.cost_center_number === frm.doc.cost_center_number) {
|
if (
|
||||||
|
data.cost_center_name === frm.doc.cost_center_name &&
|
||||||
|
data.cost_center_number === frm.doc.cost_center_number
|
||||||
|
) {
|
||||||
d.hide();
|
d.hide();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -83,12 +88,12 @@ frappe.ui.form.on('Cost Center', {
|
|||||||
cost_center_name: data.cost_center_name,
|
cost_center_name: data.cost_center_name,
|
||||||
cost_center_number: cstr(data.cost_center_number),
|
cost_center_number: cstr(data.cost_center_number),
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
merge: data.merge
|
merge: data.merge,
|
||||||
},
|
},
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
frappe.dom.unfreeze();
|
frappe.dom.unfreeze();
|
||||||
if(!r.exc) {
|
if (!r.exc) {
|
||||||
if(r.message) {
|
if (r.message) {
|
||||||
frappe.set_route("Form", "Cost Center", r.message);
|
frappe.set_route("Form", "Cost Center", r.message);
|
||||||
} else {
|
} else {
|
||||||
frm.set_value("cost_center_name", data.cost_center_name);
|
frm.set_value("cost_center_name", data.cost_center_name);
|
||||||
@@ -96,44 +101,42 @@ frappe.ui.form.on('Cost Center', {
|
|||||||
}
|
}
|
||||||
d.hide();
|
d.hide();
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
primary_action_label: __('Update')
|
primary_action_label: __("Update"),
|
||||||
});
|
});
|
||||||
d.show();
|
d.show();
|
||||||
},
|
},
|
||||||
|
|
||||||
parent_cost_center(frm) {
|
parent_cost_center(frm) {
|
||||||
if(!frm.doc.company) {
|
if (!frm.doc.company) {
|
||||||
frappe.msgprint(__('Please enter company name first'));
|
frappe.msgprint(__("Please enter company name first"));
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
hide_unhide_group_ledger(frm) {
|
hide_unhide_group_ledger(frm) {
|
||||||
let doc = frm.doc;
|
let doc = frm.doc;
|
||||||
if (doc.is_group == 1) {
|
if (doc.is_group == 1) {
|
||||||
frm.add_custom_button(__('Convert to Non-Group'),
|
frm.add_custom_button(__("Convert to Non-Group"), () => frm.events.convert_to_ledger(frm));
|
||||||
() => frm.events.convert_to_ledger(frm));
|
|
||||||
} else if (doc.is_group == 0) {
|
} else if (doc.is_group == 0) {
|
||||||
frm.add_custom_button(__('Convert to Group'),
|
frm.add_custom_button(__("Convert to Group"), () => frm.events.convert_to_group(frm));
|
||||||
() => frm.events.convert_to_group(frm));
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
convert_to_group(frm) {
|
convert_to_group(frm) {
|
||||||
frm.call('convert_ledger_to_group').then(r => {
|
frm.call("convert_ledger_to_group").then((r) => {
|
||||||
if(r.message === 1) {
|
if (r.message === 1) {
|
||||||
frm.refresh();
|
frm.refresh();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
convert_to_ledger(frm) {
|
convert_to_ledger(frm) {
|
||||||
frm.call('convert_group_to_ledger').then(r => {
|
frm.call("convert_group_to_ledger").then((r) => {
|
||||||
if(r.message === 1) {
|
if (r.message === 1) {
|
||||||
frm.refresh();
|
frm.refresh();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -41,7 +41,7 @@
|
|||||||
"in_list_view": 1,
|
"in_list_view": 1,
|
||||||
"in_standard_filter": 1,
|
"in_standard_filter": 1,
|
||||||
"label": "Cost Center Number",
|
"label": "Cost Center Number",
|
||||||
"read_only": 1
|
"read_only_depends_on": "eval:!doc.__islocal"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"fieldname": "parent_cost_center",
|
"fieldname": "parent_cost_center",
|
||||||
@@ -170,4 +170,4 @@
|
|||||||
"sort_field": "modified",
|
"sort_field": "modified",
|
||||||
"sort_order": "ASC",
|
"sort_order": "ASC",
|
||||||
"states": []
|
"states": []
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,54 +1,84 @@
|
|||||||
frappe.treeview_settings["Cost Center"] = {
|
frappe.treeview_settings["Cost Center"] = {
|
||||||
breadcrumb: "Accounts",
|
breadcrumb: "Accounts",
|
||||||
get_tree_root: false,
|
get_tree_root: false,
|
||||||
filters: [{
|
filters: [
|
||||||
fieldname: "company",
|
|
||||||
fieldtype:"Select",
|
|
||||||
options: erpnext.utils.get_tree_options("company"),
|
|
||||||
label: __("Company"),
|
|
||||||
default: erpnext.utils.get_tree_default("company")
|
|
||||||
}],
|
|
||||||
root_label: "Cost Centers",
|
|
||||||
get_tree_nodes: 'erpnext.accounts.utils.get_children',
|
|
||||||
add_tree_node: 'erpnext.accounts.utils.add_cc',
|
|
||||||
menu_items:[
|
|
||||||
{
|
{
|
||||||
label: __('New Company'),
|
fieldname: "company",
|
||||||
action: function() { frappe.new_doc("Company", true) },
|
fieldtype: "Select",
|
||||||
condition: 'frappe.boot.user.can_create.indexOf("Company") !== -1'
|
options: erpnext.utils.get_tree_options("company"),
|
||||||
}
|
label: __("Company"),
|
||||||
|
default: erpnext.utils.get_tree_default("company"),
|
||||||
|
},
|
||||||
],
|
],
|
||||||
fields:[
|
root_label: "Cost Centers",
|
||||||
{fieldtype:'Data', fieldname:'cost_center_name', label:__('New Cost Center Name'), reqd:true},
|
get_tree_nodes: "erpnext.accounts.utils.get_children",
|
||||||
{fieldtype:'Check', fieldname:'is_group', label:__('Is Group'),
|
add_tree_node: "erpnext.accounts.utils.add_cc",
|
||||||
description:__('Further cost centers can be made under Groups but entries can be made against non-Groups')},
|
menu_items: [
|
||||||
{fieldtype:'Data', fieldname:'cost_center_number', label:__('Cost Center Number'),
|
{
|
||||||
description: __("Number of new Cost Center, it will be included in the cost center name as a prefix")}
|
label: __("New Company"),
|
||||||
|
action: function () {
|
||||||
|
frappe.new_doc("Company", true);
|
||||||
|
},
|
||||||
|
condition: 'frappe.boot.user.can_create.indexOf("Company") !== -1',
|
||||||
|
},
|
||||||
],
|
],
|
||||||
ignore_fields:["parent_cost_center"],
|
fields: [
|
||||||
onload: function(treeview) {
|
{ fieldtype: "Data", fieldname: "cost_center_name", label: __("New Cost Center Name"), reqd: true },
|
||||||
|
{
|
||||||
|
fieldtype: "Check",
|
||||||
|
fieldname: "is_group",
|
||||||
|
label: __("Is Group"),
|
||||||
|
description: __(
|
||||||
|
"Further cost centers can be made under Groups but entries can be made against non-Groups"
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
fieldtype: "Data",
|
||||||
|
fieldname: "cost_center_number",
|
||||||
|
label: __("Cost Center Number"),
|
||||||
|
description: __(
|
||||||
|
"Number of new Cost Center, it will be included in the cost center name as a prefix"
|
||||||
|
),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
ignore_fields: ["parent_cost_center"],
|
||||||
|
onload: function (treeview) {
|
||||||
function get_company() {
|
function get_company() {
|
||||||
return treeview.page.fields_dict.company.get_value();
|
return treeview.page.fields_dict.company.get_value();
|
||||||
}
|
}
|
||||||
|
|
||||||
// tools
|
// tools
|
||||||
treeview.page.add_inner_button(__("Chart of Accounts"), function() {
|
treeview.page.add_inner_button(
|
||||||
frappe.set_route('Tree', 'Account', {company: get_company()});
|
__("Chart of Accounts"),
|
||||||
}, __('View'));
|
function () {
|
||||||
|
frappe.set_route("Tree", "Account", { company: get_company() });
|
||||||
|
},
|
||||||
|
__("View")
|
||||||
|
);
|
||||||
|
|
||||||
// make
|
// make
|
||||||
treeview.page.add_inner_button(__("Budget List"), function() {
|
treeview.page.add_inner_button(
|
||||||
frappe.set_route('List', 'Budget', {company: get_company()});
|
__("Budget List"),
|
||||||
}, __('Budget'));
|
function () {
|
||||||
|
frappe.set_route("List", "Budget", { company: get_company() });
|
||||||
|
},
|
||||||
|
__("Budget")
|
||||||
|
);
|
||||||
|
|
||||||
treeview.page.add_inner_button(__("Monthly Distribution"), function() {
|
treeview.page.add_inner_button(
|
||||||
frappe.set_route('List', 'Monthly Distribution', {company: get_company()});
|
__("Monthly Distribution"),
|
||||||
}, __('Budget'));
|
function () {
|
||||||
|
frappe.set_route("List", "Monthly Distribution", { company: get_company() });
|
||||||
|
},
|
||||||
|
__("Budget")
|
||||||
|
);
|
||||||
|
|
||||||
treeview.page.add_inner_button(__("Budget Variance Report"), function() {
|
treeview.page.add_inner_button(
|
||||||
frappe.set_route('query-report', 'Budget Variance Report', {company: get_company()});
|
__("Budget Variance Report"),
|
||||||
}, __('Budget'));
|
function () {
|
||||||
|
frappe.set_route("query-report", "Budget Variance Report", { company: get_company() });
|
||||||
}
|
},
|
||||||
|
__("Budget")
|
||||||
}
|
);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|||||||
@@ -1,19 +1,24 @@
|
|||||||
// Copyright (c) 2022, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2022, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Cost Center Allocation', {
|
frappe.ui.form.on("Cost Center Allocation", {
|
||||||
setup: function(frm) {
|
setup: function (frm) {
|
||||||
let filters = {"is_group": 0};
|
frm.set_query("main_cost_center", function () {
|
||||||
if (frm.doc.company) {
|
|
||||||
$.extend(filters, {
|
|
||||||
"company": frm.doc.company
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
frm.set_query('main_cost_center', function() {
|
|
||||||
return {
|
return {
|
||||||
filters: filters
|
filters: {
|
||||||
|
company: frm.doc.company,
|
||||||
|
is_group: 0,
|
||||||
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
}
|
|
||||||
|
frm.set_query("cost_center", "allocation_percentages", function () {
|
||||||
|
return {
|
||||||
|
filters: {
|
||||||
|
company: frm.doc.company,
|
||||||
|
is_group: 0,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
});
|
||||||
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,44 +1,41 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Coupon Code', {
|
frappe.ui.form.on("Coupon Code", {
|
||||||
setup: function(frm) {
|
setup: function (frm) {
|
||||||
frm.set_query("pricing_rule", function() {
|
frm.set_query("pricing_rule", function () {
|
||||||
return {
|
return {
|
||||||
filters: [
|
filters: [["Pricing Rule", "coupon_code_based", "=", "1"]],
|
||||||
["Pricing Rule","coupon_code_based", "=", "1"]
|
|
||||||
]
|
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
coupon_name:function(frm){
|
coupon_name: function (frm) {
|
||||||
if (frm.doc.__islocal===1) {
|
if (frm.doc.__islocal === 1) {
|
||||||
frm.trigger("make_coupon_code");
|
frm.trigger("make_coupon_code");
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
coupon_type:function(frm){
|
coupon_type: function (frm) {
|
||||||
if (frm.doc.__islocal===1) {
|
if (frm.doc.__islocal === 1) {
|
||||||
frm.trigger("make_coupon_code");
|
frm.trigger("make_coupon_code");
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
make_coupon_code: function(frm) {
|
make_coupon_code: function (frm) {
|
||||||
var coupon_name=frm.doc.coupon_name;
|
var coupon_name = frm.doc.coupon_name;
|
||||||
var coupon_code;
|
var coupon_code;
|
||||||
if (frm.doc.coupon_type=='Gift Card') {
|
if (frm.doc.coupon_type == "Gift Card") {
|
||||||
coupon_code=Math.random().toString(12).substring(2, 12).toUpperCase();
|
coupon_code = Math.random().toString(12).substring(2, 12).toUpperCase();
|
||||||
|
} else if (frm.doc.coupon_type == "Promotional") {
|
||||||
|
coupon_name = coupon_name.replace(/\s/g, "");
|
||||||
|
coupon_code = coupon_name.toUpperCase().slice(0, 8);
|
||||||
}
|
}
|
||||||
else if(frm.doc.coupon_type=='Promotional'){
|
frm.doc.coupon_code = coupon_code;
|
||||||
coupon_name=coupon_name.replace(/\s/g,'');
|
frm.refresh_field("coupon_code");
|
||||||
coupon_code=coupon_name.toUpperCase().slice(0,8);
|
|
||||||
}
|
|
||||||
frm.doc.coupon_code=coupon_code;
|
|
||||||
frm.refresh_field('coupon_code');
|
|
||||||
},
|
},
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
if (frm.doc.pricing_rule) {
|
if (frm.doc.pricing_rule) {
|
||||||
frm.add_custom_button(__("Add/Edit Coupon Conditions"), function(){
|
frm.add_custom_button(__("Add/Edit Coupon Conditions"), function () {
|
||||||
frappe.set_route("Form", "Pricing Rule", frm.doc.pricing_rule);
|
frappe.set_route("Form", "Pricing Rule", frm.doc.pricing_rule);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -80,7 +80,7 @@
|
|||||||
{
|
{
|
||||||
"fieldname": "valid_upto",
|
"fieldname": "valid_upto",
|
||||||
"fieldtype": "Date",
|
"fieldtype": "Date",
|
||||||
"label": "Valid Upto"
|
"label": "Valid Up To"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"depends_on": "eval: doc.coupon_type == \"Promotional\"",
|
"depends_on": "eval: doc.coupon_type == \"Promotional\"",
|
||||||
@@ -115,7 +115,7 @@
|
|||||||
"read_only": 1
|
"read_only": 1
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"modified": "2019-10-19 14:48:14.602481",
|
"modified": "2024-01-24 02:20:26.145996",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Coupon Code",
|
"name": "Coupon Code",
|
||||||
|
|||||||
@@ -1,28 +1,27 @@
|
|||||||
// Copyright (c) 2022, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2022, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Currency Exchange Settings', {
|
frappe.ui.form.on("Currency Exchange Settings", {
|
||||||
service_provider: function(frm) {
|
service_provider: function (frm) {
|
||||||
if (frm.doc.service_provider == "exchangerate.host") {
|
if (frm.doc.service_provider == "exchangerate.host") {
|
||||||
let result = ['result'];
|
let result = ["result"];
|
||||||
let params = {
|
let params = {
|
||||||
date: '{transaction_date}',
|
date: "{transaction_date}",
|
||||||
from: '{from_currency}',
|
from: "{from_currency}",
|
||||||
to: '{to_currency}'
|
to: "{to_currency}",
|
||||||
};
|
};
|
||||||
add_param(frm, "https://api.exchangerate.host/convert", params, result);
|
add_param(frm, "https://api.exchangerate.host/convert", params, result);
|
||||||
} else if (frm.doc.service_provider == "frankfurter.app") {
|
} else if (frm.doc.service_provider == "frankfurter.app") {
|
||||||
let result = ['rates', '{to_currency}'];
|
let result = ["rates", "{to_currency}"];
|
||||||
let params = {
|
let params = {
|
||||||
base: '{from_currency}',
|
base: "{from_currency}",
|
||||||
symbols: '{to_currency}'
|
symbols: "{to_currency}",
|
||||||
};
|
};
|
||||||
add_param(frm, "https://frankfurter.app/{transaction_date}", params, result);
|
add_param(frm, "https://frankfurter.app/{transaction_date}", params, result);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
function add_param(frm, api, params, result) {
|
function add_param(frm, api, params, result) {
|
||||||
var row;
|
var row;
|
||||||
frm.clear_table("req_params");
|
frm.clear_table("req_params");
|
||||||
@@ -30,13 +29,13 @@ function add_param(frm, api, params, result) {
|
|||||||
|
|
||||||
frm.doc.api_endpoint = api;
|
frm.doc.api_endpoint = api;
|
||||||
|
|
||||||
$.each(params, function(key, value) {
|
$.each(params, function (key, value) {
|
||||||
row = frm.add_child("req_params");
|
row = frm.add_child("req_params");
|
||||||
row.key = key;
|
row.key = key;
|
||||||
row.value = value;
|
row.value = value;
|
||||||
});
|
});
|
||||||
|
|
||||||
$.each(result, function(key, value) {
|
$.each(result, function (key, value) {
|
||||||
row = frm.add_child("result_key");
|
row = frm.add_child("result_key");
|
||||||
row.key = value;
|
row.key = value;
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ frappe.ui.form.on("Dunning", {
|
|||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
customer: frm.doc.customer,
|
customer: frm.doc.customer,
|
||||||
outstanding_amount: [">", 0],
|
outstanding_amount: [">", 0],
|
||||||
status: "Overdue"
|
status: "Overdue",
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
@@ -19,16 +19,16 @@ frappe.ui.form.on("Dunning", {
|
|||||||
filters: {
|
filters: {
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
root_type: "Income",
|
root_type: "Income",
|
||||||
is_group: 0
|
is_group: 0,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
frm.set_query("cost_center", () => {
|
frm.set_query("cost_center", () => {
|
||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
is_group: 0
|
is_group: 0,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -51,7 +51,8 @@ frappe.ui.form.on("Dunning", {
|
|||||||
__("Payment"),
|
__("Payment"),
|
||||||
function () {
|
function () {
|
||||||
frm.events.make_payment_entry(frm);
|
frm.events.make_payment_entry(frm);
|
||||||
}, __("Create")
|
},
|
||||||
|
__("Create")
|
||||||
);
|
);
|
||||||
frm.page.set_inner_btn_group_as_primary(__("Create"));
|
frm.page.set_inner_btn_group_as_primary(__("Create"));
|
||||||
}
|
}
|
||||||
@@ -69,7 +70,7 @@ frappe.ui.form.on("Dunning", {
|
|||||||
get_query_filters: {
|
get_query_filters: {
|
||||||
docstatus: 1,
|
docstatus: 1,
|
||||||
status: "Overdue",
|
status: "Overdue",
|
||||||
company: frm.doc.company
|
company: frm.doc.company,
|
||||||
},
|
},
|
||||||
allow_child_item_selection: true,
|
allow_child_item_selection: true,
|
||||||
child_fieldname: "payment_schedule",
|
child_fieldname: "payment_schedule",
|
||||||
@@ -78,9 +79,12 @@ frappe.ui.form.on("Dunning", {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
frappe.dynamic_link = { doc: frm.doc, fieldname: 'customer', doctype: 'Customer' };
|
frappe.dynamic_link = { doc: frm.doc, fieldname: "customer", doctype: "Customer" };
|
||||||
|
|
||||||
frm.toggle_display("customer_name", (frm.doc.customer_name && frm.doc.customer_name !== frm.doc.customer));
|
frm.toggle_display(
|
||||||
|
"customer_name",
|
||||||
|
frm.doc.customer_name && frm.doc.customer_name !== frm.doc.customer
|
||||||
|
);
|
||||||
},
|
},
|
||||||
// When multiple companies are set up. in case company name is changed set default company address
|
// When multiple companies are set up. in case company name is changed set default company address
|
||||||
company: function (frm) {
|
company: function (frm) {
|
||||||
@@ -90,8 +94,8 @@ frappe.ui.form.on("Dunning", {
|
|||||||
args: { name: frm.doc.company, existing_address: frm.doc.company_address || "" },
|
args: { name: frm.doc.company, existing_address: frm.doc.company_address || "" },
|
||||||
debounce: 2000,
|
debounce: 2000,
|
||||||
callback: function (r) {
|
callback: function (r) {
|
||||||
frm.set_value("company_address", r && r.message || "");
|
frm.set_value("company_address", (r && r.message) || "");
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
if (frm.fields_dict.currency) {
|
if (frm.fields_dict.currency) {
|
||||||
@@ -125,16 +129,16 @@ frappe.ui.form.on("Dunning", {
|
|||||||
transaction_date: frm.doc.posting_date,
|
transaction_date: frm.doc.posting_date,
|
||||||
from_currency: frm.doc.currency,
|
from_currency: frm.doc.currency,
|
||||||
to_currency: company_currency,
|
to_currency: company_currency,
|
||||||
args: "for_selling"
|
args: "for_selling",
|
||||||
},
|
},
|
||||||
freeze: true,
|
freeze: true,
|
||||||
freeze_message: __("Fetching exchange rates ..."),
|
freeze_message: __("Fetching exchange rates ..."),
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
const exchange_rate = flt(r.message);
|
const exchange_rate = flt(r.message);
|
||||||
if (exchange_rate != frm.doc.conversion_rate) {
|
if (exchange_rate != frm.doc.conversion_rate) {
|
||||||
frm.set_value("conversion_rate", exchange_rate);
|
frm.set_value("conversion_rate", exchange_rate);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
frm.trigger("conversion_rate");
|
frm.trigger("conversion_rate");
|
||||||
@@ -166,8 +170,7 @@ frappe.ui.form.on("Dunning", {
|
|||||||
get_dunning_letter_text: function (frm) {
|
get_dunning_letter_text: function (frm) {
|
||||||
if (frm.doc.dunning_type) {
|
if (frm.doc.dunning_type) {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method:
|
method: "erpnext.accounts.doctype.dunning.dunning.get_dunning_letter_text",
|
||||||
"erpnext.accounts.doctype.dunning.dunning.get_dunning_letter_text",
|
|
||||||
args: {
|
args: {
|
||||||
dunning_type: frm.doc.dunning_type,
|
dunning_type: frm.doc.dunning_type,
|
||||||
language: frm.doc.language,
|
language: frm.doc.language,
|
||||||
@@ -204,10 +207,7 @@ frappe.ui.form.on("Dunning", {
|
|||||||
calculate_overdue_days: function (frm) {
|
calculate_overdue_days: function (frm) {
|
||||||
frm.doc.overdue_payments.forEach((row) => {
|
frm.doc.overdue_payments.forEach((row) => {
|
||||||
if (frm.doc.posting_date && row.due_date) {
|
if (frm.doc.posting_date && row.due_date) {
|
||||||
const overdue_days = moment(frm.doc.posting_date).diff(
|
const overdue_days = moment(frm.doc.posting_date).diff(row.due_date, "days");
|
||||||
row.due_date,
|
|
||||||
"days"
|
|
||||||
);
|
|
||||||
frappe.model.set_value(row.doctype, row.name, "overdue_days", overdue_days);
|
frappe.model.set_value(row.doctype, row.name, "overdue_days", overdue_days);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -215,15 +215,16 @@ frappe.ui.form.on("Dunning", {
|
|||||||
calculate_interest: function (frm) {
|
calculate_interest: function (frm) {
|
||||||
frm.doc.overdue_payments.forEach((row) => {
|
frm.doc.overdue_payments.forEach((row) => {
|
||||||
const interest_per_day = frm.doc.rate_of_interest / 100 / 365;
|
const interest_per_day = frm.doc.rate_of_interest / 100 / 365;
|
||||||
const interest = flt((interest_per_day * row.overdue_days * row.outstanding), precision("interest", row));
|
const interest = flt(
|
||||||
|
interest_per_day * row.overdue_days * row.outstanding,
|
||||||
|
precision("interest", row)
|
||||||
|
);
|
||||||
frappe.model.set_value(row.doctype, row.name, "interest", interest);
|
frappe.model.set_value(row.doctype, row.name, "interest", interest);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
calculate_totals: function (frm) {
|
calculate_totals: function (frm) {
|
||||||
const total_interest = frm.doc.overdue_payments
|
const total_interest = frm.doc.overdue_payments.reduce((prev, cur) => prev + cur.interest, 0);
|
||||||
.reduce((prev, cur) => prev + cur.interest, 0);
|
const total_outstanding = frm.doc.overdue_payments.reduce((prev, cur) => prev + cur.outstanding, 0);
|
||||||
const total_outstanding = frm.doc.overdue_payments
|
|
||||||
.reduce((prev, cur) => prev + cur.outstanding, 0);
|
|
||||||
const dunning_amount = total_interest + frm.doc.dunning_fee;
|
const dunning_amount = total_interest + frm.doc.dunning_fee;
|
||||||
const base_dunning_amount = dunning_amount * frm.doc.conversion_rate;
|
const base_dunning_amount = dunning_amount * frm.doc.conversion_rate;
|
||||||
const grand_total = total_outstanding + dunning_amount;
|
const grand_total = total_outstanding + dunning_amount;
|
||||||
@@ -240,8 +241,7 @@ frappe.ui.form.on("Dunning", {
|
|||||||
},
|
},
|
||||||
make_payment_entry: function (frm) {
|
make_payment_entry: function (frm) {
|
||||||
return frappe.call({
|
return frappe.call({
|
||||||
method:
|
method: "erpnext.accounts.doctype.payment_entry.payment_entry.get_payment_entry",
|
||||||
"erpnext.accounts.doctype.payment_entry.payment_entry.get_payment_entry",
|
|
||||||
args: {
|
args: {
|
||||||
dt: frm.doc.doctype,
|
dt: frm.doc.doctype,
|
||||||
dn: frm.doc.name,
|
dn: frm.doc.name,
|
||||||
@@ -257,5 +257,5 @@ frappe.ui.form.on("Dunning", {
|
|||||||
frappe.ui.form.on("Overdue Payment", {
|
frappe.ui.form.on("Overdue Payment", {
|
||||||
interest: function (frm) {
|
interest: function (frm) {
|
||||||
frm.trigger("calculate_totals");
|
frm.trigger("calculate_totals");
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -85,7 +85,14 @@ class Dunning(AccountsController):
|
|||||||
frappe.throw(
|
frappe.throw(
|
||||||
_(
|
_(
|
||||||
"The currency of invoice {} ({}) is different from the currency of this dunning ({})."
|
"The currency of invoice {} ({}) is different from the currency of this dunning ({})."
|
||||||
).format(row.sales_invoice, invoice_currency, self.currency)
|
).format(
|
||||||
|
frappe.get_desk_link(
|
||||||
|
"Sales Invoice",
|
||||||
|
row.sales_invoice,
|
||||||
|
),
|
||||||
|
invoice_currency,
|
||||||
|
self.currency,
|
||||||
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
def validate_overdue_payments(self):
|
def validate_overdue_payments(self):
|
||||||
|
|||||||
@@ -1,75 +1,79 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Exchange Rate Revaluation', {
|
frappe.ui.form.on("Exchange Rate Revaluation", {
|
||||||
setup: function(frm) {
|
setup: function (frm) {
|
||||||
frm.set_query("party_type", "accounts", function() {
|
frm.set_query("party_type", "accounts", function () {
|
||||||
return {
|
return {
|
||||||
"filters": {
|
filters: {
|
||||||
"name": ["in", Object.keys(frappe.boot.party_account_types)],
|
name: ["in", Object.keys(frappe.boot.party_account_types)],
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
frm.set_query("account", "accounts", function(doc) {
|
frm.set_query("account", "accounts", function (doc) {
|
||||||
return {
|
return {
|
||||||
"filters": {
|
filters: {
|
||||||
"company": doc.company
|
company: doc.company,
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {
|
||||||
if(frm.doc.docstatus==1) {
|
if (frm.doc.docstatus == 1) {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: 'check_journal_entry_condition',
|
method: "check_journal_entry_condition",
|
||||||
doc: frm.doc,
|
doc: frm.doc,
|
||||||
callback: function(r) {
|
callback: function (r) {
|
||||||
if (r.message) {
|
if (r.message) {
|
||||||
frm.add_custom_button(__('Journal Entries'), function() {
|
frm.add_custom_button(
|
||||||
return frm.events.make_jv(frm);
|
__("Journal Entries"),
|
||||||
}, __('Create'));
|
function () {
|
||||||
|
return frm.events.make_jv(frm);
|
||||||
|
},
|
||||||
|
__("Create")
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
validate_rounding_loss: function(frm) {
|
validate_rounding_loss: function (frm) {
|
||||||
let allowance = frm.doc.rounding_loss_allowance;
|
let allowance = frm.doc.rounding_loss_allowance;
|
||||||
if (!(allowance >= 0 && allowance < 1)) {
|
if (!(allowance >= 0 && allowance < 1)) {
|
||||||
frappe.throw(__("Rounding Loss Allowance should be between 0 and 1"));
|
frappe.throw(__("Rounding Loss Allowance should be between 0 and 1"));
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
rounding_loss_allowance: function(frm) {
|
rounding_loss_allowance: function (frm) {
|
||||||
frm.events.validate_rounding_loss(frm);
|
frm.events.validate_rounding_loss(frm);
|
||||||
},
|
},
|
||||||
|
|
||||||
validate: function(frm) {
|
validate: function (frm) {
|
||||||
frm.events.validate_rounding_loss(frm);
|
frm.events.validate_rounding_loss(frm);
|
||||||
},
|
},
|
||||||
|
|
||||||
get_entries: function(frm, account) {
|
get_entries: function (frm, account) {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "get_accounts_data",
|
method: "get_accounts_data",
|
||||||
doc: cur_frm.doc,
|
doc: cur_frm.doc,
|
||||||
account: account,
|
account: account,
|
||||||
callback: function(r){
|
callback: function (r) {
|
||||||
frappe.model.clear_table(frm.doc, "accounts");
|
frappe.model.clear_table(frm.doc, "accounts");
|
||||||
if(r.message) {
|
if (r.message) {
|
||||||
r.message.forEach((d) => {
|
r.message.forEach((d) => {
|
||||||
cur_frm.add_child("accounts",d);
|
cur_frm.add_child("accounts", d);
|
||||||
});
|
});
|
||||||
frm.events.get_total_gain_loss(frm);
|
frm.events.get_total_gain_loss(frm);
|
||||||
refresh_field("accounts");
|
refresh_field("accounts");
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
get_total_gain_loss: function(frm) {
|
get_total_gain_loss: function (frm) {
|
||||||
if(!(frm.doc.accounts && frm.doc.accounts.length)) return;
|
if (!(frm.doc.accounts && frm.doc.accounts.length)) return;
|
||||||
|
|
||||||
let total_gain_loss = 0;
|
let total_gain_loss = 0;
|
||||||
frm.doc.accounts.forEach((d) => {
|
frm.doc.accounts.forEach((d) => {
|
||||||
@@ -80,7 +84,7 @@ frappe.ui.form.on('Exchange Rate Revaluation', {
|
|||||||
frm.refresh_fields();
|
frm.refresh_fields();
|
||||||
},
|
},
|
||||||
|
|
||||||
make_jv : function(frm) {
|
make_jv: function (frm) {
|
||||||
let revaluation_journal = null;
|
let revaluation_journal = null;
|
||||||
let zero_balance_journal = null;
|
let zero_balance_journal = null;
|
||||||
frappe.call({
|
frappe.call({
|
||||||
@@ -88,66 +92,68 @@ frappe.ui.form.on('Exchange Rate Revaluation', {
|
|||||||
doc: frm.doc,
|
doc: frm.doc,
|
||||||
freeze: true,
|
freeze: true,
|
||||||
freeze_message: "Making Journal Entries...",
|
freeze_message: "Making Journal Entries...",
|
||||||
callback: function(r){
|
callback: function (r) {
|
||||||
if (r.message) {
|
if (r.message) {
|
||||||
let response = r.message;
|
let response = r.message;
|
||||||
if(response['revaluation_jv'] || response['zero_balance_jv']) {
|
if (response["revaluation_jv"] || response["zero_balance_jv"]) {
|
||||||
frappe.msgprint(__("Journals have been created"));
|
frappe.msgprint(__("Journals have been created"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
frappe.ui.form.on("Exchange Rate Revaluation Account", {
|
frappe.ui.form.on("Exchange Rate Revaluation Account", {
|
||||||
new_exchange_rate: function(frm, cdt, cdn) {
|
new_exchange_rate: function (frm, cdt, cdn) {
|
||||||
var row = frappe.get_doc(cdt, cdn);
|
var row = frappe.get_doc(cdt, cdn);
|
||||||
row.new_balance_in_base_currency = flt(row.new_exchange_rate * flt(row.balance_in_account_currency),
|
row.new_balance_in_base_currency = flt(
|
||||||
precision("new_balance_in_base_currency", row));
|
row.new_exchange_rate * flt(row.balance_in_account_currency),
|
||||||
|
precision("new_balance_in_base_currency", row)
|
||||||
|
);
|
||||||
row.gain_loss = row.new_balance_in_base_currency - flt(row.balance_in_base_currency);
|
row.gain_loss = row.new_balance_in_base_currency - flt(row.balance_in_base_currency);
|
||||||
refresh_field("accounts");
|
refresh_field("accounts");
|
||||||
frm.events.get_total_gain_loss(frm);
|
frm.events.get_total_gain_loss(frm);
|
||||||
},
|
},
|
||||||
|
|
||||||
account: function(frm, cdt, cdn) {
|
account: function (frm, cdt, cdn) {
|
||||||
var row = locals[cdt][cdn];
|
var row = locals[cdt][cdn];
|
||||||
if (row.account) {
|
if (row.account) {
|
||||||
get_account_details(frm, cdt, cdn);
|
get_account_details(frm, cdt, cdn);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
party: function(frm, cdt, cdn) {
|
party: function (frm, cdt, cdn) {
|
||||||
var row = locals[cdt][cdn];
|
var row = locals[cdt][cdn];
|
||||||
if (row.party && row.account) {
|
if (row.party && row.account) {
|
||||||
get_account_details(frm, cdt, cdn);
|
get_account_details(frm, cdt, cdn);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
accounts_remove: function(frm) {
|
accounts_remove: function (frm) {
|
||||||
frm.events.get_total_gain_loss(frm);
|
frm.events.get_total_gain_loss(frm);
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
var get_account_details = function(frm, cdt, cdn) {
|
var get_account_details = function (frm, cdt, cdn) {
|
||||||
var row = frappe.get_doc(cdt, cdn);
|
var row = frappe.get_doc(cdt, cdn);
|
||||||
if(!frm.doc.company || !frm.doc.posting_date) {
|
if (!frm.doc.company || !frm.doc.posting_date) {
|
||||||
frappe.throw(__("Please select Company and Posting Date to getting entries"));
|
frappe.throw(__("Please select Company and Posting Date to getting entries"));
|
||||||
}
|
}
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "erpnext.accounts.doctype.exchange_rate_revaluation.exchange_rate_revaluation.get_account_details",
|
method: "erpnext.accounts.doctype.exchange_rate_revaluation.exchange_rate_revaluation.get_account_details",
|
||||||
args:{
|
args: {
|
||||||
account: row.account,
|
account: row.account,
|
||||||
company: frm.doc.company,
|
company: frm.doc.company,
|
||||||
posting_date: frm.doc.posting_date,
|
posting_date: frm.doc.posting_date,
|
||||||
party_type: row.party_type,
|
party_type: row.party_type,
|
||||||
party: row.party,
|
party: row.party,
|
||||||
rounding_loss_allowance: frm.doc.rounding_loss_allowance
|
rounding_loss_allowance: frm.doc.rounding_loss_allowance,
|
||||||
},
|
},
|
||||||
callback: function(r){
|
callback: function (r) {
|
||||||
$.extend(row, r.message);
|
$.extend(row, r.message);
|
||||||
refresh_field("accounts");
|
refresh_field("accounts");
|
||||||
frm.events.get_total_gain_loss(frm);
|
frm.events.get_total_gain_loss(frm);
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -44,7 +44,7 @@ class ExchangeRateRevaluation(Document):
|
|||||||
self.set_total_gain_loss()
|
self.set_total_gain_loss()
|
||||||
|
|
||||||
def validate_rounding_loss_allowance(self):
|
def validate_rounding_loss_allowance(self):
|
||||||
if not (self.rounding_loss_allowance >= 0 and self.rounding_loss_allowance < 1):
|
if self.rounding_loss_allowance < 0 or self.rounding_loss_allowance >= 1:
|
||||||
frappe.throw(_("Rounding Loss Allowance should be between 0 and 1"))
|
frappe.throw(_("Rounding Loss Allowance should be between 0 and 1"))
|
||||||
|
|
||||||
def set_total_gain_loss(self):
|
def set_total_gain_loss(self):
|
||||||
|
|||||||
@@ -1,8 +1,6 @@
|
|||||||
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
|
||||||
// For license information, please see license.txt
|
// For license information, please see license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Finance Book', {
|
frappe.ui.form.on("Finance Book", {
|
||||||
refresh: function(frm) {
|
refresh: function (frm) {},
|
||||||
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,17 +1,21 @@
|
|||||||
// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
||||||
// License: GNU General Public License v3. See license.txt
|
// License: GNU General Public License v3. See license.txt
|
||||||
|
|
||||||
frappe.ui.form.on('Fiscal Year', {
|
frappe.ui.form.on("Fiscal Year", {
|
||||||
onload: function(frm) {
|
onload: function (frm) {
|
||||||
if(frm.doc.__islocal) {
|
if (frm.doc.__islocal) {
|
||||||
frm.set_value("year_start_date",
|
frm.set_value(
|
||||||
frappe.datetime.add_days(frappe.defaults.get_default("year_end_date"), 1));
|
"year_start_date",
|
||||||
|
frappe.datetime.add_days(frappe.defaults.get_default("year_end_date"), 1)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
year_start_date: function(frm) {
|
year_start_date: function (frm) {
|
||||||
if (!frm.doc.is_short_year) {
|
if (!frm.doc.is_short_year) {
|
||||||
let year_end_date =
|
let year_end_date = frappe.datetime.add_days(
|
||||||
frappe.datetime.add_days(frappe.datetime.add_months(frm.doc.year_start_date, 12), -1);
|
frappe.datetime.add_months(frm.doc.year_start_date, 12),
|
||||||
|
-1
|
||||||
|
);
|
||||||
frm.set_value("year_end_date", year_end_date);
|
frm.set_value("year_end_date", year_end_date);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
"allow_import": 1,
|
"allow_import": 1,
|
||||||
"autoname": "field:year",
|
"autoname": "field:year",
|
||||||
"creation": "2013-01-22 16:50:25",
|
"creation": "2013-01-22 16:50:25",
|
||||||
"description": "**Fiscal Year** represents a Financial Year. All accounting entries and other major transactions are tracked against **Fiscal Year**.",
|
"description": "Represents a Financial Year. All accounting entries and other major transactions are tracked against the Fiscal Year.",
|
||||||
"doctype": "DocType",
|
"doctype": "DocType",
|
||||||
"document_type": "Setup",
|
"document_type": "Setup",
|
||||||
"engine": "InnoDB",
|
"engine": "InnoDB",
|
||||||
@@ -82,10 +82,11 @@
|
|||||||
"icon": "fa fa-calendar",
|
"icon": "fa fa-calendar",
|
||||||
"idx": 1,
|
"idx": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2020-11-05 12:16:53.081573",
|
"modified": "2024-01-30 12:35:38.645968",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Fiscal Year",
|
"name": "Fiscal Year",
|
||||||
|
"naming_rule": "By fieldname",
|
||||||
"owner": "Administrator",
|
"owner": "Administrator",
|
||||||
"permissions": [
|
"permissions": [
|
||||||
{
|
{
|
||||||
@@ -118,9 +119,18 @@
|
|||||||
{
|
{
|
||||||
"read": 1,
|
"read": 1,
|
||||||
"role": "Employee"
|
"role": "Employee"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"read": 1,
|
||||||
|
"role": "Accounts Manager"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"read": 1,
|
||||||
|
"role": "Stock Manager"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"show_name_in_global_search": 1,
|
"show_name_in_global_search": 1,
|
||||||
"sort_field": "name",
|
"sort_field": "name",
|
||||||
"sort_order": "DESC"
|
"sort_order": "DESC",
|
||||||
|
"states": []
|
||||||
}
|
}
|
||||||
@@ -39,7 +39,7 @@ def test_record_generator():
|
|||||||
]
|
]
|
||||||
|
|
||||||
start = 2012
|
start = 2012
|
||||||
end = now_datetime().year + 5
|
end = now_datetime().year + 25
|
||||||
for year in range(start, end):
|
for year in range(start, end):
|
||||||
test_records.append(
|
test_records.append(
|
||||||
{
|
{
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user