def edit_dialog(self): form_view = self.env.ref('project.edit_project') return { 'name': _('Project'), 'res_model': 'project.project', 'res_id': self.id, 'views': [(form_view.id, 'form'),], 'type': 'ir.actions.act_window', 'target': 'inline' }
def unlink(self): analytic_accounts_to_delete = self.env['account.analytic.account'] for project in self: if project.tasks: raise UserError(_('You cannot delete a project containing tasks. You can either delete all the project\'s tasks and then delete the project or simply deactivate the project.')) if project.analytic_account_id and not project.analytic_account_id.line_ids: analytic_accounts_to_delete |= project.analytic_account_id res = super(Project, self).unlink() analytic_accounts_to_delete.unlink() return res
def _default_location_id(self): company_user = self.env.user.company_id warehouse = self.env['stock.warehouse'].search( [('company_id', '=', company_user.id)], limit=1) if warehouse: return warehouse.lot_stock_id.id else: raise UserError( _('You must define a warehouse for the company: %s.') % (company_user.name, ))
def action_done(self): """ Generate all purchase order based on selected lines, should only be called on one agreement at a time """ if any(purchase_order.state in ['draft', 'sent', 'to approve'] for purchase_order in self.mapped('purchase_ids')): raise UserError( _('You have to cancel or validate every RfQ before closing the purchase requisition.' )) self.write({'state': 'done'})
def edit_dialog(self): form_view = self.env.ref('hr.view_hr_job_form') return { 'name': _('Job'), 'res_model': 'hr.job', 'res_id': self.id, 'views': [(form_view.id, 'form'),], 'type': 'ir.actions.act_window', 'target': 'inline' }
def create_advice(self): for run in self: if run.available_advice: raise UserError( _("Payment advice already exists for %s, 'Set to Draft' to create a new advice." ) % (run.name, )) company = self.env.user.company_id advice = self.env['hr.payroll.advice'].create({ 'batch_id': run.id, 'company_id': company.id, 'name': run.name, 'date': run.date_end, 'bank_id': company.partner_id.bank_ids and company.partner_id.bank_ids[0].id or False }) for slip in run.slip_ids: # TODO is it necessary to interleave the calls ? slip.action_payslip_done() if not slip.employee_id.bank_account_id or not slip.employee_id.bank_account_id.acc_number: raise UserError( _('Please define bank account for the %s employee') % (slip.employee_id.name)) payslip_line = self.env['hr.payslip.line'].search( [('slip_id', '=', slip.id), ('code', '=', 'NET')], limit=1) if payslip_line: self.env['hr.payroll.advice.line'].create({ 'advice_id': advice.id, 'name': slip.employee_id.bank_account_id.acc_number, 'ifsc_code': slip.employee_id.bank_account_id.bank_bic or '', 'employee_id': slip.employee_id.id, 'bysal': payslip_line.total }) self.write({'available_advice': True})
def write(self, vals): if self and 'is_mail_thread' in vals: if not all(rec.state == 'manual' for rec in self): raise UserError(_('Only custom models can be modified.')) if not all(rec.is_mail_thread <= vals['is_mail_thread'] for rec in self): raise UserError( _('Field "Mail Thread" cannot be changed to "False".')) res = super(IrModel, self).write(vals) # setup models; this reloads custom models in registry self.pool.setup_models(self._cr) # update database schema of models models = self.pool.descendants(self.mapped('model'), '_inherits') self.pool.init_models( self._cr, models, dict(self._context, update_custom_fields=True)) else: res = super(IrModel, self).write(vals) return res
def print_report(self): """ To get the date and print the report @return : return report """ if (not self.env.user.company_id.logo): raise UserError( _("You have to set a logo or a layout for your company.")) elif (not self.env.user.company_id.external_report_layout): raise UserError( _("You have to set your reports's header and footer layout.")) datas = {'ids': self.env.context.get('active_ids', [])} res = self.read(['price_list', 'qty1', 'qty2', 'qty3', 'qty4', 'qty5']) res = res and res[0] or {} res['price_list'] = res['price_list'][0] datas['form'] = res return self.env.ref('product.action_report_pricelist').report_action( [], data=datas)
def get_bar_graph_datas(self): data = [] today = datetime.strptime(fields.Date.context_today(self), DF) data.append({'label': _('Past'), 'value':0.0, 'type': 'past'}) day_of_week = int(format_datetime(today, 'e', locale=self._context.get('lang') or 'en_US')) first_day_of_week = today + timedelta(days=-day_of_week+1) for i in range(-1,4): if i==0: label = _('This Week') elif i==3: label = _('Future') else: start_week = first_day_of_week + timedelta(days=i*7) end_week = start_week + timedelta(days=6) if start_week.month == end_week.month: label = str(start_week.day) + '-' +str(end_week.day)+ ' ' + format_date(end_week, 'MMM', locale=self._context.get('lang') or 'en_US') else: label = format_date(start_week, 'd MMM', locale=self._context.get('lang') or 'en_US')+'-'+format_date(end_week, 'd MMM', locale=self._context.get('lang') or 'en_US') data.append({'label':label,'value':0.0, 'type': 'past' if i<0 else 'future'}) # Build SQL query to find amount aggregated by week (select_sql_clause, query_args) = self._get_bar_graph_select_query() query = '' start_date = (first_day_of_week + timedelta(days=-7)) for i in range(0,6): if i == 0: query += "("+select_sql_clause+" and date < '"+start_date.strftime(DF)+"')" elif i == 5: query += " UNION ALL ("+select_sql_clause+" and date >= '"+start_date.strftime(DF)+"')" else: next_date = start_date + timedelta(days=7) query += " UNION ALL ("+select_sql_clause+" and date >= '"+start_date.strftime(DF)+"' and date < '"+next_date.strftime(DF)+"')" start_date = next_date self.env.cr.execute(query, query_args) query_results = self.env.cr.dictfetchall() for index in range(0, len(query_results)): if query_results[index].get('aggr_date') != None: data[index]['value'] = query_results[index].get('total') [graph_title, graph_key] = self._graph_title_and_key() return [{'values': data, 'title': graph_title, 'key': graph_key}]
def check_packages_are_identical(self): '''Some shippers require identical packages in the same shipment. This utility checks it.''' self.ensure_one() if self.package_ids: packages = [p.packaging_id for p in self.package_ids] if len(set(packages)) != 1: package_names = ', '.join([str(p.name) for p in packages]) raise UserError( _('You are shipping different packaging types in the same shipment.\nPackaging Types: %s' % package_names)) return True
def action_view_timesheet_plan(self): return { 'name': _('Overview'), 'type': 'ir.actions.client', 'tag': 'timesheet.plan', 'context': { 'active_id': self.id, 'active_ids': self.ids, 'search_default_project_id': self.id, } }
def _compute_cash_all(self): for session in self: session.cash_journal_id = session.cash_register_id = session.cash_control = False if session.config_id.cash_control: for statement in session.statement_ids: if statement.journal_id.type == 'cash': session.cash_control = True session.cash_journal_id = statement.journal_id.id session.cash_register_id = statement.id if not session.cash_control and session.state != 'closed': raise UserError(_("Cash control can only be applied to cash journals."))
def create(self, values): if not values.get('name', False) or values['name'] == _('New'): if values.get('picking_type_id'): values['name'] = self.env['stock.picking.type'].browse(values['picking_type_id']).sequence_id.next_by_id() else: values['name'] = self.env['ir.sequence'].next_by_code('mrp.production') or _('New') if not values.get('procurement_group_id'): values['procurement_group_id'] = self.env["procurement.group"].create({'name': values['name']}).id production = super(MrpProduction, self).create(values) production._generate_moves() return production
def _check_attribute_value_ids(self): for product in self: attributes = self.env['product.attribute'] for value in product.attribute_value_ids: if value.attribute_id in attributes: raise ValidationError( _('Error! It is not allowed to choose more than one value for a given attribute.' )) if value.attribute_id.create_variant: attributes |= value.attribute_id return True
def _process(self, cancel_backorder=False): self.pick_ids.action_done() if cancel_backorder: for pick_id in self.pick_ids: backorder_pick = self.env['stock.picking'].search([ ('backorder_id', '=', pick_id.id) ]) backorder_pick.action_cancel() pick_id.message_post( body=_("Back order <em>%s</em> <b>cancelled</b>.") % (backorder_pick.name))
def run(self, product_id, product_qty, product_uom, location_id, name, origin, values): values.setdefault('company_id', self.env['res.company']._company_default_get('procurement.group')) values.setdefault('priority', '1') values.setdefault('date_planned', fields.Datetime.now()) rule = self._get_rule(product_id, location_id, values) if not rule: raise UserError(_('No procurement rule found. Please verify the configuration of your routes')) getattr(rule, '_run_%s' % rule.action)(product_id, product_qty, product_uom, location_id, name, origin, values) return True
def create_cash_statement(self): ctx = self._context.copy() ctx.update({'journal_id': self.id, 'default_journal_id': self.id, 'default_journal_type': 'cash'}) return { 'name': _('Create cash statement'), 'type': 'ir.actions.act_window', 'view_type': 'form', 'view_mode': 'form', 'res_model': 'account.bank.statement', 'context': ctx, }
def _validate_fiscalyear_lock(self, values): if values.get('fiscalyear_lock_date'): nb_draft_entries = self.env['account.move'].search([ ('company_id', 'in', [c.id for c in self]), ('state', '=', 'draft'), ('date', '<=', values['fiscalyear_lock_date']) ]) if nb_draft_entries: raise ValidationError( _('There are still unposted entries in the period you want to lock. You should either post or delete them.' ))
def unlink(self): product_ctx = dict(self.env.context or {}, active_test=False) if self.with_context(product_ctx).search_count([('id', 'in', self.ids), ('available_in_pos', '=', True)]): if self.env['pos.session'].search_count([('state', '!=', 'closed') ]): raise UserError( _('You cannot delete a product saleable in point of sale while a session is still opened.' )) return super(ProductTemplate, self).unlink()
def _check_account_ids(self, vals): # Raise an error to prevent the account.budget.post to have not specified account_ids. # This check is done on create because require=True doesn't work on Many2many fields. if 'account_ids' in vals: account_ids = self.resolve_2many_commands('account_ids', vals['account_ids']) else: account_ids = self.account_ids if not account_ids: raise ValidationError( _('The budget must have at least one account.'))
def create(self, values): if not values.get('resource_calendar_id'): values['resource_calendar_id'] = self.env[ 'resource.calendar'].create({ 'name': _('Standard 40 hours/week') }).id company = super(ResCompany, self).create(values) # calendar created from form view: no company_id set because record was still not created if not company.resource_calendar_id.company_id: company.resource_calendar_id.company_id = company.id return company
def open_frontend_cb(self): if not self.ids: return {} for session in self.filtered(lambda s: s.user_id.id != self.env.uid): raise UserError(_("You cannot use the session of another user. This session is owned by %s. " "Please first close this one to use this point of sale.") % session.user_id.name) return { 'type': 'ir.actions.act_url', 'target': 'self', 'url': '/pos/web/', }
def execute_code(self, code_exec): def reconciled_inv(): """ returns the list of invoices that are set as reconciled = True """ return self.env['account.invoice'].search([('reconciled', '=', True)]).ids def order_columns(item, cols=None): """ This function is used to display a dictionary as a string, with its columns in the order chosen. :param item: dict :param cols: list of field names :returns: a list of tuples (fieldname: value) in a similar way that would dict.items() do except that the returned values are following the order given by cols :rtype: [(key, value)] """ if cols is None: cols = list(item) return [(col, item.get(col)) for col in cols if col in item] localdict = { 'cr': self.env.cr, 'uid': self.env.uid, 'reconciled_inv': reconciled_inv, # specific function used in different tests 'result': None, # used to store the result of the test 'column_order': None, # used to choose the display order of columns (in case you are returning a list of dict) '_': _, } safe_eval(code_exec, localdict, mode="exec", nocopy=True) result = localdict['result'] column_order = localdict.get('column_order', None) if not isinstance(result, (tuple, list, set)): result = [result] if not result: result = [_('The test was passed successfully')] else: def _format(item): if isinstance(item, dict): return ', '.join([ "%s: %s" % (tup[0], tup[1]) for tup in order_columns(item, column_order) ]) else: return item result = [_format(rec) for rec in result] return result
def action_created_invoice(self): self.ensure_one() return { 'name': _('Invoice created'), 'type': 'ir.actions.act_window', 'view_mode': 'form', 'res_model': 'account.invoice', 'view_id': self.env.ref('account.invoice_form').id, 'target': 'current', 'res_id': self.invoice_id.id, }
def invoice_confirm(self): context = dict(self._context or {}) active_ids = context.get('active_ids', []) or [] for record in self.env['account.invoice'].browse(active_ids): if record.state != 'draft': raise UserError( _("Selected invoice(s) cannot be confirmed as they are not in 'Draft' state." )) record.action_invoice_open() return {'type': 'ir.actions.act_window_close'}
def write(self, values): # When we modify the currency of the company, we reflect the change on the list0 pricelist, if # that pricelist is not used by another company. Otherwise, we create a new pricelist for the # given currency. ProductPricelist = self.env['product.pricelist'] currency_id = values.get('currency_id') main_pricelist = self.env.ref('product.list0', False) if currency_id and main_pricelist: nb_companies = self.search_count([]) for company in self: existing_pricelist = ProductPricelist.search([ ('company_id', 'in', (False, company.id)), ('currency_id', '=', currency_id) ]) if existing_pricelist: continue if currency_id == company.currency_id.id: continue currency_match = main_pricelist.currency_id == company.currency_id company_match = (main_pricelist.company_id == company or (main_pricelist.company_id.id is False and nb_companies == 1)) if currency_match and company_match: main_pricelist.write({'currency_id': currency_id}) else: params = { 'currency': self.env['res.currency'].browse(currency_id).name, 'company': company.name } pricelist = ProductPricelist.create({ 'name': _("Default %(currency)s pricelist for %(company)s") % params, 'currency_id': currency_id, 'company_id': company.id, }) field = self.env['ir.model.fields'].search([ ('model', '=', 'res.partner'), ('name', '=', 'property_product_pricelist') ]) self.env['ir.property'].create({ 'name': 'property_product_pricelist', 'company_id': company.id, 'value_reference': 'product.pricelist,%s' % pricelist.id, 'fields_id': field.id }) return super(ResCompany, self).write(values)
def account_move_get(self): if self.number: name = self.number elif self.journal_id.sequence_id: if not self.journal_id.sequence_id.active: raise UserError( _('Please activate the sequence of selected journal !')) name = self.journal_id.sequence_id.with_context( ir_sequence_date=self.date).next_by_id() else: raise UserError(_('Please define a sequence on the journal.')) move = { 'name': name, 'journal_id': self.journal_id.id, 'narration': self.narration, 'date': self.account_date, 'ref': self.reference, } return move
def get_worked_day_lines(self, contracts, date_from, date_to): """ @param contract: Browse record of contracts @return: returns a list of dict containing the input that should be applied for the given contract between date_from and date_to """ res = [] # fill only if the contract as a working schedule linked for contract in contracts.filtered( lambda contract: contract.resource_calendar_id): day_from = datetime.combine(fields.Date.from_string(date_from), datetime_time.min) day_to = datetime.combine(fields.Date.from_string(date_to), datetime_time.max) # compute leave days leaves = {} day_leave_intervals = contract.employee_id.iter_leaves( day_from, day_to, calendar=contract.resource_calendar_id) for day_intervals in day_leave_intervals: for interval in day_intervals: holiday = interval[2]['leaves'].holiday_id current_leave_struct = leaves.setdefault( holiday.holiday_status_id, { 'name': holiday.holiday_status_id.name, 'sequence': 5, 'code': holiday.holiday_status_id.name, 'number_of_days': 0.0, 'number_of_hours': 0.0, 'contract_id': contract.id, }) leave_time = (interval[1] - interval[0]).seconds / 3600 current_leave_struct['number_of_hours'] += leave_time work_hours = contract.employee_id.get_day_work_hours_count( interval[0].date(), calendar=contract.resource_calendar_id) if work_hours: current_leave_struct[ 'number_of_days'] += leave_time / work_hours # compute worked days work_data = contract.employee_id.get_work_days_data( day_from, day_to, calendar=contract.resource_calendar_id) attendances = { 'name': _("Normal Working Days paid at 100%"), 'sequence': 1, 'code': 'WORK100', 'number_of_days': work_data['days'], 'number_of_hours': work_data['hours'], 'contract_id': contract.id, } res.append(attendances) res.extend(leaves.values()) return res
def _add_event(self, event_name="New Event", context=None, **kwargs): product = request.env.ref('event_sale.product_product_event', raise_if_not_found=False) if product: context = dict(context or {}, default_event_ticket_ids=[[0, 0, { 'name': _('Registration'), 'product_id': product.id, 'deadline': False, 'seats_max': 1000, 'price': 0, }]]) return super(WebsiteEventSaleController, self)._add_event(event_name, context, **kwargs)
def loader(self, channel_id, **kwargs): username = kwargs.get("username", _("Visitor")) channel = request.env['im_livechat.channel'].sudo().browse(channel_id) info = request.env['im_livechat.channel'].get_livechat_info( channel.id, username=username) return request.render('im_livechat.loader', { 'info': info, 'web_session_required': True }, headers=[('Content-Type', 'application/javascript')])