gestion des demandes d'évolution pour le centre kalachakra non géré dans les module booking et opendons
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

630 lines
27 KiB

from odoo import models, fields, api
from odoo.exceptions import UserError, ValidationError, Warning
from psycopg2 import sql, DatabaseError
from dateutil.relativedelta import relativedelta
from datetime import datetime
from werkzeug import utils
class EventRegistration(models.Model):
_inherit = 'event.registration'
room_id = fields.Many2one(
'booking.room',
String='Room',
index=True,
group_expand='_read_group_room_ids',
track_visibility='onchange',
)
booking_event=fields.Boolean(related='event_id.booking_event')
event_end=fields.Boolean(related='event_id.stage_id.pipe_end')
medical_concern=fields.Selection(
[('have medical concern','I have a medical concern to report'),
('have no medical concern','I have no medical concern to report'),
('no answer','I don\'t want to answer')],
string='Medical concern',
)
medical_information=fields.Char('Medical informations')
medical_contact_name=fields.Char('Name and Firstname of the contact')
medical_contact_phone=fields.Char('Phone of the contact')
questionnaire_ids=fields.One2many(
'event.registration_questionnaire',
'event_registration_id',
String='Questionnaire',
readonly=True
)
option_ids=fields.One2many(
'event.registration_option',
'event_registration_id',
String='Options',
readonly=True
)
donation_ids=fields.One2many(
'donation.donation',
'event_registration_id',
String='Donations',
readonly=True
)
@api.model
def _default_currency(self):
company = self.env['res.company']._company_default_get(
'event.registration')
return company.currency_id
currency_id = fields.Many2one(
'res.currency',
string='Currency',
required=True,
track_visibility='onchange',
ondelete='restrict',
default=_default_currency
)
down_payment=fields.Boolean('down payment',default=False)
firstname=fields.Char('Firstname')
age=fields.Integer('Age')
gender=fields.Selection([('male','Male'),('femelle','Femelle')],string='gender')
mobile=fields.Char('Mobile')
city=fields.Char('City')
image_right_clearance=fields.Boolean('image right clearance')
train_arrival_time=fields.Float(string="train arrival time")
train_arrival_date=fields.Date(string="train arrival date")
kanban_color=fields.Char('kanban color',compute='_compute_kanban_color')
invoice_state=fields.Selection(related='invoice_id.payment_state')
down_payment_invoice_state=fields.Selection(related='down_payment_invoice_id.payment_state')
balance_invoice_state=fields.Selection(related='balance_invoice_id.payment_state')
invoice_id=fields.Many2one('account.move', readonly=True, ondelete="cascade")
#invoice_state=fields.Selection(related='invoice_id.state')
down_payment_invoice_id=fields.Many2one('account.move', ondelete="cascade")
#down_payment_invoice_state=fields.Selection(related='down_payment_order_id.state')
balance_invoice_id=fields.Many2one('account.move' ,ondelete="cascade")
#balance_invoice_state=fields.Selection(related='balance_order_id.state')
payment_status=fields.Char(string='payment status',compute='_compute_payment_status')
payment_adjustement=fields.Monetary('payment adjustement',currency_field='currency_id')
def _compute_payment_status(self):
for rec in self:
rec.payment_status='not paid'
if rec.invoice_id:
if rec.invoice_state not in ('paid'):rec.payment_status='not paid'
if rec.invoice_state=='paid':rec.payment_status='paid'
else:
if rec.down_payment_invoice_id and balance_invoice_id:
if rec.down_payment_invoice_state!='paid':rec.payment_status='down payment not paid'
if rec.down_payment_invoice_state=='paid' and rec.balance_payment_invoice_state=='paid' :rec.payment_status='paid'
if rec.down_payment_invoice_state=='paid' and rec.balance_payment_invoice_state!='paid':rec.payment_status='down payment paid'
if rec.payment_status=='paid':
rec.state='open'
else:
rec.state='draft'
# @api.onchange('payment_status')
# def _onchange_payment_status(self):
# if self.payment_status=='paid' :self.state='open'
def _compute_kanban_color(self):
for rec in self:
rec.kanban_color=''
if rec.gender=='male':rec.kanban_color="d0e0e3"
if rec.gender=='femelle':rec.kanban_color="eebbcc"
@api.model
def _read_group_room_ids(self, stages, domain, order):
return self.env['booking.room'].search([])
@api.model
def create(self, vals_list):
reg = super(EventRegistration, self).create(vals_list)
return reg
def action_event_registration_order(self):
return True
def create_donation(self,event_registration_id,partner_id,product_id,price_unit):
vals={}
vals['partner_id']=int(partner_id)
vals['donation_date']=datetime.now()
vals['tax_receipt_option']='annual'
#mode de paiement CB par defaut
electronic_method=self.env['account.payment.method'].search([('code','=','electronic')],limit=1)
if electronic_method:
cb_mode=self.env['account.payment.mode'].search([('payment_method_id','=',int(electronic_method.id))],limit=1)
if cb_mode:
vals['payment_mode_id']=cb_mode.id
else:
raise Warning('please configure credit card mode')
#tant que le devis n'est pas validé (paiment effectué), le don est en brouillon
vals['state']='draft'
vals['payment_ref']='internet'
donation_draft=self.env['donation.donation'].sudo().create(vals)
#ajout du don au niveau de l'inscription
reg=self.env['event.registration'].search([('id','=',int(event_registration_id))])
if reg:
reg.write({'donation_ids':[(4,int(donation_draft.id))]})
vals={}
#create line donation
vals['donation_id']=donation_draft.id
product=self.env['product.product'].search([('id','=',int(product_id))])
vals['product_id']=int(product_id)
vals['display_name']=product.name
vals['quantity']=1
vals['unit_price']=price_unit
vals['tax_receipt_ok']=product.tax_receipt_ok
donation_line=self.env['donation.line'].sudo().create(vals)
donation_draft.state='done'
def action_event_registration_generate_invoice(self,id_registration=None):
#suppression des factures existantes
if self.invoice_id:
invoice=self.env['account.move'].sudo().search([('id','=',int(self.invoice_id))])
invoice.state='draft'
#invoice2=self.env['account.move'].sudo().search([('payment_reference','=',invoice.payment_reference)])
#invoice2.unlink()
#raise Warning(invoice2)
if self.down_payment_invoice_id:
invoice=self.env['account.move'].sudo().search([('id','=',int(self.down_payment_invoice_id))])
invoice.state='draft'
# self.env['account.move'].search([('id','=',int(self.down_payment_invoice_id))]).unlink()
# self.down_payment_invoice_id=False
if self.balance_invoice_id:
invoice=self.env['account.move'].sudo().search([('id','=',int(self.balance_invoice_id))])
invoice.state='draft'
# self.env['account.move'].search([('id','=',int(self.balance_invoice_id))]).unlink()
# self.balance_invoice_id=False
#suppression des dons existants
donation=self.env['donation.donation'].sudo().search([('id','in',self.donation_ids.ids)])
for d in donation:
d.state='draft'
self.env['donation.donation'].sudo().search([('id','in',self.donation_ids.ids)]).unlink()
self.donation_ids=False
if id_registration:reg=self.env['event.registration'].search([('id','=',int(id_registration))])
else : reg=self
event=self.env['event.event'].search([('id','=',int(reg.event_id))])
selected_registrant_options=self.env['event.registration_option'].search([
('event_registration_id','=',int(reg.id))])
#controles avant traitement : un produit doit être associé à l'événement
if not event.booking_product_id: raise Warning('product missing for event booking')
#Prix à appliquer au produit en fonction du statut de l'inscrit
status=reg.partner_id.member_status
product_price=event.booking_price
if status=='not member':product_price=event.booking_price
if status=='member':product_price=event.booking_member_price
if status=='super member':product_price=event.booking_super_member_price
#Prix à appliquer au produit si paiement de l'adhésion
membership_option=False
#membership_product=self.env['event.membership_product'].search([])
membership_product=self.env['product.product'].sudo().search([('membership_product','=',True)],limit=1)
if membership_product:
if selected_registrant_options:
for opt in selected_registrant_options:
if opt.booking_option_id==membership_product.id:
membership_option=True
if status!="super member":
product_price=event.booking_member_price
if self.payment_adjustement!=0:
product_price=product_price+self.payment_adjustement
#calcul du montant total à régler
#création du devis sans accompte
if not reg.down_payment:
#création de la facture
vals={}
vals['partner_id']=int(reg.partner_id)
vals['invoice_date']=datetime.now()
#mode de paiement CB par defaut
electronic_method=self.env['account.payment.method'].sudo().search([('code','=','electronic')],limit=1)
if electronic_method:
cb_mode=self.env['account.payment.mode'].sudo().search([('payment_method_id','=',int(electronic_method.id))],limit=1)
if cb_mode:
vals['payment_mode_id']=cb_mode.id
else:
raise Warning('please configure credit card mode')
vals['move_type']='out_invoice'
vals['state']='draft'
#vals['currency_id']=self.currency_id.id
invoice=self.env['account.move'].sudo().create(vals)
invoice.state='posted'
invoice.name='REC'+str(invoice.id)
invoice.payment_reference=invoice.name
vals={}
account_credit=self.env['account.account'].sudo().search([('code','=','707100')])
account_debit=self.env['account.account'].sudo().search([('code','=','411100')])
vals['move_id']=invoice.id
vals['product_id']=int(event.booking_product_id)
vals['quantity']=1
vals['price_unit']=product_price
vals['name']=event.booking_product_id.name
vals['account_id']=int(account_credit.id)
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals)
# #debit_line
vals_d={}
vals_d['move_id']=invoice.id
vals_d['debit']=product_price
vals_d['credit']=0
vals_d['date']=datetime.now()
vals_d['partner_id']=int(reg.partner_id)
vals_d['product_id']=int(event.booking_product_id)
vals_d['name']=event.booking_product_id.name
vals_d['account_id']=int(account_debit.id)
vals_d['quantity']=1
vals_d['price_unit']=product_price
vals_d['exclude_from_invoice_tab']=True
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals_d)
l=self.env['account.move.line'].sudo().search([('move_id','=',invoice.id),('balance','<',0)])
l.partner_id=int(reg.partner_id)
#ajout des options
if selected_registrant_options:
for option in selected_registrant_options:
prd=self.env['product.product'].sudo().search([('id','=',int(option.booking_option_id.id))])
#prix à appliquer aux options en fonction du statut ou de la présence de l'option d'adhesion
event_option=self.env['booking.option'].sudo().search(['&',('event_id','=',int(reg.event_id)),('booking_option_id','=',int(option.booking_option_id.id))],limit=1)
if event_option:
if status=="super member":price_unit=event_option.booking_option_super_member_price
if status=="member":price_unit=event_option.booking_option_member_price
if status=="not member" and membership_option:price_unit=event_option.booking_option_member_price
if status=="not member" and not membership_option:price_unit=event_option.booking_option_price
vals={}
vals['move_id']=invoice.id
#ajout du produit
vals['product_id']=int(option.booking_option_id.id)
vals['quantity']=1
vals['price_unit']=price_unit
vals['name']=prd.name
vals['account_id']=int(account_credit.id)
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals)
#debit_line
vals_d={}
vals_d['move_id']=invoice.id
vals_d['debit']=price_unit
vals_d['credit']=0
vals_d['date']=datetime.now()
vals_d['partner_id']=int(reg.partner_id)
vals_d['product_id']=int(option.booking_option_id.id)
vals_d['name']=prd.name
vals_d['account_id']=int(account_debit.id)
vals_d['quantity']=1
vals_d['price_unit']=price_unit
vals_d['exclude_from_invoice_tab']=True
invoice_line=self.env['account.move.line'].with_context(check_move_validity=True).sudo().create([vals_d])
l=self.env['account.move.line'].sudo().search([('move_id','=',invoice.id),('balance','<',0)])
l.partner_id=int(reg.partner_id)
#si l'option est un produit de don on créé un don pour la personne
if prd.donation: self.sudo().create_donation(reg.id,reg.partner_id,vals['product_id'],vals['price_unit'])
reg.invoice_id=invoice.id
return invoice
#2 factures si paiement avec acompte
else:
#création de la 1ère facture d'acompte
vals={}
vals['partner_id']=int(reg.partner_id)
vals['invoice_date']=datetime.now()
#mode de paiement CB par defaut
electronic_method=self.env['account.payment.method'].sudo().search([('code','=','electronic')],limit=1)
if electronic_method:
cb_mode=self.env['account.payment.mode'].sudo().search([('payment_method_id','=',int(electronic_method.id))],limit=1)
if cb_mode:
vals['payment_mode_id']=cb_mode.id
else:
raise Warning('please configure credit card mode')
vals['move_type']='out_invoice'
vals['state']='draft'
#vals['currency_id']=self.currency_id.id
invoice=self.env['account.move'].sudo().create(vals)
invoice.state='posted'
invoice.name='REC'+str(invoice.id)
invoice.payment_reference=invoice.name
vals={}
account_credit=self.env['account.account'].sudo().search([('code','=','707100')])
account_debit=self.env['account.account'].sudo().search([('code','=','411100')])
vals['move_id']=invoice.id
vals['product_id']=int(event.booking_product_id)
vals['quantity']=1
vals['price_unit']=event.booking_down_payment
vals['name']='Acompte '+event.booking_product_id.name
vals['account_id']=int(account_credit.id)
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals)
# #debit_line
vals_d={}
vals_d['move_id']=invoice.id
vals_d['debit']=event.booking_down_payment
vals_d['credit']=0
vals_d['date']=datetime.now()
vals_d['partner_id']=int(reg.partner_id)
vals_d['product_id']=int(event.booking_product_id)
vals_d['name']='Acompte '+event.booking_product_id.name
vals_d['account_id']=int(account_debit.id)
vals_d['quantity']=1
vals_d['price_unit']=event.booking_down_payment
vals_d['exclude_from_invoice_tab']=True
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals_d)
l=self.env['account.move.line'].sudo().search([('move_id','=',invoice.id),('balance','<',0)])
l.partner_id=int(reg.partner_id)
reg.down_payment_invoice_id=invoice.id
#création 2ème facture de solde + paiement des options
vals={}
vals['partner_id']=int(reg.partner_id)
vals['invoice_date']=datetime.now()
vals['move_type']='out_invoice'
vals['state']='draft'
#vals['currency_id']=self.currency_id.id
invoice=self.env['account.move'].sudo().create(vals)
invoice.state='posted'
invoice.name='REC'+str(invoice.id)
invoice.payment_reference=invoice.name
vals={}
vals['move_id']=invoice.id
vals['product_id']=int(event.booking_product_id)
vals['quantity']=1
vals['price_unit']=product_price-event.booking_down_payment
vals['name']='solde '+event.booking_product_id.name
vals['account_id']=int(account_credit.id)
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals)
# #debit_line
vals_d={}
vals_d['move_id']=invoice.id
vals_d['debit']=product_price-event.booking_down_payment
vals_d['credit']=0
vals_d['date']=datetime.now()
vals_d['partner_id']=int(reg.partner_id)
vals_d['product_id']=int(event.booking_product_id)
vals_d['name']='solde '+event.booking_product_id.name
vals_d['account_id']=int(account_debit.id)
vals_d['quantity']=1
vals_d['price_unit']=product_price-event.booking_down_payment
vals_d['exclude_from_invoice_tab']=True
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals_d)
l=self.env['account.move.line'].sudo().search([('move_id','=',invoice.id),('balance','<',0)])
l.partner_id=int(reg.partner_id)
#ajout des options
if selected_registrant_options:
for option in selected_registrant_options:
prd=self.env['product.product'].sudo().search([('id','=',int(option.booking_option_id.id))])
#prix à appliquer aux options en fonction du statut ou de la présence de l'option d'adhesion
event_option=self.env['booking.option'].search(['&',('event_id','=',int(reg.event_id)),('booking_option_id','=',int(option.booking_option_id.id))])
if event_option:
if status=="super member":price_unit=event_option.booking_option_super_member_price
if status=="member":price_unit=event_option.booking_option_member_price
if status=="not member" and membership_option:price_unit=event_option.booking_option_member_price
if status=="not member" and not membership_option:price_unit=event_option.booking_option_price
#calcul du prix en fonction du sejour,nuité, ou jour
# if prd.price_per=='day':
# price_unit=price_unit*event.duration
# if prd.price_per=='night':
# price_unit=price_unit*event.duration-1
vals={}
vals['move_id']=invoice.id
#ajout du produit
vals['product_id']=int(event.booking_product_id)
vals['quantity']=1
vals['price_unit']=price_unit
vals['name']=prd.name
vals['account_id']=int(account_credit.id)
invoice_line=self.env['account.move.line'].with_context(check_move_validity=False).sudo().create(vals)
#debit_line
vals_d={}
vals_d['move_id']=invoice.id
vals_d['debit']=price_unit
vals_d['credit']=0
vals_d['date']=datetime.now()
vals_d['partner_id']=int(reg.partner_id)
vals_d['product_id']=int(option.booking_option_id.id)
vals_d['name']=prd.name
vals_d['account_id']=int(account_debit.id)
vals_d['quantity']=1
vals_d['price_unit']=price_unit
vals_d['exclude_from_invoice_tab']=True
invoice_line=self.env['account.move.line'].with_context(check_move_validity=True).sudo().create([vals_d])
l=self.env['account.move.line'].search([('move_id','=',invoice.id),('balance','<',0)])
l.partner_id=int(reg.partner_id)
#si l'option est un produit de don on créé un don pour la personne
if prd.donation: self.sudo().create_donation(reg.id,reg.partner_id,vals['product_id'],vals['price_unit'])
reg.balance_invoice_id=invoice.id
return invoice.id
def info_objet(self,model_id,objet_id):
field_list=request.env[model_id].sudo().fields_get()
result=[]
for key in field_list:
result.append((key,key))
result.sort()
return result
def create_payment(self,invoice_id,code_payment_method):
invoice=self.env['account.move'].search([('id','=',int(invoice_id))])
payment_method=self.env['account.payment.method'].search([('code','=',code_payment_method),('payment_type','=','inbound')])
bank=self.env['account.journal'].search([('type','=','bank')])
if not payment_method : raise Warning ('please set up the '+code_payment_method+ ' method')
if not bank : raise Warning ('please set up the bank journal !')
Payment = self.env['account.payment'].with_context(default_invoice_ids=[(4, invoice_id, False)])
payment = Payment.create({
'date': datetime.now(),
'payment_method_id': payment_method.id,
'payment_type': 'inbound',
'partner_type': 'customer',
'partner_id': invoice.partner_id.id,
'amount': invoice.amount_residual,
'journal_id': int(bank.id),
'company_id': self.env.company,
'currency_id': int(self.currency_id)
#'payment_difference_handling': 'reconcile',
#'writeoff_account_id': self.diff_income_account.id,
})
payment.state='posted'
invoice.payment_id=payment.id
invoice.payment_order_ok=True
class EventRegistration_questionnaire(models.Model):
_name = 'event.registration_questionnaire'
_description = 'event registration questionnaire'
sequence = fields.Integer(string="sequence", default=10)
question=fields.Text(string='question',readonly=True)
answer=fields.Text(string='answer')
event_registration_id=fields.Many2one(
'event.registration',
String='Event registration',
index=True,
readonly=True,
track_visibility='onchange',
ondelete='cascade'
)
class EventRegistration_option(models.Model):
_name = 'event.registration_option'
_description = 'event registration option'
booking_option_id=fields.Many2one('product.product',string='booking options',domain="[('id','in',selectable_option_ids)]")
booking_option_price=fields.Monetary('Price',currency_field='currency_id',readonly=True)
selectable_option_ids = fields.Many2many('product.product', compute='_compute_selectable_option')
event_registration_id=fields.Many2one(
'event.registration',
String='Event registration',
index=True,
readonly=True,
track_visibility='onchange',
)
def _compute_selectable_option(self):
selectable_options=self.env['booking.option'].search([('event_id','=',int(self.event_registration_id.event_id))])
if selectable_options:
self.selectable_option_ids=selectable_options.booking_option_id.ids
@api.model
def _default_currency(self):
company = self.env['res.company']._company_default_get(
'event.event')
return company.currency_id
currency_id = fields.Many2one(
'res.currency',
string='Currency',
required=True,
states={'done': [('readonly', True)]},
track_visibility='onchange',
ondelete='restrict',
default=_default_currency
)