Compare commits
991 Commits
release/re
...
master_sf_
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
39afc99b8f | ||
|
|
b74bc62804 | ||
|
|
94f57629e5 | ||
|
|
e4c845a9f6 | ||
|
|
d239509299 | ||
|
|
457f0aa2ac | ||
|
|
84266364e3 | ||
|
|
ea88d8284a | ||
|
|
d2ec420f57 | ||
|
|
97d33adabd | ||
|
|
c11f3cc66c | ||
|
|
6b4a7e35a9 | ||
|
|
11100c9260 | ||
|
|
941c3ca43a | ||
|
|
05f9528ca9 | ||
|
|
b205945f65 | ||
|
|
c1dc28488a | ||
|
|
547d6608e6 | ||
|
|
dacb3cc076 | ||
|
|
282657fbca | ||
|
|
7e516c6f0b | ||
|
|
34e2a49bef | ||
|
|
ff4bdd2f2d | ||
|
|
b239fdf847 | ||
|
|
47feb4cf3c | ||
|
|
63b732ff42 | ||
|
|
50d63c28d6 | ||
|
|
73b7ff7d1b | ||
|
|
ccdcd01372 | ||
|
|
198296f0f8 | ||
|
|
f122343e31 | ||
|
|
82fa39f1a3 | ||
|
|
841e1b4ce2 | ||
|
|
1ab62d7724 | ||
|
|
28a46d395b | ||
|
|
64c66f1272 | ||
|
|
f8d957486b | ||
|
|
1866607967 | ||
|
|
40efdf6f3b | ||
|
|
f910df3ce5 | ||
|
|
c99c96a9ea | ||
|
|
95cc557577 | ||
|
|
fa78389f47 | ||
|
|
f7381c43aa | ||
|
|
76c5db61da | ||
|
|
88ffc34a68 | ||
|
|
4f65b34aeb | ||
|
|
4a26d18b46 | ||
|
|
664ac8128a | ||
|
|
ce285818cf | ||
|
|
6f7811a843 | ||
|
|
54ed90e892 | ||
|
|
f8060113d9 | ||
|
|
48ab891991 | ||
|
|
7f384c3f56 | ||
|
|
01a2771dfb | ||
|
|
45b6214ddd | ||
|
|
c96ff3f5b4 | ||
|
|
d84758232e | ||
|
|
479953e082 | ||
|
|
27881589d4 | ||
|
|
79ec3f2c91 | ||
|
|
715b4181be | ||
|
|
0ccda10c65 | ||
|
|
5b4376b5f9 | ||
|
|
1050f7616b | ||
|
|
3a9cc0c09c | ||
|
|
4d63b90373 | ||
|
|
43c4614650 | ||
|
|
eba9ccf083 | ||
|
|
947100a9d4 | ||
|
|
ed4924651a | ||
|
|
3cc2bb94fe | ||
|
|
8ecb3eb50a | ||
|
|
819d89c278 | ||
|
|
66d47c60bc | ||
|
|
0340563749 | ||
|
|
271e23a67f | ||
|
|
de42382f58 | ||
|
|
3728809d10 | ||
|
|
d4e2ace8a6 | ||
|
|
1d4188df7e | ||
|
|
a2323293ca | ||
|
|
29bd1c2968 | ||
|
|
6c35ec13fd | ||
|
|
83107b05e2 | ||
|
|
5fb7165306 | ||
|
|
c569b60d5c | ||
|
|
bd2748659a | ||
|
|
3ee233c0bc | ||
|
|
d63081dffa | ||
|
|
0932ec95bf | ||
|
|
7361da0e5d | ||
|
|
2dbddf532c | ||
|
|
eb867e62d8 | ||
|
|
d75504960a | ||
|
|
93efbf742e | ||
|
|
7c3ac138b5 | ||
|
|
63444d3dd1 | ||
|
|
2fcad742b8 | ||
|
|
f341ef5e83 | ||
|
|
d488824e3d | ||
|
|
0c28700f75 | ||
|
|
48d97f3e57 | ||
|
|
ef17c9920c | ||
|
|
ef643a5a72 | ||
|
|
b7ff8d0bd5 | ||
|
|
1e721d68bf | ||
|
|
7454297dcd | ||
|
|
4e0a023c36 | ||
|
|
155c5eb329 | ||
|
|
45718ab925 | ||
|
|
562c8dda8d | ||
|
|
84a37a970f | ||
|
|
37cc02e97a | ||
|
|
7a8753408b | ||
|
|
eb853d0be9 | ||
|
|
52438733d7 | ||
|
|
b986dd8473 | ||
|
|
98fdb581fb | ||
|
|
ea7380288c | ||
|
|
9beecab21d | ||
|
|
2e6932e054 | ||
|
|
5ca9e028d8 | ||
|
|
64e2b71a34 | ||
|
|
8d52c94aed | ||
|
|
9d91a1c99f | ||
|
|
d6fdeafef6 | ||
|
|
371b3a9d65 | ||
|
|
36c1c7b170 | ||
|
|
38d3a7901d | ||
|
|
2223259d13 | ||
|
|
aba270182d | ||
|
|
c9378fc9fe | ||
|
|
378850682d | ||
|
|
02c35803da | ||
|
|
75b60c1ec8 | ||
|
|
2cd4424ba1 | ||
|
|
d52f0aed6e | ||
|
|
d197fc5b9e | ||
|
|
34280fe24b | ||
|
|
fd88a37aec | ||
|
|
0082a308fa | ||
|
|
b5f5826c80 | ||
|
|
5024a9254d | ||
|
|
2a14a630d5 | ||
|
|
ef8ea2599f | ||
|
|
e9ab4270a9 | ||
|
|
a99d651509 | ||
|
|
c54a5b36d4 | ||
|
|
ae844cf203 | ||
|
|
ec66ea76ba | ||
|
|
8643c41193 | ||
|
|
bed0483496 | ||
|
|
a648208656 | ||
|
|
98af6d0530 | ||
|
|
5af1953e04 | ||
|
|
b1a08be57b | ||
|
|
15981aadf1 | ||
|
|
e19cb52e70 | ||
|
|
5269d09d0e | ||
|
|
e7e64720c6 | ||
|
|
a6701a842e | ||
|
|
d697bd13a1 | ||
|
|
6e20a466ce | ||
|
|
dd5c9775fc | ||
|
|
82c274591c | ||
|
|
4f73f57ddf | ||
|
|
269141dfb2 | ||
|
|
cab0e1ce0b | ||
|
|
d4ff7ffaa9 | ||
|
|
d238d09cc3 | ||
|
|
4cee5213bb | ||
|
|
759e4a481d | ||
|
|
1213afe834 | ||
|
|
35fda7106a | ||
|
|
b8baa84270 | ||
|
|
6591e663b6 | ||
|
|
bad5c8d489 | ||
|
|
68f8c94332 | ||
|
|
ddfb233452 | ||
|
|
bbf62d2302 | ||
|
|
17b09c1f6d | ||
|
|
e0fc70ec60 | ||
|
|
4558fc0336 | ||
|
|
4609ec442a | ||
|
|
eb7d9e4168 | ||
|
|
8706e25b0d | ||
|
|
85fea64f49 | ||
|
|
f74215c9f6 | ||
|
|
cc8906980c | ||
|
|
56f1ba0f25 | ||
|
|
0990d73075 | ||
|
|
7d877a0cbb | ||
|
|
e13bad8483 | ||
|
|
22ebb1bbe1 | ||
|
|
bc888d7984 | ||
|
|
c92d4f7868 | ||
|
|
667a2a81fb | ||
|
|
4a22071f94 | ||
|
|
ec2075c874 | ||
|
|
ebc9716019 | ||
|
|
d067c5b8c4 | ||
|
|
72c9c9872e | ||
|
|
2b541fe041 | ||
|
|
f6e371f223 | ||
|
|
0aefe9e656 | ||
|
|
4f8f29e41a | ||
|
|
ffb32c7ce2 | ||
|
|
3cacca80e9 | ||
|
|
a3356fe195 | ||
|
|
3c70e1623e | ||
|
|
51628c081a | ||
|
|
18ebe6bcb4 | ||
|
|
63ac4f2b44 | ||
|
|
1b6ca170c0 | ||
|
|
2966260f51 | ||
|
|
c4069995e0 | ||
|
|
54920982a2 | ||
|
|
f947a3ed58 | ||
|
|
5e86d67316 | ||
|
|
7354a19696 | ||
|
|
78e3d77000 | ||
|
|
47ad2410cf | ||
|
|
fa2eb7b3cf | ||
|
|
0cee6ebd77 | ||
|
|
73f161ffa4 | ||
|
|
ff06d5c3be | ||
|
|
78cb177ac5 | ||
|
|
9601502360 | ||
|
|
739b7e600c | ||
|
|
27da7639b2 | ||
|
|
258e3bdb9f | ||
|
|
7f3e9927d5 | ||
|
|
927f726030 | ||
|
|
7576200fc4 | ||
|
|
4ffb9d636f | ||
|
|
24f0547343 | ||
|
|
402a323673 | ||
|
|
5e1685417f | ||
|
|
9dfe34ce9a | ||
|
|
190d6da217 | ||
|
|
8946b44280 | ||
|
|
f21d085462 | ||
|
|
43f53197c4 | ||
|
|
ac43be1262 | ||
|
|
8bf1c56efd | ||
|
|
d66791dc41 | ||
|
|
ce6b36a77e | ||
|
|
4acae01009 | ||
|
|
213b76a280 | ||
|
|
c675e1d67c | ||
|
|
8a9f6ab34f | ||
|
|
8aca6ce084 | ||
|
|
cb0c093006 | ||
|
|
1e7d7008b4 | ||
|
|
ef453dbc1e | ||
|
|
9f1e635c8d | ||
|
|
92037f3f04 | ||
|
|
4ba0566d27 | ||
|
|
5d870d53f6 | ||
|
|
6a674cdb5b | ||
|
|
fbce132173 | ||
|
|
98e13cba99 | ||
|
|
7ce2f6c797 | ||
|
|
7502792438 | ||
|
|
9efb13cf01 | ||
|
|
b14e263a2e | ||
|
|
6f41ef3047 | ||
|
|
de29f0c938 | ||
|
|
589a24f595 | ||
|
|
85186f94f5 | ||
|
|
ffc363a31c | ||
|
|
a047ad3bb6 | ||
|
|
cc3289c834 | ||
|
|
e1093a3c69 | ||
|
|
ba955ca658 | ||
|
|
946abc5cf7 | ||
|
|
57ea9ed8f4 | ||
|
|
f8a12b1fe3 | ||
|
|
722f6257ae | ||
|
|
ccbe311c58 | ||
|
|
0f6ca0876c | ||
|
|
bb60fd0339 | ||
|
|
eefbd5939b | ||
|
|
7c01196f17 | ||
|
|
4c58f4d7f3 | ||
|
|
c741587341 | ||
|
|
6ad2fa80f1 | ||
|
|
55694ae303 | ||
|
|
8423b12119 | ||
|
|
5a7ba7f87e | ||
|
|
d36da3df24 | ||
|
|
302a5f0cf1 | ||
|
|
b4fef421dd | ||
|
|
5f5e991d33 | ||
|
|
43a49242c5 | ||
|
|
2e5694cd1a | ||
|
|
3c123a07ea | ||
|
|
dec5ddd154 | ||
|
|
22864b9669 | ||
|
|
528fa483a2 | ||
|
|
b5a3815f1f | ||
|
|
1719e0394e | ||
|
|
eae902ee92 | ||
|
|
01c57a8691 | ||
|
|
2808005ce9 | ||
|
|
06c5f65df2 | ||
|
|
e0bad6ed40 | ||
|
|
35c8b9316e | ||
|
|
2ddfbb0dde | ||
|
|
988c4a460d | ||
|
|
c050e2f11a | ||
|
|
95e49c7b0f | ||
|
|
e46a13889e | ||
|
|
335151f6ca | ||
|
|
908e4a3df6 | ||
|
|
6b403f2c1e | ||
|
|
da5e322229 | ||
|
|
4f9ac16a07 | ||
|
|
4342844845 | ||
|
|
8bc68e1edd | ||
|
|
763d64a1ca | ||
|
|
8a10d18f37 | ||
|
|
181f490d47 | ||
|
|
322718d19a | ||
|
|
96eeb1cab7 | ||
|
|
d5c82e4a28 | ||
|
|
436adc5ff6 | ||
|
|
97a5d91fce | ||
|
|
9eee8557c2 | ||
|
|
4394dd023e | ||
|
|
d39bbe4f99 | ||
|
|
b188c8adfe | ||
|
|
ea6fd42b2e | ||
|
|
625499f758 | ||
|
|
0c2d6dd582 | ||
|
|
f6a9c97e7f | ||
|
|
e2d741937e | ||
|
|
9a3404f4b8 | ||
|
|
d000aa095f | ||
|
|
8945801db8 | ||
|
|
40f327ea17 | ||
|
|
44a2604dbd | ||
|
|
0ae7424f04 | ||
|
|
091af92e8d | ||
|
|
3ed338ed64 | ||
|
|
65781570e7 | ||
|
|
e1f7aeaa96 | ||
|
|
a0a580588c | ||
|
|
a2f2a21a4c | ||
|
|
1ddb446bc6 | ||
|
|
dcdc6851b6 | ||
|
|
ece4e56118 | ||
|
|
7cd104c047 | ||
|
|
80a7dd75c8 | ||
|
|
ec2ef752b3 | ||
|
|
57d5c57048 | ||
|
|
9b7c22c35e | ||
|
|
6711f6f6e6 | ||
|
|
7ac7077f8c | ||
|
|
ed20249988 | ||
|
|
dba8d23348 | ||
|
|
ab9062983c | ||
|
|
37493a4688 | ||
|
|
689d149edc | ||
|
|
9b9106c5da | ||
|
|
9a43af98c3 | ||
|
|
1eae92f2b2 | ||
|
|
4560bbc0ed | ||
|
|
2d5ef0aae4 | ||
|
|
f230ad55fb | ||
|
|
096542c8ff | ||
|
|
d123ca5173 | ||
|
|
388929f207 | ||
|
|
29b9223a14 | ||
|
|
cf283377cd | ||
|
|
5f218e69d4 | ||
|
|
7f5fb165de | ||
|
|
eec79d7d3e | ||
|
|
00809d88f6 | ||
|
|
18b0cc6ea0 | ||
|
|
54d9902ae4 | ||
|
|
eff39a39e3 | ||
|
|
005a7bb68e | ||
|
|
afc1701150 | ||
|
|
72eada0639 | ||
|
|
979e8a47ab | ||
|
|
e119a364c1 | ||
|
|
c7b9bbb18d | ||
|
|
3cb3dce247 | ||
|
|
a7e1c89e66 | ||
|
|
ca1060ada5 | ||
|
|
69578ab054 | ||
|
|
511bed47ff | ||
|
|
26a0412649 | ||
|
|
4989ff773c | ||
|
|
04c0d68763 | ||
|
|
589035d42b | ||
|
|
5726d50106 | ||
|
|
6e9c326a52 | ||
|
|
fc1cdf4d0e | ||
|
|
45178ac38b | ||
|
|
09ee1c26b1 | ||
|
|
64180ca57f | ||
|
|
0c052a118c | ||
|
|
cb9fd43f11 | ||
|
|
1dc55c2770 | ||
|
|
0ca6d46a7b | ||
|
|
3624ef4755 | ||
|
|
f07a003f2c | ||
|
|
0ef46407dd | ||
|
|
f7f3c005f8 | ||
|
|
cae5e14587 | ||
|
|
a2990b8f2e | ||
|
|
5121e455d2 | ||
|
|
4a14fa6bf6 | ||
|
|
f251878637 | ||
|
|
9a5aa52801 | ||
|
|
5b3193d3ff | ||
|
|
52befb6233 | ||
|
|
9ce1963d44 | ||
|
|
1b710b205f | ||
|
|
0d253c54c8 | ||
|
|
d2c5fdb509 | ||
|
|
40209958f2 | ||
|
|
778896a670 | ||
|
|
fcacf609e9 | ||
|
|
5cd134758a | ||
|
|
b8f8e90444 | ||
|
|
b50a852f77 | ||
|
|
ea94d74657 | ||
|
|
b5bea1f811 | ||
|
|
8416630593 | ||
|
|
6572ca25fe | ||
|
|
6a7e6ee5c5 | ||
|
|
aff35f2dd4 | ||
|
|
8ead5655cf | ||
|
|
d6b3a5a3f1 | ||
|
|
19d8f6ae73 | ||
|
|
ae8e304d7f | ||
|
|
e154f5b763 | ||
|
|
804bdb60e8 | ||
|
|
302636635c | ||
|
|
c465822774 | ||
|
|
f9063bf3d9 | ||
|
|
ea6fb5e570 | ||
|
|
0e672aef79 | ||
|
|
11ec04de5b | ||
|
|
efe98b5133 | ||
|
|
2d2abfce25 | ||
|
|
821a7a63be | ||
|
|
de221ba67e | ||
|
|
c5bb9a32d0 | ||
|
|
925fc2f2b3 | ||
|
|
41f379ef5f | ||
|
|
acc791978d | ||
|
|
f24c1ab4a5 | ||
|
|
179899e483 | ||
|
|
b8d21b7fa5 | ||
|
|
295f7ecae3 | ||
|
|
d2a76a03d2 | ||
|
|
1e172cb4e3 | ||
|
|
4424cb58f4 | ||
|
|
cd0ea08b21 | ||
|
|
10065e95d3 | ||
|
|
2c06c6f6a1 | ||
|
|
1eeaf2f85d | ||
|
|
aa96e63fff | ||
|
|
7ac09653c3 | ||
|
|
9c3ed0166b | ||
|
|
3c8ce870df | ||
|
|
d8e65a20d5 | ||
|
|
10a622b52d | ||
|
|
c1ffd3f870 | ||
|
|
a98b7456c0 | ||
|
|
7e3d40bd38 | ||
|
|
83d45b6d3f | ||
|
|
fe237dc742 | ||
|
|
35c13dc51c | ||
|
|
08477e4d94 | ||
|
|
069d1f50b0 | ||
|
|
dd60dee22d | ||
|
|
e49362e2e3 | ||
|
|
d5b5231873 | ||
|
|
2b080c1639 | ||
|
|
bd3bfc979e | ||
|
|
5a3233d539 | ||
|
|
3e8f045a40 | ||
|
|
d1fab6aab0 | ||
|
|
a3357e01aa | ||
|
|
c46a148856 | ||
|
|
5794f75f0b | ||
|
|
01d9d4a636 | ||
|
|
2931d6a92d | ||
|
|
5e6ae1ff55 | ||
|
|
d7a0dc578b | ||
|
|
44a11c839f | ||
|
|
9808f49b3d | ||
|
|
b40a87df88 | ||
|
|
72e9443048 | ||
|
|
c6f6927d57 | ||
|
|
ade7588a9c | ||
|
|
281f03670e | ||
|
|
7356e0afb7 | ||
|
|
fcd86e230a | ||
|
|
bf1271a742 | ||
|
|
324ed283c4 | ||
|
|
ebb8007549 | ||
|
|
361f187026 | ||
|
|
b35f444e49 | ||
|
|
9b2a2d644d | ||
|
|
93ca2000a1 | ||
|
|
ca43aa836e | ||
|
|
26ad5b5b3f | ||
|
|
937ea42af3 | ||
|
|
9b957848c2 | ||
|
|
36579d22ac | ||
|
|
e662490cb5 | ||
|
|
038ce8e139 | ||
|
|
e1a4784092 | ||
|
|
6d4d393b9b | ||
|
|
c956b06f57 | ||
|
|
da02d68c12 | ||
|
|
eb9b43dc91 | ||
|
|
ab66e24c9d | ||
|
|
fbbce6332d | ||
|
|
554b86e641 | ||
|
|
54317a529e | ||
|
|
78d00e9157 | ||
|
|
89cb61f244 | ||
|
|
deef246a6d | ||
|
|
9de201705f | ||
|
|
8f8d83d4cb | ||
|
|
c703012ec4 | ||
|
|
f1780181fa | ||
|
|
f5e36f601c | ||
|
|
6c0b84ec43 | ||
|
|
3e438a10ee | ||
|
|
9218633a5e | ||
|
|
c646e70a66 | ||
|
|
40521e06a8 | ||
|
|
7fee98cdee | ||
|
|
4b7c277a25 | ||
|
|
064397b32b | ||
|
|
048155bc9c | ||
|
|
d439c9140d | ||
|
|
296659ebb0 | ||
|
|
a82063d078 | ||
|
|
f17ff2bc57 | ||
|
|
5df3de7dcd | ||
|
|
b37738fbc3 | ||
|
|
79f3dce0ec | ||
|
|
4b87ea3f0e | ||
|
|
098ac0e7e9 | ||
|
|
6825364a2b | ||
|
|
0cac8fbb4f | ||
|
|
dce748c6a7 | ||
|
|
536c766272 | ||
|
|
422edbcb02 | ||
|
|
d13961ff5f | ||
|
|
b603934637 | ||
|
|
62d303168e | ||
|
|
39bc206344 | ||
|
|
715d835633 | ||
|
|
9e356682dc | ||
|
|
5dc392a27b | ||
|
|
3d2c62f5db | ||
|
|
1e3f0d5ee5 | ||
|
|
b26919a40d | ||
|
|
9ffe338532 | ||
|
|
08d333e4e2 | ||
|
|
47c501c6c6 | ||
|
|
335c79e618 | ||
|
|
ba986995ed | ||
|
|
2a45cdd53a | ||
|
|
0cdf37bb50 | ||
|
|
bae2592587 | ||
|
|
c86cc27510 | ||
|
|
2dded43e39 | ||
|
|
eb6e638018 | ||
|
|
f64c21dacd | ||
|
|
426aa78ed4 | ||
|
|
42c65496ff | ||
|
|
e893abd83e | ||
|
|
78e2e7184e | ||
|
|
ce575adc88 | ||
|
|
6668e0ee2f | ||
|
|
647d21dea3 | ||
|
|
0e13e2190e | ||
|
|
7f3d50a130 | ||
|
|
7b2908defa | ||
|
|
a8211171b0 | ||
|
|
c57daa2c52 | ||
|
|
4ed7ecf628 | ||
|
|
8a6ebb331a | ||
|
|
b333e27c51 | ||
|
|
6761851407 | ||
|
|
ada7936d1b | ||
|
|
9c40aa9a7e | ||
|
|
0694541653 | ||
|
|
e4e2dca22c | ||
|
|
e259fd0c05 | ||
|
|
a767c6491f | ||
|
|
6c2045d0c3 | ||
|
|
6fe56605ab | ||
|
|
bf2c7fd3c5 | ||
|
|
54fc91baa2 | ||
|
|
376f2b3079 | ||
|
|
3c50f19e2d | ||
|
|
08622b10b9 | ||
|
|
dc5b68cca0 | ||
|
|
1d399527e0 | ||
|
|
b3bfa69656 | ||
|
|
96e226836e | ||
|
|
062ca66328 | ||
|
|
7ab8269088 | ||
|
|
1241737dea | ||
|
|
813e424ec9 | ||
|
|
8c08893aa1 | ||
|
|
5ad35de76b | ||
|
|
3c8dac799d | ||
|
|
29c1c7a54d | ||
|
|
2c27a9b575 | ||
|
|
0e4b9e44f8 | ||
|
|
a07a1ba268 | ||
|
|
f537fbc597 | ||
|
|
a6b7167f3b | ||
|
|
c4de966dea | ||
|
|
03cfc00be5 | ||
|
|
cc05e8423e | ||
|
|
e78516f73c | ||
|
|
a277bb402e | ||
|
|
e5793638f7 | ||
|
|
9673fd165d | ||
|
|
e92905fe32 | ||
|
|
1b521ae460 | ||
|
|
4e0d8f1c88 | ||
|
|
aecf2121a1 | ||
|
|
e2d7576a5e | ||
|
|
cc13e5cd9a | ||
|
|
271f34a03b | ||
|
|
366e816268 | ||
|
|
1532184008 | ||
|
|
9f180e307d | ||
|
|
f0a4cf1d0f | ||
|
|
6c734eead4 | ||
|
|
f7e4ce416a | ||
|
|
5a60eed5b1 | ||
|
|
bf34de58fc | ||
|
|
cccc2f8493 | ||
|
|
894d3b9ea3 | ||
|
|
0b85f29262 | ||
|
|
9dbea66b73 | ||
|
|
9a7ac4dfa6 | ||
|
|
e6ca4c27ac | ||
|
|
a8560a0684 | ||
|
|
4f74996f24 | ||
|
|
5b26abc203 | ||
|
|
49654f1ff6 | ||
|
|
a9b7f99944 | ||
|
|
34e858ffe4 | ||
|
|
41efe81119 | ||
|
|
7cab8cd287 | ||
|
|
5f9c5961a5 | ||
|
|
a79500d0ad | ||
|
|
4399700c3d | ||
|
|
36fd17b6c7 | ||
|
|
9d52466f61 | ||
|
|
112efccb7c | ||
|
|
45b9177da4 | ||
|
|
745658eff2 | ||
|
|
ce8b0127b8 | ||
|
|
f58fb2ea13 | ||
|
|
d333621c7a | ||
|
|
563023fa3c | ||
|
|
3d2c7425c4 | ||
|
|
aaa19b96fd | ||
|
|
5d8f0f83b2 | ||
|
|
1547a6064f | ||
|
|
55b2daa0a3 | ||
|
|
d469c09f15 | ||
|
|
a03cb31b29 | ||
|
|
d2b20761b5 | ||
|
|
0f47b4b8c3 | ||
|
|
0cfb16b9d9 | ||
|
|
8ec5e05739 | ||
|
|
5393ef686a | ||
|
|
e92c9675b6 | ||
|
|
e6bad80031 | ||
|
|
070890e3b6 | ||
|
|
6e50774b23 | ||
|
|
fc18d34495 | ||
|
|
ed0d57c364 | ||
|
|
3f27ae0f35 | ||
|
|
cec426920b | ||
|
|
09a6255d9c | ||
|
|
d187bb2bba | ||
|
|
0a6cf74bc2 | ||
|
|
c0202330f8 | ||
|
|
1dabdd157e | ||
|
|
36dc8070fa | ||
|
|
a5da18bbc7 | ||
|
|
510e8d49fb | ||
|
|
051273017d | ||
|
|
f49557090a | ||
|
|
d1656278ea | ||
|
|
0675937588 | ||
|
|
c0d006d139 | ||
|
|
2fa47eae27 | ||
|
|
cb2e1ecabe | ||
|
|
9f1233d20e | ||
|
|
a783f7ec7b | ||
|
|
db50253100 | ||
|
|
5f7f905540 | ||
|
|
1c86cc1421 | ||
|
|
1ea6f649f0 | ||
|
|
115a3e0712 | ||
|
|
f0421b873c | ||
|
|
913feea2a9 | ||
|
|
5d36513e59 | ||
|
|
94d6085f92 | ||
|
|
f361106c40 | ||
|
|
a46cd0f515 | ||
|
|
2c6e1a40f5 | ||
|
|
ffb775abb7 | ||
|
|
2c15532c73 | ||
|
|
1980ee2a9a | ||
|
|
bba4e55770 | ||
|
|
a9bbe98e8f | ||
|
|
11e3bbddd8 | ||
|
|
c01dfddfb4 | ||
|
|
50dcc9f7ba | ||
|
|
41a7aea01e | ||
|
|
066b256b0c | ||
|
|
754047bf02 | ||
|
|
f5bf95ab6e | ||
|
|
5ea25fae73 | ||
|
|
c367e39d5f | ||
|
|
dfec70081b | ||
|
|
d0c35695d5 | ||
|
|
95eb6bd18b | ||
|
|
599d2280f5 | ||
|
|
e1397f4b93 | ||
|
|
d49e8779f9 | ||
|
|
71c606974c | ||
|
|
a0ed14aed1 | ||
|
|
be3d4979b7 | ||
|
|
373ce89a2c | ||
|
|
56317ab111 | ||
|
|
683d79a4e3 | ||
|
|
362801f527 | ||
|
|
a81ad08740 | ||
|
|
d2d5702125 | ||
|
|
9c47a6bdba | ||
|
|
f0a887887e | ||
|
|
fffe0a230b | ||
|
|
81dbbf980c | ||
|
|
2600d15e2b | ||
|
|
c60b91c315 | ||
|
|
639dd4e78d | ||
|
|
3c4286319f | ||
|
|
55016918eb | ||
|
|
4236600b39 | ||
|
|
e84842d0a3 | ||
|
|
60df55d71e | ||
|
|
6643684e9b | ||
|
|
f77a1f6167 | ||
|
|
a467aef925 | ||
|
|
b1b805959a | ||
|
|
e602095b50 | ||
|
|
39214e5352 | ||
|
|
ba05827126 | ||
|
|
89bd9533d7 | ||
|
|
fd2228ba59 | ||
|
|
2758817048 | ||
|
|
2e916337e9 | ||
|
|
47b8a0051b | ||
|
|
76e6502afe | ||
|
|
1b96f420ec | ||
|
|
00645364b3 | ||
|
|
fdad5100ae | ||
|
|
8cd03a1040 | ||
|
|
41c2523201 | ||
|
|
22a1ae11a6 | ||
|
|
4939c6d6db | ||
|
|
460670843f | ||
|
|
66caeee1cd | ||
|
|
28041cbef9 | ||
|
|
36a2bcca6e | ||
|
|
fddddf1649 | ||
|
|
3e61e31314 | ||
|
|
549a64b012 | ||
|
|
dbaad85670 | ||
|
|
b731ffba33 | ||
|
|
9048b32405 | ||
|
|
98d2aa756a | ||
|
|
3749872780 | ||
|
|
de8bebc1f9 | ||
|
|
b468ac216c | ||
|
|
05f5b10833 | ||
|
|
8686d93651 | ||
|
|
258e24eb05 | ||
|
|
19c4b99bae | ||
|
|
cc4b58b136 | ||
|
|
33fdd0f051 | ||
|
|
d36250aa48 | ||
|
|
ad43b43beb | ||
|
|
f9ace6da7c | ||
|
|
12b4b418ea | ||
|
|
60b77e09d6 | ||
|
|
891fe257e1 | ||
|
|
6859458db2 | ||
|
|
ca7c3867cd | ||
|
|
4bcf8236ef | ||
|
|
74d557a0fc | ||
|
|
3686c0e070 | ||
|
|
536d7e9e79 | ||
|
|
67e79c5fb8 | ||
|
|
0c3217824e | ||
|
|
9eddfe36d6 | ||
|
|
9655281b67 | ||
|
|
18b584438a | ||
|
|
2deaffb4eb | ||
|
|
709f29185d | ||
|
|
886de3195c | ||
|
|
d9e5ffa68d | ||
|
|
8996297521 | ||
|
|
030a900580 | ||
|
|
0d1cb49cb7 | ||
|
|
4370236edf | ||
|
|
e01209f343 | ||
|
|
b4803f03fa | ||
|
|
c9d4f0667a | ||
|
|
8840e9642d | ||
|
|
96c22a5d46 | ||
|
|
30c823189c | ||
|
|
3ed503391e | ||
|
|
121861863f | ||
|
|
c2c8d63848 | ||
|
|
befe0c2b00 | ||
|
|
44a9ad340b | ||
|
|
55bac0020f | ||
|
|
a5d8e88f1d | ||
|
|
d3124bb9fe | ||
|
|
64fd6ef5dc | ||
|
|
001b2ead57 | ||
|
|
d0be097a9b | ||
|
|
0be8d0fbb2 | ||
|
|
71faa8a835 | ||
|
|
12afc1ef83 | ||
|
|
34624e6592 | ||
|
|
a16effd8db | ||
|
|
f59299d4d5 | ||
|
|
c7cef27ad6 | ||
|
|
b88b0fc38a | ||
|
|
4297d41dda | ||
|
|
3f85d058cc | ||
|
|
680bed9944 | ||
|
|
d3e307d195 | ||
|
|
86a011343d | ||
|
|
fe4bd3834e | ||
|
|
d3992c2a2e | ||
|
|
e62ed636e7 | ||
|
|
f0fdeff699 | ||
|
|
dec85dc92f | ||
|
|
f4f9591f35 | ||
|
|
efb7334486 | ||
|
|
b9c1224442 | ||
|
|
ca1a3ff120 | ||
|
|
da8e543819 | ||
|
|
eb236fea11 | ||
|
|
1d271d9167 | ||
|
|
c5cf614645 | ||
|
|
167c280fa4 | ||
|
|
69157a7b1f | ||
|
|
2939e6bf82 | ||
|
|
96bbf3a677 | ||
|
|
e3580d9ac8 | ||
|
|
ded1789813 | ||
|
|
759f947fa7 | ||
|
|
302aed16ec | ||
|
|
7d1db793b1 | ||
|
|
83396f5434 | ||
|
|
fe9baf08f0 | ||
|
|
b47cd0cdfe | ||
|
|
251e289fd1 | ||
|
|
1d4ecb9895 | ||
|
|
f3a7dcc6a4 | ||
|
|
ebd56eb5e0 | ||
|
|
4f99a162b5 | ||
|
|
28843b0733 | ||
|
|
8a0c968b10 | ||
|
|
ef1c7b6b25 | ||
|
|
03fe730c50 | ||
|
|
a0d3b40548 | ||
|
|
dfba055019 | ||
|
|
9d3c4f8163 | ||
|
|
08831812ae | ||
|
|
8b75658787 | ||
|
|
25ac346cb7 | ||
|
|
2d15782228 | ||
|
|
856237c4cb | ||
|
|
a47c751b04 | ||
|
|
9bec39f4e6 | ||
|
|
33bf88968c | ||
|
|
7163e025d2 | ||
|
|
11ec448e81 | ||
|
|
6c2fb043c4 | ||
|
|
1dcecea3d5 | ||
|
|
88f3ac3d4e | ||
|
|
983618d798 | ||
|
|
7a9c0ff163 | ||
|
|
77f7602b23 | ||
|
|
70b8521b90 | ||
|
|
1b89642dae | ||
|
|
1968ee17cb | ||
|
|
5e83fb382f | ||
|
|
974671ee07 | ||
|
|
d8b4797ffe | ||
|
|
b07e7707c7 | ||
|
|
8726f8cac3 | ||
|
|
cb7960387b | ||
|
|
6eaf92b841 | ||
|
|
ec0b5e88b6 | ||
|
|
f1b8ee41bc | ||
|
|
97c0b95e2d | ||
|
|
7ac342bfd4 | ||
|
|
6c820ead44 | ||
|
|
c536dde2cc | ||
|
|
801ff9e076 | ||
|
|
d0e049e881 | ||
|
|
81158e2fb4 | ||
|
|
3404cccdc8 | ||
|
|
45bb78d7e9 | ||
|
|
83334e2915 | ||
|
|
d4c30f645b | ||
|
|
bd642812a9 | ||
|
|
3eca74518a | ||
|
|
37977be862 | ||
|
|
a0bd214118 | ||
|
|
7885794322 | ||
|
|
7152b54017 | ||
|
|
0fef714d61 | ||
|
|
6a2ff72dce | ||
|
|
3094379e86 | ||
|
|
77815c45a0 | ||
|
|
dd7c69ce1b | ||
|
|
e02f792300 | ||
|
|
9aca786522 | ||
|
|
134e23ea2f | ||
|
|
129f8a4d7d | ||
|
|
79e3006cdb | ||
|
|
6b140fe6dd | ||
|
|
7533d23d3e | ||
|
|
e8512b23e4 | ||
|
|
b582bfbafa | ||
|
|
11907d4c5e | ||
|
|
ed4903b6f1 | ||
|
|
b383a6d229 | ||
|
|
27eb959a2a | ||
|
|
1672a3982e | ||
|
|
40f8392bd3 | ||
|
|
1c8644983b | ||
|
|
566d9fce9c | ||
|
|
b071b14bbd | ||
|
|
9d95442720 | ||
|
|
fd225fa0e1 | ||
|
|
52fa229896 | ||
|
|
937efa5f0f | ||
|
|
87153fab3f | ||
|
|
21c33bb662 | ||
|
|
b0da7977f5 | ||
|
|
ae6764495e | ||
|
|
869e3e4b4f | ||
|
|
050e82673a | ||
|
|
1210625cfc | ||
|
|
804b401a87 | ||
|
|
a7a8e73616 | ||
|
|
d60fefb2ec | ||
|
|
4a86871039 | ||
|
|
93c3548b40 | ||
|
|
396084a498 | ||
|
|
73cc244994 | ||
|
|
fa6303bbef | ||
|
|
5ca555c520 | ||
|
|
487f6c2054 | ||
|
|
cbc8a41984 | ||
|
|
025ad213d6 | ||
|
|
0b267cc88a | ||
|
|
5be5e8b3ec |
4
jikimo_account_process/__init__.py
Normal file
4
jikimo_account_process/__init__.py
Normal file
@@ -0,0 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import controllers
|
||||
from . import models
|
||||
35
jikimo_account_process/__manifest__.py
Normal file
35
jikimo_account_process/__manifest__.py
Normal file
@@ -0,0 +1,35 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
{
|
||||
'name': "jikimo_account_process",
|
||||
|
||||
'summary': """
|
||||
Short (1 phrase/line) summary of the module's purpose, used as
|
||||
subtitle on modules listing or apps.openerp.com""",
|
||||
|
||||
'description': """
|
||||
Long description of module's purpose
|
||||
""",
|
||||
|
||||
'author': "My Company",
|
||||
'website': "https://www.yourcompany.com",
|
||||
|
||||
# Categories can be used to filter modules in modules listing
|
||||
# Check https://github.com/odoo/odoo/blob/16.0/odoo/addons/base/data/ir_module_category_data.xml
|
||||
# for the full list
|
||||
'category': 'Uncategorized',
|
||||
'version': '0.1',
|
||||
|
||||
# any module necessary for this one to work correctly
|
||||
'depends': ['base', 'account'],
|
||||
|
||||
# always loaded
|
||||
'data': [
|
||||
# 'security/ir.model.access.csv',
|
||||
# 'views/views.xml',
|
||||
# 'views/templates.xml',
|
||||
],
|
||||
# only loaded in demonstration mode
|
||||
'demo': [
|
||||
# 'demo/demo.xml',
|
||||
],
|
||||
}
|
||||
3
jikimo_account_process/controllers/__init__.py
Normal file
3
jikimo_account_process/controllers/__init__.py
Normal file
@@ -0,0 +1,3 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import controllers
|
||||
21
jikimo_account_process/controllers/controllers.py
Normal file
21
jikimo_account_process/controllers/controllers.py
Normal file
@@ -0,0 +1,21 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# from odoo import http
|
||||
|
||||
|
||||
# class JikimoAccountProcess(http.Controller):
|
||||
# @http.route('/jikimo_account_process/jikimo_account_process', auth='public')
|
||||
# def index(self, **kw):
|
||||
# return "Hello, world"
|
||||
|
||||
# @http.route('/jikimo_account_process/jikimo_account_process/objects', auth='public')
|
||||
# def list(self, **kw):
|
||||
# return http.request.render('jikimo_account_process.listing', {
|
||||
# 'root': '/jikimo_account_process/jikimo_account_process',
|
||||
# 'objects': http.request.env['jikimo_account_process.jikimo_account_process'].search([]),
|
||||
# })
|
||||
|
||||
# @http.route('/jikimo_account_process/jikimo_account_process/objects/<model("jikimo_account_process.jikimo_account_process"):obj>', auth='public')
|
||||
# def object(self, obj, **kw):
|
||||
# return http.request.render('jikimo_account_process.object', {
|
||||
# 'object': obj
|
||||
# })
|
||||
4
jikimo_account_process/models/__init__.py
Normal file
4
jikimo_account_process/models/__init__.py
Normal file
@@ -0,0 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import models
|
||||
from . import account_move
|
||||
15
jikimo_account_process/models/account_move.py
Normal file
15
jikimo_account_process/models/account_move.py
Normal file
@@ -0,0 +1,15 @@
|
||||
from odoo import models, fields, api
|
||||
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
|
||||
class CustomAccountMoveLine(models.Model):
|
||||
_inherit = 'account.move'
|
||||
_description = "account move line"
|
||||
|
||||
@api.model_create_multi
|
||||
def create(self, vals):
|
||||
for val in vals:
|
||||
val['name'] = self.env['ir.sequence'].next_by_code('account.move') or '/'
|
||||
# 因为供应商与客户支付创建流程是先创建move line在修改来填充account_payment与move line的关联
|
||||
return super(CustomAccountMoveLine, self).create(vals)
|
||||
18
jikimo_account_process/models/models.py
Normal file
18
jikimo_account_process/models/models.py
Normal file
@@ -0,0 +1,18 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# from odoo import models, fields, api
|
||||
|
||||
|
||||
# class jikimo_account_process(models.Model):
|
||||
# _name = 'jikimo_account_process.jikimo_account_process'
|
||||
# _description = 'jikimo_account_process.jikimo_account_process'
|
||||
|
||||
# name = fields.Char()
|
||||
# value = fields.Integer()
|
||||
# value2 = fields.Float(compute="_value_pc", store=True)
|
||||
# description = fields.Text()
|
||||
#
|
||||
# @api.depends('value')
|
||||
# def _value_pc(self):
|
||||
# for record in self:
|
||||
# record.value2 = float(record.value) / 100
|
||||
@@ -6,6 +6,6 @@ import { patch } from "web.utils";
|
||||
patch(WebClient.prototype, "kolpolok_custom_title_and_favicon.WebClient", {
|
||||
setup() {
|
||||
this._super();
|
||||
this.title.setParts({ zopenerp: "JIKIMO" });
|
||||
// this.title.setParts({ zopenerp: "JIKIMO" });
|
||||
},
|
||||
});
|
||||
@@ -5,7 +5,7 @@ import {patch} from '@web/core/utils/patch';
|
||||
import {_t} from "@web/core/l10n/translation";
|
||||
import {FormStatusIndicator} from "@web/views/form/form_status_indicator/form_status_indicator";
|
||||
import {ListRenderer} from "@web/views/list/list_renderer";
|
||||
import {StatusBarField} from "@web/views/fields/statusbar/statusbar_field";
|
||||
// import {StatusBarField} from "@web/views/fields/statusbar/statusbar_field";
|
||||
|
||||
import {Field} from "@web/views/fields/field";
|
||||
|
||||
@@ -53,6 +53,23 @@ const tableRequiredList = [
|
||||
]
|
||||
|
||||
patch(FormStatusIndicator.prototype, 'jikimo_frontend.FormStatusIndicator', {
|
||||
setup() {
|
||||
owl.onMounted(() => {
|
||||
try {
|
||||
const dom = this.__owl__.bdom.el
|
||||
const buttonsDom = $(dom).find('.o_form_status_indicator_buttons ')
|
||||
if (buttonsDom) {
|
||||
const dom1 = buttonsDom.children('.o_form_button_save')
|
||||
const dom2 = buttonsDom.children('.o_form_button_cancel')
|
||||
dom1.append('保存')
|
||||
dom2.append('取消')
|
||||
}
|
||||
} catch (e) {
|
||||
console.log(e)
|
||||
}
|
||||
|
||||
});
|
||||
},
|
||||
// 你可以重写或者添加一些方法和属性
|
||||
async _onDiscardChanges() {
|
||||
// var self = this;
|
||||
@@ -153,47 +170,36 @@ patch(ListRenderer.prototype, 'jikimo_frontend.ListRenderer', {
|
||||
|
||||
|
||||
// 根据进度条设置水印
|
||||
const statusbar_params = {
|
||||
'已完工': 'bg-primary',
|
||||
'完成': 'bg-primary',
|
||||
'采购订单': 'bg-primary',
|
||||
'作废': 'bg-danger',
|
||||
'封存(报废)': 'bg-danger',
|
||||
}
|
||||
patch(StatusBarField.prototype, 'jikimo_frontend.StatusBarField', {
|
||||
setup() {
|
||||
owl.onMounted(this.ribbons);
|
||||
return this._super(...arguments);
|
||||
},
|
||||
ribbons() {
|
||||
try {
|
||||
const dom = $('.o_form_sheet.position-relative')
|
||||
const status = statusbar_params[this.currentName]
|
||||
if(status && dom.length) {
|
||||
dom.prepend(`<div class="o_widget o_widget_web_ribbon">
|
||||
<div class="ribbon ribbon-top-right">
|
||||
<span class="bg-opacity-75 ${status}" title="">${this.currentName}</span>
|
||||
</div>
|
||||
</div>`)
|
||||
}
|
||||
} catch (e) {
|
||||
console.log(e)
|
||||
}
|
||||
}
|
||||
})
|
||||
// const statusbar_params = {
|
||||
// '已完工': 'bg-primary',
|
||||
// '完成': 'bg-primary',
|
||||
// '采购订单': 'bg-primary',
|
||||
// '作废': 'bg-danger',
|
||||
// '封存(报废)': 'bg-danger',
|
||||
// }
|
||||
// patch(StatusBarField.prototype, 'jikimo_frontend.StatusBarField', {
|
||||
// setup() {
|
||||
// owl.onMounted(this.ribbons);
|
||||
// return this._super(...arguments);
|
||||
// },
|
||||
// ribbons() {
|
||||
// try {
|
||||
// const dom = $('.o_form_sheet.position-relative')
|
||||
// const status = statusbar_params[this.currentName]
|
||||
// if(status && dom.length) {
|
||||
// dom.prepend(`<div class="o_widget o_widget_web_ribbon">
|
||||
// <div class="ribbon ribbon-top-right">
|
||||
// <span class="bg-opacity-75 ${status}" title="">${this.currentName}</span>
|
||||
// </div>
|
||||
// </div>`)
|
||||
// }
|
||||
// } catch (e) {
|
||||
// console.log(e)
|
||||
// }
|
||||
// }
|
||||
// })
|
||||
|
||||
$(function () {
|
||||
document.addEventListener('click', function () {
|
||||
const dom = $('.o_form_status_indicator_buttons ')
|
||||
if (dom) {
|
||||
const dom1 = dom.children().eq(0)
|
||||
const dom2 = dom.children().eq(1)
|
||||
if (!dom1.text()) {
|
||||
dom1.append('保存')
|
||||
dom2.append('取消')
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
function customRequired() {
|
||||
let timer = null
|
||||
|
||||
@@ -530,4 +530,5 @@ div:has(.o_required_modifier) > label::before {
|
||||
// 修复表格内容覆盖表头bug
|
||||
.o_list_renderer .o_list_table tbody th {
|
||||
position: unset;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -5,9 +5,9 @@
|
||||
<!-- 修改页面头部图标及文字 -->
|
||||
<template id="favicon_icon" inherit_id="web.layout" name="Web layout">
|
||||
<!-- change the title with reliance partner -->
|
||||
<xpath expr="//head//title" position="before">
|
||||
<!-- <xpath expr="//head//title" position="before">
|
||||
<title t-esc="'JIKIMO'"/>
|
||||
</xpath>
|
||||
</xpath> -->
|
||||
<!-- change the default favicon icon with -->
|
||||
<xpath expr="//head//link[@rel='shortcut icon']" position="replace">
|
||||
<link type="image/x-icon" rel="shortcut icon" href="/jikimo_frontend/static/src/img/jikimo-logo.ico"/>
|
||||
@@ -16,7 +16,7 @@
|
||||
|
||||
<!-- hide 登录页面 powerd by odoo 及管理数据库 -->
|
||||
<template id="login_page_layout" inherit_id="web.login_layout" name="Login Page Layout">
|
||||
<xpath expr="//div[@class='card-body']//div[last()]" position="replace"></xpath>
|
||||
<!-- <xpath expr="//div[@class='card-body']/div[last()]" position="replace"></xpath> -->
|
||||
</template>
|
||||
|
||||
<!-- 隐藏odoo版本信息 -->
|
||||
|
||||
@@ -324,4 +324,4 @@ def unlink(self):
|
||||
|
||||
|
||||
BaseModel._create = _create
|
||||
BaseModel.unlink = unlink
|
||||
# BaseModel.unlink = unlink
|
||||
5
jikimo_system_order/__init__.py
Normal file
5
jikimo_system_order/__init__.py
Normal file
@@ -0,0 +1,5 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import controllers
|
||||
from . import models
|
||||
from . import wizard
|
||||
39
jikimo_system_order/__manifest__.py
Normal file
39
jikimo_system_order/__manifest__.py
Normal file
@@ -0,0 +1,39 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
{
|
||||
'name': "jikimo_system_order",
|
||||
|
||||
'summary': """
|
||||
系统工单""",
|
||||
|
||||
'description': """
|
||||
用于处理针对系统的工作任务;
|
||||
员工可以通过系统工单发起申请,由维护人员处理以后,填写处理结果。
|
||||
""",
|
||||
|
||||
'author': "机企猫",
|
||||
'website': "http://www.jikimo.com",
|
||||
|
||||
# Categories can be used to filter modules in modules listing
|
||||
# Check https://github.com/odoo/odoo/blob/master/odoo/addons/base/module/module_data.xml
|
||||
# for the full list
|
||||
'category': 'Uncategorized',
|
||||
'version': '0.1',
|
||||
|
||||
# any module necessary for this one to work correctly
|
||||
'depends': ['base','mail'],
|
||||
|
||||
# always loaded
|
||||
'data': [
|
||||
'security/account_security.xml',
|
||||
'security/ir.model.access.csv',
|
||||
'wizard/order_wizard.xml',
|
||||
'views/notice_user_config.xml',
|
||||
'views/yizuo_system_order_view.xml',
|
||||
'views/work_order_number.xml',
|
||||
'views/res_config_settings_views.xml',
|
||||
],
|
||||
# only loaded in demonstration mode
|
||||
'demo': [
|
||||
'demo/demo.xml',
|
||||
],
|
||||
}
|
||||
3
jikimo_system_order/controllers/__init__.py
Normal file
3
jikimo_system_order/controllers/__init__.py
Normal file
@@ -0,0 +1,3 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import controllers
|
||||
20
jikimo_system_order/controllers/controllers.py
Normal file
20
jikimo_system_order/controllers/controllers.py
Normal file
@@ -0,0 +1,20 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
from odoo import http
|
||||
|
||||
# class TopSystemOrder(http.Controller):
|
||||
# @http.route('/jikimo_system_order/jikimo_system_order/', auth='public')
|
||||
# def index(self, **kw):
|
||||
# return "Hello, world"
|
||||
|
||||
# @http.route('/jikimo_system_order/jikimo_system_order/objects/', auth='public')
|
||||
# def list(self, **kw):
|
||||
# return http.request.render('jikimo_system_order.listing', {
|
||||
# 'root': '/jikimo_system_order/jikimo_system_order',
|
||||
# 'objects': http.request.env['jikimo_system_order.jikimo_system_order'].search([]),
|
||||
# })
|
||||
|
||||
# @http.route('/jikimo_system_order/jikimo_system_order/objects/<model("jikimo_system_order.jikimo_system_order"):obj>/', auth='public')
|
||||
# def object(self, obj, **kw):
|
||||
# return http.request.render('jikimo_system_order.object', {
|
||||
# 'object': obj
|
||||
# })
|
||||
30
jikimo_system_order/demo/demo.xml
Normal file
30
jikimo_system_order/demo/demo.xml
Normal file
@@ -0,0 +1,30 @@
|
||||
<odoo>
|
||||
<data>
|
||||
<!-- -->
|
||||
<!-- <record id="object0" model="jikimo_system_order.jikimo_system_order"> -->
|
||||
<!-- <field name="name">Object 0</field> -->
|
||||
<!-- <field name="value">0</field> -->
|
||||
<!-- </record> -->
|
||||
<!-- -->
|
||||
<!-- <record id="object1" model="jikimo_system_order.jikimo_system_order"> -->
|
||||
<!-- <field name="name">Object 1</field> -->
|
||||
<!-- <field name="value">10</field> -->
|
||||
<!-- </record> -->
|
||||
<!-- -->
|
||||
<!-- <record id="object2" model="jikimo_system_order.jikimo_system_order"> -->
|
||||
<!-- <field name="name">Object 2</field> -->
|
||||
<!-- <field name="value">20</field> -->
|
||||
<!-- </record> -->
|
||||
<!-- -->
|
||||
<!-- <record id="object3" model="jikimo_system_order.jikimo_system_order"> -->
|
||||
<!-- <field name="name">Object 3</field> -->
|
||||
<!-- <field name="value">30</field> -->
|
||||
<!-- </record> -->
|
||||
<!-- -->
|
||||
<!-- <record id="object4" model="jikimo_system_order.jikimo_system_order"> -->
|
||||
<!-- <field name="name">Object 4</field> -->
|
||||
<!-- <field name="value">40</field> -->
|
||||
<!-- </record> -->
|
||||
<!-- -->
|
||||
</data>
|
||||
</odoo>
|
||||
7
jikimo_system_order/models/__init__.py
Normal file
7
jikimo_system_order/models/__init__.py
Normal file
@@ -0,0 +1,7 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import constant
|
||||
from . import order_classify
|
||||
from . import system_work_order
|
||||
from . import work_order_template
|
||||
from . import res_config_setting
|
||||
7
jikimo_system_order/models/constant.py
Normal file
7
jikimo_system_order/models/constant.py
Normal file
@@ -0,0 +1,7 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# 工单状态
|
||||
STATE_SELECTION = [('draft', u'草稿'), ('unconfirmed', u'待确认'), ('pending', u'待处理'),
|
||||
('processed', u'已处理待评分'), ('completed', u'已完成'), ('closed', u'已关闭')]
|
||||
|
||||
GRADE = [('1', '1非常不满意'), ('2', '2不满意'), ('3', '3一般'), ('4', '4满意'), ('5', '5非常满意')]
|
||||
25
jikimo_system_order/models/order_classify.py
Normal file
25
jikimo_system_order/models/order_classify.py
Normal file
@@ -0,0 +1,25 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from odoo import models, fields, api
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
|
||||
class OrderClassify(models.Model):
|
||||
_name = 'order.classify'
|
||||
_order = 'sequence, name'
|
||||
|
||||
|
||||
@api.constrains('name')
|
||||
def check_base_name(self):
|
||||
"""类型名称唯一"""
|
||||
name_obj = self.env['order.classify'].search([('name', '=', self.name)])
|
||||
if len(name_obj) >= 2:
|
||||
raise ValidationError(u'该类型已存在')
|
||||
|
||||
# 名称
|
||||
name = fields.Char(string=u'名称', size=20)
|
||||
# 排序
|
||||
sequence = fields.Integer(default=10)
|
||||
# 是否有效
|
||||
state = fields.Boolean(default=True, string='是否有效')
|
||||
|
||||
32
jikimo_system_order/models/res_config_setting.py
Normal file
32
jikimo_system_order/models/res_config_setting.py
Normal file
@@ -0,0 +1,32 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
import logging
|
||||
from odoo import api, fields, models, _
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class ResModelWeConfigSettings(models.TransientModel):
|
||||
_inherit = 'res.config.settings'
|
||||
|
||||
lost_agent_id = fields.Char('企微通知应用ID')
|
||||
|
||||
@api.model
|
||||
def get_values(self):
|
||||
"""
|
||||
重载获取参数的方法,参数都存在系统参数中
|
||||
:return:
|
||||
"""
|
||||
values = super(ResModelWeConfigSettings, self).get_values()
|
||||
config = self.env['ir.config_parameter'].sudo()
|
||||
lost_agent_id = config.get_param('lost_agent_id', default='')
|
||||
values.update(
|
||||
lost_agent_id=lost_agent_id,
|
||||
)
|
||||
return values
|
||||
|
||||
def set_values(self):
|
||||
super(ResModelWeConfigSettings, self).set_values()
|
||||
ir_config = self.env['ir.config_parameter'].sudo()
|
||||
ir_config.set_param("lost_agent_id", self.lost_agent_id or "")
|
||||
|
||||
183
jikimo_system_order/models/system_work_order.py
Normal file
183
jikimo_system_order/models/system_work_order.py
Normal file
@@ -0,0 +1,183 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from odoo import models, fields, api
|
||||
from odoo.exceptions import ValidationError
|
||||
from odoo import exceptions
|
||||
from .constant import STATE_SELECTION, GRADE
|
||||
import datetime
|
||||
import logging
|
||||
|
||||
|
||||
class SystemWorkOrder(models.Model):
|
||||
_name = 'system.work.order'
|
||||
_inherit = ['mail.thread', 'mail.activity.mixin']
|
||||
_order = 'date desc'
|
||||
_description = u'系统工单'
|
||||
_rec_name = 'order_number'
|
||||
|
||||
def get_is_technicist(self):
|
||||
self._cr.execute(
|
||||
"select u.id from res_users u left join res_groups_users_rel r on r.uid = u.id where r.gid in (select g.id from res_groups g where g.name = '技术员权限') and u.id ='%s'",
|
||||
(self.env.user.id,))
|
||||
hr = self._cr.dictfetchall()
|
||||
if len(hr) > 0:
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
|
||||
# def get_user_department_id(self):
|
||||
# """根据用户id系统员工id"""
|
||||
# employee = self.env['hr.employee'].sudo().search([('user_id', '=', self.env.uid)], limit=1)
|
||||
# if employee:
|
||||
# if len(employee) > 0:
|
||||
# if not employee.department_id:
|
||||
# raise exceptions.Warning(u'您当前使用的用户没有所属部门')
|
||||
# return employee.department_id
|
||||
# else:
|
||||
# return False
|
||||
# else:
|
||||
# raise exceptions.Warning(u'您当前使用的用户没有关联员工')
|
||||
|
||||
@api.onchange('order_template_id')
|
||||
def get_title(self):
|
||||
"""选择模板自动填充"""
|
||||
if self.order_template_id:
|
||||
self.title = self.order_template_id.title_template
|
||||
self.text = self.order_template_id.text_template
|
||||
|
||||
# 工单编号
|
||||
order_number = fields.Char(string=u'工单编号', default='/')
|
||||
# 紧急程度
|
||||
urgency_degree = fields.Selection([('0', u'0星'), ('1', u'一星'), ('2', u'二星'), ('3', u'三星'), ('4', u'四星'),
|
||||
('5', u'五星')], string=u'紧急程度', help='五星为最紧急!', default='5')
|
||||
# 工单分类(可以配置,并调整优先级)
|
||||
order_type = fields.Many2one('order.classify', string=u'工单分类', domain=[('state', '=', True)])
|
||||
# 发起人所属公司(res.company)
|
||||
initiator_company_id = fields.Many2one('res.company', string=u'发起人所属公司', default=lambda self: self.env.user.company_id)
|
||||
# 发起人部门(hr.department)
|
||||
# initiator_department_id = fields.Many2one('hr.department', string=u'发起人部门', default=get_user_department_id)
|
||||
# 发起人(hr.employee)
|
||||
initiator_id = fields.Many2one('res.users', string=u'发起人', default=lambda self: self.env.user)
|
||||
# 发起时间
|
||||
date = fields.Datetime(string=u'发起时间', default=lambda self: fields.datetime.now())
|
||||
# 确认人
|
||||
confirm_id = fields.Many2one('res.users', string=u'确认人')
|
||||
# 确认日期
|
||||
confirmation_date = fields.Datetime(string=u'确认时间')
|
||||
# 模板
|
||||
order_template_id = fields.Many2one('work.order.template', string=u'模板', domain=[('state', '=', True)])
|
||||
# 标题
|
||||
title = fields.Char(string=u'标题')
|
||||
# 正文
|
||||
text = fields.Html(string=u'正文')
|
||||
# 状态[草稿\待确认\待处理\已处理\已关闭]
|
||||
state = fields.Selection(STATE_SELECTION, default='draft', string=u'状态')
|
||||
# 关闭原因
|
||||
close_cause = fields.Text(string=u'关闭问题原因')
|
||||
# 关闭时间
|
||||
close_time = fields.Datetime(string=u'关闭问题时间')
|
||||
# 关闭人
|
||||
close_user_id = fields.Many2one('res.users', string=u'关闭人')
|
||||
# 解决人
|
||||
solve_people_id = fields.Many2one('res.users', string=u'解决人')
|
||||
# 用户实际问题
|
||||
users_problem = fields.Text(string=u'用户实际问题')
|
||||
# 最终解决方案
|
||||
solution = fields.Text(string=u'最终解决方案')
|
||||
# 判断是否为技术人员
|
||||
# is_technicist = fields.Boolean(string=u'是否为技术人员', default=get_is_technicist)
|
||||
# 打分
|
||||
grade = fields.Selection(GRADE, string=u'评分')
|
||||
# 评价按钮的显示
|
||||
is_display = fields.Boolean('控制显示评价按钮', compute='compute_is_display')
|
||||
|
||||
def compute_is_display(self):
|
||||
for item in self:
|
||||
if item.state == 'processed' and self.env.user.id == item.initiator_id.id:
|
||||
item.is_display = True
|
||||
else:
|
||||
item.is_display = False
|
||||
|
||||
@api.onchange('order_type')
|
||||
def _onchange_order_type(self):
|
||||
self.order_template_id = None
|
||||
self.title = None
|
||||
self.text = None
|
||||
|
||||
@api.model
|
||||
def create(self, vals):
|
||||
# 创建编号
|
||||
if vals.get('order_number', '/') == '/':
|
||||
vals['order_number'] = self.env['ir.sequence'].get('system.work.order') or '/'
|
||||
return super(SystemWorkOrder, self).create(vals)
|
||||
|
||||
def do_draft(self, order=None):
|
||||
"""状态草稿"""
|
||||
bill = self
|
||||
if order:
|
||||
bill = order
|
||||
if bill.state == 'unconfirmed':
|
||||
state_remark = u'待确认 --> 草稿'
|
||||
# bill.message_post(u'操作人:%s,操作时间:%s,状态变更过程:%s' % (self.env.user.name,
|
||||
# (datetime.datetime.now() + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M:%S'), state_remark))
|
||||
bill.state = 'draft'
|
||||
|
||||
def do_unconfirmed(self):
|
||||
"""状态待确认"""
|
||||
if self.state == 'draft':
|
||||
state_remark = u'草稿 --> 待确认'
|
||||
# self.message_post(u'操作人:%s,操作时间:%s,状态变更过程:%s' % (
|
||||
# self.env.user.name,
|
||||
# (datetime.datetime.now() + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M:%S'), state_remark))
|
||||
self.state = 'unconfirmed'
|
||||
# 获取通知人
|
||||
objs = self.env['system.order.notice'].search([])
|
||||
user_ids = objs.notice_user_ids.filtered(lambda item: item.we_employee_id not in ['', False])
|
||||
we_employee_ids = user_ids.mapped('we_employee_id')
|
||||
lost_agent_id = self.env['ir.config_parameter'].sudo().get_param('lost_agent_id')
|
||||
wechat = self.env['we.config'].sudo().get_wechat(agent_id=lost_agent_id)
|
||||
# agent_id, user_ids, content
|
||||
content = """您有一张工单<font color=\"warning\">待处理</font>:**工单标题:{2}**
|
||||
>创建人:{1}
|
||||
>提交时间:{3}
|
||||
>紧急程度:{0}星
|
||||
请查看工单消息,并及时处理!
|
||||
""".format(self.urgency_degree,
|
||||
self.initiator_id.name, self.title, (self.date + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M'))
|
||||
for we_employee_id in we_employee_ids:
|
||||
try:
|
||||
wechat.message.send_markdown(agent_id=lost_agent_id, user_ids=we_employee_id, content=content)
|
||||
except Exception as e:
|
||||
logging.error('工单处理发送消息异常%s' % str(e))
|
||||
|
||||
return True
|
||||
|
||||
def do_pending(self):
|
||||
"""状态待处理"""
|
||||
if self.state == 'unconfirmed':
|
||||
state_remark = u'待确认 --> 待处理'
|
||||
# self.message_post(u'操作人:%s,操作时间:%s,状态变更过程:%s' % (
|
||||
# self.env.user.name,
|
||||
# (datetime.datetime.now() + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M:%S'), state_remark))
|
||||
self.state = 'pending'
|
||||
self.confirm_id = self.env.user
|
||||
self.confirmation_date = fields.datetime.now()
|
||||
return True
|
||||
|
||||
def urned_off(self):
|
||||
"""状态关闭"""
|
||||
if self.close_cause:
|
||||
self.state = 'closed'
|
||||
self.close_time = fields.datetime.now()
|
||||
else:
|
||||
raise ValidationError(u'请注明关闭原因')
|
||||
return True
|
||||
|
||||
def unlink(self):
|
||||
for item in self:
|
||||
if item.state != "draft":
|
||||
raise ValidationError(u'只能删除状态为【草稿】的工单。')
|
||||
elif item.env.uid != item.initiator_id.id:
|
||||
raise ValidationError(u'非本人不能删除')
|
||||
else:
|
||||
super(SystemWorkOrder, item).unlink()
|
||||
38
jikimo_system_order/models/work_order_template.py
Normal file
38
jikimo_system_order/models/work_order_template.py
Normal file
@@ -0,0 +1,38 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from odoo import models, fields, api
|
||||
|
||||
|
||||
class WorkOrderTemplate(models.Model):
|
||||
_name = 'work.order.template'
|
||||
_order = 'num'
|
||||
|
||||
# 编号
|
||||
num = fields.Char(string=u'编号', default='/')
|
||||
# 名称
|
||||
name = fields.Char(string=u'模板名称', required="1")
|
||||
# 分类
|
||||
work_order_type = fields.Many2one('order.classify', string=u'系统工单分类', domain=[('state', '=', True)])
|
||||
# 模板标题
|
||||
title_template = fields.Char(string=u'模板标题')
|
||||
# 模板正文
|
||||
text_template = fields.Html(string=u'模板正文')
|
||||
# 模板说明
|
||||
template_explain = fields.Text(string=u'模板说明')
|
||||
# 是否有效
|
||||
state = fields.Boolean(default=True, string=u'是否有效')
|
||||
|
||||
@api.model
|
||||
def create(self, vals):
|
||||
# 创建编号
|
||||
if vals.get('num', '/') == '/':
|
||||
vals['num'] = self.env['ir.sequence'].get('work.order.template') or '/'
|
||||
return super(WorkOrderTemplate, self).create(vals)
|
||||
|
||||
|
||||
class SystemOrderNotice(models.Model):
|
||||
_name = 'system.order.notice'
|
||||
_description = '工单处理人设置'
|
||||
|
||||
notice_user_ids = fields.Many2many('res.users', string='工单处理人')
|
||||
|
||||
24
jikimo_system_order/security/account_security.xml
Normal file
24
jikimo_system_order/security/account_security.xml
Normal file
@@ -0,0 +1,24 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<data noupdate="0"> <!-- noupdate表示,当模块升级时是否更新本条数据-->
|
||||
<!--运维权限组-->
|
||||
<record id="group_operations_permissions_rwc" model="res.groups">
|
||||
<field name="name">运维权限</field>
|
||||
</record>
|
||||
|
||||
<record id="system_order_user_rule" model="ir.rule">
|
||||
<field name="name">用户访问工单信息</field>
|
||||
<field name="model_id" ref="model_system_work_order"/>
|
||||
<field name="groups" eval="[(4, ref('base.group_user'))]"/>
|
||||
<field name="domain_force">[('initiator_id', '=', user.id)]</field>
|
||||
</record>
|
||||
|
||||
<record id="system_order_group_operations_rule" model="ir.rule">
|
||||
<field name="name">运维访问工单信息</field>
|
||||
<field name="model_id" ref="model_system_work_order"/>
|
||||
<field name="groups" eval="[(4, ref('jikimo_system_order.group_operations_permissions_rwc'))]"/>
|
||||
<field name="domain_force">[(1, '=', 1)]</field>
|
||||
</record>
|
||||
|
||||
</data>
|
||||
</odoo>
|
||||
16
jikimo_system_order/security/ir.model.access.csv
Normal file
16
jikimo_system_order/security/ir.model.access.csv
Normal file
@@ -0,0 +1,16 @@
|
||||
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
|
||||
|
||||
inside_system_order_classify_r,jikimo_system_order.order_classify,model_order_classify,,1,1,1,1
|
||||
inside_system_work_order_rc,jikimo_system_order.system_work_order,model_system_work_order,,1,1,1,1
|
||||
inside_work_order_template_r,jikimo_system_order.work_order_template,model_work_order_template,,1,1,1,1
|
||||
|
||||
inside_system_order_classify_rwc,jikimo_system_order.order_classify,model_order_classify,group_operations_permissions_rwc,1,1,1,0
|
||||
inside_system_work_order_rwc,jikimo_system_order.system_work_order,model_system_work_order,group_operations_permissions_rwc,1,1,1,0
|
||||
inside_work_order_template_rwc,jikimo_system_order.work_order_template,model_work_order_template,group_operations_permissions_rwc,1,1,1,0
|
||||
|
||||
order_close_wizard_group_user,jikimo_system_order.order_close_wizard,model_order_close_wizard,base.group_user,1,1,1,1
|
||||
order_other_wizard_group_user,jikimo_system_order.order_other_wizard,model_order_other_wizard,base.group_user,1,1,1,1
|
||||
order_technician_wizard_group_user,jikimo_system_order.order_technician_wizard,model_order_technician_wizard,base.group_user,1,1,1,1
|
||||
system_work_order_wizard_group_user,jikimo_system_order.system_work_order_wizard,model_system_work_order_wizard,base.group_user,1,1,1,1
|
||||
|
||||
system_order_notice_group_user,jikimo_system_order.system_order_notice,model_system_order_notice,base.group_user,1,1,1,1
|
||||
|
BIN
jikimo_system_order/static/description/icon.png
Normal file
BIN
jikimo_system_order/static/description/icon.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 2.7 KiB |
BIN
jikimo_system_order/static/description/系统工单.png
Normal file
BIN
jikimo_system_order/static/description/系统工单.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 533 B |
58
jikimo_system_order/views/notice_user_config.xml
Normal file
58
jikimo_system_order/views/notice_user_config.xml
Normal file
@@ -0,0 +1,58 @@
|
||||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<odoo>
|
||||
<data>
|
||||
# ---------- 工单通知处理人设置 ------------
|
||||
|
||||
<record model="ir.ui.view" id="tree_system_order_notice_view">
|
||||
<field name="name">tree.system.order.notice</field>
|
||||
<field name="model">system.order.notice</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree string="工单处理人设置" editable="top">
|
||||
<field name="notice_user_ids" widget="many2many_tags" required="1" options="{'no_create': True, 'no_edit': True}"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
|
||||
<record model="ir.ui.view" id="search_system_order_notice_view">
|
||||
<field name="name">search.system.order.notice</field>
|
||||
<field name="model">system.order.notice</field>
|
||||
<field name="arch" type="xml">
|
||||
<search string="工单处理人设置">
|
||||
<field name="notice_user_ids" string="模糊搜索"
|
||||
filter_domain="[('notice_user_ids', 'ilike', self)]"/>
|
||||
<separator></separator>
|
||||
|
||||
<field name="notice_user_ids" string="处理人"/>
|
||||
|
||||
</search>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
|
||||
<record model="ir.actions.act_window" id="action_system_order_notice_view">
|
||||
<field name="name">工单处理人</field>
|
||||
<field name="res_model">system.order.notice</field>
|
||||
<field name="view_mode">tree</field>
|
||||
<field name="domain">[]</field>
|
||||
<field name="context">{}</field>
|
||||
<field name="help" type="html">
|
||||
<p class="o_view_nocontent_smiling_face">
|
||||
[工单处理人] 还没有哦!点左上角的[创建]按钮,沙发归你了!
|
||||
</p>
|
||||
<p>
|
||||
</p>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
</data>
|
||||
</odoo>
|
||||
28
jikimo_system_order/views/res_config_settings_views.xml
Normal file
28
jikimo_system_order/views/res_config_settings_views.xml
Normal file
@@ -0,0 +1,28 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<data>
|
||||
<record id="res_config_settings_we_view_form_inherit" model="ir.ui.view">
|
||||
<field name="name">res.config.settings.we.view.form.inherit.bpm</field>
|
||||
<field name="model">res.config.settings</field>
|
||||
<field name="inherit_id" ref="base.res_config_settings_view_form"/>
|
||||
<field name="arch" type="xml">
|
||||
<xpath expr="//div[hasclass('app_settings_block')]/div[6]" position="after">
|
||||
<div>
|
||||
<h2>企微通知应用ID</h2>
|
||||
<div class="row mt16 o_settings_container" id="jd_api">
|
||||
<div class="col-12 col-lg-6 o_setting_box">
|
||||
<div class="o_setting_left_pane"/>
|
||||
<div class="o_setting_right_pane">
|
||||
<div class="text-muted">
|
||||
<label for="lost_agent_id"/>
|
||||
<field name="lost_agent_id"/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
</data>
|
||||
</odoo>
|
||||
23
jikimo_system_order/views/work_order_number.xml
Normal file
23
jikimo_system_order/views/work_order_number.xml
Normal file
@@ -0,0 +1,23 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
|
||||
<odoo>
|
||||
<data noupdate="True">
|
||||
<!-- 工单流水号 -->
|
||||
<record id="seq_work_order" model="ir.sequence">
|
||||
<field name="name">seq_work_order</field>
|
||||
<field name="company_id"/>
|
||||
<field name="code">system.work.order</field>
|
||||
<field name="prefix">SO%(year)s%(month)s%(day)s</field>
|
||||
<field name="padding">1</field>
|
||||
</record>
|
||||
|
||||
<!-- 模板编号 -->
|
||||
<record id="seq_order_template" model="ir.sequence">
|
||||
<field name="name">seq_order_template</field>
|
||||
<field name="company_id"/>
|
||||
<field name="code">work.order.template</field>
|
||||
<field name="prefix">TL</field>
|
||||
<field name="padding">1</field>
|
||||
</record>
|
||||
</data>
|
||||
</odoo>
|
||||
243
jikimo_system_order/views/yizuo_system_order_view.xml
Normal file
243
jikimo_system_order/views/yizuo_system_order_view.xml
Normal file
@@ -0,0 +1,243 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
|
||||
<odoo>
|
||||
<data>
|
||||
<!--工单信息-->
|
||||
<record model="ir.ui.view" id="work_order_tree">
|
||||
<field name="name">工单信息</field>
|
||||
<field name="model">system.work.order</field><!--对应表单名称-->
|
||||
<field name="arch" type="xml">
|
||||
<tree>
|
||||
<field name="state" widget="badge" decoration-primary="state == 'draft'"
|
||||
decoration-success="state in ('processed', 'completed')"
|
||||
decoration-danger="state == 'pending'" decoration-warning="state in ('unconfirmed')"/>
|
||||
<field name="order_number"/>
|
||||
<field name="title"/>
|
||||
<field name="initiator_id"/>
|
||||
<field name="date"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!--新建系统工单-->
|
||||
<record model="ir.ui.view" id="ork_order_form">
|
||||
<field name="name">新建系统工单</field>
|
||||
<field name="model">system.work.order</field>
|
||||
<field name="arch" type="xml">
|
||||
<form>
|
||||
<header>
|
||||
<field name="is_display" invisible="1"/>
|
||||
<button string='提交' class="oe_highlight" states="draft"
|
||||
type="object" name="do_unconfirmed"
|
||||
attrs="{'invisible': [('state', '!=', 'draft')]}"/>
|
||||
<button string='追回编辑' states="unconfirmed"
|
||||
type="action" name="%(system_work_order_wizard_view_act_window)d"
|
||||
context="{'explain':'确认要执行此操作吗?','object_name':'system.work.order','function_name':'do_draft','object_id':id}"/>
|
||||
|
||||
<button name="do_pending" states="unconfirmed"
|
||||
string="确认可处理" type="object" class="oe_highlight"
|
||||
groups="jikimo_system_order.group_operations_permissions_rwc"/>
|
||||
|
||||
<button string='处理工单' class="oe_highlight" states="pending"
|
||||
type="action" name="%(launch_order_technician_wizard)d"
|
||||
groups="jikimo_system_order.group_operations_permissions_rwc"/>
|
||||
<button string='评价' class="oe_highlight" attrs="{'invisible': [('is_display', '=', False)]}"
|
||||
type="action" name="%(launch_order_other_wizard)d" context="{'active_id':id}"/>
|
||||
<button name="%(launch_order_close_wizard)d" string="关闭该工单"
|
||||
attrs="{'invisible': ['|',('state', '=', 'draft'),'|',('state','=','completed'),('state','=','closed')]}"
|
||||
type="action" context="{'active_id':id}"/>
|
||||
|
||||
<field name="state" widget="statusbar"/>
|
||||
</header>
|
||||
<sheet>
|
||||
<group>
|
||||
<!-- <label for="order_number" class="oe_edit_only"/>-->
|
||||
<group>
|
||||
<field name="order_number" required="True" readonly="1"/>
|
||||
<field name="order_type" required="True" attrs="{'readonly': [('state', '!=', 'draft')]}" options="{'no_create': True}"/>
|
||||
<field name="date" required="True" readonly="True"/>
|
||||
<field name="order_template_id" attrs="{'readonly': [('state', '!=', 'draft')]}"
|
||||
domain="[('work_order_type','=',order_type),('state','=',True)]" options="{'no_create': True}"/>
|
||||
<field name="confirmation_date" readonly="True"/>
|
||||
<field name="urgency_degree" required="True" attrs="{'readonly': [('state','!=','draft')]}" widget="priority"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="initiator_company_id" required="True" readonly="True"/>
|
||||
<!-- <field name="initiator_department_id" required="True" readonly="True"/>-->
|
||||
<field name="initiator_id" required="True" readonly="True"/>
|
||||
<field name="confirm_id" readonly="True"/>
|
||||
<field name="solve_people_id" readonly="True"/>
|
||||
<field name="close_user_id" readonly="True"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="title" attrs="{'readonly': [('state', '!=', 'draft')]}" required="True"/>
|
||||
</group>
|
||||
</group>
|
||||
<notebook>
|
||||
<page string="工单内容">
|
||||
<field name="text" attrs="{'readonly': [('state','!=','draft')]}" required="True"/>
|
||||
</page>
|
||||
<page string="解决方案">
|
||||
<group>
|
||||
<field name="users_problem" readonly="True"/>
|
||||
<field name="solution" readonly="True"/>
|
||||
</group>
|
||||
</page>
|
||||
<page string="其他">
|
||||
<group>
|
||||
<field name="close_cause" readonly="True"/>
|
||||
<field name="close_time" readonly="True"/>
|
||||
<field name="grade" readonly="True"/>
|
||||
</group>
|
||||
</page>
|
||||
</notebook>
|
||||
</sheet>
|
||||
<!-- <div class="oe_chatter">-->
|
||||
<!-- <field name="message_follower_ids" widget="mail_followers"/>-->
|
||||
<!-- <field name="message_ids" widget="mail_thread"/>-->
|
||||
<!-- </div>-->
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!-- 搜索工单 -->
|
||||
<record model="ir.ui.view" id="restaurant_search">
|
||||
<field name="name">搜索工单</field>
|
||||
<field name="model">system.work.order</field>
|
||||
<field name="arch" type="xml">
|
||||
<search>
|
||||
<field string='发起人' name="initiator_id" widget="char" required="True"/>
|
||||
<field string='标题' name="title" widget="char"/>
|
||||
<field string='正文' name="text" widget="html"/>
|
||||
<field string='实际问题' name="users_problem" widget="text"/>
|
||||
<field string='解决方案' name="solution" widget="text"/>
|
||||
<filter name="today" string="今日工单" domain="[('date','=',time.strftime('%%Y-%%m-%%d'))]"/>
|
||||
<filter name="yesterday" string="昨日工单"
|
||||
domain="[('date', '=', (context_today() - relativedelta(days=1)).strftime('%Y-%m-%d'))]"/>
|
||||
<filter name="month" string="本月工单"
|
||||
domain="[('date','>=', time.strftime('%Y-%m-01')),('date','<', (context_today() + relativedelta(months=1)).strftime('%Y-%m-01'))]"/>
|
||||
<filter name="last_month" string="上月工单"
|
||||
domain="[('date','<', time.strftime('%Y-%m-01')),('date','>=', (context_today() - relativedelta(months=1)).strftime('%Y-%m-01'))]"/>
|
||||
<filter name="unconfirmed" string="待确认" domain="[('state','=','unconfirmed')]"/>
|
||||
<filter name="pending" string="待处理" domain="[('state','=','pending')]"/>
|
||||
<filter name="processed" string="已处理"
|
||||
domain="['|', ('state','=','processed'), ('state','=','closed')]"/>
|
||||
<group>
|
||||
<filter string='发起人' name="initiator_id" context='{"group_by":"initiator_id"}'/>
|
||||
<filter string='工单分类' name="order_type" context='{"group_by":"order_type"}'/>
|
||||
<filter string='模板' name="order_template_id" context='{"group_by":"order_template_id"}'/>
|
||||
<filter string='状态' name="state" context='{"group_by":"state"}'/>
|
||||
<filter string='紧急情况' name="state" context='{"group_by":"urgency_degree"}'/>
|
||||
</group>
|
||||
</search>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record model="ir.ui.view" id="graph_tree">
|
||||
<field name="name">工单图表</field>
|
||||
<field name="model">system.work.order</field><!--对应表单名称-->
|
||||
<field name="arch" type="xml">
|
||||
<pivot>
|
||||
<field name="date" type="row" interval="day"/>
|
||||
<field name="order_type" type="col"/>
|
||||
<field name="state" type="row"/>
|
||||
</pivot>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!-- 工单 -->
|
||||
<record model="ir.actions.act_window" id="system_order">
|
||||
<field name="name">工单</field>
|
||||
<field name="res_model">system.work.order</field>
|
||||
<field name="view_mode">tree,form,search,graph,pivot</field>
|
||||
</record>
|
||||
|
||||
<!--工单模板信息-->
|
||||
<record model="ir.ui.view" id="order_template_tree">
|
||||
<field name="name">工单模板信息</field>
|
||||
<field name="model">work.order.template</field><!--对应表单名称-->
|
||||
<field name="arch" type="xml">
|
||||
<tree>
|
||||
<field name="num"/>
|
||||
<field name="name"/>
|
||||
<field name="work_order_type"/>
|
||||
<field name="title_template"/>
|
||||
<field name="template_explain"/>
|
||||
<field name="state"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!--新建系统工单模板-->
|
||||
<record model="ir.ui.view" id="order_template_form">
|
||||
<field name="name">新建系统工单模板</field>
|
||||
<field name="model">work.order.template</field>
|
||||
<field name="arch" type="xml">
|
||||
<form>
|
||||
<sheet>
|
||||
<group>
|
||||
<field name="num" required="True" readonly="True"/>
|
||||
<field name="name" required="True"/>
|
||||
<field name="work_order_type" required="True"/>
|
||||
<field name="template_explain" required="True" style="height: 50px;"/>
|
||||
<field name="title_template" required="True"/>
|
||||
<field name="state"/>
|
||||
<field name="text_template" required="True"/>
|
||||
</group>
|
||||
</sheet>
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!-- 工单模板 -->
|
||||
<record model="ir.actions.act_window" id="work_template">
|
||||
<field name="name">工单模板</field>
|
||||
<field name="res_model">work.order.template</field>
|
||||
<field name="view_mode">tree,form</field>
|
||||
</record>
|
||||
|
||||
<!--工单分类信息-->
|
||||
<record model="ir.ui.view" id="order_type_tree">
|
||||
<field name="name">工单分类信息</field>
|
||||
<field name="model">order.classify</field><!--对应表单名称-->
|
||||
<field name="arch" type="xml">
|
||||
<tree>
|
||||
<field name="sequence" widget="handle"/>
|
||||
<field name="name"/>
|
||||
<field name="state"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!--新建系统分类信息-->
|
||||
<record model="ir.ui.view" id="order_type_form">
|
||||
<field name="name">新建系统分类信息</field>
|
||||
<field name="model">order.classify</field>
|
||||
<field name="arch" type="xml">
|
||||
<form>
|
||||
<sheet>
|
||||
<group>
|
||||
<field name="name" required="True"/>
|
||||
<field name="sequence" invisible="True"/>
|
||||
<field name="state"/>
|
||||
</group>
|
||||
</sheet>
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!-- 工单分类 -->
|
||||
<record model="ir.actions.act_window" id="classify">
|
||||
<field name="name">工单分类</field>
|
||||
<field name="res_model">order.classify</field>
|
||||
<field name="view_mode">tree,form</field>
|
||||
</record>
|
||||
|
||||
|
||||
<menuitem name="系统工单" id="work_order_1_list" web_icon="jikimo_system_order,static/description/系统工单.png"/>
|
||||
<menuitem name="工单" id="work_order" parent="work_order_1_list" action="system_order"/>
|
||||
<menuitem name="工单模板" id="work_order_template" parent="work_order_1_list" action="work_template" groups="jikimo_system_order.group_operations_permissions_rwc"/>
|
||||
<menuitem name="工单分类" id="work_order_type" parent="work_order_1_list" action="classify" groups="jikimo_system_order.group_operations_permissions_rwc"/>
|
||||
<menuitem name="工单设置" id="system_order_notice_user_config" parent="work_order_1_list" action="action_system_order_notice_view" groups="jikimo_system_order.group_operations_permissions_rwc"/>
|
||||
</data>
|
||||
</odoo>
|
||||
6
jikimo_system_order/wizard/__init__.py
Normal file
6
jikimo_system_order/wizard/__init__.py
Normal file
@@ -0,0 +1,6 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import order_other_wizard
|
||||
from . import order_technician_wizard
|
||||
from . import order_close_wizard
|
||||
from . import system_work_order_wizard
|
||||
79
jikimo_system_order/wizard/order_close_wizard.py
Normal file
79
jikimo_system_order/wizard/order_close_wizard.py
Normal file
@@ -0,0 +1,79 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from odoo import models, fields, api
|
||||
from odoo.addons.jikimo_system_order.models.constant import STATE_SELECTION
|
||||
from odoo.exceptions import ValidationError
|
||||
import datetime, logging
|
||||
|
||||
|
||||
class OrderCloseWizard(models.TransientModel):
|
||||
_name = 'order.close.wizard'
|
||||
|
||||
|
||||
def get_context(self):
|
||||
if self._context.get('active_id'):
|
||||
obj = self.env['system.work.order'].browse(self._context.get('active_id'))
|
||||
if obj.initiator_id.id != self.env.user.id:
|
||||
raise ValidationError(u'非本人无法操作')
|
||||
return obj
|
||||
|
||||
order_id = fields.Many2one('system.work.order', string=u'工单ID',
|
||||
default=lambda self: self.get_context().id)
|
||||
# 关闭原因
|
||||
close_cause = fields.Text(string=u'关闭问题原因', default=lambda self: self.get_context().close_cause)
|
||||
# 关闭时间
|
||||
close_time = fields.Datetime(string=u'关闭问题时间', default=fields.datetime.now())
|
||||
# 状态
|
||||
state = fields.Selection(STATE_SELECTION, default='closed', string=u'状态')
|
||||
# 关闭人
|
||||
close_user_id = fields.Many2one('res.users', string=u'关闭人', default=lambda self: self.env.user)
|
||||
|
||||
|
||||
def sure(self):
|
||||
self.order_id.close_cause = self.close_cause
|
||||
self.order_id.close_time = self.close_time
|
||||
if self.order_id.state == 'unconfirmed':
|
||||
state_remark = u'待确认 --> 已关闭'
|
||||
if self.order_id.state == 'pending':
|
||||
state_remark = u'待处理 --> 已关闭'
|
||||
if self.order_id.state == 'processed':
|
||||
state_remark = u'已处理待评分 --> 已关闭'
|
||||
# self.order_id.message_post(u'操作人:%s,操作时间:%s,状态变更过程:%s' % (
|
||||
# self.env.user.name,
|
||||
# (datetime.datetime.now() + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M:%S'), state_remark))
|
||||
self.order_id.state = self.state
|
||||
self.order_id.close_user_id = self.close_user_id
|
||||
we_employee_ids = []
|
||||
if self.order_id.initiator_id.we_employee_id:
|
||||
we_employee_ids.append(self.order_id.initiator_id.we_employee_id)
|
||||
lost_agent_id = self.env['ir.config_parameter'].sudo().get_param('lost_agent_id')
|
||||
wechat = self.env['we.config'].sudo().get_wechat(agent_id=lost_agent_id)
|
||||
# agent_id, user_ids, content
|
||||
content = """您提交的工单-**工单标题:{0}**-<font color=\"#FF0000\">**已关闭**</font>
|
||||
>提交时间:{1}
|
||||
>处理时间:{2}
|
||||
>处理人:{3}
|
||||
如有问题,请联系系统管理员!
|
||||
""".format(self.order_id.title,
|
||||
(self.order_id.date + datetime.timedelta(hours=8)).strftime(
|
||||
'%Y-%m-%d %H:%M'), (datetime.datetime.now() + datetime.timedelta(
|
||||
hours=8)).strftime('%Y-%m-%d %H:%M'), self.env.user.name or '')
|
||||
# wechat.message.send_markdown(agent_id=lost_agent_id, user_ids=we_employee_ids, content=content)
|
||||
for we_employee_id in we_employee_ids:
|
||||
try:
|
||||
wechat.message.send_markdown(agent_id=lost_agent_id, user_ids=we_employee_id, content=content)
|
||||
except Exception as e:
|
||||
logging.error('工单关闭发送消息异常%s' % str(e))
|
||||
return {}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
42
jikimo_system_order/wizard/order_other_wizard.py
Normal file
42
jikimo_system_order/wizard/order_other_wizard.py
Normal file
@@ -0,0 +1,42 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from odoo import models, fields, api
|
||||
from odoo.exceptions import ValidationError
|
||||
from odoo.addons.jikimo_system_order.models.constant import STATE_SELECTION, GRADE
|
||||
import datetime
|
||||
|
||||
|
||||
class OrderOtherWizard(models.TransientModel):
|
||||
_name = 'order.other.wizard'
|
||||
|
||||
|
||||
def get_context(self):
|
||||
if self._context.get('active_id'):
|
||||
obj = self.env['system.work.order'].browse(self._context.get('active_id'))
|
||||
if obj.initiator_id.id != self.env.user.id:
|
||||
raise ValidationError(u'非本人无法操作')
|
||||
return obj
|
||||
|
||||
order_id = fields.Many2one('system.work.order', string=u'工单ID',
|
||||
default=lambda self: self.get_context().id)
|
||||
# 关闭时间
|
||||
close_time = fields.Datetime(string=u'关闭时间', default=fields.datetime.now())
|
||||
# 状态
|
||||
state = fields.Selection(STATE_SELECTION, default='completed', string=u'状态')
|
||||
# 打分
|
||||
grade = fields.Selection(GRADE, string=u'评分')
|
||||
# 关闭人
|
||||
close_user_id = fields.Many2one('res.users', string=u'关闭人', default=lambda self: self.env.user)
|
||||
|
||||
|
||||
def sure(self):
|
||||
self.order_id.close_time = self.close_time
|
||||
self.order_id.grade = self.grade
|
||||
if self.order_id.state == 'processed':
|
||||
state_remark = u'已处理待评分 --> 已完成'
|
||||
# self.order_id.message_post(u'操作人:%s,操作时间:%s,状态变更过程:%s' % (
|
||||
# self.env.user.name,
|
||||
# (datetime.datetime.now() + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M:%S'), state_remark))
|
||||
self.order_id.state = self.state
|
||||
self.order_id.close_user_id = self.close_user_id
|
||||
return {}
|
||||
59
jikimo_system_order/wizard/order_technician_wizard.py
Normal file
59
jikimo_system_order/wizard/order_technician_wizard.py
Normal file
@@ -0,0 +1,59 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from odoo import models, fields, api
|
||||
from odoo.addons.jikimo_system_order.models.constant import STATE_SELECTION
|
||||
import datetime
|
||||
import logging
|
||||
|
||||
|
||||
class OrderTechnicianWizard(models.TransientModel):
|
||||
_name = 'order.technician.wizard'
|
||||
|
||||
order_id = fields.Many2one('system.work.order', string=u'工单ID',
|
||||
default=lambda self: self.env.context.get('active_id'))
|
||||
# 解决人
|
||||
solve_people_id = fields.Many2one('res.users', string=u'解决人', default=lambda self: self.env.user)
|
||||
# 用户实际问题
|
||||
users_problem = fields.Text(string=u'用户实际问题')
|
||||
# 最终解决方案
|
||||
solution = fields.Text(string=u'最终解决方案')
|
||||
# 状态
|
||||
state = fields.Selection(STATE_SELECTION, default='processed', string=u'状态')
|
||||
|
||||
def sure(self):
|
||||
self.order_id.solve_people_id = self.solve_people_id
|
||||
self.order_id.users_problem = self.users_problem
|
||||
self.order_id.solution = self.solution
|
||||
if self.order_id.state == 'pending':
|
||||
state_remark = u'待处理 --> 已处理待评分'
|
||||
# self.order_id.message_post(u'操作人:%s,操作时间:%s,状态变更过程:%s' % (
|
||||
# self.env.user.name,
|
||||
# (datetime.datetime.now() + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M:%S'), state_remark))
|
||||
self.order_id.state = self.state
|
||||
# 获取通知人
|
||||
# objs = self.env['system.order.notice'].search([])
|
||||
# user_ids = objs.notice_user_ids.filtered(lambda item: item.we_employee_id not in ['', False])
|
||||
# we_employee_ids = user_ids.mapped('we_employee_id')
|
||||
we_employee_ids = []
|
||||
if self.order_id.initiator_id.we_employee_id:
|
||||
we_employee_ids.append(self.order_id.initiator_id.we_employee_id)
|
||||
print(we_employee_ids)
|
||||
lost_agent_id = self.env['ir.config_parameter'].sudo().get_param('lost_agent_id')
|
||||
wechat = self.env['we.config'].sudo().get_wechat(agent_id=lost_agent_id)
|
||||
# agent_id, user_ids, content
|
||||
content = """您提交的工单-**工单标题:{0}**-<font color=\"info\">**已处理**</font>
|
||||
>提交时间:{1}
|
||||
>处理反馈:{4}
|
||||
>处理时间:{2}
|
||||
>处理人:{3}
|
||||
如有问题,请联系系统管理员!
|
||||
""".format(self.order_id.title,
|
||||
(self.order_id.date + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M'), (datetime.datetime.now() + datetime.timedelta(hours=8)).strftime('%Y-%m-%d %H:%M'), self.env.user.name or '', self.solution or '')
|
||||
# wechat.message.send_markdown(agent_id=lost_agent_id, user_ids=we_employee_ids, content=content)
|
||||
for we_employee_id in we_employee_ids:
|
||||
try:
|
||||
wechat.message.send_markdown(agent_id=lost_agent_id, user_ids=we_employee_id, content=content)
|
||||
except Exception as e:
|
||||
logging.error('工单处理发送消息异常%s' % str(e))
|
||||
|
||||
return {}
|
||||
122
jikimo_system_order/wizard/order_wizard.xml
Normal file
122
jikimo_system_order/wizard/order_wizard.xml
Normal file
@@ -0,0 +1,122 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<data>
|
||||
<!-- 技术员向导form-->
|
||||
<record model="ir.ui.view" id="wizard_technician_form_view">
|
||||
<field name="name">技术员向导</field>
|
||||
<field name="model">order.technician.wizard</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="技术员编辑">
|
||||
<group>
|
||||
<field name="order_id" required="1" readonly="1"/>
|
||||
<field name="solve_people_id" required="1"/>
|
||||
<field name="users_problem" required="1" style="height: 50px;"/>
|
||||
<field name="solution" required="1" style="height: 50px;"/>
|
||||
</group>
|
||||
<footer>
|
||||
<button name="sure" string="确定" type="object" class="oe_highlight"/>
|
||||
or
|
||||
<button string="取消" class="oe_link" special="cancel"/>
|
||||
</footer>
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record model="ir.actions.act_window" id="launch_order_technician_wizard">
|
||||
<field name="name">技术员编辑</field>
|
||||
<field name="type">ir.actions.act_window</field>
|
||||
<field name="res_model">order.technician.wizard</field>
|
||||
<field name="view_mode">form</field>
|
||||
<field name="view_id" ref="wizard_technician_form_view"/>
|
||||
<field name="context">{'display_default_code':False}</field>
|
||||
<field name="target">new</field>
|
||||
</record>
|
||||
|
||||
|
||||
|
||||
<!-- 其它向导form-->
|
||||
<record model="ir.ui.view" id="wizard_other_form_view">
|
||||
<field name="name">其它向导</field>
|
||||
<field name="model">order.other.wizard</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="其它编辑">
|
||||
<group>
|
||||
<field name="order_id" required="1" readonly="1"/>
|
||||
<field name="close_time" required="1" readonly="1"/>
|
||||
<field name="grade" required="1"/>
|
||||
<field name="close_user_id" required="1" readonly="1"/>
|
||||
</group>
|
||||
<footer>
|
||||
<button name="sure" string="确定" type="object" class="oe_highlight"/>
|
||||
or
|
||||
<button string="取消" class="oe_link" special="cancel"/>
|
||||
</footer>
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record model="ir.actions.act_window" id="launch_order_other_wizard">
|
||||
<field name="name">其它编辑</field>
|
||||
<field name="type">ir.actions.act_window</field>
|
||||
<field name="res_model">order.other.wizard</field>
|
||||
<field name="view_mode">form</field>
|
||||
<field name="view_id" ref="wizard_other_form_view"/>
|
||||
<field name="context">{'display_default_code':False}</field>
|
||||
<field name="target">new</field>
|
||||
</record>
|
||||
|
||||
<!--关闭向导form-->
|
||||
<record model="ir.ui.view" id="wizard_close_form_view">
|
||||
<field name="name">关闭向导</field>
|
||||
<field name="model">order.close.wizard</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="关闭工单">
|
||||
<group>
|
||||
<field name="order_id" required="1" readonly="1"/>
|
||||
<field name="close_cause" required="1" style="height: 50px;"/>
|
||||
<field name="close_time" required="1" readonly="1"/>
|
||||
<field name="close_user_id" required="1" readonly="1"/>
|
||||
</group>
|
||||
<footer>
|
||||
<button name="sure" string="确定" type="object" class="oe_highlight"/>
|
||||
or
|
||||
<button string="取消" class="oe_link" special="cancel"/>
|
||||
</footer>
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record model="ir.actions.act_window" id="launch_order_close_wizard">
|
||||
<field name="name">关闭工单</field>
|
||||
<field name="type">ir.actions.act_window</field>
|
||||
<field name="res_model">order.close.wizard</field>
|
||||
<field name="view_mode">form</field>
|
||||
<field name="view_id" ref="wizard_close_form_view"/>
|
||||
<field name="context">{'display_default_code':False}</field>
|
||||
<field name="target">new</field>
|
||||
</record>
|
||||
|
||||
<record id="system_work_order_wizard_view" model="ir.ui.view">
|
||||
<field name="name">system_work_order_wizard_view</field>
|
||||
<field name="model">system.work.order.wizard</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="二次确认">
|
||||
<field name="explain" readonly="1"/>
|
||||
<footer>
|
||||
<button name="sure" string="确定" type="object" class="oe_highlight"/>
|
||||
or
|
||||
<button string="取消" class="oe_link" special="cancel"/>
|
||||
</footer>
|
||||
</form>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record model="ir.actions.act_window" id="system_work_order_wizard_view_act_window">
|
||||
<field name="name">二次确认</field>
|
||||
<field name="type">ir.actions.act_window</field>
|
||||
<field name="res_model">system.work.order.wizard</field>
|
||||
<field name="view_mode">form</field>
|
||||
<field name="target">new</field>
|
||||
</record>
|
||||
</data>
|
||||
</odoo>
|
||||
42
jikimo_system_order/wizard/system_work_order_wizard.py
Normal file
42
jikimo_system_order/wizard/system_work_order_wizard.py
Normal file
@@ -0,0 +1,42 @@
|
||||
#!/usr/bin/env python
|
||||
# -*- coding: utf-8 -*-
|
||||
# @Time : 2017/12/12 9:46
|
||||
# @Author : GuoXiang
|
||||
# @Site :
|
||||
# @File : system_work_order_wizard.py
|
||||
# @Software: PyCharm
|
||||
# @Desc :
|
||||
# @license : Copyright©2018 www.dasmaster.com All Rights Reserved.
|
||||
# @Contact : xg1230205321@163.com
|
||||
from odoo import models, api, fields
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
|
||||
class SystemWorkOrderWizard(models.TransientModel):
|
||||
_name = "system.work.order.wizard"
|
||||
_description = u"追回确认"
|
||||
|
||||
|
||||
def _get_explain(self):
|
||||
if self._context.get('object_id'):
|
||||
obj = self.env['system.work.order'].browse(self._context.get('object_id'))
|
||||
if obj.initiator_id.id != self.env.user.id:
|
||||
raise ValidationError(u'非本人无法操作')
|
||||
if self._context.get('explain'):
|
||||
return self._context["explain"]
|
||||
|
||||
explain = fields.Char(default=_get_explain)
|
||||
|
||||
|
||||
def sure(self):
|
||||
"""
|
||||
确认
|
||||
:return:
|
||||
"""
|
||||
if self._context.get('object_id') and self._context.get('object_name') and self._context.get(
|
||||
'explain') and self._context.get('function_name'):
|
||||
work_sheet_obj = self.env[self._context["object_name"]].search([('id', '=', int(self._context["object_id"]))])
|
||||
class_name = self._context.get('object_name') # 获得对象类名
|
||||
method_name = self._context.get('function_name') # 获得对象的方法
|
||||
obj_function = getattr(self.env[class_name], method_name)
|
||||
obj_function(work_sheet_obj)
|
||||
@@ -1,7 +1,7 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
from odoo import fields, models
|
||||
from odoo import fields, models, api
|
||||
|
||||
|
||||
class MrpProduction(models.Model):
|
||||
@@ -12,7 +12,8 @@ class MrpProduction(models.Model):
|
||||
check_ids = fields.One2many('quality.check', 'production_id', string="Checks")
|
||||
|
||||
def _split_productions(self, amounts=False, cancel_remaining_qty=False, set_consumed_qty=False):
|
||||
productions = super()._split_productions(amounts=amounts, cancel_remaining_qty=cancel_remaining_qty, set_consumed_qty=set_consumed_qty)
|
||||
productions = super()._split_productions(amounts=amounts, cancel_remaining_qty=cancel_remaining_qty,
|
||||
set_consumed_qty=set_consumed_qty)
|
||||
backorders = productions[1:]
|
||||
if not backorders:
|
||||
return productions
|
||||
@@ -20,3 +21,4 @@ class MrpProduction(models.Model):
|
||||
if wo.current_quality_check_id.component_id:
|
||||
wo.current_quality_check_id._update_component_quantity()
|
||||
return productions
|
||||
|
||||
|
||||
@@ -1,41 +1,44 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<!-- Manufacturing Order for Planing view -->
|
||||
<record id="mrp_production_tree_view_planning" model="ir.ui.view">
|
||||
<field name="name">mrp.production.tree.inherit.planning</field>
|
||||
<field name="model">mrp.production</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree default_order="date_planned_start asc" decoration-info="state=='confirmed'" decoration-danger="date_planned_start<current_date and state not in ('done','cancel')" decoration-muted="state in ('done','cancel')" string="Manufacturing Orders" name="Production">
|
||||
<field name="message_needaction" invisible="1"/>
|
||||
<field name="name"/>
|
||||
<field name="date_planned_start"/>
|
||||
<field name="product_id"/>
|
||||
<field name="product_qty" sum="Total Qty" string="Quantity"/>
|
||||
<field name="product_uom_id" string="Unit of Measure" options="{'no_open':True,'no_create':True}" groups="uom.group_uom"/>
|
||||
<field name="reservation_state" string="Availability"/>
|
||||
<field name="origin"/>
|
||||
<field name="state"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
<!-- Manufacturing Order for Planing view -->
|
||||
<record id="mrp_production_tree_view_planning" model="ir.ui.view">
|
||||
<field name="name">mrp.production.tree.inherit.planning</field>
|
||||
<field name="model">mrp.production</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree default_order="date_planned_start asc" decoration-info="state=='confirmed'"
|
||||
decoration-danger="date_planned_start<current_date and state not in ('done','cancel')"
|
||||
decoration-muted="state in ('done','cancel')" string="Manufacturing Orders" name="Production">
|
||||
<field name="message_needaction" invisible="1"/>
|
||||
<field name="name"/>
|
||||
<field name="date_planned_start"/>
|
||||
<field name="product_id"/>
|
||||
<field name="product_qty" sum="Total Qty" string="Quantity"/>
|
||||
<field name="product_uom_id" string="Unit of Measure" options="{'no_open':True,'no_create':True}"
|
||||
groups="uom.group_uom"/>
|
||||
<field name="reservation_state" string="Availability"/>
|
||||
<field name="origin"/>
|
||||
<field name="state"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!-- <record id="mrp_production_form_inherit_planning" model="ir.ui.view">-->
|
||||
<!-- <field name="name">mrp.production.form_inherit_planning</field>-->
|
||||
<!-- <field name="model">mrp.production</field>-->
|
||||
<!-- <field name="inherit_id" ref="mrp.mrp_production_form_view"/>-->
|
||||
<!-- <field name="arch" type="xml">-->
|
||||
<!-- <xpath expr="div[hasclass('oe_chatter')]" position="replace">-->
|
||||
<!-- <!– 这里放置替换后的内容 –>-->
|
||||
<!-- </xpath>-->
|
||||
<!-- <xpath expr="//notebook" position="after">-->
|
||||
<!-- <div class="oe_chatter">-->
|
||||
<!-- <field name="message_follower_ids"/>-->
|
||||
<!-- <field name="activity_ids"/>-->
|
||||
<!-- <field name="message_ids"/>-->
|
||||
<!-- </div>-->
|
||||
<!-- </xpath>-->
|
||||
<!-- </field>-->
|
||||
<!-- </record>-->
|
||||
<!-- <record id="mrp_production_form_inherit_planning" model="ir.ui.view">-->
|
||||
<!-- <field name="name">mrp.production.form_inherit_planning</field>-->
|
||||
<!-- <field name="model">mrp.production</field>-->
|
||||
<!-- <field name="inherit_id" ref="mrp.mrp_production_form_view"/>-->
|
||||
<!-- <field name="arch" type="xml">-->
|
||||
<!-- <xpath expr="div[hasclass('oe_chatter')]" position="replace">-->
|
||||
<!-- <!– 这里放置替换后的内容 –>-->
|
||||
<!-- </xpath>-->
|
||||
<!-- <xpath expr="//notebook" position="after">-->
|
||||
<!-- <div class="oe_chatter">-->
|
||||
<!-- <field name="message_follower_ids"/>-->
|
||||
<!-- <field name="activity_ids"/>-->
|
||||
<!-- <field name="message_ids"/>-->
|
||||
<!-- </div>-->
|
||||
<!-- </xpath>-->
|
||||
<!-- </field>-->
|
||||
<!-- </record>-->
|
||||
|
||||
<record id="mrp_production_view_search_inherit_planning" model="ir.ui.view">
|
||||
<field name="name">mrp.production.search.view.inherit.planning</field>
|
||||
@@ -43,7 +46,9 @@
|
||||
<field name="inherit_id" ref="mrp.view_mrp_production_filter"/>
|
||||
<field name="arch" type="xml">
|
||||
<filter name="filter_planned" position="attributes">
|
||||
<attribute name="domain">[('is_planned', '=', True), ('date_planned_start', '!=', False), ('date_planned_finished', '!=', False)]</attribute>
|
||||
<attribute name="domain">[('is_planned', '=', True), ('date_planned_start', '!=', False),
|
||||
('date_planned_finished', '!=', False)]
|
||||
</attribute>
|
||||
</filter>
|
||||
</field>
|
||||
</record>
|
||||
@@ -51,30 +56,33 @@
|
||||
<record id="production_order_unplan_server_action" model="ir.actions.server">
|
||||
<field name="name">Unplan orders</field>
|
||||
<field name="model_id" ref="mrp.model_mrp_production"/>
|
||||
<field name="binding_model_id" ref="mrp.model_mrp_production" />
|
||||
<field name="binding_model_id" ref="mrp.model_mrp_production"/>
|
||||
<field name="binding_view_types">list</field>
|
||||
<field name="state">code</field>
|
||||
<field name="code">records.button_unplan()</field>
|
||||
</record>
|
||||
|
||||
<record id="mrp.act_product_mrp_production_workcenter" model="ir.actions.act_window">
|
||||
<field name="domain">[('bom_id', '!=', False), ('bom_id.operation_ids.workcenter_id', '=', active_id), ('date_planned_start', '!=', False), ('date_planned_finished', '!=', False)]</field>
|
||||
<field name="domain">[('bom_id', '!=', False), ('bom_id.operation_ids.workcenter_id', '=', active_id),
|
||||
('date_planned_start', '!=', False), ('date_planned_finished', '!=', False)]
|
||||
</field>
|
||||
<field name="view_id" ref="mrp_production_tree_view_planning"/>
|
||||
</record>
|
||||
|
||||
|
||||
<menuitem id="mrp_workorder_menu_planning"
|
||||
name="Work Orders"
|
||||
sequence="2"
|
||||
parent="mrp.mrp_planning_menu_root"
|
||||
groups="mrp.group_mrp_routings"/>
|
||||
name="Work Orders"
|
||||
sequence="2"
|
||||
parent="mrp.mrp_planning_menu_root"
|
||||
groups="mrp.group_mrp_routings"/>
|
||||
<menuitem id="menu_mrp_workorder_production"
|
||||
name="Planning by Production"
|
||||
sequence="1"
|
||||
action="mrp.action_mrp_workorder_production"
|
||||
parent="mrp_workorder_menu_planning"/>
|
||||
name="Planning by Production"
|
||||
sequence="1"
|
||||
action="mrp.action_mrp_workorder_production"
|
||||
parent="mrp_workorder_menu_planning"/>
|
||||
<menuitem id="menu_mrp_workorder_workcenter"
|
||||
name="Planning by Workcenter"
|
||||
sequence="2"
|
||||
action="mrp_workorder.action_mrp_workorder_dependencies_workcenter"
|
||||
parent="mrp_workorder_menu_planning"/>
|
||||
name="Planning by Workcenter"
|
||||
sequence="2"
|
||||
action="mrp_workorder.action_mrp_workorder_dependencies_workcenter"
|
||||
parent="mrp_workorder_menu_planning"/>
|
||||
</odoo>
|
||||
|
||||
BIN
quality_control/static/description/质量.png
Normal file
BIN
quality_control/static/description/质量.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 702 B |
@@ -1024,7 +1024,7 @@
|
||||
<menuitem
|
||||
id="menu_quality_root"
|
||||
name="Quality"
|
||||
web_icon="quality_control,static/description/icon.svg"
|
||||
web_icon="quality_control,static/description/质量.png"
|
||||
sequence="150"
|
||||
groups="quality.group_quality_user"/>
|
||||
|
||||
|
||||
@@ -1,2 +1,3 @@
|
||||
pystrich
|
||||
cpca
|
||||
pycryptodome==3.20
|
||||
|
||||
@@ -35,6 +35,7 @@
|
||||
],
|
||||
'web.assets_backend': [
|
||||
'sf_base/static/src/scss/*.scss',
|
||||
'sf_base/static/src/js/*.js',
|
||||
],
|
||||
|
||||
},
|
||||
|
||||
@@ -5,3 +5,4 @@ from . import fixture
|
||||
from . import functional_fixture
|
||||
from . import tool_other_features
|
||||
from . import basic_parameters_fixture
|
||||
from . import ir_sequence
|
||||
|
||||
@@ -13,7 +13,7 @@ class BasicParametersFixture(models.Model):
|
||||
diameter = fields.Float('直径(mm)', digits=(16, 2))
|
||||
|
||||
# '零点卡盘' 字段
|
||||
weight = fields.Float('重量(mm)', digits=(16, 2))
|
||||
weight = fields.Float('重量(kg)', digits=(16, 2))
|
||||
orientation_dish_diameter = fields.Float('定位盘直径(mm)', digits=(16, 2))
|
||||
clamping_diameter = fields.Float('装夹直径(mm)', digits=(16, 2))
|
||||
clamping_num = fields.Selection([('1', '1'), ('2', '2'), ('4', '4'), ('6', '6'), ('8', '8')], string='装夹单元数')
|
||||
|
||||
@@ -61,12 +61,10 @@ class MrsMaterialModel(models.Model):
|
||||
supplier_ids = fields.One2many('sf.supplier.sort', 'materials_model_id', string='供应商')
|
||||
active = fields.Boolean('有效', default=True)
|
||||
|
||||
@api.onchange('gain_way')
|
||||
def _check_gain_way(self):
|
||||
if not self.gain_way:
|
||||
raise UserError("请选择获取方式")
|
||||
if self.gain_way in ['外协', '采购']:
|
||||
if not self.supplier_ids:
|
||||
@api.constrains("gain_way")
|
||||
def _check_supplier_ids(self):
|
||||
for item in self:
|
||||
if item.gain_way in ('外协', '采购') and not item.supplier_ids:
|
||||
raise UserError("请添加供应商")
|
||||
|
||||
|
||||
@@ -86,17 +84,21 @@ class MrsProductionProcessCategory(models.Model):
|
||||
class MrsProductionProcess(models.Model):
|
||||
_name = 'sf.production.process'
|
||||
_description = '表面工艺'
|
||||
order = 'sequence asc'
|
||||
|
||||
code = fields.Char("编码")
|
||||
name = fields.Char('名称')
|
||||
remark = fields.Text("备注")
|
||||
sequence = fields.Integer('排序')
|
||||
# processing_order_ids = fields.One2many('sf.processing.order', 'production_process_id', string='工序')
|
||||
partner_process_ids = fields.Many2many('res.partner', 'process_ids', '加工工厂')
|
||||
active = fields.Boolean('有效', default=True)
|
||||
parameter_ids = fields.One2many('sf.production.process.parameter', 'process_id', string='可选参数')
|
||||
category_id = fields.Many2one('sf.production.process.category')
|
||||
category_id = fields.Many2one('sf.production.process.category', string='表面工艺类别')
|
||||
# workcenter_ids = fields.Many2many('mrp.workcenter', 'rel_workcenter_process', required=True)
|
||||
|
||||
processing_day = fields.Float('加工天数/d')
|
||||
travel_day = fields.Float('路途天数/d')
|
||||
sequence = fields.Integer('排序')
|
||||
|
||||
# class MrsProcessingTechnology(models.Model):
|
||||
# _name = 'sf.processing.technology'
|
||||
@@ -143,8 +145,12 @@ class MrsProductionProcessParameter(models.Model):
|
||||
is_check = fields.Boolean(default=False)
|
||||
# price = fields.Float('单价')
|
||||
process_id = fields.Many2one('sf.production.process', string='表面工艺')
|
||||
process_description = fields.Char(string='工艺描述')
|
||||
materials_model_ids = fields.Many2many('sf.materials.model', 'applicable_material', string='适用材料')
|
||||
processing_day = fields.Float('加工天数/d')
|
||||
travel_day = fields.Float('路途天数/d')
|
||||
active = fields.Boolean('有效', default=True)
|
||||
processing_mm = fields.Char('加工厚度/mm')
|
||||
|
||||
def name_get(self):
|
||||
result = []
|
||||
|
||||
74
sf_base/models/ir_sequence.py
Normal file
74
sf_base/models/ir_sequence.py
Normal file
@@ -0,0 +1,74 @@
|
||||
import calendar
|
||||
from datetime import timedelta
|
||||
|
||||
from odoo import models, fields
|
||||
|
||||
|
||||
class IrSequence(models.Model):
|
||||
_inherit = 'ir.sequence'
|
||||
|
||||
date_range_period = fields.Selection(
|
||||
[('day', '每日'), ('month', '每月'), ('year', '每年')],
|
||||
string='日期期间',
|
||||
)
|
||||
|
||||
def _next(self, sequence_date=None):
|
||||
""" Returns the next number in the preferred sequence in all the ones given in self."""
|
||||
if not self.use_date_range:
|
||||
return self._next_do()
|
||||
# date mode
|
||||
dt = sequence_date or self._context.get('ir_sequence_date', fields.Date.today())
|
||||
seq_date = self.env['ir.sequence.date_range'].search(
|
||||
[
|
||||
('sequence_id', '=', self.id),
|
||||
('date_from', '<=', dt),
|
||||
('date_to', '>=', dt),
|
||||
('date_range_period', '=', self.date_range_period)
|
||||
], limit=1)
|
||||
if not seq_date:
|
||||
if self.date_range_period:
|
||||
seq_date = self._create_date_range_seq_by_period(dt, self.date_range_period)
|
||||
else:
|
||||
seq_date = self._create_date_range_seq(dt)
|
||||
return seq_date.with_context(ir_sequence_date_range=seq_date.date_from)._next()
|
||||
|
||||
def _create_date_range_seq_by_period(self, date, period):
|
||||
if period == 'year':
|
||||
year = fields.Date.from_string(date).strftime('%Y')
|
||||
date_from = '{}-01-01'.format(year)
|
||||
date_to = '{}-12-31'.format(year)
|
||||
if period == 'month':
|
||||
# 计算当前月份的第一天和最后一天
|
||||
year = fields.Date.from_string(date).strftime('%Y')
|
||||
month = fields.Date.from_string(date).strftime('%m')
|
||||
date_from = fields.Date.from_string(date).strftime('%Y-%m-01')
|
||||
date_to = '{}-{}-{}'.format(year, month, calendar.monthrange(int(year), int(month))[1])
|
||||
if period == 'day':
|
||||
date_from = date
|
||||
date_to = date
|
||||
date_range = self.env['ir.sequence.date_range'].search(
|
||||
[
|
||||
('sequence_id', '=', self.id),
|
||||
('date_to', '>=', date_from),
|
||||
('date_to', '<=', date),
|
||||
('date_range_period', '=', period)
|
||||
],
|
||||
order='date_to desc', limit=1)
|
||||
if date_range:
|
||||
date_from = date_range.date_to + timedelta(days=1)
|
||||
seq_date_range = self.env['ir.sequence.date_range'].sudo().create({
|
||||
'date_from': date_from,
|
||||
'date_to': date_to,
|
||||
'sequence_id': self.id,
|
||||
'date_range_period': period,
|
||||
})
|
||||
return seq_date_range
|
||||
|
||||
|
||||
class IrSequenceDateRange(models.Model):
|
||||
_inherit = 'ir.sequence.date_range'
|
||||
|
||||
date_range_period = fields.Selection(
|
||||
[('day', '每日'), ('month', '每月'), ('year', '每年')],
|
||||
string='日期期间',
|
||||
)
|
||||
@@ -321,7 +321,7 @@ class ToolInventory(models.Model):
|
||||
prefix = fields.Char('前缀')
|
||||
postfix = fields.Char('后缀')
|
||||
diameter = fields.Float('直径(mm)')
|
||||
angle = fields.Float('R角(mm)')
|
||||
angle = fields.Float('R角(mm)',default=0)
|
||||
tool_length = fields.Float('刀具总长(mm)')
|
||||
blade_length = fields.Float('避空长/刃长(mm)')
|
||||
knife_head_name = fields.Char('刀头名称')
|
||||
|
||||
@@ -1,10 +0,0 @@
|
||||
diff a/sf_base/models/tool_base_new.py b/sf_base/models/tool_base_new.py (rejected hunks)
|
||||
@@ -108,6 +108,4 @@
|
||||
cutting_speed_ids = fields.One2many('sf.cutting.speed', 'standard_library_id', string='切削速度Vc')
|
||||
- feed_per_tooth_ids = fields.One2many('sf.feed.per.tooth', 'standard_library_id', '每齿走刀量fz',
|
||||
- domain=[('cutting_speed', '!=', False)])
|
||||
- feed_per_tooth_ids_3 = fields.One2many('sf.feed.per.tooth', 'standard_library_id', '每齿走刀量fz',
|
||||
- domain=[('cutting_speed', '!=', False)])
|
||||
+ feed_per_tooth_ids = fields.One2many('sf.feed.per.tooth', 'standard_library_id', '每齿走刀量fz')
|
||||
+ feed_per_tooth_ids_3 = fields.One2many('sf.feed.per.tooth', 'standard_library_id', '每齿走刀量fz')
|
||||
|
||||
@@ -21,8 +21,9 @@ class ToolMaterialsBasicParameters(models.Model):
|
||||
neck_length = fields.Float('颈部长度(mm)')
|
||||
handle_diameter = fields.Float('柄部直径(mm)')
|
||||
handle_length = fields.Float('柄部长度(mm)')
|
||||
blade_tip_diameter = fields.Integer('刀尖直径(mm)')
|
||||
blade_tip_working_size = fields.Char('刀尖处理尺寸(R半径mm/倒角度)', size=20)
|
||||
blade_tip_diameter = fields.Float('刀尖直径(mm)')
|
||||
blade_tip_working_size = fields.Char('刀尖倒角度(°)', size=20)
|
||||
tip_r_size = fields.Float('刀尖R角(mm)',default=0)
|
||||
blade_tip_taper = fields.Integer('刀尖锥度(°)')
|
||||
blade_diameter = fields.Float('刃部直径(mm)')
|
||||
blade_length = fields.Float('刃部长度(mm)')
|
||||
@@ -37,7 +38,7 @@ class ToolMaterialsBasicParameters(models.Model):
|
||||
width = fields.Float('宽度(mm)')
|
||||
cutting_blade_length = fields.Float('切削刃长(mm)')
|
||||
relief_angle = fields.Integer('后角(°)')
|
||||
blade_tip_circular_arc_radius = fields.Char('刀尖圆弧半径(mm)', size=20)
|
||||
blade_tip_circular_arc_radius = fields.Char('刀尖圆弧半径(mm)', size=20,default='0')
|
||||
inscribed_circle_diameter = fields.Float('内接圆直径IC/D(mm)')
|
||||
install_aperture_diameter = fields.Float('安装孔直径(mm)')
|
||||
chip_breaker_groove = fields.Selection([('无', '无'), ('单面', '单面'), ('双面', '双面')],
|
||||
|
||||
@@ -242,3 +242,8 @@ access_sf_fixture_materials_basic_parameters_group_sf_stock_manager,sf_fixture_m
|
||||
access_sf_multi_mounting_type_group_sf_stock_manager,sf_multi_mounting_type_group_sf_stock_manager,model_sf_multi_mounting_type,sf_base.group_sf_stock_manager,1,0,0,0
|
||||
access_sf_machine_brand_group_sf_stock_manager,sf_machine_brand_group_sf_stock_manager,model_sf_machine_brand,sf_base.group_sf_stock_manager,1,0,0,0
|
||||
access_sf_cutting_tool_type_group_sf_stock_manager,sf_cutting_tool_type_group_sf_stock_manager,model_sf_cutting_tool_type,sf_base.group_sf_stock_manager,1,0,0,0
|
||||
|
||||
|
||||
access_sf_cutting_tool_material_group_plan_dispatch,sf_cutting_tool_material_group_plan_dispatch,model_sf_cutting_tool_material,sf_base.group_plan_dispatch,1,0,0,0
|
||||
access_sf_functional_cutting_tool_model_group_plan_dispatch,sf_functional_cutting_tool_model_group_plan_dispatch,model_sf_functional_cutting_tool_model,sf_base.group_plan_dispatch,1,0,0,0
|
||||
access_sf_cutting_tool_type_group_plan_dispatch,sf_cutting_tool_type_group_plan_dispatch,model_sf_cutting_tool_type,sf_base.group_plan_dispatch,1,0,0,0
|
||||
|
||||
|
62
sf_base/static/src/js/custom_barcode_handlers.js
Normal file
62
sf_base/static/src/js/custom_barcode_handlers.js
Normal file
@@ -0,0 +1,62 @@
|
||||
/** @odoo-module **/
|
||||
|
||||
import { registry } from "@web/core/registry";
|
||||
import { barcodeGenericHandlers } from '@barcodes/barcode_handlers';
|
||||
import { patch } from "@web/core/utils/patch";
|
||||
|
||||
// 定义新的 clickOnButton 函数
|
||||
function customClickOnButton(selector) {
|
||||
console.log("This is the custom clickOnButton function!");
|
||||
|
||||
const buttons = document.body.querySelectorAll(selector);
|
||||
|
||||
let length = buttons.length;
|
||||
if (length > 0) {
|
||||
buttons[length - 1].click();
|
||||
} else {
|
||||
console.warn(`Button with selector ${selector} not found`);
|
||||
}
|
||||
}
|
||||
|
||||
patch(barcodeGenericHandlers, "start", {
|
||||
start(env, { ui, barcode, notification }) {
|
||||
// 使用新定义的 clickOnButton 函数
|
||||
const COMMANDS = {
|
||||
"O-CMD.EDIT": () => customClickOnButton(".o_form_button_edit"),
|
||||
"O-CMD.DISCARD": () => customClickOnButton(".o_form_button_cancel"),
|
||||
"O-CMD.SAVE": () => customClickOnButton(".o_form_button_save"),
|
||||
"O-CMD.PREV": () => customClickOnButton(".o_pager_previous"),
|
||||
"O-CMD.NEXT": () => customClickOnButton(".o_pager_next"),
|
||||
"O-CMD.PAGER-FIRST": () => updatePager("first"),
|
||||
"O-CMD.PAGER-LAST": () => updatePager("last"),
|
||||
"O-CMD.CONFIRM": () => customClickOnButton(".jikimo_button_confirm"),
|
||||
"O-CMD.FLUSHED": () => customClickOnButton(".jikimo_button_flushed"),
|
||||
};
|
||||
|
||||
barcode.bus.addEventListener("barcode_scanned", (ev) => {
|
||||
const barcode = ev.detail.barcode;
|
||||
if (barcode.startsWith("O-BTN.")) {
|
||||
let targets = [];
|
||||
try {
|
||||
targets = getVisibleElements(ui.activeElement, `[barcode_trigger=${barcode.slice(6)}]`);
|
||||
} catch (_e) {
|
||||
console.warn(`Barcode '${barcode}' is not valid`);
|
||||
}
|
||||
for (let elem of targets) {
|
||||
elem.click();
|
||||
}
|
||||
}
|
||||
if (barcode.startsWith("O-CMD.")) {
|
||||
const fn = COMMANDS[barcode];
|
||||
if (fn) {
|
||||
fn();
|
||||
} else {
|
||||
notification.add(env._t("Barcode: ") + `'${barcode}'`, {
|
||||
title: env._t("Unknown barcode command"),
|
||||
type: "danger"
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
})
|
||||
42
sf_base/static/src/js/remove_focus.js
Normal file
42
sf_base/static/src/js/remove_focus.js
Normal file
@@ -0,0 +1,42 @@
|
||||
/** @odoo-module **/
|
||||
|
||||
import { registry } from '@web/core/registry';
|
||||
|
||||
import { formView } from '@web/views/form/form_view';
|
||||
import { FormController } from '@web/views/form/form_controller';
|
||||
|
||||
import { listView } from '@web/views/list/list_view';
|
||||
import { ListController } from '@web/views/list/list_controller'
|
||||
|
||||
import { onRendered, onMounted } from "@odoo/owl";
|
||||
|
||||
export class RemoveFocusFormController extends FormController {
|
||||
setup() {
|
||||
super.setup();
|
||||
|
||||
onMounted(() => {
|
||||
this.__owl__.bdom.el.querySelectorAll(':focus').forEach(element => element.blur());
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
registry.category('views').add('remove_focus_form_view', {
|
||||
...formView,
|
||||
Controller: RemoveFocusFormController,
|
||||
});
|
||||
|
||||
|
||||
export class RemoveFocusListController extends ListController {
|
||||
setup() {
|
||||
super.setup();
|
||||
|
||||
onMounted(() => {
|
||||
this.__owl__.bdom.el.querySelectorAll(':focus').forEach(element => element.blur());
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
registry.category('views').add('remove_focus_list_view', {
|
||||
...listView,
|
||||
Controller: RemoveFocusListController,
|
||||
});
|
||||
@@ -159,9 +159,6 @@ td.o_required_modifier {
|
||||
display:inline;
|
||||
}
|
||||
.diameter{
|
||||
display: flex !important;
|
||||
justify-content: flex-start !important;
|
||||
align-items: center !important;
|
||||
}
|
||||
.o_address_format {
|
||||
display: flex !important;
|
||||
|
||||
@@ -12,11 +12,10 @@
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record model="ir.ui.view" id="mrs_production_process_parameter_form">
|
||||
<field name="model">sf.production.process.parameter</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="表面工艺可选参数" create="0" delete="0">
|
||||
<form string="表面工艺可选参数" create="0" delete="0" >
|
||||
<sheet>
|
||||
<div class="oe_title">
|
||||
<h1>
|
||||
@@ -26,14 +25,19 @@
|
||||
<group>
|
||||
<group>
|
||||
<field name="code" readonly="1"/>
|
||||
<field name="process_id" readonly="1"/>
|
||||
<field name="process_id" attrs="{'readonly': [('code', '!=', False)]}"/>
|
||||
<field name="process_description" attrs="{'readonly': [('code', '!=', False)]}"/>
|
||||
<field name="gain_way"/>
|
||||
</group>
|
||||
|
||||
<group>
|
||||
<field name="processing_day" attrs="{'readonly': [('code', '!=', False)]}"/>
|
||||
<field name="travel_day" attrs="{'readonly': [('code', '!=', False)]}"/>
|
||||
<field name="processing_mm" attrs="{'readonly': [('code', '!=', False)]}"/>
|
||||
</group>
|
||||
</group>
|
||||
<notebook>
|
||||
<page string="适用材料">
|
||||
<field name="materials_model_ids"></field>
|
||||
<field name="materials_model_ids" attrs="{'readonly': [('code', '!=', False)]}"></field>
|
||||
</page>
|
||||
</notebook>
|
||||
</sheet>
|
||||
@@ -48,7 +52,7 @@
|
||||
<search>
|
||||
<filter name="filter_active" string="已归档" domain="[('active','=',False)]"/>
|
||||
<field name="name" string="名称" filter_domain="[('name','ilike',self)]"/>
|
||||
<field name="code" string="编码" filter_domain="[('codeNum','ilike',self)]"/>
|
||||
<field name="code" string="编码" filter_domain="[('code','ilike',self)]"/>
|
||||
<searchpanel class="account_root">
|
||||
<field name="process_id" icon="fa-filter"/>
|
||||
</searchpanel>
|
||||
@@ -136,7 +140,7 @@
|
||||
<field name="model">sf.production.process.category</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree string="表面工艺类别" default_order="sequence, id" create="0" edit="0" delete="1">
|
||||
<field name="sequence" widget="handle" string="序号"/>
|
||||
<field name="sequence" widget="handle" string="序号" readonly="1"/>
|
||||
<field name="code"/>
|
||||
<field name="name" string="名称"/>
|
||||
</tree>
|
||||
@@ -159,7 +163,8 @@
|
||||
<record model="ir.ui.view" id="sf_production_process_tree">
|
||||
<field name="model">sf.production.process</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree string="表面工艺" create="0" edit="0" delete="1">
|
||||
<tree string="表面工艺" create="0" edit="0" delete="0">
|
||||
<field name="sequence" string="加工顺序" readonly="1"/>
|
||||
<field name="code"/>
|
||||
<field name="name" string="名称"/>
|
||||
<field name="remark"/>
|
||||
@@ -170,7 +175,7 @@
|
||||
<record model="ir.ui.view" id="sf_production_process_form">
|
||||
<field name="model">sf.production.process</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="表面工艺" create="0" edit="1" delete="1">
|
||||
<form string="表面工艺" create="0" delete="0">
|
||||
<sheet>
|
||||
<div class="oe_title">
|
||||
<h1>
|
||||
@@ -179,41 +184,46 @@
|
||||
</div>
|
||||
<group>
|
||||
<group>
|
||||
<field name="code"/>
|
||||
<field name="code" readonly="1"/>
|
||||
<field name="category_id" readonly="1"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="processing_day" readonly="1"/>
|
||||
<field name="travel_day" readonly="1"/>
|
||||
</group>
|
||||
<notebook>
|
||||
<page string="可选参数">
|
||||
<field name="parameter_ids">
|
||||
<tree force_save="1">
|
||||
<field name="code" readonly="1" force_save="1"/>
|
||||
<field name="name"/>
|
||||
<field name="gain_way"/>
|
||||
<field name='process_id' default="default"/>
|
||||
</tree>
|
||||
<form>
|
||||
<sheet>
|
||||
<group>
|
||||
<group>
|
||||
<field name="code"/>
|
||||
<field name="name" string="参数名"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name='process_id'/>
|
||||
<field name="gain_way"/>
|
||||
</group>
|
||||
</group>
|
||||
<notebook>
|
||||
<page string="适用材料">
|
||||
<field name="materials_model_ids"/>
|
||||
</page>
|
||||
</notebook>
|
||||
</sheet>
|
||||
</form>
|
||||
</field>
|
||||
</page>
|
||||
|
||||
</notebook>
|
||||
</group>
|
||||
<notebook>
|
||||
<page string="可选参数" >
|
||||
<field name="parameter_ids" >
|
||||
<tree force_save="1" create="0">
|
||||
<field name="code" readonly="1" force_save="1"/>
|
||||
<field name="name" readonly="1"/>
|
||||
<field name="gain_way"/>
|
||||
<field name='process_id' default="default"/>
|
||||
</tree>
|
||||
<form>
|
||||
<sheet>
|
||||
<group>
|
||||
<group>
|
||||
<field name="code"/>
|
||||
<field name="name" string="参数名"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name='process_id'/>
|
||||
<field name="gain_way"/>
|
||||
</group>
|
||||
</group>
|
||||
<notebook>
|
||||
<page string="适用材料">
|
||||
<field name="materials_model_ids"/>
|
||||
</page>
|
||||
</notebook>
|
||||
</sheet>
|
||||
</form>
|
||||
</field>
|
||||
</page>
|
||||
|
||||
</notebook>
|
||||
<group>
|
||||
<group>
|
||||
<field name="remark"/>
|
||||
@@ -251,7 +261,7 @@
|
||||
<group>
|
||||
<group>
|
||||
<field name="materials_no" readonly="1" force_save="1"/>
|
||||
<field name="gain_way" required="1"/>
|
||||
<field name="gain_way" required="0"/>
|
||||
<field name="tensile_strength" required="1"/>
|
||||
<field name="hardness" required="1"/>
|
||||
<field name="density" readonly="1"/>
|
||||
@@ -270,9 +280,9 @@
|
||||
<notebook>
|
||||
<page string="供应商">
|
||||
<field name='supplier_ids' class="supplier_ids_set_css">
|
||||
<tree editable='bottom'>
|
||||
<tree editable='bottom' delete="1">
|
||||
<field name="sequence" widget="handle" string="序号"/>
|
||||
<field name="partner_id" string="名称"/>
|
||||
<field name="partner_id" string="名称" options="{'no_create': True}"/>
|
||||
</tree>
|
||||
</field>
|
||||
</page>
|
||||
|
||||
@@ -171,7 +171,7 @@
|
||||
<field name="width"/>
|
||||
<field name="height"/>
|
||||
<field name="diameter"/>
|
||||
<field name="weight"/>
|
||||
<field name="weight" string="重量(kg)"/>
|
||||
<field name="orientation_dish_diameter"/>
|
||||
<field name="clamping_diameter"/>
|
||||
<field name="clamping_num"/>
|
||||
@@ -197,7 +197,7 @@
|
||||
<field name="width"/>
|
||||
<field name="height"/>
|
||||
<field name="diameter"/>
|
||||
<field name="weight"/>
|
||||
<field name="weight" string="重量(kg)"/>
|
||||
<field name="clamping_diameter"/>
|
||||
<field name="connector_diameter"/>
|
||||
<field name="chucking_power_max"/>
|
||||
@@ -220,7 +220,7 @@
|
||||
<field name="length"/>
|
||||
<field name="width"/>
|
||||
<field name="height"/>
|
||||
<field name="weight"/>
|
||||
<field name="weight" string="重量(kg)"/>
|
||||
<field name="gripper_length_min"/>
|
||||
<field name="gripper_width_min"/>
|
||||
<field name="gripper_height_min"/>
|
||||
@@ -248,7 +248,7 @@
|
||||
<field name="length"/>
|
||||
<field name="width"/>
|
||||
<field name="height"/>
|
||||
<field name="weight"/>
|
||||
<field name="weight" string="重量(kg)"/>
|
||||
<field name="gripper_length_min"/>
|
||||
<field name="gripper_width_min"/>
|
||||
<field name="gripper_height_min"/>
|
||||
@@ -278,7 +278,7 @@
|
||||
<field name="width"/>
|
||||
<field name="height"/>
|
||||
<field name="height_tolerance_value"/>
|
||||
<field name="weight"/>
|
||||
<field name="weight" string="重量(kg)"/>
|
||||
<field name="gripper_length_min"/>
|
||||
<field name="gripper_width_min"/>
|
||||
<field name="gripper_height_min"/>
|
||||
@@ -307,7 +307,7 @@
|
||||
<field name="length"/>
|
||||
<field name="width"/>
|
||||
<field name="height"/>
|
||||
<field name="weight"/>
|
||||
<field name="weight" string="重量(kg)"/>
|
||||
<field name="gripper_length_min"/>
|
||||
<field name="gripper_width_min"/>
|
||||
<field name="gripper_height_min"/>
|
||||
@@ -335,7 +335,7 @@
|
||||
<field name="width"/>
|
||||
<field name="height"/>
|
||||
<field name="diameter"/>
|
||||
<field name="weight"/>
|
||||
<field name="weight" string="重量(kg)"/>
|
||||
<field name="gripper_length_min"/>
|
||||
<field name="gripper_width_min"/>
|
||||
<field name="gripper_height_min"/>
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
<field name="handle_length"/>
|
||||
<field name="blade_tip_diameter"/>
|
||||
<field name="blade_tip_working_size"/>
|
||||
<field name="tip_r_size"/>
|
||||
<field name="blade_tip_taper"/>
|
||||
<field name="blade_diameter"/>
|
||||
<field name="blade_length"/>
|
||||
@@ -95,6 +96,7 @@
|
||||
<field name="handle_length"/>
|
||||
<field name="blade_tip_diameter"/>
|
||||
<field name="blade_tip_working_size"/>
|
||||
<field name="tip_r_size"/>
|
||||
<field name="blade_tip_taper"/>
|
||||
<field name="blade_diameter"/>
|
||||
<field name="blade_length"/>
|
||||
@@ -139,6 +141,7 @@
|
||||
</group>
|
||||
<group attrs="{'invisible': [('cutting_tool_type', '!=', '整体式刀具')]}">
|
||||
<field name="blade_tip_working_size"/>
|
||||
<field name="tip_r_size"/>
|
||||
<field name="blade_tip_diameter" class="diameter"/>
|
||||
<field name="blade_tip_taper"/>
|
||||
<field name="blade_helix_angle"/>
|
||||
|
||||
@@ -80,10 +80,10 @@
|
||||
<field name="name">sf.cutter.function.tree</field>
|
||||
<field name="model">sf.functional.cutting.tool.model</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree string="功能刀具类型" create="0" delete="0" edit="1">
|
||||
<field name="name" string="名称"/>
|
||||
<field name="code"/>
|
||||
<field name="remark"/>
|
||||
<tree string="功能刀具类型" create="0" delete="0" edit="1" editable="bottom">
|
||||
<field name="name" string="名称" readonly="1"/>
|
||||
<field name="code" readonly="1"/>
|
||||
<field name="remark" readonly="1"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
@@ -222,6 +222,7 @@
|
||||
<field name="handle_diameter" class="diameter"/>
|
||||
<field name="handle_length"/>
|
||||
<field name="blade_tip_working_size" class="du"/>
|
||||
<field name="tip_r_size"/>
|
||||
<field name="blade_tip_diameter" class="diameter"/>
|
||||
<field name="blade_tip_taper" class="du"/>
|
||||
<field name="blade_helix_angle" class="du"/>
|
||||
@@ -577,7 +578,7 @@
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<record model="ir.ui.view" id="view_cutting_tool_material_search">
|
||||
<record model="ir.ui.view" id="view_cutting_tool_inventory_search">
|
||||
<field name="name">sf.tool.inventory.search</field>
|
||||
<field name="model">sf.tool.inventory</field>
|
||||
<field name="arch" type="xml">
|
||||
|
||||
@@ -36,7 +36,7 @@ class Http(models.AbstractModel):
|
||||
post_time = int(datas['HTTP_TIMESTAMP'])
|
||||
datetime_post = datetime.fromtimestamp(post_time)
|
||||
datetime_now = datetime.now().replace(microsecond=0)
|
||||
datetime_del = datetime_now + timedelta(seconds=5)
|
||||
datetime_del = datetime_now + timedelta(seconds=30)
|
||||
if datetime_post > datetime_del:
|
||||
raise AuthenticationError('请求已过期')
|
||||
check_str = '%s%s%s' % (datas['HTTP_TOKEN'], post_time, factory_secret.sf_secret_key)
|
||||
|
||||
@@ -149,7 +149,7 @@ class JdEclp(models.Model):
|
||||
},
|
||||
}
|
||||
_logger.info('准备调接口1')
|
||||
url1 = config['bfm_url'] + '/api/create/jd/order'
|
||||
url1 = config['bfm_url_new'] + '/api/create/jd/order'
|
||||
requests.post(url1, json=json1, data=None)
|
||||
_logger.info('调用成功1')
|
||||
_logger.info('准备调接口2')
|
||||
@@ -158,9 +158,12 @@ class JdEclp(models.Model):
|
||||
'orderNo': self.origin,
|
||||
},
|
||||
}
|
||||
url2 = config['bfm_url'] + '/api/get/jd/no'
|
||||
url2 = config['bfm_url_new'] + '/api/get/jd/no'
|
||||
response = requests.post(url2, json=json2, data=None)
|
||||
# _logger.info('调用成功2', response.json()['result']['wbNo'])
|
||||
tem_ret = response.json().get('result')
|
||||
if not tem_ret:
|
||||
raise ValidationError('京东物流返回异常,请联系管理员')
|
||||
self.carrier_tracking_ref = response.json()['result'].get('wbNo')
|
||||
if not self.carrier_tracking_ref:
|
||||
raise ValidationError('物流下单未成功,请联系管理员')
|
||||
@@ -193,7 +196,7 @@ class JdEclp(models.Model):
|
||||
'no': self.origin,
|
||||
},
|
||||
}
|
||||
url1 = config['bfm_url'] + '/api/create/jd/bill'
|
||||
url1 = config['bfm_url_new'] + '/api/create/jd/bill'
|
||||
response = requests.post(url1, json=json1, data=None)
|
||||
# _logger.info('调用成功2', response.json())
|
||||
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
import traceback
|
||||
from datetime import datetime
|
||||
import logging
|
||||
import requests
|
||||
from odoo import fields, models
|
||||
from odoo.exceptions import UserError
|
||||
from odoo import fields, models, _
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -14,26 +16,51 @@ class StatusChange(models.Model):
|
||||
def action_confirm(self):
|
||||
# 在原有方法执行前记录日志和执行其他操作
|
||||
logging.info('函数已经执行=============')
|
||||
server_product_none = []
|
||||
for order in self.order_line:
|
||||
gain_way_no = order.product_template_id.model_process_parameters_ids.filtered(lambda a: not a.gain_way)
|
||||
if gain_way_no:
|
||||
process_parameters = [item.name for item in gain_way_no]
|
||||
raise UserError(
|
||||
_("请先至【制造】-【配置】中【表面工艺可选参数】为【%s】填写获取方式", ", ".join(process_parameters)))
|
||||
for item in order.product_template_id.model_process_parameters_ids:
|
||||
if item.gain_way == '外协':
|
||||
server_product = self.env['product.template'].search(
|
||||
[('server_product_process_parameters_id', '=', item.id),
|
||||
('detailed_type', '=', 'service')])
|
||||
if not server_product:
|
||||
server_product_none.append(item.name)
|
||||
if server_product_none:
|
||||
raise UserError(_("请先至【产品】中创建【表面工艺参数】为【%s】的服务产品", ", ".join(server_product_none)))
|
||||
|
||||
# 使用super()来调用原始方法(在本例中为'sale.order'模型的'action_confirm'方法)
|
||||
res = super(StatusChange, self).action_confirm()
|
||||
|
||||
# 原有方法执行后,进行额外的操作(如调用外部API)
|
||||
process_start_time = str(datetime.now())
|
||||
config = self.env['res.config.settings'].get_values()
|
||||
json1 = {
|
||||
'params': {
|
||||
'model_name': 'jikimo.process.order',
|
||||
'field_name': 'name',
|
||||
'default_code': self.default_code,
|
||||
'state': '加工中',
|
||||
'process_start_time': process_start_time,
|
||||
},
|
||||
}
|
||||
url1 = config['bfm_url'] + '/api/get/state/get_order'
|
||||
requests.post(url1, json=json1, data=None)
|
||||
logging.info('接口已经执行=============')
|
||||
|
||||
try:
|
||||
res = super(StatusChange, self).action_confirm()
|
||||
# 原有方法执行后,进行额外的操作(如调用外部API)
|
||||
process_start_time = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
|
||||
config = self.env['res.config.settings'].get_values()
|
||||
json1 = {
|
||||
'params': {
|
||||
'model_name': 'jikimo.process.order',
|
||||
'field_name': 'name',
|
||||
'default_code': self.default_code,
|
||||
'state': '加工中',
|
||||
'process_start_time': process_start_time,
|
||||
},
|
||||
}
|
||||
url1 = config['bfm_url_new'] + '/api/get/state/get_order'
|
||||
ret = requests.post(url1, json=json1, data=None)
|
||||
ret = ret.json()
|
||||
if not ret.get('error'):
|
||||
logging.info('接口已经执行=============')
|
||||
else:
|
||||
traceback_error = traceback.format_exc()
|
||||
logging.error("bfm订单状态同步失败:%s" % traceback_error)
|
||||
raise UserError('工厂加工同步订单状态到bfm失败')
|
||||
except UserError as e:
|
||||
traceback_error = traceback.format_exc()
|
||||
logging.error("工厂加工同步订单状态失败:%s " % traceback_error)
|
||||
raise UserError(e)
|
||||
return res
|
||||
|
||||
def action_cancel(self):
|
||||
@@ -54,7 +81,7 @@ class StatusChange(models.Model):
|
||||
'state': '待派单',
|
||||
},
|
||||
}
|
||||
url1 = config['bfm_url'] + '/api/get/state/cancel_order'
|
||||
url1 = config['bfm_url_new'] + '/api/get/state/cancel_order'
|
||||
requests.post(url1, json=json1, data=None)
|
||||
|
||||
return res
|
||||
@@ -202,12 +229,12 @@ class FinishStatusChange(models.Model):
|
||||
[('id', 'child_of', self.picking_type_id.warehouse_id.view_location_id.id),
|
||||
('usage', '!=', 'supplier')])
|
||||
if self.env['stock.move'].search([
|
||||
('state', 'in', ['confirmed', 'partially_available', 'waiting', 'assigned']),
|
||||
('product_qty', '>', 0),
|
||||
('location_id', 'in', wh_location_ids),
|
||||
('move_orig_ids', '=', False),
|
||||
('picking_id', 'not in', self.ids),
|
||||
('product_id', 'in', lines.product_id.ids)], limit=1):
|
||||
('state', 'in', ['confirmed', 'partially_available', 'waiting', 'assigned']),
|
||||
('product_qty', '>', 0),
|
||||
('location_id', 'in', wh_location_ids),
|
||||
('move_orig_ids', '=', False),
|
||||
('picking_id', 'not in', self.ids),
|
||||
('product_id', 'in', lines.product_id.ids)], limit=1):
|
||||
action = self.action_view_reception_report()
|
||||
action['context'] = {'default_picking_ids': self.ids}
|
||||
return action
|
||||
|
||||
@@ -122,7 +122,7 @@ class ResMrpBomMo(models.Model):
|
||||
# 查bom的原材料
|
||||
def get_raw_bom(self, product):
|
||||
raw_bom = self.env['product.product'].search(
|
||||
[('categ_id.type', '=', '原材料'), ('materials_type_id', '=', product.materials_type_id.id)])
|
||||
[('categ_id.type', '=', '原材料'), ('materials_type_id', '=', product.materials_type_id.id)],limit=1)
|
||||
return raw_bom
|
||||
|
||||
|
||||
|
||||
@@ -22,6 +22,16 @@
|
||||
<field name="company_id" ref="base.main_company"/>
|
||||
</record>
|
||||
|
||||
<record id="stock_location_tool_dismantle" model="stock.location">
|
||||
<field name="name">拆解</field>
|
||||
<field name="location_id" ref="stock.stock_location_locations_virtual"/>
|
||||
<field name="usage">internal</field>
|
||||
<field name="barcode">DJCJ</field>
|
||||
<field name="scrap_location">true</field>
|
||||
<field name="active">true</field>
|
||||
<field name="company_id" ref="base.main_company"/>
|
||||
</record>
|
||||
|
||||
|
||||
<record id="after_assembly_picking_in" model="stock.picking.type">
|
||||
<field name="name">刀具组装入库</field>
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<odoo>
|
||||
<data>
|
||||
<record id="mrp.product_template_action" model="ir.actions.act_window">
|
||||
<field name="context">
|
||||
{"search_default_categ_id":1,"search_default_consumable": 1, 'default_detailed_type': 'product'}
|
||||
</field>
|
||||
</record>
|
||||
<record model="ir.ui.view" id="view_sale_product_template_form_inherit_sf">
|
||||
<field name="name">product.template.form.inherit.sf</field>
|
||||
<field name="model">product.template</field>
|
||||
@@ -88,7 +93,8 @@
|
||||
</div>
|
||||
<field name="model_volume" string="体积[mm³]"/>
|
||||
<field name="product_model_type_id" string="模型类型"/>
|
||||
<field name="model_processing_panel" placeholder="例如R,U" string="加工面板" readonly="1"/>
|
||||
<field name="model_processing_panel" placeholder="例如R,U" string="加工面板"
|
||||
readonly="1"/>
|
||||
<field name="model_machining_precision"/>
|
||||
<field name="model_process_parameters_ids" string="表面工艺参数"
|
||||
widget="many2many_tags"
|
||||
@@ -103,11 +109,11 @@
|
||||
'刀具')], 'required': True}
|
||||
</attribute>
|
||||
</xpath>
|
||||
<!-- <xpath expr="//field[@name='default_code']" position="attributes">-->
|
||||
<!-- <attribute name="attrs">{'readonly': [('categ_type', '=', '刀具')], 'invisible':-->
|
||||
<!-- [('product_variant_count', '>' , 1)]}-->
|
||||
<!-- </attribute>-->
|
||||
<!-- </xpath>-->
|
||||
<!-- <xpath expr="//field[@name='default_code']" position="attributes">-->
|
||||
<!-- <attribute name="attrs">{'readonly': [('categ_type', '=', '刀具')], 'invisible':-->
|
||||
<!-- [('product_variant_count', '>' , 1)]}-->
|
||||
<!-- </attribute>-->
|
||||
<!-- </xpath>-->
|
||||
</field>
|
||||
</record>
|
||||
|
||||
@@ -185,6 +191,8 @@
|
||||
attrs="{'invisible': [('cutting_tool_type', '!=', '整体式刀具')],'readonly': [('id', '!=', False)]}"/>
|
||||
<field name="cutting_tool_blade_tip_working_size"
|
||||
attrs="{'invisible': [('cutting_tool_type', '!=', '整体式刀具')],'readonly': [('id', '!=', False)]}"/>
|
||||
<field name="cutting_tool_blade_tip_r_size"
|
||||
attrs="{'invisible': [('cutting_tool_type', '!=', '整体式刀具')],'readonly': [('id', '!=', False)]}"/>
|
||||
<field name="cutting_tool_blade_tip_diameter" string="刀尖直径(mm)" class="diameter"
|
||||
attrs="{'invisible': [('cutting_tool_type', '!=', '整体式刀具')],'readonly': [('id', '!=', False)]}"/>
|
||||
<field name="cutting_tool_blade_tip_taper" string="刀尖锥度(°)"
|
||||
|
||||
3
sf_hr/__init__.py
Normal file
3
sf_hr/__init__.py
Normal file
@@ -0,0 +1,3 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import models
|
||||
24
sf_hr/__manifest__.py
Normal file
24
sf_hr/__manifest__.py
Normal file
@@ -0,0 +1,24 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
{
|
||||
'name': '机企猫智能工厂 员工管理',
|
||||
'version': '1.0',
|
||||
'summary': '智能工厂员工模块',
|
||||
'sequence': 1,
|
||||
'category': 'sf',
|
||||
'website': 'https://www.sf.jikimo.com',
|
||||
'depends': ['base', 'hr'],
|
||||
'data': [
|
||||
'views/hr_employee.xml',
|
||||
'views/res_config_settings_views.xml',
|
||||
'data/cron_data.xml',
|
||||
],
|
||||
'demo': [
|
||||
],
|
||||
'qweb': [
|
||||
],
|
||||
'license': 'LGPL-3',
|
||||
'installable': True,
|
||||
'application': False,
|
||||
'auto_install': False,
|
||||
}
|
||||
15
sf_hr/data/cron_data.xml
Normal file
15
sf_hr/data/cron_data.xml
Normal file
@@ -0,0 +1,15 @@
|
||||
<odoo>
|
||||
<data noupdate="1">
|
||||
<record model="ir.cron" id="ir_cron_employee_info_sync">
|
||||
<field name="name">员工企微id同步</field>
|
||||
<field name="model_id" ref="hr.model_hr_employee"/>
|
||||
<field name="state">code</field>
|
||||
<field name="code">model._employee_info_sync()</field>
|
||||
<field name="interval_number">1</field>
|
||||
<field name="interval_type">days</field>
|
||||
<field name="numbercall">-1</field>
|
||||
<field name="doall" eval="False"/>
|
||||
</record>
|
||||
|
||||
</data>
|
||||
</odoo>
|
||||
4
sf_hr/models/__init__.py
Normal file
4
sf_hr/models/__init__.py
Normal file
@@ -0,0 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from . import hr_employee
|
||||
from . import res_config_setting
|
||||
28
sf_hr/models/hr_employee.py
Normal file
28
sf_hr/models/hr_employee.py
Normal file
@@ -0,0 +1,28 @@
|
||||
import logging
|
||||
import requests
|
||||
from odoo import models, fields, api, _
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class JkmPracticeEmployee(models.Model):
|
||||
_inherit = 'hr.employee'
|
||||
_description = '员工信息'
|
||||
|
||||
we_id = fields.Char(string='企微ID', index=True)
|
||||
|
||||
def _employee_info_sync(self):
|
||||
url = '/api/get/organization'
|
||||
config = self.env['res.config.settings'].get_values()
|
||||
ret = requests.post((config['ims_url'] + url), json={}, data={})
|
||||
result = ret.json()['result']
|
||||
if result['code'] == 200:
|
||||
if result['employee_list']:
|
||||
for employee_info in result['employee_list']:
|
||||
if employee_info['work_email']:
|
||||
hr_employee = self.sudo().search([('work_email', '=', employee_info['work_email'])])
|
||||
hr_employee.write({'we_id': employee_info['we_id']})
|
||||
if hr_employee.user_id:
|
||||
hr_employee.user_id.write({'we_employee_id': employee_info['we_id']})
|
||||
else:
|
||||
logging.info('_employee_info_sync error:%s' % result['message'])
|
||||
30
sf_hr/models/res_config_setting.py
Normal file
30
sf_hr/models/res_config_setting.py
Normal file
@@ -0,0 +1,30 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
import logging
|
||||
from odoo import api, fields, models
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class ResIMSConfigSettings(models.TransientModel):
|
||||
_inherit = 'res.config.settings'
|
||||
|
||||
ims_url = fields.Char('综合管理系统访问地址')
|
||||
|
||||
@api.model
|
||||
def get_values(self):
|
||||
"""
|
||||
重载获取参数的方法,参数都存在系统参数中
|
||||
:return:
|
||||
"""
|
||||
values = super(ResIMSConfigSettings, self).get_values()
|
||||
config = self.env['ir.config_parameter'].sudo()
|
||||
ims_url = config.get_param('ims_url', default='')
|
||||
values.update(
|
||||
ims_url=ims_url,
|
||||
)
|
||||
return values
|
||||
|
||||
def set_values(self):
|
||||
super(ResIMSConfigSettings, self).set_values()
|
||||
ir_config = self.env['ir.config_parameter'].sudo()
|
||||
ir_config.set_param("ims_url", self.ims_url or "")
|
||||
0
sf_hr/security/ir.model.access.csv
Normal file
0
sf_hr/security/ir.model.access.csv
Normal file
|
|
24
sf_hr/views/hr_employee.xml
Normal file
24
sf_hr/views/hr_employee.xml
Normal file
@@ -0,0 +1,24 @@
|
||||
<?xml version="1.0" encoding="utf-8" ?>
|
||||
<odoo>
|
||||
<data>
|
||||
<record id="view_form_employee_extend" model="ir.ui.view">
|
||||
<field name="name">employee_form</field>
|
||||
<field name="model">hr.employee</field>
|
||||
<field name="inherit_id" ref="hr.view_employee_form"/>
|
||||
<field name="arch" type="xml">
|
||||
<xpath expr="//group//field[@name='work_email']" position="attributes">
|
||||
<attribute name="required">1</attribute>
|
||||
</xpath>
|
||||
<xpath expr="//page[@name='public']" position='after'>
|
||||
<page string="企业微信">
|
||||
<group col="2">
|
||||
<group>
|
||||
<field name="we_id"/>
|
||||
</group>
|
||||
</group>
|
||||
</page>
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
</data>
|
||||
</odoo>
|
||||
28
sf_hr/views/res_config_settings_views.xml
Normal file
28
sf_hr/views/res_config_settings_views.xml
Normal file
@@ -0,0 +1,28 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<data>
|
||||
<record id="res_config_settings_finance_view_form_extend" model="ir.ui.view">
|
||||
<field name="name">res.config.settings.finance.view.form.extend</field>
|
||||
<field name="model">res.config.settings</field>
|
||||
<field name="inherit_id" ref="base.res_config_settings_view_form"/>
|
||||
<field name="arch" type="xml">
|
||||
<xpath expr="//div[hasclass('app_settings_block')]/div" position="before">
|
||||
<div>
|
||||
<h2>综合管理系统接口配置</h2>
|
||||
<div class="row mt16 o_settings_container" id="jd_api">
|
||||
<div class="col-12 col-lg-6 o_setting_box">
|
||||
<div class="o_setting_left_pane"/>
|
||||
<div class="o_setting_right_pane">
|
||||
<div class="text-muted">
|
||||
<label for="ims_url"/>
|
||||
<field name="ims_url"/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
</data>
|
||||
</odoo>
|
||||
@@ -1,2 +1,3 @@
|
||||
from . import models
|
||||
from . import wizard
|
||||
from . import controllers
|
||||
|
||||
1
sf_machine_connect/controllers/__init__.py
Normal file
1
sf_machine_connect/controllers/__init__.py
Normal file
@@ -0,0 +1 @@
|
||||
from . import controllers
|
||||
1320
sf_machine_connect/controllers/controllers.py
Normal file
1320
sf_machine_connect/controllers/controllers.py
Normal file
File diff suppressed because it is too large
Load Diff
@@ -2,3 +2,4 @@ from . import ftp_client
|
||||
from . import ftp_operate
|
||||
from . import py2opcua
|
||||
from . import res_config_setting
|
||||
from . import mrp_workorder
|
||||
|
||||
@@ -121,130 +121,169 @@ class Machine_ftp(models.Model):
|
||||
"""
|
||||
_inherit = 'maintenance.equipment'
|
||||
|
||||
# 机床首次上线时间(默认取值2024年08月01日零点)
|
||||
|
||||
def _get_default_online_time(self):
|
||||
return datetime(2024, 1, 1, 0, 0, 0)
|
||||
|
||||
first_online_time = fields.Datetime(string='首次上线时间', default=_get_default_online_time)
|
||||
|
||||
# workorder_ids = fields.One2many('mrp.workorder', 'machine_tool_id', string='工单')
|
||||
|
||||
# 机床配置项目
|
||||
# ftp相关
|
||||
ftp_num = fields.Char('ftp账号')
|
||||
ftp_pwd = fields.Char('ftp密码')
|
||||
ftp_host = fields.Char('ftp地址')
|
||||
ftp_port = fields.Integer('ftp端口')
|
||||
ftp_remote_path = fields.Char('机床ftp路径')
|
||||
# 补偿值写入相关
|
||||
x_compensation_node = fields.Char('x补偿值节点')
|
||||
y_compensation_node = fields.Char('y补偿值节点')
|
||||
# 数采配置相关
|
||||
machine_ip = fields.Char('机床IP')
|
||||
machine_signed = fields.Char('机床刷新间隔')
|
||||
machine_status = fields.Char('机床在线状态')
|
||||
machine_cnc_type = fields.Char('机床CNC型号')
|
||||
machine_axis_count = fields.Char('机床轴总数')
|
||||
machine_run_status = fields.Char('机床运行状态')
|
||||
machine_emg_status = fields.Char('机床急停状态')
|
||||
machine_cut_status = fields.Char('机床当前切削状态')
|
||||
machine_mode = fields.Char('机床当前操作模式')
|
||||
machine_spindle_load = fields.Char('机床主轴负载')
|
||||
machine_x_mach = fields.Char('机床X轴机械坐标')
|
||||
machine_x_abs_mach = fields.Char('机床X轴当前位置')
|
||||
machine_x_rel_mach = fields.Char('机床X轴相对工件坐标')
|
||||
machine_x_dis_mach = fields.Char('机床X轴目标距离')
|
||||
machine_x_axis_load = fields.Char('机床X轴伺服轴负载')
|
||||
machine_y_mach = fields.Char('机床Y轴机械坐标')
|
||||
machine_y_abs_mach = fields.Char('机床Y轴当前位置')
|
||||
machine_y_rel_mach = fields.Char('机床Y轴相对工件坐标')
|
||||
machine_y_dis_mach = fields.Char('机床Y轴目标距离')
|
||||
machine_y_axis_load = fields.Char('机床Y轴伺服轴负载')
|
||||
machine_z_mach = fields.Char('机床Z轴机械坐标')
|
||||
machine_z_abs_mach = fields.Char('机床Z轴当前位置')
|
||||
machine_z_rel_mach = fields.Char('机床Z轴相对工件坐标')
|
||||
machine_z_dis_mach = fields.Char('机床Z轴目标距离')
|
||||
machine_z_axis_load = fields.Char('机床Z轴伺服轴负载')
|
||||
machine_tool_num = fields.Char('机床当前刀位号')
|
||||
machine_program = fields.Char('机床主程序名称')
|
||||
machine_current_prg = fields.Char('机床当前执行指令')
|
||||
machine_prg_seq = fields.Char('机床当前执行语句号')
|
||||
machine_spindle_speed_set = fields.Char('机床设定主轴速度')
|
||||
machine_act_spindle_speed = fields.Char('机床实际主轴转速')
|
||||
machine_feed_speed_set = fields.Char('机床设定进给速度')
|
||||
machine_act_feed_speed = fields.Char('机床实际进给速度')
|
||||
machine_spindle_feed = fields.Char('机床主轴倍率')
|
||||
machine_feed_rate = fields.Char('机床进给倍率')
|
||||
machine_rapid_feed = fields.Char('机床快速移动倍率')
|
||||
machine_run_time = fields.Char('机床运行时间')
|
||||
machine_cut_time = fields.Char('机床切削时间')
|
||||
machine_keep_alive_time = fields.Char('机床上电时间')
|
||||
machine_circle_time = fields.Char('机床循环时间')
|
||||
machine_product_counts = fields.Char('机床加工件数')
|
||||
machine_system_date = fields.Char('机床系统日期')
|
||||
machine_system_time = fields.Char('机床系统时间')
|
||||
machine_alarm_msg = fields.Char('机床系统报警')
|
||||
# # 机床配置项目
|
||||
# # ftp相关
|
||||
# ftp_num = fields.Char('ftp账号')
|
||||
# ftp_pwd = fields.Char('ftp密码')
|
||||
# ftp_host = fields.Char('ftp地址')
|
||||
# ftp_port = fields.Integer('ftp端口')
|
||||
# ftp_remote_path = fields.Char('机床ftp路径')
|
||||
# # 补偿值写入相关
|
||||
# x_compensation_node = fields.Char('x补偿值节点')
|
||||
# y_compensation_node = fields.Char('y补偿值节点')
|
||||
# # 数采配置相关
|
||||
# machine_ip = fields.Char('机床IP')
|
||||
# machine_signed = fields.Char('机床刷新间隔')
|
||||
# machine_status = fields.Char('机床在线状态')
|
||||
# machine_cnc_type = fields.Char('机床CNC型号')
|
||||
# machine_axis_count = fields.Char('机床轴总数')
|
||||
# machine_run_status = fields.Char('机床运行状态')
|
||||
# machine_emg_status = fields.Char('机床急停状态')
|
||||
# machine_cut_status = fields.Char('机床当前切削状态')
|
||||
# machine_mode = fields.Char('机床当前操作模式')
|
||||
# machine_spindle_load = fields.Char('机床主轴负载')
|
||||
# machine_x_mach = fields.Char('机床X轴机械坐标')
|
||||
# machine_x_abs_mach = fields.Char('机床X轴当前位置')
|
||||
# machine_x_rel_mach = fields.Char('机床X轴相对工件坐标')
|
||||
# machine_x_dis_mach = fields.Char('机床X轴目标距离')
|
||||
# machine_x_axis_load = fields.Char('机床X轴伺服轴负载')
|
||||
# machine_y_mach = fields.Char('机床Y轴机械坐标')
|
||||
# machine_y_abs_mach = fields.Char('机床Y轴当前位置')
|
||||
# machine_y_rel_mach = fields.Char('机床Y轴相对工件坐标')
|
||||
# machine_y_dis_mach = fields.Char('机床Y轴目标距离')
|
||||
# machine_y_axis_load = fields.Char('机床Y轴伺服轴负载')
|
||||
# machine_z_mach = fields.Char('机床Z轴机械坐标')
|
||||
# machine_z_abs_mach = fields.Char('机床Z轴当前位置')
|
||||
# machine_z_rel_mach = fields.Char('机床Z轴相对工件坐标')
|
||||
# machine_z_dis_mach = fields.Char('机床Z轴目标距离')
|
||||
# machine_z_axis_load = fields.Char('机床Z轴伺服轴负载')
|
||||
# machine_tool_num = fields.Char('机床当前刀位号')
|
||||
# machine_program = fields.Char('机床主程序名称')
|
||||
# machine_current_prg = fields.Char('机床当前执行指令')
|
||||
# machine_prg_seq = fields.Char('机床当前执行语句号')
|
||||
# machine_spindle_speed_set = fields.Char('机床设定主轴速度')
|
||||
# machine_act_spindle_speed = fields.Char('机床实际主轴转速')
|
||||
# machine_feed_speed_set = fields.Char('机床设定进给速度')
|
||||
# machine_act_feed_speed = fields.Char('机床实际进给速度')
|
||||
# machine_spindle_feed = fields.Char('机床主轴倍率')
|
||||
# machine_feed_rate = fields.Char('机床进给倍率')
|
||||
# machine_rapid_feed = fields.Char('机床快速移动倍率')
|
||||
# machine_run_time = fields.Char('机床运行时间')
|
||||
# machine_cut_time = fields.Char('机床切削时间')
|
||||
# machine_keep_alive_time = fields.Char('机床上电时间')
|
||||
# machine_circle_time = fields.Char('机床循环时间')
|
||||
# machine_product_counts = fields.Char('机床加工件数')
|
||||
# machine_system_date = fields.Char('机床系统日期')
|
||||
# machine_system_time = fields.Char('机床系统时间')
|
||||
# machine_alarm_msg = fields.Char('机床系统报警')
|
||||
|
||||
# 刀位配置
|
||||
tool_num1 = fields.Char('刀位1')
|
||||
tool_num2 = fields.Char('刀位2')
|
||||
tool_num3 = fields.Char('刀位3')
|
||||
tool_num4 = fields.Char('刀位4')
|
||||
tool_num5 = fields.Char('刀位5')
|
||||
tool_num6 = fields.Char('刀位6')
|
||||
tool_num7 = fields.Char('刀位7')
|
||||
tool_num8 = fields.Char('刀位8')
|
||||
tool_num9 = fields.Char('刀位9')
|
||||
tool_num10 = fields.Char('刀位10')
|
||||
tool_num11 = fields.Char('刀位11')
|
||||
tool_num12 = fields.Char('刀位12')
|
||||
tool_num13 = fields.Char('刀位13')
|
||||
tool_num14 = fields.Char('刀位14')
|
||||
tool_num15 = fields.Char('刀位15')
|
||||
tool_num16 = fields.Char('刀位16')
|
||||
tool_num17 = fields.Char('刀位17')
|
||||
tool_num18 = fields.Char('刀位18')
|
||||
tool_num19 = fields.Char('刀位19')
|
||||
tool_num20 = fields.Char('刀位20')
|
||||
tool_num21 = fields.Char('刀位21')
|
||||
tool_num22 = fields.Char('刀位22')
|
||||
tool_num23 = fields.Char('刀位23')
|
||||
tool_num24 = fields.Char('刀位24')
|
||||
# # 刀位配置
|
||||
# tool_num1 = fields.Char('刀位1')
|
||||
# tool_num2 = fields.Char('刀位2')
|
||||
# tool_num3 = fields.Char('刀位3')
|
||||
# tool_num4 = fields.Char('刀位4')
|
||||
# tool_num5 = fields.Char('刀位5')
|
||||
# tool_num6 = fields.Char('刀位6')
|
||||
# tool_num7 = fields.Char('刀位7')
|
||||
# tool_num8 = fields.Char('刀位8')
|
||||
# tool_num9 = fields.Char('刀位9')
|
||||
# tool_num10 = fields.Char('刀位10')
|
||||
# tool_num11 = fields.Char('刀位11')
|
||||
# tool_num12 = fields.Char('刀位12')
|
||||
# tool_num13 = fields.Char('刀位13')
|
||||
# tool_num14 = fields.Char('刀位14')
|
||||
# tool_num15 = fields.Char('刀位15')
|
||||
# tool_num16 = fields.Char('刀位16')
|
||||
# tool_num17 = fields.Char('刀位17')
|
||||
# tool_num18 = fields.Char('刀位18')
|
||||
# tool_num19 = fields.Char('刀位19')
|
||||
# tool_num20 = fields.Char('刀位20')
|
||||
# tool_num21 = fields.Char('刀位21')
|
||||
# tool_num22 = fields.Char('刀位22')
|
||||
# tool_num23 = fields.Char('刀位23')
|
||||
# tool_num24 = fields.Char('刀位24')
|
||||
|
||||
# 机床采集项目
|
||||
timestamp = fields.Datetime('时间戳', readonly=True)
|
||||
signed = fields.Integer('刷新间隔', readonly=True)
|
||||
status = fields.Boolean('在线状态', readonly=True)
|
||||
time_on = fields.Char('总在线时长', readonly=True)
|
||||
time_on_now = fields.Char('本次在线时长', readonly=True)
|
||||
tool_num = fields.Integer('当前刀具', readonly=True)
|
||||
program = fields.Char('当前程序', readonly=True)
|
||||
run_status = fields.Selection([('0', '空闲中'), ('1', '加工中'), ('2', '加工中'), ('3', '加工中')], string='运行状态',
|
||||
readonly=True, default='0')
|
||||
run_time = fields.Char('总运行时长', readonly=True)
|
||||
cut_time = fields.Char('总切削时长', readonly=True)
|
||||
cut_status = fields.Selection([('0', '未切削'), ('1', '切削中'), ('2', '切削中'), ('3', '切削中')], string='切削状态',
|
||||
readonly=True, default='0')
|
||||
spindle_speed = fields.Char('主轴转速', readonly=True)
|
||||
status = fields.Boolean('机床在线状态', readonly=True)
|
||||
# run_status = fields.Selection([('0', '空闲中'), ('1', '加工中'), ('2', '加工中'), ('3', '加工中')], string='机床运行状态',
|
||||
# readonly=True, default='0')
|
||||
run_status = fields.Char('机床运行状态', readonly=True)
|
||||
run_time = fields.Char('机床累计运行时长', readonly=True)
|
||||
# 机床系统日期
|
||||
system_date = fields.Char('机床系统日期', readonly=True)
|
||||
# 机床系统时间
|
||||
system_time = fields.Char('机床系统时间', readonly=True)
|
||||
cut_time = fields.Char('机床累计切削时间', readonly=True)
|
||||
# cut_status = fields.Selection([('0', '未切削'), ('1', '切削中'), ('2', '切削中'), ('3', '切削中')], string='机床当前切削状态',
|
||||
# readonly=True, default='0')
|
||||
cut_status = fields.Char('机床当前切削状态', readonly=True)
|
||||
# 当前程序名
|
||||
program = fields.Char('机床当前程序', readonly=True)
|
||||
# 当前刀具号
|
||||
tool_num = fields.Integer('机床当前刀具号', readonly=True)
|
||||
# 机床通电开机时间, 机床加工件数, 机床当前操作模式, 开始加工时间, 结束加工时间, 加工程序开始时间, 加工程序结束时间, 待机开始时间,
|
||||
# 待机结束时间, 机床离线开始时间, 机床离线结束时间, 机床急停状态, 机床主程序名称, 程序运行的状态, 机床当前执行指令, 机床当前执行语句号
|
||||
# 机床X轴当前位置, 机床Y轴当前位置, 机床Z轴当前位置
|
||||
machine_power_on_time = fields.Char('机床通电开机时间', readonly=True)
|
||||
product_counts = fields.Char('机床加工件数', readonly=True)
|
||||
mode = fields.Char('机床当前操作模式', readonly=True)
|
||||
start_time = fields.Char('开始加工时间', readonly=True)
|
||||
end_time = fields.Char('结束加工时间', readonly=True)
|
||||
program_start_time = fields.Char('加工程序开始时间', readonly=True)
|
||||
program_end_time = fields.Char('加工程序结束时间', readonly=True)
|
||||
standby_start_time = fields.Char('待机开始时间', readonly=True)
|
||||
standby_end_time = fields.Char('待机结束时间', readonly=True)
|
||||
offline_start_time = fields.Char('机床离线开始时间', readonly=True)
|
||||
offline_end_time = fields.Char('机床离线结束时间', readonly=True)
|
||||
emg_status = fields.Char('机床急停状态', readonly=True)
|
||||
program_name = fields.Char('机床主程序名称', readonly=True)
|
||||
program_status = fields.Char('程序运行状态', readonly=True)
|
||||
current_program = fields.Char('机床当前执行指令', readonly=True)
|
||||
current_program_seq = fields.Char('机床当前执行语句号', readonly=True)
|
||||
x_abs_pos = fields.Char('机床X轴当前位置(mm)', readonly=True)
|
||||
y_abs_pos = fields.Char('机床Y轴当前位置(mm)', readonly=True)
|
||||
z_abs_pos = fields.Char('机床Z轴当前位置(mm)', readonly=True)
|
||||
|
||||
tool_num_process_time1 = fields.Char('刀位1', readonly=True, default='0')
|
||||
tool_num_process_time2 = fields.Char('刀位2', readonly=True, default='0')
|
||||
tool_num_process_time3 = fields.Char('刀位3', readonly=True, default='0')
|
||||
tool_num_process_time4 = fields.Char('刀位4', readonly=True, default='0')
|
||||
tool_num_process_time5 = fields.Char('刀位5', readonly=True, default='0')
|
||||
tool_num_process_time6 = fields.Char('刀位6', readonly=True, default='0')
|
||||
tool_num_process_time7 = fields.Char('刀位7', readonly=True, default='0')
|
||||
tool_num_process_time8 = fields.Char('刀位8', readonly=True, default='0')
|
||||
tool_num_process_time9 = fields.Char('刀位9', readonly=True, default='0')
|
||||
tool_num_process_time10 = fields.Char('刀位10', readonly=True, default='0')
|
||||
tool_num_process_time11 = fields.Char('刀位11', readonly=True, default='0')
|
||||
tool_num_process_time12 = fields.Char('刀位12', readonly=True, default='0')
|
||||
tool_num_process_time13 = fields.Char('刀位13', readonly=True, default='0')
|
||||
tool_num_process_time14 = fields.Char('刀位14', readonly=True, default='0')
|
||||
tool_num_process_time15 = fields.Char('刀位15', readonly=True, default='0')
|
||||
tool_num_process_time16 = fields.Char('刀位16', readonly=True, default='0')
|
||||
tool_num_process_time17 = fields.Char('刀位17', readonly=True, default='0')
|
||||
tool_num_process_time18 = fields.Char('刀位18', readonly=True, default='0')
|
||||
tool_num_process_time19 = fields.Char('刀位19', readonly=True, default='0')
|
||||
tool_num_process_time20 = fields.Char('刀位20', readonly=True, default='0')
|
||||
tool_num_process_time21 = fields.Char('刀位21', readonly=True, default='0')
|
||||
tool_num_process_time22 = fields.Char('刀位22', readonly=True, default='0')
|
||||
tool_num_process_time23 = fields.Char('刀位23', readonly=True, default='0')
|
||||
tool_num_process_time24 = fields.Char('刀位24', readonly=True, default='0')
|
||||
# 机床设定进给速度, 机床实际进给速度, 机床设定主轴转速, 机床实际主轴转速, 机床主轴负载, 机床X轴伺服轴负载, 机床Y轴伺服轴负载
|
||||
# 机床Z轴伺服轴负载, 机床快速移动倍率, 机床进给倍率, 机床X轴机械坐标, 机床Y轴机械坐标, 机床Z轴机械坐标, 机床X轴相对工件坐标
|
||||
# 机床Y轴相对工件坐标, 机床Z轴相对工件坐标, 机床X轴目标距离, 机床Y轴目标距离, 机床Z轴目标距离
|
||||
feed_speed_set = fields.Char('机床设定进给速度(mm/min)', readonly=True)
|
||||
act_feed_speed = fields.Char('机床实际进给速度(mm/min)', readonly=True)
|
||||
spindle_speed_set = fields.Char('机床设定主轴转速(r/min)', readonly=True)
|
||||
act_spindle_speed = fields.Char('机床实际主轴转速(r/min)', readonly=True)
|
||||
spindle_load = fields.Char('机床主轴负载(%)', readonly=True)
|
||||
x_axis_load = fields.Char('机床X轴伺服轴负载(%)', readonly=True)
|
||||
y_axis_load = fields.Char('机床Y轴伺服轴负载(%)', readonly=True)
|
||||
z_axis_load = fields.Char('机床Z轴伺服轴负载(%)', readonly=True)
|
||||
rapid_feed = fields.Char('机床快速移动倍率(%)', readonly=True)
|
||||
feed_rate = fields.Char('机床进给倍率(%)', readonly=True)
|
||||
x_mach_coord = fields.Char('机床X轴机械坐标(mm)', readonly=True)
|
||||
y_mach_coord = fields.Char('机床Y轴机械坐标(mm)', readonly=True)
|
||||
z_mach_coord = fields.Char('机床Z轴机械坐标(mm)', readonly=True)
|
||||
x_rel_coord = fields.Char('机床X轴相对工件坐标(mm)', readonly=True)
|
||||
y_rel_coord = fields.Char('机床Y轴相对工件坐标(mm)', readonly=True)
|
||||
z_rel_coord = fields.Char('机床Z轴相对工件坐标(mm)', readonly=True)
|
||||
x_dis_coord = fields.Char('机床X轴目标距离(mm)', readonly=True)
|
||||
y_dis_coord = fields.Char('机床Y轴目标距离(mm)', readonly=True)
|
||||
z_dis_coord = fields.Char('机床Z轴目标距离(mm)', readonly=True)
|
||||
|
||||
# 故障报警时间, 故障报警信息, 故障消除时间(复原时间)
|
||||
alarm_time = fields.Char('故障报警时间', readonly=True)
|
||||
alarm_msg = fields.Char('故障报警信息', readonly=True)
|
||||
clear_time = fields.Char('故障消除时间(复原时间)', readonly=True)
|
||||
|
||||
# # 开动率
|
||||
run_rate = fields.Char('开动率', readonly=True)
|
||||
|
||||
|
||||
class WorkCenterBarcode(models.Model):
|
||||
@@ -259,39 +298,59 @@ class WorkCenterBarcode(models.Model):
|
||||
button_compensation_state = fields.Boolean(string='是否已经补偿', readonly=True)
|
||||
button_up_all_state = fields.Boolean(string='是否已经全部下发', readonly=True)
|
||||
machine_tool_id = fields.Many2one('sf.machine_tool.type', string='机床')
|
||||
machine_tool_name = fields.Char(string='机床名称', default='未知机床', compute='_run_info', readonly=True)
|
||||
machine_tool_type_id = fields.Char(string='机床型号', default='未知型号', compute='_run_info', readonly=True)
|
||||
machine_tool_status = fields.Boolean(string='在线状态', compute='_run_info', readonly=True)
|
||||
# machine_tool_name = fields.Char(string='机床名称', default='未知机床', compute='_run_info', readonly=True)
|
||||
# machine_tool_type_id = fields.Char(string='机床型号', default='未知型号', compute='_run_info', readonly=True)
|
||||
# machine_tool_status = fields.Boolean(string='在线状态', compute='_run_info', readonly=True)
|
||||
# machine_tool_run_status = fields.Selection([('0', '关机中'), ('1', '加工中'), ('2', '加工中'), ('3', '加工中')],
|
||||
# string='运行状态', compute='_run_info', readonly=True, default='0')
|
||||
# machine_tool_timestamp = fields.Datetime('时间戳', compute='_run_info', readonly=True)
|
||||
# machine_tool_time_on = fields.Char('总在线时长', compute='_run_info', readonly=True)
|
||||
# machine_tool_time_on_now = fields.Char('本次在线时长', compute='_run_info', readonly=True)
|
||||
# machine_tool_tool_num = fields.Integer('当前刀具', compute='_run_info', readonly=True)
|
||||
# machine_tool_program = fields.Char('当前程序', compute='_run_info', readonly=True)
|
||||
# machine_tool_machine_ip = fields.Char('机床IP', compute='_run_info', readonly=True)
|
||||
# machine_tool_cut_status = fields.Selection([('0', '未切削'), ('1', '切削中'), ('2', '切削中'), ('3', '切削中')],
|
||||
# string='切削状态', compute='_run_info', readonly=True, default='0')
|
||||
# machine_tool_compensation_value_x = fields.Char('x补偿值', compute='_run_info', readonly=True)
|
||||
# machine_tool_compensation_value_y = fields.Char('y补偿值', compute='_run_info', readonly=True)
|
||||
|
||||
machine_tool_name = fields.Char(string='机床名称', default='未知机床', readonly=True)
|
||||
machine_tool_type_id = fields.Char(string='机床型号', default='未知型号', readonly=True)
|
||||
machine_tool_status = fields.Boolean(string='在线状态', readonly=True)
|
||||
machine_tool_run_status = fields.Selection([('0', '关机中'), ('1', '加工中'), ('2', '加工中'), ('3', '加工中')],
|
||||
string='运行状态', compute='_run_info', readonly=True, default='0')
|
||||
machine_tool_timestamp = fields.Datetime('时间戳', compute='_run_info', readonly=True)
|
||||
machine_tool_time_on = fields.Char('总在线时长', compute='_run_info', readonly=True)
|
||||
machine_tool_time_on_now = fields.Char('本次在线时长', compute='_run_info', readonly=True)
|
||||
machine_tool_tool_num = fields.Integer('当前刀具', compute='_run_info', readonly=True)
|
||||
machine_tool_program = fields.Char('当前程序', compute='_run_info', readonly=True)
|
||||
machine_tool_machine_ip = fields.Char('机床IP', compute='_run_info', readonly=True)
|
||||
string='运行状态', readonly=True, default='0')
|
||||
machine_tool_timestamp = fields.Datetime('时间戳', readonly=True)
|
||||
machine_tool_time_on = fields.Char('总在线时长', readonly=True)
|
||||
machine_tool_time_on_now = fields.Char('本次在线时长', readonly=True)
|
||||
machine_tool_tool_num = fields.Integer('当前刀具', readonly=True)
|
||||
machine_tool_program = fields.Char('当前程序', readonly=True)
|
||||
machine_tool_machine_ip = fields.Char('机床IP', readonly=True)
|
||||
machine_tool_cut_status = fields.Selection([('0', '未切削'), ('1', '切削中'), ('2', '切削中'), ('3', '切削中')],
|
||||
string='切削状态', compute='_run_info', readonly=True, default='0')
|
||||
machine_tool_compensation_value_x = fields.Char('x补偿值', compute='_run_info', readonly=True)
|
||||
machine_tool_compensation_value_y = fields.Char('y补偿值', compute='_run_info', readonly=True)
|
||||
string='切削状态', readonly=True, default='0')
|
||||
machine_tool_compensation_value_x = fields.Char('x补偿值', readonly=True)
|
||||
machine_tool_compensation_value_y = fields.Char('y补偿值', readonly=True)
|
||||
|
||||
# 工单状态
|
||||
|
||||
delivery_records = fields.One2many('delivery.record', 'workorder_id', string="下发记录")
|
||||
|
||||
@api.depends('equipment_id.timestamp')
|
||||
def _run_info(self):
|
||||
# self.machine_tool_name = '1号机床'
|
||||
self.machine_tool_name = self.equipment_id.name
|
||||
self.machine_tool_type_id = self.equipment_id.type_id.name
|
||||
self.machine_tool_status = self.equipment_id.status
|
||||
self.machine_tool_run_status = self.equipment_id.run_status
|
||||
self.machine_tool_timestamp = self.equipment_id.timestamp
|
||||
self.machine_tool_time_on = self.equipment_id.time_on
|
||||
self.machine_tool_time_on_now = self.equipment_id.time_on_now
|
||||
self.machine_tool_tool_num = self.equipment_id.tool_num
|
||||
self.machine_tool_program = self.equipment_id.program
|
||||
self.machine_tool_machine_ip = self.equipment_id.machine_ip
|
||||
self.machine_tool_cut_status = self.equipment_id.cut_status
|
||||
self.machine_tool_compensation_value_x = self.compensation_value_x
|
||||
self.machine_tool_compensation_value_y = self.compensation_value_y
|
||||
# self.machine_tool_name = self.equipment_id.name
|
||||
# self.machine_tool_type_id = self.equipment_id.type_id.name
|
||||
# self.machine_tool_status = self.equipment_id.status
|
||||
# self.machine_tool_run_status = self.equipment_id.run_status
|
||||
# self.machine_tool_timestamp = self.equipment_id.timestamp
|
||||
# self.machine_tool_time_on = self.equipment_id.time_on
|
||||
# self.machine_tool_time_on_now = self.equipment_id.time_on_now
|
||||
# self.machine_tool_tool_num = self.equipment_id.tool_num
|
||||
# self.machine_tool_program = self.equipment_id.program
|
||||
# self.machine_tool_machine_ip = self.equipment_id.machine_ip
|
||||
# self.machine_tool_cut_status = self.equipment_id.cut_status
|
||||
# self.machine_tool_compensation_value_x = self.compensation_value_x
|
||||
# self.machine_tool_compensation_value_y = self.compensation_value_y
|
||||
pass
|
||||
|
||||
def compensation(self):
|
||||
|
||||
|
||||
38
sf_machine_connect/models/mrp_workorder.py
Normal file
38
sf_machine_connect/models/mrp_workorder.py
Normal file
@@ -0,0 +1,38 @@
|
||||
import re
|
||||
|
||||
from odoo import fields, models, api
|
||||
|
||||
|
||||
class ResMrpWorkOrder(models.Model):
|
||||
_inherit = 'mrp.workorder'
|
||||
|
||||
mixed_search_field = fields.Char(string='坯料产品名称/RFID')
|
||||
|
||||
@api.model
|
||||
def web_read_group(self, domain, fields, groupby, limit=None, offset=0, orderby=False,
|
||||
lazy=True, expand=False, expand_limit=None, expand_orderby=False):
|
||||
domain = domain or []
|
||||
for index, item in enumerate(domain):
|
||||
if isinstance(item, list):
|
||||
if item[0] == 'mixed_search_field':
|
||||
if self._is_rfid_code(item[2]):
|
||||
domain[index] = ['rfid_code', item[1], item[2]]
|
||||
else:
|
||||
domain[index] = ['product_tmpl_name', item[1], item[2]]
|
||||
|
||||
return super(ResMrpWorkOrder, self).web_read_group(domain, fields, groupby, limit=limit, offset=offset, orderby=orderby,
|
||||
lazy=lazy, expand=expand, expand_limit=expand_limit, expand_orderby=expand_orderby)
|
||||
|
||||
def _is_rfid_code(self, tag):
|
||||
"""
|
||||
判断是否是rfid_code
|
||||
"""
|
||||
# 基于长度判断(假设RFID标签长度为10到16个字符)
|
||||
if not 10 <= len(tag) <= 16:
|
||||
return False
|
||||
|
||||
# 基于字符集判断(仅包含数字和字母)
|
||||
if not re.match("^[0-9]*$", tag):
|
||||
return False
|
||||
|
||||
return True
|
||||
@@ -8,11 +8,15 @@ _logger = logging.getLogger(__name__)
|
||||
class ResBFMConfigSettings(models.TransientModel):
|
||||
_inherit = 'res.config.settings'
|
||||
|
||||
bfm_url = fields.Selection(
|
||||
[("https://bfm.cs.jikimo.com", "开发环境(https://bfm.cs.jikimo.com)"),
|
||||
("https://bfm.t.jikimo.com", "测试环境(https://bfm.t.jikimo.com)"),
|
||||
# ("正式环境", "https://bfm.jikimo.com")], string='bfm环境', store=True)
|
||||
("https://bfm.jikimo.com", "正式环境(https://bfm.jikimo.com)")], string='bfm环境', store=True)
|
||||
# bfm_url = fields.Selection(
|
||||
# [("https://bfm.cs.jikimo.com", "开发环境(https://bfm.cs.jikimo.com)"),
|
||||
# ("https://bfm.t.jikimo.com", "测试环境(https://bfm.t.jikimo.com)"),
|
||||
# ("https://bfm.r.jikimo.com", "预发布环境(https://bfm.r.jikimo.com)"),
|
||||
# # ("正式环境", "https://bfm.jikimo.com")], string='bfm环境', store=True)
|
||||
# ("https://bfm.jikimo.com", "正式环境(https://bfm.jikimo.com)")], string='bfm环境', store=True)
|
||||
|
||||
bfm_url_new = fields.Char('业务平台环境路径', placeholder='请输入当前对应的业务平台环境路径')
|
||||
get_check_file_path = fields.Char('获取检查文件路径', default='')
|
||||
|
||||
@api.model
|
||||
def get_values(self):
|
||||
@@ -22,14 +26,17 @@ class ResBFMConfigSettings(models.TransientModel):
|
||||
"""
|
||||
values = super(ResBFMConfigSettings, self).get_values()
|
||||
config = self.env['ir.config_parameter'].sudo()
|
||||
bfm_url = config.get_param('bfm_url', default='')
|
||||
bfm_url_new = config.get_param('bfm_url_new', default='')
|
||||
get_check_file_path = config.get_param('get_check_file_path', default='')
|
||||
|
||||
values.update(
|
||||
bfm_url=bfm_url,
|
||||
bfm_url_new=bfm_url_new,
|
||||
get_check_file_path=get_check_file_path
|
||||
)
|
||||
return values
|
||||
|
||||
def set_values(self):
|
||||
super(ResBFMConfigSettings, self).set_values()
|
||||
ir_config = self.env['ir.config_parameter'].sudo()
|
||||
ir_config.set_param("bfm_url", self.bfm_url or "")
|
||||
ir_config.set_param("bfm_url_new", self.bfm_url_new or "")
|
||||
ir_config.set_param("get_check_file_path", self.get_check_file_path or "")
|
||||
|
||||
@@ -26,6 +26,7 @@
|
||||
<filter string="自动编程" name="no_manual_quotation" domain="[('manual_quotation', '=', False)]"/>
|
||||
</xpath>
|
||||
<xpath expr="//field[@name='production_id']" position="before">
|
||||
<field name="mixed_search_field"/>
|
||||
<field name="product_tmpl_name"/>
|
||||
<field name="rfid_code"/>
|
||||
</xpath>
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
<field name="program_name"/>
|
||||
<field name="functional_tool_type_id"/>
|
||||
<field name="cutting_tool_name"/>
|
||||
<field name="tool_state"/>
|
||||
<field name="cutting_tool_no"/>
|
||||
<field name="processing_type"/>
|
||||
<field name="margin_x_y"/>
|
||||
|
||||
@@ -13,294 +13,139 @@
|
||||
<page string="机床运行状态" attrs="{'invisible': [('equipment_type', '!=', '机床')]}">
|
||||
<group string='状态监控'>
|
||||
<group>
|
||||
<field name="timestamp"/>
|
||||
<field name="signed"/>
|
||||
<field name="status"/>
|
||||
<field name="time_on"/>
|
||||
<field name="time_on_now"/>
|
||||
</group>
|
||||
<group>
|
||||
<!-- <field name="timestamp"/> -->
|
||||
<!-- <field name="status"/> -->
|
||||
<field name="run_status"/>
|
||||
<field name="run_time"/>
|
||||
<field name="system_date"/>
|
||||
<field name="first_online_time"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="cut_status"/>
|
||||
<field name="cut_time"/>
|
||||
<!-- <field name="cut_time"/> -->
|
||||
<field name="program"/>
|
||||
<field name="tool_num"/>
|
||||
<field name="spindle_speed"/>
|
||||
</group>
|
||||
</group>
|
||||
<!-- <group string='刀位统计'> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num_process_time1"/> -->
|
||||
<!-- <field name="tool_num_process_time5"/> -->
|
||||
<!-- <field name="tool_num_process_time9"/> -->
|
||||
<!-- <field name="tool_num_process_time13"/> -->
|
||||
<!-- <field name="tool_num_process_time17"/> -->
|
||||
<!-- <field name="tool_num_process_time21"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num_process_time2"/> -->
|
||||
<!-- <field name="tool_num_process_time6"/> -->
|
||||
<!-- <field name="tool_num_process_time10"/> -->
|
||||
<!-- <field name="tool_num_process_time14"/> -->
|
||||
<!-- <field name="tool_num_process_time18"/> -->
|
||||
<!-- <field name="tool_num_process_time22"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num_process_time3"/> -->
|
||||
<!-- <field name="tool_num_process_time7"/> -->
|
||||
<!-- <field name="tool_num_process_time11"/> -->
|
||||
<!-- <field name="tool_num_process_time15"/> -->
|
||||
<!-- <field name="tool_num_process_time19"/> -->
|
||||
<!-- <field name="tool_num_process_time23"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num_process_time4"/> -->
|
||||
<!-- <field name="tool_num_process_time8"/> -->
|
||||
<!-- <field name="tool_num_process_time12"/> -->
|
||||
<!-- <field name="tool_num_process_time16"/> -->
|
||||
<!-- <field name="tool_num_process_time20"/> -->
|
||||
<!-- <field name="tool_num_process_time24"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
|
||||
<!-- <div class="o_address_format"> -->
|
||||
<!-- <label for="tool_num_process_time1" string="刀位1"/> -->
|
||||
<!-- <field name="tool_num_process_time1" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time2" string="刀位2"/> -->
|
||||
<!-- <field name="tool_num_process_time2" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time3" string="刀位3"/> -->
|
||||
<!-- <field name="tool_num_process_time3" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time4" string="刀位4"/> -->
|
||||
<!-- <field name="tool_num_process_time4" class="o_form_label"/> -->
|
||||
<!-- <div></div> -->
|
||||
<!-- <label for="tool_num_process_time5" string="刀位5"/> -->
|
||||
<!-- <field name="tool_num_process_time5" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time6" string="刀位6"/> -->
|
||||
<!-- <field name="tool_num_process_time6" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time7" string="刀位7"/> -->
|
||||
<!-- <field name="tool_num_process_time7" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time8" string="刀位8"/> -->
|
||||
<!-- <field name="tool_num_process_time8" class="o_form_label"/> -->
|
||||
<!-- <div></div> -->
|
||||
<!-- <label for="tool_num_process_time9" string="刀位9"/> -->
|
||||
<!-- <field name="tool_num_process_time9" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time10" string="刀位10"/> -->
|
||||
<!-- <field name="tool_num_process_time10" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time11" string="刀位11"/> -->
|
||||
<!-- <field name="tool_num_process_time11" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time12" string="刀位12"/> -->
|
||||
<!-- <field name="tool_num_process_time12" class="o_form_label"/> -->
|
||||
<!-- <div></div> -->
|
||||
<!-- <label for="tool_num_process_time13" string="刀位13"/> -->
|
||||
<!-- <field name="tool_num_process_time13" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time14" string="刀位14"/> -->
|
||||
<!-- <field name="tool_num_process_time14" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time15" string="刀位15"/> -->
|
||||
<!-- <field name="tool_num_process_time15" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time16" string="刀位16"/> -->
|
||||
<!-- <field name="tool_num_process_time16" class="o_form_label"/> -->
|
||||
<!-- <div></div> -->
|
||||
<!-- <label for="tool_num_process_time17" string="刀位17"/> -->
|
||||
<!-- <field name="tool_num_process_time17" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time18" string="刀位18"/> -->
|
||||
<!-- <field name="tool_num_process_time18" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time19" string="刀位19"/> -->
|
||||
<!-- <field name="tool_num_process_time19" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time20" string="刀位20"/> -->
|
||||
<!-- <field name="tool_num_process_time20" class="o_form_label"/> -->
|
||||
<!-- <div></div> -->
|
||||
<!-- <label for="tool_num_process_time21" string="刀位21"/> -->
|
||||
<!-- <field name="tool_num_process_time21" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time22" string="刀位22"/> -->
|
||||
<!-- <field name="tool_num_process_time22" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time23" string="刀位23"/> -->
|
||||
<!-- <field name="tool_num_process_time23" class="o_form_label"/> -->
|
||||
<!-- <span>&nbsp;</span> -->
|
||||
<!-- <label for="tool_num_process_time24" string="刀位24"/> -->
|
||||
<!-- <field name="tool_num_process_time24" class="o_form_label"/> -->
|
||||
<!-- </div> -->
|
||||
<!-- </group> -->
|
||||
</page>
|
||||
<page string="机床运行数据" attrs="{'invisible': [('equipment_type', '!=', '机床')]}">
|
||||
<!-- <group string="机床配置">--> -->
|
||||
<group string="ftp相关">
|
||||
<group>
|
||||
<field name="ftp_num"/>
|
||||
<field name="ftp_pwd"/>
|
||||
<field name="ftp_host"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="ftp_port"/>
|
||||
<field name="ftp_remote_path"/>
|
||||
</group>
|
||||
<group string="运行数据">
|
||||
<group>
|
||||
<field name="machine_power_on_time"/>
|
||||
<field name="product_counts"/>
|
||||
<field name="mode"/>
|
||||
<field name="start_time"/>
|
||||
<field name="end_time"/>
|
||||
<field name="program_start_time"/>
|
||||
<field name="program_end_time"/>
|
||||
<field name="standby_start_time"/>
|
||||
<field name="standby_end_time"/>
|
||||
<field name="offline_start_time"/>
|
||||
<field name="offline_end_time"/>
|
||||
<field name="emg_status"/>
|
||||
<field name="program_name"/>
|
||||
<field name="program_status"/>
|
||||
<field name="current_program"/>
|
||||
<field name="current_program_seq"/>
|
||||
<field name="x_abs_pos"/>
|
||||
<field name="y_abs_pos"/>
|
||||
<field name="z_abs_pos"/>
|
||||
</group>
|
||||
<group string="补偿值相关">
|
||||
<group>
|
||||
<field name="x_compensation_node"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="y_compensation_node"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="feed_speed_set"/>
|
||||
<field name="act_feed_speed"/>
|
||||
<field name="spindle_speed_set"/>
|
||||
<field name="act_spindle_speed"/>
|
||||
<field name="spindle_load"/>
|
||||
<field name="x_axis_load"/>
|
||||
<field name="y_axis_load"/>
|
||||
<field name="z_axis_load"/>
|
||||
<field name="rapid_feed"/>
|
||||
<field name="feed_rate"/>
|
||||
<field name="x_mach_coord"/>
|
||||
<field name="y_mach_coord"/>
|
||||
<field name="z_mach_coord"/>
|
||||
<field name="x_rel_coord"/>
|
||||
<field name="y_rel_coord"/>
|
||||
<field name="z_rel_coord"/>
|
||||
<field name="x_dis_coord"/>
|
||||
<field name="y_dis_coord"/>
|
||||
<field name="z_dis_coord"/>
|
||||
</group>
|
||||
<group string="数采相关">
|
||||
<group>
|
||||
<field name="machine_ip"/>
|
||||
<field name="machine_signed"/>
|
||||
<field name="machine_status"/>
|
||||
<field name="machine_cnc_type"/>
|
||||
<field name="machine_axis_count"/>
|
||||
<field name="machine_run_status"/>
|
||||
<field name="machine_emg_status"/>
|
||||
<field name="machine_cut_status"/>
|
||||
<field name="machine_mode"/>
|
||||
<field name="machine_spindle_load"/>
|
||||
<field name="machine_x_mach"/>
|
||||
<field name="machine_x_abs_mach"/>
|
||||
<field name="machine_x_rel_mach"/>
|
||||
<field name="machine_x_dis_mach"/>
|
||||
<field name="machine_x_axis_load"/>
|
||||
<field name="machine_y_mach"/>
|
||||
<field name="machine_y_abs_mach"/>
|
||||
<field name="machine_y_rel_mach"/>
|
||||
<field name="machine_y_dis_mach"/>
|
||||
<field name="machine_y_axis_load"/>
|
||||
<field name="machine_z_mach"/>
|
||||
<field name="machine_z_abs_mach"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="machine_z_rel_mach"/>
|
||||
<field name="machine_z_dis_mach"/>
|
||||
<field name="machine_z_axis_load"/>
|
||||
<field name="machine_tool_num"/>
|
||||
<field name="machine_program"/>
|
||||
<field name="machine_current_prg"/>
|
||||
<field name="machine_prg_seq"/>
|
||||
<field name="machine_spindle_speed_set"/>
|
||||
<field name="machine_act_spindle_speed"/>
|
||||
<field name="machine_feed_speed_set"/>
|
||||
<field name="machine_act_feed_speed"/>
|
||||
<field name="machine_spindle_feed"/>
|
||||
<field name="machine_feed_rate"/>
|
||||
<field name="machine_rapid_feed"/>
|
||||
<field name="machine_run_time"/>
|
||||
<field name="machine_cut_time"/>
|
||||
<field name="machine_keep_alive_time"/>
|
||||
<field name="machine_circle_time"/>
|
||||
<field name="machine_product_counts"/>
|
||||
<field name="machine_system_date"/>
|
||||
<field name="machine_system_time"/>
|
||||
<field name="machine_alarm_msg"/>
|
||||
</group>
|
||||
</group>
|
||||
<!-- </group> -->
|
||||
</page>
|
||||
<!-- <page string="刀位配置"> -->
|
||||
<!-- <group string="刀位配置"> -->
|
||||
</group>
|
||||
<!-- <group string="ftp相关"> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num1"/> -->
|
||||
<!-- <field name="tool_num5"/> -->
|
||||
<!-- <field name="tool_num9"/> -->
|
||||
<!-- <field name="tool_num13"/> -->
|
||||
<!-- <field name="tool_num17"/> -->
|
||||
<!-- <field name="tool_num21"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num2"/> -->
|
||||
<!-- <field name="tool_num6"/> -->
|
||||
<!-- <field name="tool_num10"/> -->
|
||||
<!-- <field name="tool_num14"/> -->
|
||||
<!-- <field name="tool_num18"/> -->
|
||||
<!-- <field name="tool_num22"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <field name="ftp_num"/> -->
|
||||
<!-- <field name="ftp_pwd"/> -->
|
||||
<!-- <field name="ftp_host"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num3"/> -->
|
||||
<!-- <field name="tool_num7"/> -->
|
||||
<!-- <field name="tool_num11"/> -->
|
||||
<!-- <field name="tool_num15"/> -->
|
||||
<!-- <field name="tool_num19"/> -->
|
||||
<!-- <field name="tool_num23"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="tool_num4"/> -->
|
||||
<!-- <field name="tool_num8"/> -->
|
||||
<!-- <field name="tool_num12"/> -->
|
||||
<!-- <field name="tool_num16"/> -->
|
||||
<!-- <field name="tool_num20"/> -->
|
||||
<!-- <field name="tool_num24"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <field name="ftp_port"/> -->
|
||||
<!-- <field name="ftp_remote_path"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
<!-- </page> -->
|
||||
<!-- </notebook> -->
|
||||
<!-- <group string="补偿值相关"> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="x_compensation_node"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="y_compensation_node"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group string="数采相关"> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="machine_ip"/> -->
|
||||
<!-- <field name="machine_signed"/> -->
|
||||
<!-- <field name="machine_status"/> -->
|
||||
<!-- <field name="machine_cnc_type"/> -->
|
||||
<!-- <field name="machine_axis_count"/> -->
|
||||
<!-- <field name="machine_run_status"/> -->
|
||||
<!-- <field name="machine_emg_status"/> -->
|
||||
<!-- <field name="machine_cut_status"/> -->
|
||||
<!-- <field name="machine_mode"/> -->
|
||||
<!-- <field name="machine_spindle_load"/> -->
|
||||
<!-- <field name="machine_x_mach"/> -->
|
||||
<!-- <field name="machine_x_abs_mach"/> -->
|
||||
<!-- <field name="machine_x_rel_mach"/> -->
|
||||
<!-- <field name="machine_x_dis_mach"/> -->
|
||||
<!-- <field name="machine_x_axis_load"/> -->
|
||||
<!-- <field name="machine_y_mach"/> -->
|
||||
<!-- <field name="machine_y_abs_mach"/> -->
|
||||
<!-- <field name="machine_y_rel_mach"/> -->
|
||||
<!-- <field name="machine_y_dis_mach"/> -->
|
||||
<!-- <field name="machine_y_axis_load"/> -->
|
||||
<!-- <field name="machine_z_mach"/> -->
|
||||
<!-- <field name="machine_z_abs_mach"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="machine_z_rel_mach"/> -->
|
||||
<!-- <field name="machine_z_dis_mach"/> -->
|
||||
<!-- <field name="machine_z_axis_load"/> -->
|
||||
<!-- <field name="machine_tool_num"/> -->
|
||||
<!-- <field name="machine_program"/> -->
|
||||
<!-- <field name="machine_current_prg"/> -->
|
||||
<!-- <field name="machine_prg_seq"/> -->
|
||||
<!-- <field name="machine_spindle_speed_set"/> -->
|
||||
<!-- <field name="machine_act_spindle_speed"/> -->
|
||||
<!-- <field name="machine_feed_speed_set"/> -->
|
||||
<!-- <field name="machine_act_feed_speed"/> -->
|
||||
<!-- <field name="machine_spindle_feed"/> -->
|
||||
<!-- <field name="machine_feed_rate"/> -->
|
||||
<!-- <field name="machine_rapid_feed"/> -->
|
||||
<!-- <field name="machine_run_time"/> -->
|
||||
<!-- <field name="machine_cut_time"/> -->
|
||||
<!-- <field name="machine_keep_alive_time"/> -->
|
||||
<!-- <field name="machine_circle_time"/> -->
|
||||
<!-- <field name="machine_product_counts"/> -->
|
||||
<!-- <field name="machine_system_date"/> -->
|
||||
<!-- <field name="machine_system_time"/> -->
|
||||
<!-- <field name="machine_alarm_msg"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
</page>
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
<!-- 刀具寿命 -->
|
||||
<!-- <record id="view_cutting_tool_inherited" model="ir.ui.view"> -->
|
||||
<!-- <field name="name">sf_cutting_tool_extension</field> -->
|
||||
<!-- <field name="model">sf.cutting_tool.type</field> -->
|
||||
<!-- <field name="inherit_id" ref="sf_base.form_sf_machine_tool_type"/> -->
|
||||
<!-- <field name="arch" type="xml"> -->
|
||||
<!-- <xpath expr="//form//group" position="after"> -->
|
||||
<!-- <group string='刀具寿命'> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="total_cut_time"/> -->
|
||||
<!-- <field name="tool_position"/> -->
|
||||
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="predict_life_time"/> -->
|
||||
|
||||
<!-- </group> -->
|
||||
|
||||
<!-- <div> -->
|
||||
|
||||
<!-- <div> -->
|
||||
<!-- <field name='is_connect_tool_position' invisible='1'/> -->
|
||||
<!-- <button string="绑定刀位" name="tool_connect_machine" type="object" confirm="是否确认绑定此刀位" -->
|
||||
<!-- class="btn-primary"/> -->
|
||||
<!-- attrs='{"invisible": [("is_connect_tool_position","!=", -->
|
||||
<!-- "False")]}' -->
|
||||
<!-- <span> </span> -->
|
||||
<!-- <button string="解绑刀位" name="tool_unconnect_machine" type="object" confirm="是否解绑此刀位" -->
|
||||
<!-- class="btn-primary"/> -->
|
||||
<!-- attrs='{"invisible": [("is_connect_tool_position","!=", -->
|
||||
<!-- "False")]}' -->
|
||||
|
||||
<!-- </div> -->
|
||||
|
||||
|
||||
|
||||
|
||||
<!-- </div> -->
|
||||
<!-- </group> -->
|
||||
<!-- </xpath> -->
|
||||
<!-- </field> -->
|
||||
<!-- </record> -->
|
||||
</odoo>
|
||||
|
||||
@@ -14,8 +14,23 @@
|
||||
<div class="o_setting_left_pane"/>
|
||||
<div class="o_setting_right_pane">
|
||||
<div class="text-muted">
|
||||
<label for="bfm_url" />
|
||||
<field name="bfm_url" string="访问地址"/>
|
||||
<label for="bfm_url_new" />
|
||||
<field name="bfm_url_new" string="业务平台访问地址"/>
|
||||
</div>
|
||||
</div>
|
||||
<!-- </div> -->
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h2>获取检测报告服务配置</h2>
|
||||
<div class="row mt16 o_settings_container" id="check_report_config">
|
||||
<div class="col-12 col-lg-6 o_setting_box">
|
||||
<div class="o_setting_left_pane"/>
|
||||
<div class="o_setting_right_pane">
|
||||
<div class="text-muted">
|
||||
<label for="get_check_file_path" />
|
||||
<field name="get_check_file_path" string="检测报告服务地址"/>
|
||||
</div>
|
||||
</div>
|
||||
<!-- </div> -->
|
||||
@@ -23,6 +38,18 @@
|
||||
</div>
|
||||
</div>
|
||||
</xpath>
|
||||
<xpath expr="//div[@id='check_report_config']/div" position="after">
|
||||
<div class="col-12 col-lg-6 o_setting_box">
|
||||
<div class="o_setting_left_pane">
|
||||
<field name="is_get_detection_file"/>
|
||||
</div>
|
||||
<div class="o_setting_right_pane">
|
||||
<div class="text-muted">
|
||||
<label for="is_get_detection_file"/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</xpath>
|
||||
</field>
|
||||
</record>
|
||||
</data>
|
||||
|
||||
@@ -24,6 +24,7 @@ class SfEquipmentSaintenanceStandards(models.Model):
|
||||
remark = fields.Char('备注')
|
||||
maintenance_type = fields.Selection([('保养', '保养'), ("检修", "检修")], string='类型', default='保养')
|
||||
name = fields.Char(string='名称')
|
||||
active = fields.Boolean(default=True)
|
||||
|
||||
@api.model_create_multi
|
||||
def create(self, vals_list):
|
||||
|
||||
@@ -38,8 +38,7 @@ class SfMaintenanceEquipment(models.Model):
|
||||
|
||||
crea_url = "/api/machine_tool/create"
|
||||
|
||||
|
||||
#AGV运行日志
|
||||
# AGV运行日志
|
||||
agv_logs = fields.One2many('maintenance.equipment.agv.log', 'equipment_id', string='AGV运行日志')
|
||||
# 1212修改后的字段
|
||||
number_of_axles = fields.Selection(
|
||||
@@ -117,7 +116,6 @@ class SfMaintenanceEquipment(models.Model):
|
||||
# num = "%04d" % m
|
||||
# return num
|
||||
|
||||
|
||||
equipment_maintenance_standards_ids = fields.Many2many('equipment.maintenance.standards',
|
||||
'sf_maintenance_equipment_ids', string='设备维保标准')
|
||||
eq_maintenance_id = fields.Many2one('equipment.maintenance.standards', string='设备保养标准',
|
||||
@@ -179,7 +177,8 @@ class SfMaintenanceEquipment(models.Model):
|
||||
type_id = fields.Many2one('sf.machine_tool.type', '型号')
|
||||
|
||||
state = fields.Selection(
|
||||
[("正常", "正常"), ("故障停机", "故障停机"), ("计划维保", "计划维保"), ("空闲", "空闲"), ("封存(报废)", "封存(报废)")],
|
||||
[("正常", "正常"), ("故障停机", "故障停机"), ("计划维保", "计划维保"), ("空闲", "空闲"),
|
||||
("封存(报废)", "封存(报废)")],
|
||||
default='正常', string="机床状态")
|
||||
run_time = fields.Char('总运行时长')
|
||||
# 0606新增字段
|
||||
@@ -328,7 +327,7 @@ class SfMaintenanceEquipment(models.Model):
|
||||
item.tool_diameter_min = item.type_id.tool_diameter_min
|
||||
item.machine_tool_category = item.type_id.machine_tool_category.id
|
||||
item.brand_id = item.type_id.brand_id.id
|
||||
#新增修改字段
|
||||
# 新增修改字段
|
||||
item.taper_type_id = item.type_id.taper_type_id.id
|
||||
item.function_type = item.type_id.function_type
|
||||
item.a_axis = item.type_id.a_axis
|
||||
@@ -370,7 +369,6 @@ class SfMaintenanceEquipment(models.Model):
|
||||
item.image_id = item.type_id.jg_image_id.ids
|
||||
item.image_lq_id = item.type_id.lq_image_id.ids
|
||||
|
||||
|
||||
# AGV小车设备参数
|
||||
AGV_L = fields.Char('AGV尺寸(长)')
|
||||
AGV_W = fields.Char('AGV尺寸(宽)')
|
||||
@@ -461,18 +459,6 @@ class SfMaintenanceEquipment(models.Model):
|
||||
original_value = fields.Char('原值')
|
||||
incomplete_value = fields.Char('残值')
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# 注册同步机床
|
||||
def enroll_machine_tool(self):
|
||||
sf_sync_config = self.env['res.config.settings'].get_values()
|
||||
@@ -763,7 +749,7 @@ class SfMaintenanceEquipment(models.Model):
|
||||
image_id = fields.Many2many('maintenance.equipment.image', 'equipment_id',
|
||||
domain="[('type', '=', '加工能力')]")
|
||||
image_lq_id = fields.Many2many('maintenance.equipment.image', 'equipment_lq_id', string='冷却方式',
|
||||
domain="[('type', '=', '冷却方式')]")
|
||||
domain="[('type', '=', '冷却方式')]")
|
||||
|
||||
|
||||
class SfRobotAxisNum(models.Model):
|
||||
@@ -777,4 +763,5 @@ class SfRobotAxisNum(models.Model):
|
||||
weight = fields.Char('最大负载(kg)')
|
||||
permissible_load_torque = fields.Char('允许负载扭矩(N-m)')
|
||||
permissible_inertial_torque = fields.Char('允许惯性扭矩(kg-m²)')
|
||||
equipment_id = fields.Many2one('maintenance.equipment', string='机器人', domain="[('equipment_type', '=', '机器人')]")
|
||||
equipment_id = fields.Many2one('maintenance.equipment', string='机器人',
|
||||
domain="[('equipment_type', '=', '机器人')]")
|
||||
|
||||
@@ -1,30 +1,41 @@
|
||||
# -*-coding:utf-8-*-
|
||||
from odoo import fields, models
|
||||
from odoo import fields, models, api
|
||||
|
||||
|
||||
class SfMaintenanceLogs(models.Model):
|
||||
_name = 'sf.maintenance.logs'
|
||||
_description = '设备故障日志'
|
||||
_order = 'alarm_time desc'
|
||||
|
||||
code = fields.Char(string='编码')
|
||||
name = fields.Char(string='名称')
|
||||
code = fields.Char(string='编码', readonly=True)
|
||||
name = fields.Char(string='名称', compute='_compute_name')
|
||||
type = fields.Selection([('type1', '类型1'), ('type2', '类型2')], string='类型')
|
||||
brand = fields.Many2one('sf.machine.brand', related='maintenance_equipment_id.brand_id', string='品牌')
|
||||
maintenance_equipment_id = fields.Many2one('maintenance.equipment', string='设备')
|
||||
maintenance_equipment_id = fields.Many2one('maintenance.equipment', string='机台号')
|
||||
maintenance_equipment_oee_id = fields.Many2one('maintenance.equipment.oee', string='设备oee')
|
||||
code_location = fields.Char(string='编码位置')
|
||||
fault_type = fields.Selection(
|
||||
[('电气类', '电气类'), ('机械类', '机械类'), ('程序类', '程序类'), ('系统类', '系统类')], string='故障类型')
|
||||
fault_code = fields.Char(string='故障代码')
|
||||
fault_alarm_info = fields.Char(string='故障报警信息')
|
||||
fault_alarm_info = fields.Text(string='故障报警信息')
|
||||
alarm_level = fields.Selection([('一级', '一级(严重)'), ('二级', '二级(中等)'), ('三级', '三级(轻微)')],
|
||||
string='报警级别')
|
||||
alarm_time = fields.Datetime(string='报警时间')
|
||||
alarm_time = fields.Datetime(string='故障报警时间')
|
||||
alarm_way = fields.Selection([('文本提示报警', '文本提示报警'), ('声光报警', '声光报警'), ('图文报警', '图文报警')],
|
||||
string='报警方式')
|
||||
fault_process = fields.Text(string='故障处理方法')
|
||||
operator = fields.Many2one('res.users', string='处理人')
|
||||
recovery_time = fields.Datetime(string='复原时间')
|
||||
recovery_time = fields.Datetime(string='故障消除时间')
|
||||
fault_duration = fields.Float(string='故障时长')
|
||||
note = fields.Text(string='备注')
|
||||
active = fields.Boolean('Active', default=True)
|
||||
|
||||
@api.depends('code')
|
||||
def _compute_name(self):
|
||||
for record in self:
|
||||
if record.code:
|
||||
record.name = self.env['maintenance.equipment'].sudo().search([('code', '=', record.code), ('active', '=', True)]).name
|
||||
record.maintenance_equipment_id = self.env['maintenance.equipment'].sudo().search([('code', '=', record.code), ('active', '=', True)]).id
|
||||
else:
|
||||
record.name = ''
|
||||
|
||||
|
||||
@@ -1,5 +1,46 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
import re
|
||||
import json
|
||||
import datetime
|
||||
import requests
|
||||
from odoo import api, fields, models, _
|
||||
from odoo.exceptions import UserError
|
||||
|
||||
|
||||
def convert_to_seconds(time_str):
|
||||
# 修改正则表达式,使 H、M、S 部分可选
|
||||
|
||||
if time_str is None:
|
||||
return 0
|
||||
|
||||
pattern = r"(?:(\d+)H)?(?:(\d+)M)?(?:(\d+)S)?"
|
||||
|
||||
match = re.match(pattern, time_str)
|
||||
|
||||
if match:
|
||||
# 提取各时间单位,如果某个单位缺失则默认设为0
|
||||
hours = int(match.group(1)) if match.group(1) else 0
|
||||
minutes = int(match.group(2)) if match.group(2) else 0
|
||||
seconds = int(match.group(3)) if match.group(3) else 0
|
||||
|
||||
# 计算总秒数
|
||||
total_seconds = hours * 3600 + minutes * 60 + seconds
|
||||
if total_seconds == 0:
|
||||
# return None
|
||||
pattern = r"(?:(\d+)小时)?(?:(\d+)分钟)?(?:(\d+)秒)?"
|
||||
match = re.match(pattern, time_str)
|
||||
if match:
|
||||
# 提取各时间单位,如果某个单位缺失则默认设为0
|
||||
hours = int(match.group(1)) if match.group(1) else 0
|
||||
minutes = int(match.group(2)) if match.group(2) else 0
|
||||
seconds = int(match.group(3)) if match.group(3) else 0
|
||||
|
||||
# 计算总秒数
|
||||
total_seconds = hours * 3600 + minutes * 60 + seconds
|
||||
return total_seconds
|
||||
else:
|
||||
return None
|
||||
return total_seconds
|
||||
|
||||
|
||||
class SfMaintenanceEquipmentOEE(models.Model):
|
||||
@@ -7,23 +48,227 @@ class SfMaintenanceEquipmentOEE(models.Model):
|
||||
_description = '设备OEE'
|
||||
|
||||
name = fields.Char('设备oee')
|
||||
equipment_id = fields.Many2one('maintenance.equipment', '设备',
|
||||
equipment_id = fields.Many2one('maintenance.equipment', '机台号',
|
||||
domain="[('category_id.equipment_type', '=', '机床'),('state_zc', '=', '已注册')]")
|
||||
|
||||
equipment_code = fields.Char('设备编码', related='equipment_id.code', store=True)
|
||||
|
||||
type_id = fields.Many2one('sf.machine_tool.type', '型号', related='equipment_id.type_id')
|
||||
machine_tool_picture = fields.Binary('设备图片', related='equipment_id.machine_tool_picture')
|
||||
machine_tool_picture = fields.Binary('设备图片', related='equipment_id.machine_tool_picture')
|
||||
state = fields.Selection(
|
||||
[("正常", "正常"), ("故障停机", "故障停机"), ("计划维保", "计划维保"), ("空闲", "空闲"),
|
||||
("封存(报废)", "封存(报废)")],
|
||||
default='正常', string="机床状态", related='equipment_id.state')
|
||||
run_time = fields.Float('正常运行总时长(h)')
|
||||
equipment_time = fields.Float('总时长(h)')
|
||||
done_nums = fields.Integer('累计加工总件数')
|
||||
utilization_rate = fields.Char('开动率')
|
||||
fault_time = fields.Float('故障停机总时长(h)')
|
||||
fault_nums = fields.Integer('故障次数')
|
||||
|
||||
online_time = fields.Char('开机时长(小时)', reaonly='True')
|
||||
|
||||
offline_time = fields.Char('关机时长(小时)', reaonly='True')
|
||||
idle_nums = fields.Integer('待机次数', reaonly='True')
|
||||
# 待机时长
|
||||
|
||||
idle_time = fields.Char('待机时长(小时)', reaonly='True')
|
||||
|
||||
# 待机率
|
||||
idle_rate = fields.Char('待机率(%)', reaonly='True')
|
||||
|
||||
work_time = fields.Char('加工时长(小时)', reaonly='True')
|
||||
work_rate = fields.Char('可用率(%)', reaonly='True')
|
||||
fault_time = fields.Char('故障时长(小时)', reaonly='True')
|
||||
fault_rate = fields.Char('故障率(%)', reaonly='True')
|
||||
fault_nums = fields.Integer('故障次数', reaonly='True')
|
||||
|
||||
# 设备故障日志
|
||||
sf_maintenance_logs_ids = fields.One2many('sf.maintenance.logs', 'maintenance_equipment_oee_id', '设备故障日志',
|
||||
related='equipment_id.sf_maintenance_logs_ids')
|
||||
oee_logs = fields.One2many('maintenance.equipment.oee.logs', 'equipment_oee_id', string='运行日志')
|
||||
|
||||
day_logs_detail = fields.Html('日运行日志详情')
|
||||
history_logs_detail = fields.Html('历史运行日志详情')
|
||||
begin_time = fields.Date('开始时间')
|
||||
end_time = fields.Date('结束时间')
|
||||
|
||||
# 获取日志详情
|
||||
def get_day_logs(self):
|
||||
base_url = self.env['ir.config_parameter'].sudo().get_param('web.base.url')
|
||||
print(base_url)
|
||||
config = self.env['ir.config_parameter'].sudo()
|
||||
# url = 'http://172.16.10.112:8069/api/logs/list'
|
||||
# url_time = 'http://localhost:9069/api/RunningTimeDetail'
|
||||
url = base_url + '/api/logs/list'
|
||||
url_time = base_url + '/api/RunningTimeDetail'
|
||||
machine_list = [self.equipment_code]
|
||||
begin_time = datetime.datetime.now().strftime('%Y-%m-%d') + ' 00:00:00'
|
||||
end_time = datetime.datetime.now().strftime('%Y-%m-%d') + ' 23:59:59'
|
||||
|
||||
# 请求的数据
|
||||
data = {
|
||||
"machine_list": str(machine_list),
|
||||
"begin_time": begin_time,
|
||||
"end_time": end_time
|
||||
}
|
||||
|
||||
data_time = {
|
||||
"machine_list": str(machine_list)
|
||||
}
|
||||
|
||||
print(data)
|
||||
|
||||
# 发送POST请求
|
||||
response = requests.post(url, json={}, data=data)
|
||||
response_time = requests.post(url_time, json={}, data=data_time)
|
||||
# print(response.json()) # 输出服务器返回的响应
|
||||
print(response_time.json())
|
||||
if response_time.status_code == 200:
|
||||
result_time = response_time.json()
|
||||
real_dict = result_time['data'][self.equipment_code]
|
||||
print('=', result_time)
|
||||
if result_time['status'] == 1:
|
||||
self.online_time = round((convert_to_seconds(real_dict['power_on_time']) - convert_to_seconds(
|
||||
real_dict['power_on_24_time'])) / 3600, 2)
|
||||
self.work_time = round(
|
||||
(convert_to_seconds(real_dict['cut_time']) - convert_to_seconds(real_dict['cut_24_time'])) / 3600,
|
||||
2)
|
||||
self.offline_time = 24 - (float(self.online_time) if self.online_time else 0)
|
||||
self.idle_time = float(self.online_time) - float(
|
||||
self.work_time) if self.online_time and self.work_time else 0
|
||||
self.idle_rate = round(
|
||||
float(self.idle_time) / (float(self.online_time) if self.online_time else 1) * 100, 2)
|
||||
self.work_rate = round(
|
||||
float(self.work_time) / (float(self.online_time) if self.online_time else 1) * 100, 2)
|
||||
self.fault_time = (float(real_dict['alarm_last_24_time']) if real_dict[
|
||||
'alarm_last_24_time'] else 0) / 3600
|
||||
self.fault_rate = round(
|
||||
float(self.fault_time) / (float(self.online_time) if self.online_time else 1) * 100, 2)
|
||||
self.fault_nums = real_dict['alarm_last_24_nums']
|
||||
self.idle_nums = real_dict['idle_count']
|
||||
|
||||
if response.status_code == 200:
|
||||
result = response.json()
|
||||
print('============', result)
|
||||
if result['status'] == 1:
|
||||
logs_list = result['data'][self.equipment_code]
|
||||
logs_detail = ''
|
||||
log_state = ''
|
||||
for log in logs_list:
|
||||
if log['state'] != log_state:
|
||||
print('loooooooooooooooooooogs', log)
|
||||
production_name = log['production_name'] if log['production_name'] else ' '
|
||||
logs_detail += '<tr><td>' + log['time'] + '</td><td>' + log[
|
||||
'state'] + '</td><td>' + production_name + '</td></tr>'
|
||||
log_state = log['state']
|
||||
# self.day_logs_detail = '<table><tr><th>时间</th><th>事件/状态</th><th>加工工单</th></tr>' + logs_detail + '</table>'
|
||||
self.day_logs_detail = '''
|
||||
<table border="1" style="border-collapse: collapse; width: 100%; text-align: center;">
|
||||
<tr style="background-color: #f2f2f2;">
|
||||
<th style="padding: 8px; border: 1px solid #ddd;">时间</th>
|
||||
<th style="padding: 8px; border: 1px solid #ddd;">事件/状态</th>
|
||||
<th style="padding: 8px; border: 1px solid #ddd;">加工工单</th>
|
||||
</tr>
|
||||
{logs_detail}
|
||||
</table>
|
||||
'''.format(logs_detail=logs_detail)
|
||||
|
||||
else:
|
||||
self.day_logs_detail = '获取日志失败'
|
||||
else:
|
||||
self.day_logs_detail = '获取日志失败'
|
||||
|
||||
# 获取历史日志详情
|
||||
def get_history_logs(self):
|
||||
config = self.env['ir.config_parameter'].sudo()
|
||||
base_url = self.env['ir.config_parameter'].sudo().get_param('web.base.url')
|
||||
# url = 'http://172.16.10.112:8069/api/logs/list'
|
||||
url = base_url + '/api/logs/list'
|
||||
url_time = base_url + '/api/RunningTimeDetail'
|
||||
machine_list = [self.equipment_code]
|
||||
if not self.begin_time:
|
||||
raise UserError('请选择开始时间')
|
||||
if not self.end_time:
|
||||
raise UserError('请选择结束时间')
|
||||
|
||||
begin_time = self.begin_time.strftime('%Y-%m-%d') + ' 00:00:00'
|
||||
end_time = self.end_time.strftime('%Y-%m-%d') + ' 23:59:59'
|
||||
|
||||
# 请求的数据
|
||||
data = {
|
||||
"machine_list": str(machine_list),
|
||||
"begin_time": begin_time,
|
||||
"end_time": end_time
|
||||
}
|
||||
|
||||
print(data)
|
||||
|
||||
# 发送POST请求
|
||||
response = requests.post(url, json={}, data=data)
|
||||
print(response.json()) # 输出服务器返回的响应
|
||||
if response.status_code == 200:
|
||||
result = response.json()
|
||||
print('============', result)
|
||||
if result['status'] == 1:
|
||||
logs_list = result['data'][self.equipment_code]
|
||||
logs_detail = ''
|
||||
log_state = ''
|
||||
for log in logs_list:
|
||||
if log['state'] != log_state:
|
||||
production_name = log['production_name'] if log['production_name'] else ' '
|
||||
logs_detail += '<tr><td>' + log['time'] + '</td><td>' + log[
|
||||
'state'] + '</td><td>' + production_name + '</td></tr>'
|
||||
log_state = log['state']
|
||||
# self.day_logs_detail = '<table><tr><th>时间</th><th>事件/状态</th><th>加工工单</th></tr>' + logs_detail + '</table>'
|
||||
self.history_logs_detail = '''
|
||||
<table border="1" style="border-collapse: collapse; width: 100%; text-align: center;">
|
||||
<tr style="background-color: #f2f2f2;">
|
||||
<th style="padding: 8px; border: 1px solid #ddd;">时间</th>
|
||||
<th style="padding: 8px; border: 1px solid #ddd;">事件/状态</th>
|
||||
<th style="padding: 8px; border: 1px solid #ddd;">加工工单</th>
|
||||
</tr>
|
||||
{logs_detail}
|
||||
</table>
|
||||
'''.format(logs_detail=logs_detail)
|
||||
|
||||
else:
|
||||
self.history_logs_detail = '获取日志失败'
|
||||
else:
|
||||
self.history_logs_detail = '获取日志失败'
|
||||
|
||||
# 下载历史日志
|
||||
def download_history_logs(self):
|
||||
config = self.env['ir.config_parameter'].sudo()
|
||||
url = 'http://172.16.10.112:8069/api/logs/list'
|
||||
machine_list = [self.equipment_code]
|
||||
if not self.begin_time:
|
||||
raise UserError('请选择开始时间')
|
||||
if not self.end_time:
|
||||
raise UserError('请选择结束时间')
|
||||
|
||||
begin_time = self.begin_time.strftime('%Y-%m-%d') + ' 00:00:00'
|
||||
end_time = self.end_time.strftime('%Y-%m-%d') + ' 23:59:59'
|
||||
|
||||
# 请求的数据
|
||||
data = {
|
||||
"machine_list": str(machine_list),
|
||||
"begin_time": begin_time,
|
||||
"end_time": end_time
|
||||
}
|
||||
|
||||
print(data)
|
||||
|
||||
# 发送POST请求
|
||||
response = requests.post(url, json={}, data=data)
|
||||
print(response.json()) # 输出服务器返回的响应
|
||||
if response.status_code == 200:
|
||||
result = response.json()
|
||||
print('============', result)
|
||||
if result['status'] == 1:
|
||||
logs_list = result['data'][self.equipment_code]
|
||||
logs_detail = ''
|
||||
for log in logs_list:
|
||||
production_name = log['production_name'] if log['production_name'] else ' '
|
||||
# todo 下载日志
|
||||
|
||||
else:
|
||||
self.history_logs_detail = '下载日志失败'
|
||||
else:
|
||||
self.history_logs_detail = '下载日志失败'
|
||||
|
||||
def name_get(self):
|
||||
result = []
|
||||
@@ -38,12 +283,57 @@ class SfMaintenanceEquipmentOEELog(models.Model):
|
||||
_name = 'maintenance.equipment.oee.logs'
|
||||
_description = '设备运行日志'
|
||||
|
||||
name = fields.Char('运行日志')
|
||||
run_time = fields.Datetime('时间')
|
||||
state = fields.Selection([("开机", "开机"), ("关机", "关机"), ("等待", "等待"), ("开始加工", "开始加工"),
|
||||
("结束加工", "结束加工"), ("故障", "故障"),
|
||||
("检修", "检修"), ("保养", "保养")], default="", string="事件/状态")
|
||||
workorder_id = fields.Char('加工订单')
|
||||
time = fields.Char('持续时长')
|
||||
color = fields.Char('颜色', default=1)
|
||||
equipment_id = fields.Many2one('maintenance.equipment', '机台号', readonly='True')
|
||||
equipment_code = fields.Char('设备编码', readonly='True')
|
||||
name = fields.Char('设备名称', readonly='True')
|
||||
function_type = fields.Selection(
|
||||
[("ZXJGZX", "钻铣加工中心"), ("CXJGZX", "车削加工中心"), ("FHJGZX", "复合加工中心")],
|
||||
default="", string="功能类型")
|
||||
machine_tool_picture = fields.Binary('设备图片')
|
||||
type_id = fields.Many2one('sf.machine_tool.type', '品牌型号', reaonly='True')
|
||||
state = fields.Selection([("加工", "加工"), ("关机", "关机"), ("待机", "待机"), ("故障", "故障"),
|
||||
("检修", "检修"), ("保养", "保养")], default="", string="实时状态")
|
||||
online_time = fields.Char('开机时长', reaonly='True')
|
||||
|
||||
offline_time = fields.Char('关机时长', reaonly='True')
|
||||
offline_nums = fields.Integer('关机次数', reaonly='True')
|
||||
# 待机时长
|
||||
|
||||
idle_time = fields.Char('待机时长', reaonly='True')
|
||||
|
||||
# 待机率
|
||||
idle_rate = fields.Char('待机率', reaonly='True')
|
||||
|
||||
work_time = fields.Char('加工时长', reaonly='True')
|
||||
work_rate = fields.Char('可用率', reaonly='True')
|
||||
fault_time = fields.Char('故障时长', reaonly='True')
|
||||
fault_rate = fields.Char('故障率', reaonly='True')
|
||||
fault_nums = fields.Integer('故障次数', reaonly='True')
|
||||
|
||||
detail_ids = fields.One2many('maintenance.equipment.oee.log.detail', 'log_id', string='日志详情')
|
||||
|
||||
# maintenance_time = fields.Char('维保时长')
|
||||
# work_nums = fields.Integer('加工件数')
|
||||
equipment_oee_id = fields.Many2one('maintenance.equipment.oee', '设备OEE')
|
||||
|
||||
@api.onchange('equipment_id')
|
||||
def get_name(self):
|
||||
self.name = self.equipment_id.name
|
||||
self.equipment_code = self.equipment_id.code
|
||||
|
||||
|
||||
# 设备运行日志详情
|
||||
class SfMaintenanceEquipmentOEELogDetail(models.Model):
|
||||
_name = 'maintenance.equipment.oee.log.detail'
|
||||
_description = '设备运行日志详情'
|
||||
_order = 'time desc'
|
||||
|
||||
# sequence = fields.Integer('序号', related='id')
|
||||
time = fields.Datetime('时间')
|
||||
state = fields.Selection([("加工", "加工"), ("关机", "关机"), ("待机", "待机"), ("故障", "故障"),
|
||||
("检修", "检修"), ("保养", "保养")], default="", string="事件/状态")
|
||||
production_name = fields.Char('加工工单')
|
||||
|
||||
log_id = fields.Many2one('maintenance.equipment.oee.logs', '日志')
|
||||
# equipment_code = fields.Char('设备编码', related='log_id.equipment_code')
|
||||
equipment_code = fields.Char('设备编码', readonly='True')
|
||||
|
||||
BIN
sf_maintenance/static/description/维护.png
Normal file
BIN
sf_maintenance/static/description/维护.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 858 B |
@@ -6,15 +6,16 @@
|
||||
<field name="name">equipment.maintenance.standards.form</field>
|
||||
<field name="model">equipment.maintenance.standards</field>
|
||||
<field name="arch" type="xml">
|
||||
<form string="设备维保标准">
|
||||
<form string="设备维保标准" delete="false" duplicate="false">
|
||||
<sheet>
|
||||
<group>
|
||||
<group>
|
||||
<field name="code" readonly="1" force_save="1"/>
|
||||
<field name="name" readonly="1" force_save="1"/>
|
||||
<field name="maintenance_equipment_category_id" required="1" />
|
||||
<field name="eq_maintenance_ids" invisible='1'/>
|
||||
<field name="overhaul_ids" invisible='1'/>
|
||||
<group>
|
||||
<field name="active" invisible="1"/>
|
||||
<field name="code" readonly="1" force_save="1"/>
|
||||
<field name="name" readonly="1" force_save="1"/>
|
||||
<field name="maintenance_equipment_category_id" required="1"/>
|
||||
<field name="eq_maintenance_ids" invisible='1'/>
|
||||
<field name="overhaul_ids" invisible='1'/>
|
||||
|
||||
|
||||
</group>
|
||||
@@ -50,7 +51,8 @@
|
||||
<field name="name">equipment.maintenance.standards.tree</field>
|
||||
<field name="model">equipment.maintenance.standards</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree string="设备维保标准">
|
||||
<tree string="设备维保标准" delete="false">
|
||||
<field name="active" invisible="1"/>
|
||||
<field name="code" readonly="1" force_save="1"/>
|
||||
<field name="maintenance_type" required="1"/>
|
||||
<field name="name" required="1"/>
|
||||
@@ -77,6 +79,7 @@
|
||||
<field name="name" string="日常机床保养"/>
|
||||
<field name="created_user_id" string="创建人"/>
|
||||
<field name="maintenance_equipment_category_id" string="设备类别"/>
|
||||
<filter name="filter_active" string="已归档" domain="[('active','=',False)]"/>
|
||||
</search>
|
||||
</field>
|
||||
</record>
|
||||
|
||||
@@ -8,12 +8,13 @@
|
||||
<field name="arch" type="xml">
|
||||
<tree>
|
||||
<field name="equipment_id"/>
|
||||
<field name="equipment_time"/>
|
||||
<field name="run_time"/>
|
||||
<field name="done_nums"/>
|
||||
<field name="utilization_rate"/>
|
||||
<field name="online_time"/>
|
||||
<field name="work_time"/>
|
||||
<field name="work_rate"/>
|
||||
<field name="fault_time"/>
|
||||
<field name="fault_nums"/>
|
||||
<field name="fault_rate"/>
|
||||
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
@@ -36,32 +37,102 @@
|
||||
|
||||
<group>
|
||||
<group>
|
||||
<field name="type_id" readonly="1"/>
|
||||
<field name="equipment_time"/>
|
||||
<field name="run_time"/>
|
||||
<field name="done_nums"/>
|
||||
<field name="utilization_rate"/>
|
||||
<field name="fault_time"/>
|
||||
<field name="fault_nums"/>
|
||||
<group>
|
||||
<field name="equipment_id" domain="[('name','ilike','加工中心')]"/>
|
||||
<field name="type_id"/>
|
||||
<field name="state"/>
|
||||
<field name="equipment_code"/>
|
||||
</group>
|
||||
</group>
|
||||
<group>
|
||||
<field name="machine_tool_picture" widget="image" readonly="1"/>
|
||||
<group>
|
||||
<!-- <field name="state" nolabel="1"/> -->
|
||||
<!-- <field name="state" string=""/> -->
|
||||
</group>
|
||||
<group>
|
||||
<field name="machine_tool_picture" widget="image" nolabel="1"/>
|
||||
</group>
|
||||
</group>
|
||||
</group>
|
||||
<group>
|
||||
<group>
|
||||
<group>
|
||||
<field name="online_time" readonly="1"/>
|
||||
<field name="offline_time" readonly="1"/>
|
||||
<field name="fault_rate" readonly="1"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="idle_nums" readonly="1"/>
|
||||
<field name="fault_time" readonly="1"/>
|
||||
<field name="fault_nums" readonly="1"/>
|
||||
</group>
|
||||
</group>
|
||||
<group>
|
||||
<group>
|
||||
<field name="idle_time"/>
|
||||
<field name="idle_rate"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="work_time"/>
|
||||
<field name="work_rate"/>
|
||||
</group>
|
||||
</group>
|
||||
|
||||
</group>
|
||||
<notebook>
|
||||
<page string="运行日志">
|
||||
<field name="oee_logs">
|
||||
<tree create="1" edit="1" delete="1" editable="bottom">
|
||||
<field name = 'run_time'/>
|
||||
<field name = 'state'/>
|
||||
<field name = 'workorder_id'/>
|
||||
<field name = 'time'/>
|
||||
<field name = 'color' widget="color"/>
|
||||
</tree>
|
||||
</field>
|
||||
<page string="24H日志详情">
|
||||
<group>
|
||||
<button name="get_day_logs" type="object" string="查看24H日志" t-attf-style="white-space:nowrap;"/>
|
||||
</group>
|
||||
<field name="day_logs_detail" readonly="1" widget="html"/>
|
||||
<!-- <field name="page_num"/> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <button name="previous_day_logs" type="object" string="上一页" t-attf-style="white-space:nowrap;"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <button name="next_day_logs" type="object" string="下一页" t-attf-style="white-space:nowrap;"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
|
||||
|
||||
<!-- <field name="day_logs_detail"/> -->
|
||||
<!-- <field name="day_logs_detail" widget="html" nolabel="1"/> -->
|
||||
<!-- <field name="day_logs_detail" widget="html" nolabel="1" class="oe_form_field oe_form_field_html"/> -->
|
||||
<!-- <field name="day_logs_detail" widget="html" nolabel="1" class="oe_form_field oe_form_field_html" options='{"class": "o_form_readonly"}'/> -->
|
||||
<!-- <field name="day_logs_detail" widget="html" nolabel="1" class="oe_form_field oe_form_field_html" options='{"class": "o_form_readonly", "readonly": true, "style": "width: 100%; height: 400px;"}'/> -->
|
||||
<!-- <group> -->
|
||||
<!-- <div class="oe_html_field"> -->
|
||||
<!-- <div id="pagination_day_logs"> -->
|
||||
<!-- <button id="prev_page_day_logs" disabled="true">Previous</button> -->
|
||||
<!-- <button id="next_page_day_logs">Next</button> -->
|
||||
<!-- </div> -->
|
||||
<!-- </div> -->
|
||||
<!-- </group> -->
|
||||
</page>
|
||||
</notebook>
|
||||
<!-- <page string="历史日志详情"> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="begin_time"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <field name="end_time"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <button name="get_history_logs" type="object" string="查看历史日志" t-attf-style="white-space:nowrap;"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- <group> -->
|
||||
<!-- <button name="download_history_logs" type="object" string="下载历史日志" t-attf-style="white-space:nowrap;"/> -->
|
||||
<!-- </group> -->
|
||||
<!-- </group> -->
|
||||
|
||||
<!-- </group> -->
|
||||
<!-- <field name="history_logs_detail"/> -->
|
||||
<!-- </page> -->
|
||||
</notebook>
|
||||
</sheet>
|
||||
</form>
|
||||
</field>
|
||||
|
||||
@@ -7,22 +7,20 @@
|
||||
<field name="model">sf.maintenance.logs</field>
|
||||
<field name="arch" type="xml">
|
||||
<tree>
|
||||
<field name="code"/>
|
||||
<field name="type" optional="hide"/>
|
||||
<field name="brand"/>
|
||||
<field name="maintenance_equipment_id"/>
|
||||
<!-- <field name="brand"/> -->
|
||||
<field name="name"/>
|
||||
<field name="code_location" optional="hide"/>
|
||||
<field name="fault_type"/>
|
||||
<field name="fault_code" optional="hide"/>
|
||||
<field name="alarm_time"/>
|
||||
<field name="fault_alarm_info"/>
|
||||
<field name="alarm_level" optional="hide"/>
|
||||
<field name="alarm_time"/>
|
||||
<field name="alarm_way" optional="hide"/>
|
||||
<field name="fault_process"/>
|
||||
<field name="operator"/>
|
||||
<field name="fault_process" optional="hide"/>
|
||||
<field name="operator" optional="hide"/>
|
||||
<field name="recovery_time"/>
|
||||
<field name="fault_duration"/>
|
||||
<field name="note"/>
|
||||
<field name="note" optional="hide"/>
|
||||
</tree>
|
||||
</field>
|
||||
</record>
|
||||
@@ -39,31 +37,38 @@
|
||||
<sheet>
|
||||
<div class="oe_title">
|
||||
<h1>
|
||||
<field name="code" readonly="1"/>
|
||||
<field name="name" readonly="1"/>
|
||||
</h1>
|
||||
</div>
|
||||
<group>
|
||||
<group>
|
||||
|
||||
<field name="name"/>
|
||||
<field name="type" required="1" widget="radio" options="{'horizontal': true}"/>
|
||||
<field name="brand"/>
|
||||
|
||||
<field name="code"/>
|
||||
<!-- <field name="type" required="1" widget="radio" options="{'horizontal': true}"/> -->
|
||||
<field name="maintenance_equipment_id"/>
|
||||
<field name="code_location"/>
|
||||
<field name="fault_type" required="1" widget="radio" options="{'horizontal': true}"/>
|
||||
<field name="fault_code"/>
|
||||
<field name="fault_process"/>
|
||||
</group>
|
||||
<group>
|
||||
<field name="fault_alarm_info"/>
|
||||
<field name="brand"/>
|
||||
<field name="alarm_time"/>
|
||||
<field name="alarm_way" required="1" widget="radio" options="{'horizontal': true}"/>
|
||||
<field name="operator"/>
|
||||
<field name="recovery_time"/>
|
||||
<field name="fault_duration"/>
|
||||
<field name="note"/>
|
||||
<field name="fault_alarm_info"/>
|
||||
|
||||
<!-- <field name="code_location"/> -->
|
||||
<!-- <field name="fault_type" required="1" widget="radio" options="{'horizontal': true}"/> -->
|
||||
<!-- <field name="fault_code"/> -->
|
||||
|
||||
</group>
|
||||
<group>
|
||||
<field name="operator"/>
|
||||
<field name="fault_process"/>
|
||||
<!-- <field name="alarm_way" required="1" widget="radio" options="{'horizontal': true}"/> -->
|
||||
<field name="recovery_time"/>
|
||||
<field name="fault_duration"/>
|
||||
|
||||
|
||||
</group>
|
||||
|
||||
</group>
|
||||
<group>
|
||||
<field name="note"/>
|
||||
</group>
|
||||
</sheet>
|
||||
</form>
|
||||
@@ -100,7 +105,6 @@
|
||||
</field>
|
||||
</record>
|
||||
|
||||
|
||||
<!-- Action -->
|
||||
|
||||
<record id="action_maintenance_logs" model="ir.actions.act_window">
|
||||
|
||||
@@ -1230,5 +1230,9 @@
|
||||
action="hr_equipment_action1"
|
||||
sequence="0"/>
|
||||
|
||||
<menuitem
|
||||
id="maintenance.menu_maintenance_title"
|
||||
web_icon="sf_maintenance,static/description/维护.png"/>
|
||||
|
||||
|
||||
</odoo>
|
||||
@@ -14,10 +14,15 @@
|
||||
'data': [
|
||||
'data/stock_data.xml',
|
||||
'data/empty_racks_data.xml',
|
||||
'data/panel_data.xml',
|
||||
'data/agv_scheduling_data.xml',
|
||||
'security/group_security.xml',
|
||||
'security/ir.model.access.csv',
|
||||
'wizard/workpiece_delivery_views.xml',
|
||||
'wizard/rework_wizard_views.xml',
|
||||
'wizard/production_wizard_views.xml',
|
||||
'views/mrp_views_menus.xml',
|
||||
'views/agv_scheduling_views.xml',
|
||||
'views/stock_lot_views.xml',
|
||||
'views/mrp_production_addional_change.xml',
|
||||
'views/mrp_routing_workcenter_view.xml',
|
||||
@@ -27,7 +32,7 @@
|
||||
'views/model_type_view.xml',
|
||||
'views/agv_setting_views.xml',
|
||||
'views/sf_maintenance_equipment.xml',
|
||||
|
||||
'views/res_config_settings_views.xml',
|
||||
],
|
||||
'assets': {
|
||||
|
||||
@@ -37,7 +42,9 @@
|
||||
'web.assets_backend': [
|
||||
'sf_manufacturing/static/src/xml/kanban_change.xml',
|
||||
'sf_manufacturing/static/src/js/kanban_change.js',
|
||||
'sf_manufacturing/static/src/scss/kanban_change.scss'
|
||||
'sf_manufacturing/static/src/scss/kanban_change.scss',
|
||||
'sf_manufacturing/static/src/xml/button_show_on_tree.xml',
|
||||
'sf_manufacturing/static/src/js/workpiece_delivery_wizard_confirm.js',
|
||||
]
|
||||
|
||||
},
|
||||
|
||||
@@ -2,6 +2,8 @@
|
||||
import logging
|
||||
import json
|
||||
from datetime import datetime
|
||||
|
||||
from odoo.addons.sf_manufacturing.models.agv_scheduling import RepeatTaskException
|
||||
from odoo import http
|
||||
from odoo.http import request
|
||||
|
||||
@@ -25,7 +27,8 @@ class Manufacturing_Connect(http.Controller):
|
||||
{'content': ret, 'name': 'AutoDeviceApi/GetWoInfo'})
|
||||
logging.info('RfidCode:%s' % ret['RfidCode'])
|
||||
if 'RfidCode' in ret:
|
||||
workorder = request.env['mrp.workorder'].sudo().search([('rfid_code', '=', ret['RfidCode'])])
|
||||
workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('rfid_code', '=', ret['RfidCode']), ('state', '!=', 'rework')])
|
||||
if workorder:
|
||||
for item in workorder:
|
||||
res['Datas'].append({
|
||||
@@ -122,7 +125,8 @@ class Manufacturing_Connect(http.Controller):
|
||||
logging.info('RfidCode:%s' % ret['RfidCode'])
|
||||
if 'RfidCode' in ret:
|
||||
workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('routing_type', '=', '装夹预调'), ('rfid_code', '=', ret['RfidCode'])], limit=1, order='id asc')
|
||||
[('routing_type', '=', '装夹预调'), ('rfid_code', '=', ret['RfidCode']), ('state', '!=', 'rework')],
|
||||
limit=1, order='id asc')
|
||||
if workorder:
|
||||
for item in workorder:
|
||||
if item.material_center_point:
|
||||
@@ -143,7 +147,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
logging.info('get_qcCheck error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/FeedBackStart', type='json', auth='sf_token', methods=['GET', 'POST'], csrf=False,
|
||||
@http.route('/AutoDeviceApi/FeedBackStart', type='json', auth='none', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def button_Work_START(self, **kw):
|
||||
"""
|
||||
@@ -163,7 +167,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
equipment_id = ret["DeviceId"]
|
||||
workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('production_id', '=', production_id), ('routing_type', '=', routing_type),
|
||||
('rfid_code', '!=', False)], limit=1)
|
||||
('rfid_code', '!=', False), ('state', '!=', 'rework')], limit=1)
|
||||
if not workorder:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': '该工单不存在'}
|
||||
return json.JSONEncoder().encode(res)
|
||||
@@ -191,7 +195,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
logging.info('button_Work_START error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/FeedBackEnd', type='json', auth='sf_token', methods=['GET', 'POST'], csrf=False,
|
||||
@http.route('/AutoDeviceApi/FeedBackEnd', type='json', auth='none', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def button_Work_End(self, **kw):
|
||||
"""
|
||||
@@ -211,7 +215,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
routing_type = ret['CraftId']
|
||||
workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('production_id', '=', production_id), ('routing_type', '=', routing_type),
|
||||
('rfid_code', '!=', False)], limit=1)
|
||||
('rfid_code', '!=', False), ('state', '!=', 'rework')], limit=1)
|
||||
if not workorder:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': '该工单不存在'}
|
||||
return json.JSONEncoder().encode(res)
|
||||
@@ -220,28 +224,29 @@ class Manufacturing_Connect(http.Controller):
|
||||
return json.JSONEncoder().encode(res)
|
||||
# workorder.write({'date_finished': datetime.now()})
|
||||
if ret['IsComplete'] is True:
|
||||
workorder.button_finish()
|
||||
# workorder.process_state = '待解除装夹'
|
||||
# workorder.sudo().production_id.process_state = '待解除装夹'
|
||||
workorder.write({'date_finished': datetime.now()})
|
||||
|
||||
# 根据工单的实际结束时间修改排程单的结束时间、状态,同时修改销售订单的状态
|
||||
# if workorder.date_finished:
|
||||
# request.env['sf.production.plan'].sudo().search([('production_id', '=', production_id)]).write(
|
||||
# {'actual_end_time': workorder.date_finished,
|
||||
# 'state': 'finished'})
|
||||
# production_obj = request.env['mrp.production'].sudo().search([('name', '=', production_id)])
|
||||
# if production_obj:
|
||||
# production_obj.sudo().work_order_state = '已完成'
|
||||
# production_obj.write({'state': 'done'})
|
||||
# request.env['sale.order'].sudo().search(
|
||||
# [('name', '=', production_obj.origin)]).write({'schedule_status': 'to deliver'})
|
||||
# workorder.process_state = '待解除装夹'
|
||||
# workorder.sudo().production_id.process_state = '待解除装夹'
|
||||
|
||||
# 根据工单的实际结束时间修改排程单的结束时间、状态,同时修改销售订单的状态
|
||||
# if workorder.date_finished:
|
||||
# request.env['sf.production.plan'].sudo().search([('production_id', '=', production_id)]).write(
|
||||
# {'actual_end_time': workorder.date_finished,
|
||||
# 'state': 'finished'})
|
||||
# production_obj = request.env['mrp.production'].sudo().search([('name', '=', production_id)])
|
||||
# if production_obj:
|
||||
# production_obj.sudo().work_order_state = '已完成'
|
||||
# production_obj.write({'state': 'done'})
|
||||
# request.env['sale.order'].sudo().search(
|
||||
# [('name', '=', production_obj.origin)]).write({'schedule_status': 'to deliver'})
|
||||
|
||||
except Exception as e:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': e}
|
||||
logging.info('button_Work_End error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/PartQualityInspect', type='json', auth='sf_token', methods=['GET', 'POST'], csrf=False,
|
||||
@http.route('/AutoDeviceApi/PartQualityInspect', type='json', auth='none', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def PartQualityInspect(self, **kw):
|
||||
"""
|
||||
@@ -257,39 +262,27 @@ class Manufacturing_Connect(http.Controller):
|
||||
request.env['center_control.interface.log'].sudo().create(
|
||||
{'content': ret, 'name': 'AutoDeviceApi/PartQualityInspect'})
|
||||
production_id = ret['BillId']
|
||||
routing_type = ret['CraftId']
|
||||
# routing_type = ret['CraftId']
|
||||
workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('production_id', '=', production_id), ('routing_type', '=', routing_type)], limit=1)
|
||||
[('production_id', '=', production_id), ('routing_type', '=', 'CNC加工'),
|
||||
('state', 'not in', ['rework', 'done', 'cancel'])], order='sequence asc',
|
||||
limit=1)
|
||||
if workorder:
|
||||
# workorder.test_results = ret['Quality']
|
||||
logging.info('制造订单:%s' % workorder.production_id.name)
|
||||
if 'ReportPaht' in ret:
|
||||
download_state = request.env['mrp.workorder'].with_user(
|
||||
request.env.ref("base.user_admin")).download_reportfile_tmp(workorder,
|
||||
ret['ReportPaht'])
|
||||
if download_state == 1:
|
||||
detection_ret = request.env['mrp.workorder'].with_user(
|
||||
request.env.ref("base.user_admin")).get_detection_file(workorder, ret['ReportPaht'])
|
||||
if detection_ret is True:
|
||||
stock_picking_type = request.env['stock.picking.type'].sudo().search(
|
||||
[('sequence_code', '=', 'SFP')])
|
||||
if stock_picking_type:
|
||||
stock_picking = request.env['stock.picking'].sudo().search(
|
||||
[('product_id', '=', workorder.product_id.id),
|
||||
('origin', '=', workorder.production_id.origin),
|
||||
('picking_type_id', '=', stock_picking_type.id)])
|
||||
if stock_picking:
|
||||
quality_check = request.env['quality.check'].sudo().search(
|
||||
[('product_id', '=', workorder.product_id.id),
|
||||
('picking_id', '=', stock_picking.id)])
|
||||
if quality_check:
|
||||
logging.info('质检单:%s' % quality_check.name)
|
||||
quality_check.write({'report_pdf': workorder.detection_report})
|
||||
elif download_state == 2:
|
||||
res = {'Succeed': False, 'ErrorCode': 205,
|
||||
'Error': 'ReportPaht中的工件号与制造订单%s不匹配,请检查ReportPaht是否正确' % workorder.production_id.name}
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 204, 'Error': '检测报告文件从FTP拉取失败'}
|
||||
if ret['ReportPaht'].find('.pdf') != -1:
|
||||
download_state = request.env['mrp.workorder'].with_user(
|
||||
request.env.ref("base.user_admin")).download_reportfile_tmp(workorder,
|
||||
ret['ReportPaht'])
|
||||
if download_state is True:
|
||||
detection_ret = request.env['mrp.workorder'].with_user(
|
||||
request.env.ref("base.user_admin")).get_detection_file(workorder, ret['ReportPaht'])
|
||||
logging.info('detection_ret:%s' % detection_ret)
|
||||
if detection_ret is False:
|
||||
res = {'Succeed': False, 'ErrorCode': 205, 'Error': '检测报告文件读取失败'}
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 204, 'Error': '检测报告文件从FTP拉取失败'}
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 203, 'Error': '未传ReportPaht字段'}
|
||||
else:
|
||||
@@ -299,7 +292,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
logging.info('PartQualityInspect error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/CMMProgDolod', type='json', auth='sf_token', methods=['GET', 'POST'], csrf=False,
|
||||
@http.route('/AutoDeviceApi/CMMProgDolod', type='json', auth='none', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def CMMProgDolod(self, **kw):
|
||||
"""
|
||||
@@ -317,7 +310,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
if 'RfidCode' in ret:
|
||||
logging.info('RfidCode:%s' % ret['RfidCode'])
|
||||
workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('rfid_code', '=', ret['RfidCode']), ('routing_type', '=', 'CNC加工')])
|
||||
[('rfid_code', '=', ret['RfidCode']), ('routing_type', '=', 'CNC加工'), ('state', '!=', 'rework')])
|
||||
if workorder:
|
||||
for item in workorder.cmm_ids:
|
||||
if item.program_create_date is not False:
|
||||
@@ -339,7 +332,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
logging.info('CMMProgDolod error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/NCProgDolod', type='json', auth='sf_token', methods=['GET', 'POST'], csrf=False,
|
||||
@http.route('/AutoDeviceApi/NCProgDolod', type='json', auth='none', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def NCProgDolod(self, **kw):
|
||||
"""
|
||||
@@ -357,7 +350,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
if 'RfidCode' in ret:
|
||||
logging.info('RfidCode:%s' % ret['RfidCode'])
|
||||
workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('rfid_code', '=', ret['RfidCode']), ('routing_type', '=', 'CNC加工')])
|
||||
[('rfid_code', '=', ret['RfidCode']), ('routing_type', '=', 'CNC加工'), ('state', '!=', 'rework')])
|
||||
if workorder:
|
||||
for item in workorder.cnc_ids:
|
||||
res['Datas'].append({
|
||||
@@ -395,7 +388,7 @@ class Manufacturing_Connect(http.Controller):
|
||||
ret = json.loads(datas)
|
||||
request.env['center_control.interface.log'].sudo().create(
|
||||
{'content': ret, 'name': 'AutoDeviceApi/LocationChange'})
|
||||
logging.info('LocationChange_ret===========:%s' % ret)
|
||||
logging.info('库位变更LocationChange_ret:%s' % ret)
|
||||
RfidCode = ret['RfidCode']
|
||||
ChangeType = ret['ChangeType']
|
||||
OldDeciveId = ret['OldDeciveId']
|
||||
@@ -405,40 +398,86 @@ class Manufacturing_Connect(http.Controller):
|
||||
OldDeciveStart = ret['OldDeciveStart']
|
||||
OldDeciveEnd = ret['OldDeciveEnd']
|
||||
|
||||
temp_val_sn_id = None
|
||||
old_localtion = None
|
||||
# if ChangeType == 'Part' or ChangeType == 'Tool':
|
||||
stock_lot_obj = request.env['stock.lot'].sudo().search(
|
||||
[('rfid', '=', RfidCode)], limit=1)
|
||||
logging.info('stock_lot_obj===========:%s' % stock_lot_obj)
|
||||
if not stock_lot_obj:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': '未根据RfidCode找到该产品'}
|
||||
return json.JSONEncoder().encode(res)
|
||||
if OldPosition:
|
||||
old_localtion = request.env['sf.shelf.location'].sudo().search(
|
||||
[('barcode', '=', OldPosition)], limit=1)
|
||||
logging.info('old_localtion===========:%s' % old_localtion)
|
||||
new_localtion = request.env['sf.shelf.location'].sudo().search(
|
||||
[('barcode', '=', NewPosition)], limit=1)
|
||||
logging.info('new_localtion===========:%s' % new_localtion)
|
||||
if not new_localtion:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': '没有该目标位置'}
|
||||
return json.JSONEncoder().encode(res)
|
||||
if old_localtion:
|
||||
temp_val_sn_id = old_localtion.product_sn_id
|
||||
logging.info('temp_val_sn_id===========:%s' % temp_val_sn_id)
|
||||
old_localtion.product_sn_id = None
|
||||
new_localtion.product_sn_id = temp_val_sn_id
|
||||
logging.info('====1======')
|
||||
else:
|
||||
new_localtion.product_sn_id = stock_lot_obj.id
|
||||
logging.info('=====2======')
|
||||
if ChangeType == 'Part':
|
||||
temp_val_sn_id = None
|
||||
old_localtion = None
|
||||
# if ChangeType == 'Part' or ChangeType == 'Tool':
|
||||
stock_lot_obj = request.env['stock.lot'].sudo().search(
|
||||
[('rfid', '=', RfidCode)], limit=1)
|
||||
logging.info('stock_lot_obj===========:%s' % stock_lot_obj)
|
||||
if not stock_lot_obj:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': '未根据RfidCode找到该产品'}
|
||||
return json.JSONEncoder().encode(res)
|
||||
if OldPosition:
|
||||
old_localtion = request.env['sf.shelf.location'].sudo().search(
|
||||
[('barcode', '=', OldPosition)], limit=1)
|
||||
logging.info('old_localtion===========:%s' % old_localtion)
|
||||
new_localtion = request.env['sf.shelf.location'].sudo().search(
|
||||
[('barcode', '=', NewPosition)], limit=1)
|
||||
logging.info('new_localtion===========:%s' % new_localtion)
|
||||
if not new_localtion:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': '没有该目标位置'}
|
||||
return json.JSONEncoder().encode(res)
|
||||
if old_localtion:
|
||||
temp_val_sn_id = old_localtion.product_sn_id
|
||||
logging.info('temp_val_sn_id===========:%s' % temp_val_sn_id)
|
||||
old_localtion.product_sn_id = None
|
||||
new_localtion.product_sn_id = temp_val_sn_id
|
||||
logging.info('====1======')
|
||||
else:
|
||||
new_localtion.product_sn_id = stock_lot_obj.id
|
||||
logging.info('=====2======')
|
||||
elif ChangeType == 'Tool':
|
||||
# 对功能刀具库位变更信息进行更改
|
||||
def write_tool(DeciveId):
|
||||
if 'Tool' in DeciveId:
|
||||
shelfinfo = list(filter(lambda x: x.get('DeviceId') == DeciveId,
|
||||
request.env['sf.shelf.location'].sudo().get_sf_shelf_location_info(
|
||||
DeciveId)))
|
||||
total_data = request.env['sf.shelf.location.datasync'].sudo().get_total_data()
|
||||
for item in shelfinfo:
|
||||
logging.info('货架已获取信息:%s' % item)
|
||||
shelf_barcode = request.env['sf.shelf.location.datasync'].sudo().find_our_code(
|
||||
total_data, item['Postion'])
|
||||
location_id = request.env['sf.shelf.location'].sudo().search(
|
||||
[('barcode', '=', shelf_barcode)],
|
||||
limit=1)
|
||||
if location_id:
|
||||
# 如果是线边刀库信息,则对功能刀具移动生成记录
|
||||
if 'Tool' in item['Postion']:
|
||||
tool = request.env['sf.functional.cutting.tool.entity'].sudo().search(
|
||||
[('rfid', '=', item['RfidCode']), ('functional_tool_status', '!=', '已拆除')])
|
||||
tool.sudo().tool_in_out_stock_location(location_id)
|
||||
if tool:
|
||||
location_id.product_sn_id = tool.barcode_id.id
|
||||
# 修改功能刀具状态
|
||||
if item.get('State') == '报警':
|
||||
if tool.functional_tool_status != item.get('State'):
|
||||
tool.write({
|
||||
'functional_tool_status': item['State']
|
||||
})
|
||||
else:
|
||||
location_id.product_sn_id = False
|
||||
if item['RfidCode']:
|
||||
logging.info('Rfid为【%s】的功能刀具在系统中不存在!' % item['RfidCode'])
|
||||
else:
|
||||
equipment_id = request.env['maintenance.equipment'].sudo().search([('name', '=', DeciveId)])
|
||||
if equipment_id:
|
||||
equipment_id.sudo().register_equipment_tool()
|
||||
else:
|
||||
res_1 = {'Succeed': False, 'ErrorCode': 202, 'Error': f'设备【{DeciveId}】不存在'}
|
||||
return json.JSONEncoder().encode(res_1)
|
||||
|
||||
if OldDeciveId:
|
||||
write_tool(OldDeciveId)
|
||||
elif NewDeciveId:
|
||||
write_tool(NewDeciveId)
|
||||
except Exception as e:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': e}
|
||||
logging.info('LocationChange error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/AGVToProduct', type='json', auth='sf_token', methods=['GET', 'POST'], csrf=False,
|
||||
@http.route('/AutoDeviceApi/AGVToProduct', type='json', auth='none', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def AGVToProduct(self, **kw):
|
||||
"""
|
||||
@@ -457,47 +496,60 @@ class Manufacturing_Connect(http.Controller):
|
||||
if 'DeviceId' in ret:
|
||||
logging.info('DeviceId:%s' % ret['DeviceId'])
|
||||
if 'IsComplete' in ret:
|
||||
rfid_codes = []
|
||||
workorder_ids = []
|
||||
if ret['IsComplete'] is True or ret['IsComplete'] is False:
|
||||
for i in range(1, 5):
|
||||
logging.info('F-RfidCode:%s' % i)
|
||||
if f'RfidCode{i}' in ret:
|
||||
rfid_code = ret[f'RfidCode{i}']
|
||||
logging.info('RfidCode:%s' % rfid_code)
|
||||
if rfid_code is not None:
|
||||
if rfid_code is not None and rfid_code != '':
|
||||
rfid_codes.append(rfid_code)
|
||||
domain = [
|
||||
('rfid_code', '=', rfid_code),
|
||||
('routing_type', '=', 'CNC加工')
|
||||
('routing_type', '=', 'CNC加工'), ('state', '!=', 'rework')
|
||||
]
|
||||
workorder = request.env['mrp.workorder'].sudo().search(domain, order='id asc')
|
||||
if workorder:
|
||||
for order in workorder:
|
||||
workorder_ids.append(order.id)
|
||||
if order.production_line_state == '待上产线':
|
||||
logging.info(
|
||||
'工单产线状态:%s' % order.production_line_state)
|
||||
panel_workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('rfid_code', '=', rfid_code),
|
||||
[('rfid_code', '=', rfid_code), ('state', '!=', 'rework'),
|
||||
('processing_panel', '=', order.processing_panel)])
|
||||
if panel_workorder:
|
||||
panel_workorder.write({'production_line_state': '已上产线'})
|
||||
workpiece_delivery = request.env['sf.workpiece.delivery'].sudo().search(
|
||||
[
|
||||
('rfid_code', '=', rfid_code), ('type', '=', '上产线'),
|
||||
('production_id', '=', order.production_id.id)])
|
||||
if workpiece_delivery.status == '待下发':
|
||||
workpiece_delivery.write({'is_manual_work': True})
|
||||
# workpiece_delivery = request.env['sf.workpiece.delivery'].sudo().search(
|
||||
# [
|
||||
# ('rfid_code', '=', rfid_code), ('type', '=', '上产线'),
|
||||
# ('production_id', '=', order.production_id.id),
|
||||
# ('workorder_id', '=', order.id),
|
||||
# ('workorder_state', '=', 'done')])
|
||||
# if workpiece_delivery.status == '待下发':
|
||||
# workpiece_delivery.write({'is_manual_work': True})
|
||||
# 下发
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 204,
|
||||
'Error': 'DeviceId为%s没有对应的已配送工件数据' % ret['DeviceId']}
|
||||
if ret['IsComplete'] is True:
|
||||
# 向AGV任务调度下发运送空料架任务
|
||||
workorders = request.env['mrp.workorder'].browse(workorder_ids)
|
||||
request.env['sf.agv.scheduling'].add_scheduling(ret['DeviceId'], '运送空料架', workorders)
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 203, 'Error': '未传IsComplete字段'}
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 201, 'Error': '未传DeviceId字段'}
|
||||
except RepeatTaskException as e:
|
||||
logging.info('AGVToProduct error:%s' % e)
|
||||
except Exception as e:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': e}
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': str(e)}
|
||||
logging.info('AGVToProduct error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/AGVDownProduct', type='json', auth='sf_token', methods=['GET', 'POST'], csrf=False,
|
||||
@http.route('/AutoDeviceApi/AGVDownProduct', type='json', auth='none', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def AGVDownProduct(self, **kw):
|
||||
"""
|
||||
@@ -516,7 +568,8 @@ class Manufacturing_Connect(http.Controller):
|
||||
logging.info('ret:%s' % ret)
|
||||
if 'DeviceId' in ret:
|
||||
logging.info('DeviceId:%s' % ret['DeviceId'])
|
||||
delivery_Arr = []
|
||||
# delivery_Arr = []
|
||||
workorder_ids = []
|
||||
if 'IsComplete' in ret:
|
||||
if ret['IsComplete'] is True or ret['IsComplete'] is False:
|
||||
for i in range(1, 5):
|
||||
@@ -524,48 +577,59 @@ class Manufacturing_Connect(http.Controller):
|
||||
if f'RfidCode{i}' in ret:
|
||||
rfid_code = ret[f'RfidCode{i}']
|
||||
logging.info('RfidCode:%s' % rfid_code)
|
||||
if rfid_code is not None:
|
||||
if rfid_code is not None and rfid_code != '':
|
||||
domain = [
|
||||
('rfid_code', '=', rfid_code),
|
||||
('routing_type', '=', 'CNC加工')
|
||||
('routing_type', '=', 'CNC加工'), ('state', '!=', 'rework')
|
||||
]
|
||||
workorder = request.env['mrp.workorder'].sudo().search(domain, order='id asc')
|
||||
if workorder:
|
||||
for order in workorder:
|
||||
workorder_ids.append(order.id)
|
||||
if order.production_line_state == '已上产线':
|
||||
logging.info(
|
||||
'工单产线状态:%s' % order.production_line_state)
|
||||
panel_workorder = request.env['mrp.workorder'].sudo().search(
|
||||
[('rfid_code', '=', rfid_code),
|
||||
[('rfid_code', '=', rfid_code), ('state', '!=', 'rework'),
|
||||
('processing_panel', '=', order.processing_panel)])
|
||||
if panel_workorder:
|
||||
panel_workorder.write({'production_line_state': '已下产线'})
|
||||
workpiece_delivery = request.env['sf.workpiece.delivery'].sudo().search(
|
||||
[
|
||||
('rfid_code', '=', rfid_code), ('type', '=', '下产线'),
|
||||
('production_id', '=', order.production_id.id)])
|
||||
delivery_Arr.append(workpiece_delivery.id)
|
||||
workorder.write({'state': 'to be detected'})
|
||||
# workpiece_delivery = request.env['sf.workpiece.delivery'].sudo().search(
|
||||
# [
|
||||
# ('rfid_code', '=', rfid_code), ('type', '=', '下产线'),
|
||||
# ('production_id', '=', order.production_id.id),
|
||||
# ('workorder_id', '=', order.id),
|
||||
# ('workorder_state', '=', 'done')])
|
||||
# if workpiece_delivery:
|
||||
# delivery_Arr.append(workpiece_delivery.id)
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 204,
|
||||
'Error': 'DeviceId为%s没有对应的已配送工件数据' % ret['DeviceId']}
|
||||
if delivery_Arr:
|
||||
logging.info('delivery_Arr:%s' % delivery_Arr)
|
||||
delivery_workpiece = request.env['sf.workpiece.delivery'].sudo().search(
|
||||
[('id', 'in', delivery_Arr)])
|
||||
if delivery_workpiece:
|
||||
logging.info('开始向agv下发下产线任务')
|
||||
agv_site = request.env['sf.agv.site'].sudo().search([])
|
||||
if agv_site:
|
||||
has_site = agv_site.update_site_state()
|
||||
if has_site is True:
|
||||
is_free = delivery_workpiece._check_avgsite_state()
|
||||
if is_free is True:
|
||||
delivery_workpiece._delivery_avg()
|
||||
logging.info('agv下发下产线任务下发完成')
|
||||
# if delivery_Arr:
|
||||
# logging.info('delivery_Arr:%s' % delivery_Arr)
|
||||
# delivery_workpiece = request.env['sf.workpiece.delivery'].sudo().search(
|
||||
# [('id', 'in', delivery_Arr)])
|
||||
# if delivery_workpiece:
|
||||
# logging.info('开始向agv下发下产线任务')
|
||||
# agv_site = request.env['sf.agv.site'].sudo().search([])
|
||||
# if agv_site:
|
||||
# has_site = agv_site.update_site_state()
|
||||
# if has_site is True:
|
||||
# is_free = delivery_workpiece._check_avgsite_state()
|
||||
# if is_free is True:
|
||||
# delivery_workpiece._delivery_avg()
|
||||
# logging.info('agv下发下产线任务下发完成')
|
||||
if ret['IsComplete'] is True:
|
||||
# 向AGV任务调度下发下产线任务
|
||||
workorders = request.env['mrp.workorder'].browse(workorder_ids)
|
||||
request.env['sf.agv.scheduling'].add_scheduling(ret['DeviceId'], '下产线', workorders)
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 203, 'Error': '未传IsComplete字段'}
|
||||
except RepeatTaskException as e:
|
||||
logging.info('AGVToProduct error:%s' % e)
|
||||
except Exception as e:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': e}
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': str(e)}
|
||||
logging.info('AGVDownProduct error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@@ -603,3 +667,32 @@ class Manufacturing_Connect(http.Controller):
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': e}
|
||||
logging.info('AGVDownProduct error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
|
||||
@http.route('/AutoDeviceApi/AgvStationState', type='json', auth='public', methods=['GET', 'POST'], csrf=False,
|
||||
cors="*")
|
||||
def AGVStationState(self, **kw):
|
||||
"""
|
||||
中控推送接驳站状态
|
||||
:param kw:
|
||||
:return:
|
||||
"""
|
||||
logging.info('AGVStationState:%s' % kw)
|
||||
try:
|
||||
res = {'Succeed': True}
|
||||
datas = request.httprequest.data
|
||||
ret = json.loads(datas)
|
||||
request.env['center_control.interface.log'].sudo().create(
|
||||
{'content': ret, 'name': 'AutoDeviceApi/AGVStationState'})
|
||||
logging.info('ret:%s' % ret)
|
||||
ret = ret['param']
|
||||
params = {}
|
||||
for i in range(len(ret)):
|
||||
if 'DeviceId' in ret[i] and 'AtHome' in ret[i]:
|
||||
logging.info('DeviceId:%s, AtHome:%s' % (ret[i]['DeviceId'], ret[i]['AtHome']))
|
||||
params[ret[i]['DeviceId']] = '占用' if ret[i]['AtHome'] else '空闲'
|
||||
if params:
|
||||
request.env['sf.agv.site'].update_site_state(params)
|
||||
except Exception as e:
|
||||
res = {'Succeed': False, 'ErrorCode': 202, 'Error': str(e)}
|
||||
logging.info('AGVDownProduct error:%s' % e)
|
||||
return json.JSONEncoder().encode(res)
|
||||
@@ -25,15 +25,14 @@ class Workpiece(http.Controller):
|
||||
if 'reqCode' in ret:
|
||||
if 'method' in ret:
|
||||
if ret['method'] == 'end':
|
||||
req_codes = ret['reqCode'].split(',')
|
||||
for req_code in req_codes:
|
||||
workpiece_delivery = request.env['sf.workpiece.delivery'].sudo().search(
|
||||
[('name', '=', req_code.strip()), ('task_completion_time', '=', False)])
|
||||
if workpiece_delivery:
|
||||
workpiece_delivery.write({'status': '已配送', 'task_completion_time': datetime.now()})
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 203,
|
||||
'Error': '该reqCode暂未查到对应的工件配送记录'}
|
||||
# 找到对应的AGV调度任务
|
||||
agv_scheduling = request.env['sf.agv.scheduling'].sudo().search(
|
||||
[('name', '=', ret['reqCode']), ('state', '=', '配送中')])
|
||||
if agv_scheduling:
|
||||
agv_scheduling.finish_scheduling()
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 203,
|
||||
'Error': '该reqCode暂未查到对应的AGV任务记录'}
|
||||
else:
|
||||
res = {'Succeed': False, 'ErrorCode': 204, 'Error': '未传method字段'}
|
||||
else:
|
||||
|
||||
16
sf_manufacturing/data/agv_scheduling_data.xml
Normal file
16
sf_manufacturing/data/agv_scheduling_data.xml
Normal file
@@ -0,0 +1,16 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<data noupdate="0">
|
||||
<record id="sequence_agv_scheduling" model="ir.sequence">
|
||||
<field name="name">AGV调度</field>
|
||||
<field name="code">sf.agv.scheduling</field>
|
||||
<field name="prefix">B%(year)s%(month)s%(day)s</field>
|
||||
<field name="padding">4</field>
|
||||
<field name="number_next">1</field>
|
||||
<field name="implementation">standard</field>
|
||||
<field name="use_date_range">True</field>
|
||||
<field name="date_range_period">day</field>
|
||||
<field name="company_id" eval="False"/>
|
||||
</record>
|
||||
</data>
|
||||
</odoo>
|
||||
24
sf_manufacturing/data/panel_data.xml
Normal file
24
sf_manufacturing/data/panel_data.xml
Normal file
@@ -0,0 +1,24 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<data noupdate="1">
|
||||
<record id="panel_zm" model="sf.processing.panel">
|
||||
<field name="name">ZM</field>
|
||||
</record>
|
||||
|
||||
<record id="panel_fm" model="sf.processing.panel">
|
||||
<field name="name">FM</field>
|
||||
</record>
|
||||
<record id="panel_yc" model="sf.processing.panel">
|
||||
<field name="name">YC</field>
|
||||
</record>
|
||||
<record id="panel_zc" model="sf.processing.panel">
|
||||
<field name="name">ZC</field>
|
||||
</record>
|
||||
<record id="panel_qc" model="sf.processing.panel">
|
||||
<field name="name">QC</field>
|
||||
</record>
|
||||
<record id="panel_hc" model="sf.processing.panel">
|
||||
<field name="name">HC</field>
|
||||
</record>
|
||||
</data>
|
||||
</odoo>
|
||||
@@ -1,6 +1,16 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<data noupdate="1">
|
||||
<record model="ir.cron" id="ir_cron_mrp_production">
|
||||
<field name="name">返工且编程中的制造订单定时获取Cloud编程单状态</field>
|
||||
<field name="model_id" ref="model_mrp_production"/>
|
||||
<field name="state">code</field>
|
||||
<field name="code">model._cron_get_programming_state()</field>
|
||||
<field name="interval_number">3</field>
|
||||
<field name="interval_type">minutes</field>
|
||||
<field name="numbercall">-1</field>
|
||||
</record>
|
||||
|
||||
<record id="sequence_routing_workcenter" model="ir.sequence">
|
||||
<field name="name">工序编码规则</field>
|
||||
<field name="code">mrp.routing.workcenter</field>
|
||||
|
||||
@@ -9,3 +9,5 @@ from . import stock
|
||||
from . import res_user
|
||||
from . import production_line_base
|
||||
from . import agv_setting
|
||||
from . import agv_scheduling
|
||||
from . import res_config_setting
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user