main.py 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408
  1. # -*- coding: utf-8 -*-
  2. from openerp import http
  3. from openerp.http import request
  4. from werkzeug.wrappers import Response
  5. from werkzeug.datastructures import Headers
  6. from datetime import datetime
  7. from gzip import GzipFile
  8. from StringIO import StringIO as IO
  9. import simplejson as json
  10. import gzip
  11. import logging
  12. LOGGER = logging.getLogger(__name__)
  13. DATE_FORMAT = '%Y-%m-%d'
  14. GZIP_COMPRESSION_LEVEL = 9
  15. class PaymentsSales(http.Controller):
  16. '''
  17. Get server date
  18. '''
  19. def get_server_date(self):
  20. return datetime.now().strftime(DATE_FORMAT)
  21. '''
  22. Get partner customer
  23. '''
  24. def get_user(self):
  25. user = request.env.user
  26. return {
  27. 'id': user.id,
  28. 'name': user.name,
  29. 'displayName': user.display_name,
  30. 'company': {
  31. 'id': user.company_id.id,
  32. 'name': user.company_id.name
  33. },
  34. 'currency': {
  35. 'id': user.company_id.currency_id.id,
  36. 'name': user.company_id.currency_id.name,
  37. 'displayName': user.company_id.currency_id.display_name,
  38. 'symbol': user.company_id.currency_id.symbol,
  39. 'rateSilent': user.company_id.currency_id.rate_silent,
  40. 'thousandsSeparator': user.company_id.currency_id.thousands_separator,
  41. 'decimalSeparator': user.company_id.currency_id.decimal_separator,
  42. 'decimalPlaces': user.company_id.currency_id.decimal_places,
  43. 'position': user.company_id.currency_id.position
  44. }
  45. }
  46. '''
  47. Get Supplier
  48. '''
  49. def get_supplier(self):
  50. decimal_precision = request.env['decimal.precision'].precision_get('Account')
  51. return [{
  52. 'id': supplier.id,
  53. 'name': supplier.name,
  54. 'displayName': supplier.display_name,
  55. 'ruc': supplier.ruc,
  56. 'imageMedium': supplier.image_medium,
  57. 'phone': supplier.phone,
  58. 'mobile': supplier.mobile,
  59. 'email':supplier.email,
  60. 'debit': supplier.debit,
  61. 'invoices': [{
  62. 'id': invoice.id,
  63. 'number': invoice.number ,
  64. 'dateInvoice': invoice.date_invoice,
  65. 'amountTotal': invoice.amount_total,
  66. 'residual': invoice.residual,
  67. 'currencyInvoice': {
  68. 'id': invoice.currency_id.id,
  69. 'displayName': invoice.currency_id.display_name,
  70. 'symbol': invoice.currency_id.symbol,
  71. 'rateSilent': invoice.currency_id.rate_silent,
  72. 'rate': invoice.currency_id.rate,
  73. 'thousandsSeparator': invoice.currency_id.thousands_separator,
  74. 'decimalSeparator': invoice.currency_id.decimal_separator,
  75. 'decimalPlaces': invoice.currency_id.decimal_places,
  76. 'position': invoice.currency_id.position
  77. },
  78. 'moveLines' :[{
  79. 'id': line.id,
  80. 'invoiceNumber': invoice.number,
  81. 'amountResidual': line.amount_residual,
  82. 'credit': line.credit,
  83. 'debit': line.debit,
  84. 'dateMaturity': line.date_maturity,
  85. 'amountCurrency': (line.amount_currency * -1) if (line.amount_currency != 0) else line.credit,
  86. 'amountResidualCurrency': line.amount_residual_currency,
  87. 'currencyInvoice': {
  88. 'id': invoice.currency_id.id,
  89. 'displayName': invoice.currency_id.display_name,
  90. 'symbol': invoice.currency_id.symbol,
  91. 'rateSilent': invoice.currency_id.rate_silent,
  92. 'rate': invoice.currency_id.rate,
  93. 'thousandsSeparator': invoice.currency_id.thousands_separator,
  94. 'decimalSeparator': invoice.currency_id.decimal_separator,
  95. 'decimalPlaces': invoice.currency_id.decimal_places,
  96. 'position': invoice.currency_id.position
  97. },
  98. 'currencyAmount': [{
  99. 'id': currency.id,
  100. 'displayName': currency.display_name,
  101. 'symbol': currency.symbol,
  102. 'rateSilent': currency.rate_silent,
  103. 'rate': currency.rate,
  104. 'thousandsSeparator': currency.thousands_separator,
  105. 'decimalSeparator': currency.decimal_separator,
  106. 'decimalPlaces': currency.decimal_places,
  107. 'position': currency.position,
  108. 'base': currency.base,
  109. 'accuracy': currency.accuracy,
  110. 'rounding': currency.rounding,
  111. 'amountCurencyResidual': round((line.amount_residual_currency * (currency.rate / invoice.currency_id.rate)), decimal_precision)
  112. } for currency in request.env['res.currency'].search([('active', '=', True)])]
  113. } for line in invoice.move_id.line_id if (line.amount_residual > 0 and line.state != "draft" and line.debit <= 0)],
  114. } for invoice in supplier.invoice_ids if (invoice.state == 'open') ],
  115. } for supplier in request.env['res.partner'].search([('active', '=', True), ('supplier', '=', True), ('debit', '<', 0) ])]
  116. '''
  117. Get Journal
  118. '''
  119. def get_journals(self):
  120. domain =[('active', '=', True),('type', 'in',['bank', 'cash'])]
  121. paymentsJournals = []
  122. for journal in request.env['account.journal'].search(domain, order="id"):
  123. if not (journal.store_ids >= request.env.user.store_ids):
  124. continue
  125. paymentsJournals.append({
  126. 'id': journal.id,
  127. 'name': journal.name,
  128. 'displayName': journal.display_name,
  129. 'code': journal.code,
  130. 'cashControl': journal.cash_control,
  131. 'type': journal.type,
  132. 'currency': {
  133. 'id': journal.currency.id,
  134. 'name': journal.currency.name,
  135. 'displayName': journal.currency.display_name,
  136. 'symbol': journal.currency.symbol,
  137. 'rateSilent': journal.currency.rate_silent,
  138. 'thousandsSeparator':journal.currency.thousands_separator,
  139. 'decimalSeparator': journal.currency.decimal_separator,
  140. 'decimalPlaces': journal.currency.decimal_places,
  141. 'position': journal.currency.position
  142. },
  143. 'defaultCreditAccount':{
  144. 'id': journal.default_credit_account_id.id,
  145. 'name': journal.default_credit_account_id.name,
  146. 'displayName': journal.default_credit_account_id.display_name,
  147. 'code': journal.default_credit_account_id.code,
  148. 'exchangeRate': journal.default_credit_account_id.exchange_rate,
  149. 'foreignBalance': journal.default_credit_account_id.foreign_balance,
  150. 'reconcile': journal.default_credit_account_id.reconcile,
  151. 'debit': journal.default_credit_account_id.debit,
  152. 'credit': journal.default_credit_account_id.credit,
  153. 'currencyMode': journal.default_credit_account_id.currency_mode,
  154. 'companyCurrency':{
  155. 'id': journal.default_credit_account_id.company_currency_id.id,
  156. 'name': journal.default_credit_account_id.company_currency_id.name,
  157. 'displayName': journal.default_credit_account_id.company_currency_id.display_name,
  158. 'symbol': journal.default_credit_account_id.company_currency_id.symbol,
  159. 'rateSilent': journal.default_credit_account_id.company_currency_id.rate_silent
  160. },
  161. 'currency':{
  162. 'id': journal.default_credit_account_id.currency_id.id,
  163. 'name': journal.default_credit_account_id.currency_id.name,
  164. 'displayName': journal.default_credit_account_id.currency_id.display_name,
  165. 'symbol': journal.default_credit_account_id.currency_id.symbol,
  166. 'rateSilent': journal.default_credit_account_id.currency_id.rate_silent
  167. },
  168. }
  169. })
  170. return paymentsJournals
  171. '''
  172. Get Currency
  173. '''
  174. def get_currency(self):
  175. return [{
  176. 'id': currency.id,
  177. 'name': currency.name,
  178. 'displayName': currency.display_name,
  179. 'base': currency.base,
  180. 'accuracy': currency.accuracy,
  181. 'rateSilent': currency.rate_silent,
  182. 'rounding': currency.rounding,
  183. 'symbol': currency.symbol,
  184. 'position': currency.position,
  185. 'thousandsSeparator': currency.thousands_separator,
  186. 'decimalSeparator': currency.decimal_separator,
  187. 'decimalPlaces': currency.decimal_places
  188. } for currency in request.env['res.currency'].search([('active', '=', True)])]
  189. '''
  190. Make JSON response
  191. '''
  192. def make_json_response(self, data=None, status=200):
  193. return Response(json.dumps(data), status=status, content_type='application/json')
  194. '''
  195. Make GZIP to JSON response
  196. '''
  197. def make_gzip_response(self, data=None, status=200):
  198. gzip_buffer = IO()
  199. with GzipFile(mode='wb', compresslevel=GZIP_COMPRESSION_LEVEL, fileobj=gzip_buffer) as gzip_file:
  200. gzip_file.write(json.dumps(data))
  201. contents = gzip_buffer.getvalue()
  202. gzip_buffer.close()
  203. headers = Headers()
  204. headers.add('Content-Encoding', 'gzip')
  205. headers.add('Vary', 'Accept-Encoding')
  206. headers.add('Content-Length', len(contents))
  207. return Response(contents, status=status, headers=headers, content_type='application/json')
  208. '''
  209. Logger Info
  210. '''
  211. def make_info_log(self, log):
  212. LOGGER.info(log)
  213. '''
  214. New Payments resource router
  215. '''
  216. @http.route('/eiru_payments_purchases/init', auth='user', methods=['GET'], cors='*')
  217. def init_payments(self, **kw):
  218. self.make_info_log('Sending JSON response')
  219. return self.make_gzip_response({
  220. 'date': self.get_server_date(),
  221. 'user': self.get_user(),
  222. 'supplier': self.get_supplier(),
  223. 'journals': self.get_journals(),
  224. 'currencies': self.get_currency()
  225. })
  226. '''
  227. ____ _ __ ____ __ _____ _ _ _____ ____ ____ ____ ___ ____ _____ ____ ____
  228. | _ \ / \\ \ / / \/ | ____| \ | |_ _/ ___| | _ \| _ \ / _ \ / ___| ____/ ___/ ___|
  229. | |_) / _ \\ V /| |\/| | _| | \| | | | \___ \ | |_) | |_) | | | | | | _| \___ \___ \
  230. | __/ ___ \| | | | | | |___| |\ | | | ___) | | __/| _ <| |_| | |___| |___ ___) |__) |
  231. |_| /_/ \_\_| |_| |_|_____|_| \_| |_| |____/ |_| |_| \_\\___/ \____|_____|____/____/
  232. '''
  233. '''
  234. Get the current period
  235. '''
  236. def get_period(self, date_server):
  237. return request.env['account.period'].search([('date_start','<=', date_server), ('date_stop', '>=', datetime.now().strftime(DATE_FORMAT))])
  238. '''
  239. Get Invoice
  240. '''
  241. def get_invoice(self, invoice_id):
  242. return request.env['account.invoice'].search([('id', '=', invoice_id)])
  243. '''
  244. Create Voucher
  245. '''
  246. def create_voucher(self, period, invoice, company_id, amountPayments, date_server, journalId, move_line_Ids, customerId):
  247. # Get Journal
  248. journal_id = request.env['account.journal'].browse(int(journalId))
  249. currency_id = journal_id.default_credit_account_id.currency_id.id or journal_id.default_credit_account_id.company_currency_id.id
  250. # Get Move Lines
  251. move_line = request.env['account.move.line'].browse(move_line_Ids).sorted(key=lambda r: r.id)
  252. # get customer
  253. customerId = request.env['res.partner'].browse(customerId)
  254. decimal_precision = request.env['decimal.precision'].precision_get('Account')
  255. # Create Line Voucher
  256. company_currency = request.env.user.company_id.currency_id
  257. currencyVocuher = request.env['res.currency'].browse(currency_id)
  258. line_dr_ids = []
  259. amount = round(float(amountPayments), decimal_precision)
  260. for line in move_line:
  261. amount_residual = line.amount_residual
  262. if (company_currency.id != currencyVocuher.id):
  263. amount_residual = round((amount_residual * ( currencyVocuher.rate / company_currency.rate)), decimal_precision)
  264. line_dr_ids.append([0, False, {
  265. 'date_due': line.date_maturity,
  266. 'account_id': line.account_id.id,
  267. 'date_original': line.move_id.date,
  268. 'move_line_id': line.id,
  269. 'amount_original': abs(line.credit or line.debit or 0.0),
  270. 'amount_unreconciled': abs(line.amount_residual),
  271. 'amount': min(abs(amount), abs(amount_residual)),
  272. 'reconcile': True if abs(amount_residual) == min(abs(amount), abs(amount_residual)) else False,
  273. 'currency_id': currency_id
  274. }])
  275. amount -= min(abs(amount), amount_residual)
  276. values = {
  277. 'reference': invoice.number,
  278. 'type': 'payment',
  279. 'journal_id': journal_id.id,
  280. 'company_id': company_id,
  281. 'pre_line': True,
  282. 'amount': round(float(amountPayments), decimal_precision),
  283. 'period_id': period.id,
  284. 'date': date_server,
  285. 'partner_id': customerId.id,
  286. 'account_id': journal_id.default_credit_account_id.id,
  287. 'currency_id': currency_id,
  288. 'line_dr_ids': line_dr_ids,
  289. 'payment_rate_currency_id': currency_id
  290. }
  291. account_voucher = request.env['account.voucher'].create(values)
  292. account_voucher.action_move_line_create()
  293. return account_voucher
  294. '''
  295. close invoice
  296. '''
  297. def close_invoice(self, invoiceid):
  298. invoice = request.env['account.invoice'].search([('id', '=', invoiceid)])
  299. if invoice.residual <= 0:
  300. invoice.confirm_paid()
  301. return invoice
  302. '''
  303. Create bank Statement
  304. '''
  305. def create_bank_statement(self, date_server, user_id, account_voucher):
  306. # Get bank Statamente
  307. bank_statement = request.env['account.bank.statement'].search([('journal_id', '=', account_voucher.journal_id.id), ('date', '=', date_server)])
  308. amount = account_voucher.amount
  309. if account_voucher.type == 'payment':
  310. amount = amount * -1
  311. # Create line bank
  312. bank_statement_line = [[0, False, {
  313. 'name': account_voucher.reference,
  314. 'partner_id': account_voucher.partner_id.id,
  315. 'amount': amount,
  316. 'voucher_id': account_voucher.id,
  317. 'journal_id': account_voucher.journal_id.id,
  318. 'account_id': account_voucher.account_id.id,
  319. 'journal_entry_id': account_voucher.move_id.id,
  320. 'currency_id': account_voucher.currency_id.id,
  321. 'ref': 'NP'
  322. }]]
  323. bank = {
  324. 'journal_id': account_voucher.journal_id.id,
  325. 'period_id': account_voucher.period_id.id,
  326. 'date': date_server,
  327. 'user_id': user_id,
  328. 'state': 'open' if account_voucher.journal_id.type == 'cash' else 'draft',
  329. 'line_ids': bank_statement_line
  330. }
  331. if bank_statement:
  332. if len(bank_statement) == 1:
  333. bank_statement.write(bank)
  334. else:
  335. bank_statement[len(bank_statement) -1].write(bank)
  336. else:
  337. bank_statement = bank_statement.create(bank)
  338. return bank_statement
  339. '''
  340. Payment process
  341. '''
  342. @http.route('/eiru_payments_purchases/purchases_process', type='json', auth='user', methods=['POST'], cors='*')
  343. def purchases_process(self, **kw):
  344. self.make_info_log('Processing payments purchases...')
  345. # Get Date Server
  346. date_server = datetime.now().strftime(DATE_FORMAT)
  347. #Get Periodo
  348. period = self.get_period(date_server)
  349. self.make_info_log('[OK] Getting period')
  350. # Get invoice
  351. invoice = self.get_invoice(kw.get('invoiceId'))
  352. self.make_info_log('[OK] Getting invoice')
  353. # Get User - company
  354. user_id = request.env.user.id
  355. self.make_info_log('[OK] Getting user')
  356. # Get Company
  357. company_id = request.env.user.company_id.id
  358. self.make_info_log('[OK] Getting Company')
  359. # create voucher
  360. voucher = self.create_voucher(period, invoice, company_id, kw.get('amountPayments', 0), date_server, kw.get('journalId'), kw.get('moveLinesId'), kw.get('supplierId'))
  361. self.make_info_log('[OK] creating voucher...')
  362. # close invoice
  363. close_invoice = self.close_invoice(kw.get('invoiceId'))
  364. self.make_info_log('[OK] closing invoice...')
  365. # Create bank statement
  366. bank_statement = self.create_bank_statement(date_server, user_id, voucher)
  367. self.make_info_log('[OK] creating bank statement')
  368. return {
  369. 'process': True
  370. }