Adapt to Tryton 5.2

This commit is contained in:
Albert Cervera i Areny 2019-06-11 00:42:59 +02:00
parent ead83e32c1
commit dd2a59829f
21 changed files with 256 additions and 313 deletions

View File

@ -1,28 +1,32 @@
# The COPYRIGHT file at the top level of this repository contains the full
# copyright notices and license terms.
from trytond.pool import Pool
from .prescription import *
from .specie import *
from .medication_event import *
from . import prescription
from . import medication_event
from . import specie
__all__ = ['Party', 'ProductTemplate', 'Product', 'Move', 'Template',
'TemplateLine', 'Prescription', 'PrescriptionLine', 'PrescriptionAnimal',
'PrescriptionAnimalGroup', 'Location', 'CreateInternalShipmentStart',
'CreateInternalShipment']
def register():
Pool.register(
Template,
TemplateLine,
Prescription,
PrescriptionLine,
PrescriptionAnimal,
PrescriptionAnimalGroup,
CreateInternalShipmentStart,
Location,
Move,
MedicationEvent,
Party,
Product,
ProductTemplate,
Specie,
prescription.Template,
prescription.TemplateLine,
prescription.Prescription,
prescription.PrescriptionLine,
prescription.PrescriptionAnimal,
prescription.PrescriptionAnimalGroup,
prescription.CreateInternalShipmentStart,
prescription.Location,
prescription.Move,
medication_event.MedicationEvent,
prescription.Party,
prescription.Product,
prescription.ProductTemplate,
specie.Specie,
module='farm_prescription', type_='model')
Pool.register(
CreateInternalShipment,
prescription.CreateInternalShipment,
module='farm_prescription', type_='wizard')

View File

@ -8,10 +8,9 @@ from trytond.modules.farm.events.abstract_event import (
_STATES_WRITE_DRAFT_VALIDATED, _DEPENDS_WRITE_DRAFT_VALIDATED)
__all__ = ['MedicationEvent']
__metaclass__ = PoolMeta
class MedicationEvent:
class MedicationEvent(metaclass=PoolMeta):
__name__ = 'farm.medication.event'
prescription = fields.Many2One('farm.prescription', 'Prescription',
select=True, domain=[

41
message.xml Normal file
View File

@ -0,0 +1,41 @@
<?xml version="1.0"?>
<tryton>
<data group="1">
<record model="ir.message" id="msg_template_related_to_product_or_prescription">
<field name="text">You can not change the Feed Product of Prescription Template "%(template)s" because there are products or prescriptions already related to this template.\nPlease, create a new template.</field>
</record>
<record model="ir.message" id="msg_lines_will_be_replaced">
<field name="text">Current values of prescription "%(prescription)s" will be replaced.</field>
</record>
<record model="ir.message" id="msg_lot_required_done">
<field name="text">Lot is required to set done the prescription "%(prescription)s".</field>
</record>
<record model="ir.message" id="msg_lot_expired">
<field name="text">The lot "%(lot)s" used in prescription "%(prescription)s" has expired.</field>
</record>
<record model="ir.message" id="msg_veterinarian_required_confirmed">
<field name="text">Veterinarian is requried to confirm the prescription "%(prescription)s".</field>
</record>
<record model="ir.message" id="msg_lines_required_confirmed">
<field name="text">The prescription "%(prescription)s" must have at least one line in order to be confirmed.</field>
</record>
<record model="ir.message" id="msg_from_prescription_line_invalid_prescription">
<field name="text">The Stock Move "%(move)s" has the Prescription Line "%(origin)s" as origin, but it isn't related to a Prescription or it isn't the origin's prescription.</field>
</record>
<record model="ir.message" id="msg_from_prescription_line_invalid_product_quantity">
<field name="text">The Stock Move "%(move)s" has the Prescription Line "%(origin)s" as origin, but the product and/or quantity are not the same.</field>
</record>
<record model="ir.message" id="msg_prescription_invalid_product_quantity">
<field name="text">The Stock Move "%(move)s" is related to Prescription "%(prescription)s", but the product and/or quantity are not the same.</field>
</record>
<record model="ir.message" id="msg_need_prescription">
<field name="text">Move "%(move)s" needs a confirmed prescription.</field>
</record>
<record model="ir.message" id="msg_unconfirmed_prescription">
<field name="text">Prescription "%(prescription)s" of move "%(move)s" must be confirmed before assigning the move.</field>
</record>
<record model="ir.message" id="msg_prescription_used">
<field name="text">The prescription "%(prescription)s" is used in internal shipment "%(shipment)s".</field>
</record>
</data>
</tryton>

View File

@ -10,12 +10,13 @@ from trytond.transaction import Transaction
from trytond.wizard import Wizard, StateView, StateAction, Button
from trytond.pyson import Bool, Date, Equal, Eval, If, Or
from trytond import backend
from trytond.exceptions import UserError, UserWarning
from trytond.i18n import gettext
__all__ = ['Party', 'ProductTemplate', 'Product', 'Move', 'Template',
'TemplateLine', 'Prescription', 'PrescriptionLine', 'PrescriptionAnimal',
'PrescriptionAnimalGroup', 'Location', 'CreateInternalShipmentStart',
'CreateInternalShipment']
__metaclass__ = PoolMeta
_STATES = {
'readonly': Eval('state') != 'draft',
@ -27,7 +28,7 @@ _STATES_REQUIRED = {
_DEPENDS = ['state']
class Party:
class Party(metaclass=PoolMeta):
__name__ = 'party.party'
veterinarian = fields.Boolean('Veterinarian')
@ -37,13 +38,13 @@ class Party:
}, depends=['veterinarian'])
class ProductTemplate:
class ProductTemplate(metaclass=PoolMeta):
__name__ = 'product.template'
prescription_required = fields.Boolean('Prescription required')
class Product:
class Product(metaclass=PoolMeta):
__name__ = 'product.product'
prescription_required = fields.Function(fields.Boolean(
@ -224,21 +225,10 @@ class Template(ModelSQL, ModelView, PrescriptionMixin):
},
depends=['type'])
@classmethod
def __setup__(cls):
super(Template, cls).__setup__()
cls._error_messages.update({
'template_related_to_product_or_prescription': (
'You can not change the Feed Product of Prescription '
'Template "%s" because there are products or '
'rescriptions already related to this template.\n'
'Please, create a new template.'),
})
@classmethod
def __register__(cls, module_name):
TableHandler = backend.get('TableHandler')
cursor = Transaction().connection.cursor
cursor = Transaction().connection.cursor()
table = TableHandler(cls, module_name)
sql_table = cls.__table__()
product = Table('product_product')
@ -266,10 +256,8 @@ class Template(ModelSQL, ModelView, PrescriptionMixin):
@fields.depends('product', 'name')
def on_change_product(self):
changes = {}
if self.product and not self.name:
changes['name'] = self.product.rec_name
return changes
self.name = self.product.rec_name
@classmethod
def write(cls, *args):
@ -288,9 +276,9 @@ class Template(ModelSQL, ModelView, PrescriptionMixin):
('template', '=', template.id),
])
if n_template_products or n_template_prescriptions:
cls.raise_user_error(
'template_related_to_product_or_prescription',
(template.rec_name,))
raise UserError(gettext('farm.prescription.msg_'
'template_related_to_product_or_prescription',
template=template.rec_name))
super(Template, cls).write(*args)
@ -426,7 +414,7 @@ class Prescription(Workflow, ModelSQL, ModelView, PrescriptionMixin):
cls.product.depends = ['template']
cls.unit.on_change_with.add('template')
if hasattr(Lot, 'expiry_date'):
if hasattr(Lot, 'expiration_date'):
cls.lot.domain.append(
If(Eval('state') != 'done',
('expired', '=', False),
@ -438,18 +426,6 @@ class Prescription(Workflow, ModelSQL, ModelView, PrescriptionMixin):
cls.lot.context['stock_move_date'] = Eval('delivery_date', Date())
cls.lot.depends += ['delivery_date']
cls._error_messages.update({
'lines_will_be_replaced': (
'Current values of prescription "%s" will be replaced.'),
'lot_required_done': ('Lot is required to set done the '
'prescription "%s".'),
'lot_expired': ('The lot "%(lot)s" used in prescription '
'"%(prescription)s" has expired.'),
'veterinarian_required_confirmed': ('Veterinarian is requried '
'to confirm the prescription "%s".'),
'lines_required_confirmed': ('The prescription "%s" must have '
'at least one line in order to be confirmed.'),
})
cls._transitions |= set((
('draft', 'confirmed'),
('confirmed', 'done'),
@ -476,20 +452,18 @@ class Prescription(Workflow, ModelSQL, ModelView, PrescriptionMixin):
return 'draft'
def get_rec_name(self, name):
return u'%s - %s (%s)' % (self.reference,
return '%s - %s (%s)' % (self.reference,
self.product.rec_name, str(self.date))
@fields.depends('template')
def on_change_template(self):
changes = {}
if self.template:
self.product = self.template.product
return changes
@fields.depends('animals', 'animals_groups')
@fields.depends('animals', 'animal_groups')
def on_change_with_number_of_animals(self):
animals = len(self.animals)
for group in self.animal_groups:
animals = len(self.animals or [])
for group in (self.animal_groups or []):
animals += group.quantity
return animals
@ -532,11 +506,13 @@ class Prescription(Workflow, ModelSQL, ModelView, PrescriptionMixin):
def confirm(cls, prescriptions):
for prescription in prescriptions:
if not prescription.veterinarian:
cls.raise_user_error('veterinarian_required_confirmed',
prescription.rec_name)
raise UserError(gettext('farm_prescription.'
'msg_veterinarian_required_confirmed',
prescription=prescription.rec_name))
if prescription.type != 'medical' and not prescription.lines:
cls.raise_user_error('lines_required_confirmed',
prescription.rec_name)
raise UserError(gettext(
'farm_prescription.msg_lines_required_confirmed',
prescription=prescription.rec_name))
@classmethod
@ModelView.button
@ -548,19 +524,20 @@ class Prescription(Workflow, ModelSQL, ModelView, PrescriptionMixin):
stock_move_date = Transaction().context.get('stock_move_date')
for prescription in prescriptions:
if not prescription.lot:
cls.raise_user_error('lot_required_done',
prescription.rec_name)
if hasattr(prescription.lot, 'expiry_date'):
raise UserError(gettext('farm_prescription.'
'msg_lot_required_done',
prescription=prescription.rec_name))
if hasattr(prescription.lot, 'expiration_date'):
prescription_date = prescription.delivery_date
if stock_move_date:
prescription_date = max(prescription_date, stock_move_date)
with Transaction().set_context(
stock_move_date=prescription_date):
if Lot(prescription.lot.id).expired:
cls.raise_user_error('lot_expired', {
'lot': prescription.lot.rec_name,
'prescription': prescription.rec_name,
})
raise UserError(gettext('msg_lot_expired',
lot=prescription.lot.rec_name,
prescription=prescription.rec_name,
))
@classmethod
@ModelView.button
@ -568,10 +545,9 @@ class Prescription(Workflow, ModelSQL, ModelView, PrescriptionMixin):
for prescription in prescriptions:
if not prescription.template:
continue
cls.raise_user_warning('replace_lines', 'lines_will_be_replaced',
prescription.rec_name)
raise UserWarning(gettext('replace_lines',
'farm_prescription.msg_lines_will_be_replaced',
prescription=prescription.rec_name))
prescription.set_template_vals()
prescription.save()
@ -588,7 +564,7 @@ class Prescription(Workflow, ModelSQL, ModelView, PrescriptionMixin):
self.afection = self.template.afection
self.dosage = self.template.dosage
self.waiting_period = self.template.waiting_period
self.expiry_period = self.template.expiry_period
self.expiration_period = self.template.expiration_time
rate = self.get_factor_change_quantity_unit(self.template.quantity,
self.template.unit)
@ -672,33 +648,10 @@ class PrescriptionLine(ModelSQL, ModelView, PrescriptionLineMixin):
self.quantity = Uom.round(quantity, self.unit.rounding)
class Move:
class Move(metaclass=PoolMeta):
__name__ = 'stock.move'
prescription = fields.Many2One('farm.prescription', 'Prescription')
@classmethod
def __setup__(cls):
super(Move, cls).__setup__()
cls._error_messages.update({
'from_prescription_line_invalid_prescription': (
'The Stock Move "%(move)s" has the Prescription Line '
'"%(origin)s" as origin, but it isn\'t related to a '
'Prescription or it isn\'t the origin\'s prescription.'),
'from_prescription_line_invalid_product_quantity': (
'The Stock Move "%(move)s" has the Prescription Line '
'"%(origin)s" as origin, but the product and/or quantity '
'are not the same.'),
'prescription_invalid_product_quantity': (
'The Stock Move "%(move)s" is related to Prescription '
'"%(prescription)s", but the product and/or quantity are '
'not the same.'),
'need_prescription': ('Move "%s" needs a confirmed '
'prescription'),
'unconfirmed_prescription': ('Prescription "%s" of move "%s" '
'must be confirmed before assigning the move'),
})
@classmethod
def _get_origin(cls):
models = super(Move, cls)._get_origin()
@ -724,30 +677,30 @@ class Move:
if self.origin and isinstance(self.origin, PrescriptionLine):
if (not self.prescription or
self.origin.prescription != self.prescription):
self.raise_user_error(
'from_prescription_line_invalid_prescription', {
'move': self.rec_name,
'origin': self.origin.rec_name,
})
raise UserError(gettext('farm_prescription.'
'msg_from_prescription_line_invalid_prescription',
move=self.rec_name,
origin=self.origin.rec_name,
))
if (self.product != self.origin.product or
self.quantity != Uom.compute_qty(self.origin.unit,
self.origin.quantity, self.uom)):
self.raise_user_error(
'from_prescription_line_invalid_product_quantity', {
'move': self.rec_name,
'origin': self.origin.rec_name,
})
raise UserError(gettext('farm_prescription.'
'msg_from_prescription_line_invalid_product_quantity',
move=self.rec_name,
origin=self.origin.rec_name,
))
elif self.prescription:
quantity = Uom.compute_qty(self.prescription.unit,
self.prescription.quantity + self.prescription.drug_quantity,
self.uom)
if (self.product != self.prescription.product or
self.quantity != quantity):
self.raise_user_error(
'prescription_invalid_product_quantity', {
'move': self.rec_name,
'prescription': self.prescription.rec_name,
})
raise UserError(gettext('farm_prescription.'
'msg_prescription_invalid_product_quantity',
move=self.rec_name,
prescription=self.prescription.rec_name,
))
@classmethod
def assign(cls, moves):
@ -771,14 +724,17 @@ class Move:
and not isinstance(self.shipment, ShipmentIn)
and not isinstance(self.origin, FeedEvent)):
# Purchases don't require prescription because are made to stock
self.raise_user_error('need_prescription', self.rec_name)
raise UserError(gettext('farm_prescription.msg_need_prescription',
move=self.rec_name))
if self.prescription:
if self.prescription.state == 'draft':
self.raise_user_error('unconfirmed_prescription',
(self.prescription.rec_name, self.rec_name))
raise UserError(gettext('farm_prescription.'
'msg_unconfirmed_prescription',
prescription=self.prescription.rec_name,
move=self.rec_name))
class Location:
class Location(metaclass=PoolMeta):
__name__ = 'stock.location'
prescription_required = fields.Boolean('Prescription required')
@ -817,14 +773,6 @@ class CreateInternalShipment(Wizard):
])
create_ = StateAction('stock.act_shipment_internal_form')
@classmethod
def __setup__(cls):
super(CreateInternalShipment, cls).__setup__()
cls._error_messages.update({
'prescription_used': (
'The prescription %s is used in internal shipment %s.'),
})
def default_start(self, fields):
pool = Pool()
Move = pool.get('stock.move')
@ -837,9 +785,11 @@ class CreateInternalShipment(Wizard):
move = Move.search([
('prescription', '=', prescription)])
if move:
self.raise_user_error('prescription_used', (
prescription.reference, move[0].shipment and \
move[0].shipment.code or move[0].id))
raise UserError(gettext('farm_prescription.'
'msg_prescription_used',
prescription=prescription.reference,
shipment=(move[0].shipment and move[0].shipment.code
or move[0].id)))
return {
'from_location': None,
'farm': farm.id,
@ -849,7 +799,6 @@ class CreateInternalShipment(Wizard):
pool = Pool()
Prescription = Pool().get('farm.prescription')
Shipment = pool.get('stock.shipment.internal')
Move = pool.get('stock.move')
Company = pool.get('company.company')
prescriptions = Prescription.browse(

View File

@ -161,45 +161,32 @@
<record model="ir.action.act_window" id="act_medical_prescription">
<field name="name">Medical Prescription</field>
<field name="res_model">farm.prescription</field>
<field name="domain"
eval="[('type', '=', 'medical')]"
pyson="1"/>
<field name="context"
eval="{'type': 'medical'}"
pyson="1"/>
<field name="domain" eval="[('type', '=', 'medical')]" pyson="1"/>
<field name="context" eval="{'type': 'medical'}" pyson="1"/>
</record>
<record model="ir.action.act_window.view"
id="act_medical_prescription_view1">
<record model="ir.action.act_window.view" id="act_medical_prescription_view1">
<field name="sequence" eval="10"/>
<field name="view" ref="prescription_view_list"/>
<field name="act_window" ref="act_medical_prescription"/>
</record>
<record model="ir.action.act_window.view"
id="act_medical_prescription_view2">
<record model="ir.action.act_window.view" id="act_medical_prescription_view2">
<field name="sequence" eval="20"/>
<field name="view" ref="prescription_view_form"/>
<field name="act_window" ref="act_medical_prescription"/>
</record>
<record model="ir.action.act_window.domain"
id="act_medical_prescription_draft">
<record model="ir.action.act_window.domain" id="act_medical_prescription_draft">
<field name="name">Draft</field>
<field name="sequence" eval="10"/>
<field name="domain"
eval="[('state', '=', 'draft')]"
pyson="1"/>
<field name="domain" eval="[('state', '=', 'draft')]" pyson="1"/>
<field name="act_window" ref="act_medical_prescription"/>
</record>
<record model="ir.action.act_window.domain"
id="act_medical_prescription_confirmed">
<record model="ir.action.act_window.domain" id="act_medical_prescription_confirmed">
<field name="name">Confirmed</field>
<field name="sequence" eval="20"/>
<field name="domain"
eval="[('state', '=', 'confirmed')]"
pyson="1"/>
<field name="domain" eval="[('state', '=', 'confirmed')]" pyson="1"/>
<field name="act_window" ref="act_medical_prescription"/>
</record>
<record model="ir.action.act_window.domain"
id="act_medical_prescription_all">
<record model="ir.action.act_window.domain" id="act_medical_prescription_all">
<field name="name">All</field>
<field name="sequence" eval="9999"/>
<field name="act_window" ref="act_medical_prescription"/>
@ -207,62 +194,46 @@
<record model="ir.action.act_window" id="act_feed_prescription">
<field name="name">Feed Prescription</field>
<field name="res_model">farm.prescription</field>
<field name="domain"
eval="[('type', '=', 'feed')]"
pyson="1"/>
<field name="context"
eval="{'type': 'feed'}"
pyson="1"/>
<field name="domain" eval="[('type', '=', 'feed')]" pyson="1"/>
<field name="context" eval="{'type': 'feed'}" pyson="1"/>
</record>
<record model="ir.action.act_window.view"
id="act_feed_prescription_view1">
<record model="ir.action.act_window.view" id="act_feed_prescription_view1">
<field name="sequence" eval="10"/>
<field name="view" ref="prescription_view_list"/>
<field name="act_window" ref="act_feed_prescription"/>
</record>
<record model="ir.action.act_window.view"
id="act_feed_prescription_view2">
<record model="ir.action.act_window.view" id="act_feed_prescription_view2">
<field name="sequence" eval="20"/>
<field name="view" ref="prescription_view_form"/>
<field name="act_window" ref="act_feed_prescription"/>
</record>
<record model="ir.action.act_window.domain"
id="act_feed_prescription_draft">
<record model="ir.action.act_window.domain" id="act_feed_prescription_draft">
<field name="name">Draft</field>
<field name="sequence" eval="10"/>
<field name="domain"
eval="[('state', '=', 'draft')]"
pyson="1"/>
<field name="domain" eval="[('state', '=', 'draft')]" pyson="1"/>
<field name="act_window" ref="act_feed_prescription"/>
</record>
<record model="ir.action.act_window.domain"
id="act_feed_prescription_confirmed">
<record model="ir.action.act_window.domain" id="act_feed_prescription_confirmed">
<field name="name">Confirmed</field>
<field name="sequence" eval="20"/>
<field name="domain"
eval="[('state', '=', 'confirmed')]"
pyson="1"/>
<field name="domain" eval="[('state', '=', 'confirmed')]" pyson="1"/>
<field name="act_window" ref="act_feed_prescription"/>
</record>
<record model="ir.action.act_window.domain"
id="act_feed_prescription_all">
<record model="ir.action.act_window.domain" id="act_feed_prescription_all">
<field name="name">All</field>
<field name="sequence" eval="9999"/>
<field name="act_window" ref="act_feed_prescription"/>
</record>
<record model="ir.model.access" id="access_prescription">
<field name="model"
search="[('model', '=', 'farm.prescription')]"/>
<field name="model" search="[('model', '=', 'farm.prescription')]"/>
<field name="perm_read" eval="True"/>
<field name="perm_write" eval="False"/>
<field name="perm_create" eval="False"/>
<field name="perm_delete" eval="False"/>
</record>
<record model="ir.model.access"
id="access_prescription_group_prescription">
<field name="model"
search="[('model', '=', 'farm.prescription')]"/>
<record model="ir.model.access" id="access_prescription_group_prescription">
<field name="model" search="[('model', '=', 'farm.prescription')]"/>
<field name="group" ref="group_prescription"/>
<field name="perm_read" eval="True"/>
<field name="perm_write" eval="True"/>
@ -272,15 +243,31 @@
<record model="ir.model.button" id="prescription_confirm_button">
<field name="name">confirm</field>
<field name="model"
search="[('model', '=', 'farm.prescription')]"/>
<field name="model" search="[('model', '=', 'farm.prescription')]"/>
</record>
<record model="ir.model.button-res.group"
id="prescription_confirm_button_group_veterinarian">
<record model="ir.model.button-res.group" id="prescription_confirm_button_group_veterinarian">
<field name="button" ref="prescription_confirm_button"/>
<field name="group" ref="group_veterinarian"/>
</record>
<record model="ir.model.button" id="prescription_set_template_button">
<field name="name">set_template</field>
<field name="model" search="[('model', '=', 'farm.prescription')]"/>
</record>
<record model="ir.model.button-res.group" id="prescription_set_template_button_group_veterinarian">
<field name="button" ref="prescription_set_template_button"/>
<field name="group" ref="group_veterinarian"/>
</record>
<record model="ir.model.button" id="prescription_done_button">
<field name="name">done</field>
<field name="model" search="[('model', '=', 'farm.prescription')]"/>
</record>
<record model="ir.model.button-res.group" id="prescription_done_button_group_veterinarian">
<field name="button" ref="prescription_done_button"/>
<field name="group" ref="group_veterinarian"/>
</record>
<!-- farm.prescription.line -->
<record model="ir.ui.view" id="prescription_line_view_form">
<field name="model">farm.prescription.line</field>
@ -333,14 +320,12 @@
<!-- party.party -->
<record model="ir.ui.view" id="party_view_form">
<field name="model">party.party</field>
<field name="type" eval="None"/>
<field name="inherit" ref="party.party_view_form"/>
<field name="name">party_form</field>
</record>
<record model="ir.ui.view" id="party_view_list">
<field name="model">party.party</field>
<field name="type" eval="None"/>
<field name="inherit" ref="party.party_view_tree"/>
<field name="name">party_list</field>
</record>
@ -348,7 +333,6 @@
<!-- product.template -->
<record model="ir.ui.view" id="product_template_view_form">
<field name="model">product.template</field>
<field name="type" eval="None"/>
<field name="inherit" ref="product.template_view_form"/>
<field name="name">product_template_form</field>
</record>
@ -424,13 +408,11 @@
<record model="ir.ui.view" id="location_view_form">
<field name="model">stock.location</field>
<field name="type">form</field>
<field name="inherit" ref="stock.location_view_form"/>
<field name="name">location_form</field>
</record>
<record model="ir.ui.view" id="location_view_list">
<field name="model">stock.location</field>
<field name="type">tree</field>
<field name="inherit" ref="stock.location_view_list"/>
<field name="name">location_list</field>
</record>

View File

@ -4,7 +4,7 @@
from setuptools import setup
import re
import os
import ConfigParser
import configparser
MODULE = 'recipts'
PREFIX = 'nantic'
@ -14,7 +14,7 @@ MODULE2PREFIX = {}
def read(fname):
return open(os.path.join(os.path.dirname(__file__), fname)).read()
config = ConfigParser.ConfigParser()
config = configparser.ConfigParser()
config.readfp(open('tryton.cfg'))
info = dict(config.items('tryton'))
for key in ('depends', 'extras_depend', 'xml'):

View File

@ -5,12 +5,11 @@ from trytond.pool import Pool, PoolMeta
from trytond.pyson import Bool, Eval, Not
__all__ = ['Specie']
__metaclass__ = PoolMeta
MODULE_NAME = "farm_prescription"
class Specie:
class Specie(metaclass=PoolMeta):
__name__ = 'farm.specie'
prescription_enabled = fields.Boolean('Prescriptions Enabled',

View File

@ -9,59 +9,28 @@ Imports::
>>> from decimal import Decimal
>>> from operator import attrgetter
>>> from proteus import config, Model, Wizard
>>> from trytond.tests.tools import activate_modules
>>> from trytond.modules.company.tests.tools import create_company, \
... get_company
>>> today = datetime.date.today()
Create config::
Activate module::
>>> config = config.set_trytond()
>>> config.pool.test = True
Install Prescriptions::
>>> Module = Model.get('ir.module.module')
>>> module, = Module.find([('name', '=', 'farm_prescription')])
>>> Module.install ([module.id], config.context)
>>> Wizard('ir.module.module.install_upgrade').execute('upgrade')
>>> config = activate_modules('farm_prescription')
Create company::
>>> Currency = Model.get('currency.currency')
>>> CurrencyRate = Model.get('currency.currency.rate')
>>> Company = Model.get('company.company')
>>> Party = Model.get('party.party')
>>> company_config = Wizard('company.company.config')
>>> company_config.execute('company')
>>> company = company_config.form
>>> party = Party(name='Dunder Mifflin')
>>> party.save()
>>> company.party = party
>>> currencies = Currency.find([('code', '=', 'USD')])
>>> if not currencies:
... currency = Currency(name='U.S. Dollar', symbol='$', code='USD',
... rounding=Decimal('0.01'), mon_grouping='[3, 3, 0]',
... mon_decimal_point='.', mon_thousands_sep=',')
... currency.save()
... CurrencyRate(date=today + relativedelta(month=1, day=1),
... rate=Decimal('1.0'), currency=currency).save()
... else:
... currency, = currencies
>>> company.currency = currency
>>> company_config.execute('add')
>>> company, = Company.find()
Reload the context::
>>> User = Model.get('res.user')
>>> config._context = User.get_preferences(True, config.context)
>>> _ = create_company()
>>> company = get_company()
Create inner location::
>>> Location = Model.get('stock.location')
>>> inner_farm = Location()
>>> inner_farm.name = "Test Farm/Inner Farm"
>>> inner_farm.code = "TFARMI"
>>> inner_farm.type = "storage"
>>> inner_farm.save()
>>> Location = Model.get('stock.location')
>>> inner_farm = Location()
>>> inner_farm.name = "Test Farm/Inner Farm"
>>> inner_farm.code = "TFARMI"
>>> inner_farm.type = "storage"
>>> inner_farm.save()
Check location has 'requires prescription' checked::
@ -70,30 +39,30 @@ Check location has 'requires prescription' checked::
Create production location::
>>> production_farm = Location()
>>> production_farm.name = "Test Farm/Production Farm"
>>> production_farm.code = "TFARMP"
>>> production_farm.type = "production"
>>> production_farm.save()
>>> production_farm = Location()
>>> production_farm.name = "Test Farm/Production Farm"
>>> production_farm.code = "TFARMP"
>>> production_farm.type = "production"
>>> production_farm.save()
Create lost and found::
>>> lost_n_found = Location()
>>> lost_n_found.name = "Test Lost and Found"
>>> lost_n_found.code = "TLNF"
>>> lost_n_found.type = "lost_found"
>>> lost_n_found.save()
>>> lost_n_found = Location()
>>> lost_n_found.name = "Test Lost and Found"
>>> lost_n_found.code = "TLNF"
>>> lost_n_found.type = "lost_found"
>>> lost_n_found.save()
Create farm::
>>> farm = Location()
>>> farm.name = "Test Farm"
>>> farm.code = "TFARM"
>>> farm.input_location = inner_farm
>>> farm.output_location = inner_farm
>>> farm.storage_location = inner_farm
>>> farm.production_location = production_farm
>>> farm.save()
>>> farm = Location()
>>> farm.name = "Test Farm"
>>> farm.code = "TFARM"
>>> farm.input_location = inner_farm
>>> farm.output_location = inner_farm
>>> farm.storage_location = inner_farm
>>> farm.production_location = production_farm
>>> farm.save()
Create products::
@ -147,7 +116,7 @@ Create sequence::
Create species::
>>> Specie = Model.get('farm.specie')
>>> Specie = Model.get('farm.specie')
>>> SpecieBreed = Model.get('farm.specie.breed')
>>> SpecieFarmLine = Model.get('farm.specie.farm_line')
>>> warehouse, = Location.find([('type', '=', 'warehouse')])
@ -159,8 +128,8 @@ Create species::
... individual_product=individual_product,
... group_enabled=True,
... group_product=group_product,
... prescription_enabled=True,
... prescription_sequence=prescription_sequence,
... prescription_enabled=True,
... prescription_sequence=prescription_sequence,
... removed_location=lost_n_found,
... foster_location=lost_n_found,
... lost_found_location=lost_n_found,
@ -182,39 +151,41 @@ Create species::
Create medicine product::
>>> ProductTemplate = Model.get('product.template')
>>> ProductUOM = Model.get('product.uom')
>>> product_template = ProductTemplate()
>>> product_template.name = "Template product test"
>>> product_template.type = 'goods'
>>> product_template.unique_variant = True
>>> ProductTemplate = Model.get('product.template')
>>> ProductUOM = Model.get('product.uom')
>>> product_template = ProductTemplate()
>>> product_template.name = "Template product test"
>>> product_template.type = 'goods'
>>> product_template.unique_variant = True
>>> product_template.prescription_required = True
>>> product_template.cost_price = Decimal('00.00')
>>> product_template.list_price = Decimal('00.00')
>>> uom, = ProductUOM.find([('name', '=', 'Unit')])
>>> product_template.default_uom = uom
>>> product_template.save()
>>> product_template.cost_price = Decimal('00.00')
>>> product_template.list_price = Decimal('00.00')
>>> uom, = ProductUOM.find([('name', '=', 'Unit')])
>>> product_template.default_uom = uom
>>> product_template.save()
Create prescription template::
>>> PrescriptionTemplate = Model.get('farm.prescription.template')
>>> Product = Model.get('product.product')
>>> product, = Product.find([('name', '=', 'Template product test')])
>>> product.prescription_required = True
>>> product.save()
>>> prescription_template = PrescriptionTemplate()
>>> prescription_template.product = product
>>> prescription_template.quantity = Decimal('01.00')
>>> #prescription_template.specie = pigs_specie
>>> prescription_template.save()
>>> PrescriptionTemplate = Model.get('farm.prescription.template')
>>> Product = Model.get('product.product')
>>> product, = Product.find([('name', '=', 'Template product test')])
>>> product.prescription_required = True
>>> product.save()
>>> prescription_template = PrescriptionTemplate()
>>> prescription_template.product = product
>>> prescription_template.quantity = Decimal('01.00')
>>> #prescription_template.specie = pigs_specie
>>> prescription_template.save()
Create vet::
>>> vet = Party(name="Veterinary")
>>> vet.save()
>>> Party = Model.get('party.party')
>>> vet = Party(name="Veterinary")
>>> vet.save()
Create account farm user::
>>> User = Model.get('res.user')
>>> farm_user = User()
>>> farm_user.name = 'Farm User'
>>> farm_user.login = 'farm_user'
@ -222,37 +193,34 @@ Create account farm user::
>>> Group = Model.get('res.group')
>>> groups = Group.find([
... ('name', 'in', ['Stock Administration', 'Stock',
... 'Product Administration']),
... 'Product Administration', 'Farm / Prescriptions', 'Farm']),
... ])
>>> farm_user.groups.extend(groups)
>>> farm_user.save()
>>> config.user = farm_user.id
Create prescription::
>>> Prescription = Model.get('farm.prescription')
>>> prescription = Prescription()
>>> prescription.reference = "Test prescription"
>>> prescription.farm = warehouse
>>> Prescription = Model.get('farm.prescription')
>>> prescription = Prescription()
>>> prescription.reference = "Test prescription"
>>> prescription.farm = warehouse
>>> prescription.quantity = Decimal('01.00')
>>> prescription.delivery_date = today
>>> prescription.template = prescription_template
>>> prescription_template.product = product
>>> prescription_template.quantity = Decimal('01.00')
>>> prescription_template.delivery_date = today
>>> prescription_template.number_of_animals = 1
>>> prescription_template.save()
>>> prescription.template = prescription_template
>>> prescription_template.product = product
>>> prescription_template.quantity = Decimal('01.00')
>>> prescription_template.delivery_date = today
>>> prescription_template.number_of_animals = 1
>>> prescription_template.save()
>>> prescription.save()
Create internal shipment::
>>> create_internal_shipment = Wizard('farm.prescription.internal.shipment', models=[prescription])
>>> create_internal_shipment = Wizard('farm.prescription.internal.shipment', models=[prescription])
>>> invoice_wizard = create_internal_shipment.form
>>> invoice_wizard.from_location = inner_farm
>>> create_internal_shipment.execute('create_')
>>> create_internal_shipment.execute('create_')
Check internal shipment::
@ -305,7 +273,7 @@ Create internal shipment::
>>> no_prescription_shipment.click('assign_try')
False
>>> no_prescription_shipment.state
u'waiting'
'waiting'
Create movement with no prescription::
@ -352,7 +320,7 @@ Create internal shipment::
>>> shipment.click('done')
>>> shipment.reload()
>>> shipment.state
u'done'
'done'
>>> shipments = ShipmentInternal.find([])
>>> len(shipments)
3

View File

@ -1,10 +1,11 @@
[tryton]
version=4.1.0
version=5.2.0
depends:
farm
extras_depend:
stock_lot_expiry
stock_lot_sled
xml:
prescription.xml
specie.xml
medication_event.xml
message.xml

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- This file is part of Tryton. The COPYRIGHT file at the top level of
this repository contains the full copyright notices and license terms. -->
<form string="Create Internal Shipment" col="2">
<form col="2">
<label name="from_location"/>
<field name="from_location"/>
<label name="farm"/>

View File

@ -2,7 +2,7 @@
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<data>
<xpath expr="/tree/field[@name='active']" position="after">
<xpath expr="/tree" position="inside">
<field name="veterinarian"/>
<field name="collegiate_number"/>
</xpath>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<form string="Prescription">
<form>
<label name="reference"/>
<field name="reference"/>
<label name="date"/>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<form string="Prescription Line">
<form>
<label name="product"/>
<field name="product"/>
<label name="prescription"/>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<tree string="Prescription Line">
<tree>
<field name="prescription"/>
<field name="product"/>
<field name="quantity"/>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<tree string="Prescriptions">
<tree>
<field name="reference"/>
<field name="date"/>
<field name="farm"/>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<form string="Prescription Template">
<form>
<label name="name"/>
<field name="name" colspan="3"/>
<newline/>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<form string="Prescription Template Line">
<form>
<label name="product"/>
<field name="product"/>
<label name="prescription"/>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<tree string="Prescription Template Line">
<tree>
<field name="prescription"/>
<field name="product"/>
<field name="quantity"/>

View File

@ -1,7 +1,7 @@
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full
copyright notices and license terms. -->
<tree string="Prescription Templates">
<tree>
<field name="name"/>
<field name="product"/>
<field name="quantity"/>