summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ishtar/ishtar_base/forms.py15
-rw-r--r--ishtar/ishtar_base/forms_items.py91
-rw-r--r--ishtar/ishtar_base/models.py43
-rw-r--r--ishtar/ishtar_base/urls.py12
-rw-r--r--ishtar/ishtar_base/views.py24
5 files changed, 159 insertions, 26 deletions
diff --git a/ishtar/ishtar_base/forms.py b/ishtar/ishtar_base/forms.py
index 29d9ab4d6..9faba2ac9 100644
--- a/ishtar/ishtar_base/forms.py
+++ b/ishtar/ishtar_base/forms.py
@@ -269,7 +269,18 @@ class Wizard(NamedUrlSessionFormWizard):
value = form.cleaned_data[key]
if key in associated_models:
if value:
- value = associated_models[key].objects.get(pk=value)
+ model = associated_models[key]
+ if isinstance(value, unicode) \
+ or isinstance(value, str) and "," in value:
+ value = value.split(",")
+ if isinstance(value, list) \
+ or isinstance(value, tuple):
+ value = [model.objects.get(pk=val)
+ for val in value if val]
+ if len(value) == 1:
+ value = value[0]
+ else:
+ value = model.objects.get(pk=value)
else:
value = None
dct[key] = value
@@ -335,7 +346,7 @@ class Wizard(NamedUrlSessionFormWizard):
m = getattr(self.model, dependant_item)
model = m.field.rel.to
c_dct = other_objs[dependant_item].copy()
- if hasattr(model, 'history'):
+ if issubclass(model, models.BaseHistorizedItem):
c_dct['history_modifier'] = request.user
c_item = model(**c_dct)
c_item.save()
diff --git a/ishtar/ishtar_base/forms_items.py b/ishtar/ishtar_base/forms_items.py
index 484902341..a89dc7cf1 100644
--- a/ishtar/ishtar_base/forms_items.py
+++ b/ishtar/ishtar_base/forms_items.py
@@ -185,10 +185,7 @@ class BaseTreatmentForm(forms.Form):
associated_models = {'treatment_type':models.TreatmentType,
'person':models.Person,
'location':models.Warehouse}
- treatment_type = forms.ChoiceField(label=_(u"Treatment type"),
- choices=models.TreatmentType.get_types())
- description = forms.CharField(label=_(u"Description"),
- widget=forms.Textarea, required=False)
+ treatment_type = forms.ChoiceField(label=_(u"Treatment type"), choices=[])
person = forms.IntegerField(label=_(u"Person"),
widget=widgets.JQueryAutoComplete(
reverse_lazy('autocomplete-person'), associated_model=models.Person),
@@ -198,11 +195,20 @@ class BaseTreatmentForm(forms.Form):
reverse_lazy('autocomplete-warehouse'), associated_model=models.Warehouse,
new=True),
validators=[models.valid_id(models.Warehouse)])
+ description = forms.CharField(label=_(u"Description"),
+ widget=forms.Textarea, required=False)
start_date = forms.DateField(label=_(u"Start date"), required=False,
widget=widgets.JQueryDate)
end_date = forms.DateField(label=_(u"End date"), required=False,
widget=widgets.JQueryDate)
+ def __init__(self, *args, **kwargs):
+ super(BaseTreatmentForm, self).__init__(*args, **kwargs)
+ self.fields['treatment_type'].choices = models.TreatmentType.get_types(
+ exclude=['packaging'])
+ self.fields['treatment_type'].help_text = models.TreatmentType.get_help(
+ exclude=['packaging'])
+
class ItemMultipleFormSelection(forms.Form):
form_label = _(u"Upstream items")
associated_models = {'items':models.Item}
@@ -213,13 +219,42 @@ class ItemMultipleFormSelection(forms.Form):
class ContainerForm(forms.Form):
form_label = _(u"Container")
- associated_models = {'container_type':models.ContainerType,}
reference = forms.CharField(label=_(u"Reference"))
- container_type = forms.ChoiceField(label=_(u"Container type"),
- choices=models.ContainerType.get_types())
+ container_type = forms.ChoiceField(label=_(u"Container type"), choices=[])
+ location = forms.IntegerField(label=_(u"Location"),
+ widget=widgets.JQueryAutoComplete(
+ reverse_lazy('autocomplete-warehouse'), associated_model=models.Warehouse,
+ new=True),
+ validators=[models.valid_id(models.Warehouse)])
comment = forms.CharField(label=_(u"Comment"),
widget=forms.Textarea, required=False)
+ def __init__(self, *args, **kwargs):
+ super(ContainerForm, self).__init__(*args, **kwargs)
+ self.fields['container_type'].choices = \
+ models.ContainerType.get_types()
+ self.fields['container_type'].help_text = \
+ models.ContainerType.get_help()
+
+ def save(self, user):
+ dct = self.cleaned_data
+ dct['history_modifier'] = user
+ dct['container_type'] = models.ContainerType.objects.get(
+ pk=dct['container_type'])
+ dct['location'] = models.Warehouse.objects.get(pk=dct['location'])
+ new_item = models.Container(**dct)
+ new_item.save()
+ return new_item
+
+class ContainerSelectForm(forms.Form):
+ form_label = _(u"Container")
+ associated_models = {'container':models.Container,}
+ container = forms.IntegerField(label=_(u"Container"),
+ widget=widgets.JQueryAutoComplete(reverse_lazy('autocomplete-container'),
+ associated_model=models.Container, new=True),
+ validators=[models.valid_id(models.Container)])
+
+
def check_treatment(form_name, type_key, type_list=[], not_type_list=[]):
type_list = [models.TreatmentType.objects.get(txt_idx=tpe).pk
for tpe in type_list]
@@ -242,13 +277,13 @@ def check_treatment(form_name, type_key, type_list=[], not_type_list=[]):
return func
class ResultItemForm(forms.Form):
- form_label = _("Resulting item")
+ form_label = _(u"Resulting item")
associated_models = {'material_type':models.MaterialType}
label = forms.CharField(label=_(u"ID"),
validators=[validators.MaxLengthValidator(60)])
- description = forms.CharField(label=_("Precise description"),
+ description = forms.CharField(label=_(u"Precise description"),
widget=forms.Textarea)
- material_type = forms.ChoiceField(label=_("Material type"),
+ material_type = forms.ChoiceField(label=_(u"Material type"),
choices=models.MaterialType.get_types())
volume = forms.IntegerField(label=_(u"Volume (l)"))
weight = forms.IntegerField(label=_(u"Weight (g)"))
@@ -292,6 +327,42 @@ treatment_creation_wizard = TreatmentWizard([
# Warehouse management #
########################
+class PackagingWizard(TreatmentWizard):
+ pass
+
+class BasePackagingForm(forms.Form):
+ form_label = _(u"Packaging")
+ associated_models = {'treatment_type':models.TreatmentType,
+ 'person':models.Person,
+ 'location':models.Warehouse}
+ treatment_type = forms.IntegerField(label="", widget=forms.HiddenInput)
+ person = forms.IntegerField(label=_(u"Person"),
+ widget=widgets.JQueryAutoComplete(
+ reverse_lazy('autocomplete-person'), associated_model=models.Person),
+ validators=[models.valid_id(models.Person)])
+ location = forms.IntegerField(label=_(u"Location"),
+ widget=widgets.JQueryAutoComplete(
+ reverse_lazy('autocomplete-warehouse'), associated_model=models.Warehouse,
+ new=True),
+ validators=[models.valid_id(models.Warehouse)])
+ start_date = forms.DateField(label=_(u"Date"), required=False,
+ widget=widgets.JQueryDate)
+
+ def __init__(self, *args, **kwargs):
+ super(BasePackagingForm, self).__init__(*args, **kwargs)
+ self.fields['treatment_type'].initial = \
+ models.TreatmentType.objects.get(txt_idx='packaging').pk
+
+class ItemPackagingFormSelection(ItemMultipleFormSelection):
+ form_label = _(u"Packaged items")
+
+warehouse_packaging_wizard = PackagingWizard([
+ ('base-packaging', BasePackagingForm),
+ ('container-packaging', ContainerSelectForm),
+ ('multiselecitems-packaging', ItemPackagingFormSelection),
+ ('final-packaging', FinalForm)],
+ url_name='warehouse_packaging',)
+
"""
warehouse_packaging_wizard = ItemSourceWizard([
('selec-warehouse_packaging', ItemsSelection),
diff --git a/ishtar/ishtar_base/models.py b/ishtar/ishtar_base/models.py
index 37af19f87..ee22b9973 100644
--- a/ishtar/ishtar_base/models.py
+++ b/ishtar/ishtar_base/models.py
@@ -74,7 +74,8 @@ def valid_ids(cls):
try:
cls.objects.get(pk=v)
except ObjectDoesNotExist:
- raise ValidationError(_(u"Not a valid item."))
+ raise ValidationError(
+ _(u"An item selected is not a valid item."))
return func
# unique validator for models
@@ -150,11 +151,11 @@ class GeneralType(models.Model):
return self.label
@classmethod
- def get_help(cls, dct={}):
+ def get_help(cls, dct={}, exclude=[]):
help_text = cls.HELP_TEXT
c_rank = -1
help_items = u"\n"
- for item in cls.get_types(dct=dct, instances=True):
+ for item in cls.get_types(dct=dct, instances=True, exclude=exclude):
if hasattr(item, '__iter__'):
# TODO: manage multiple levels
continue
@@ -175,18 +176,21 @@ class GeneralType(models.Model):
return u""
@classmethod
- def get_types(cls, dct={}, instances=False):
+ def get_types(cls, dct={}, instances=False, exclude=[]):
base_dct = dct.copy()
if hasattr(cls, 'parent'):
- return cls._get_parent_types(base_dct, instances)
- return cls._get_types(base_dct, instances)
+ return cls._get_parent_types(base_dct, instances, exclude=exclude)
+ return cls._get_types(base_dct, instances, exclude=exclude)
@classmethod
- def _get_types(cls, dct={}, instances=False):
+ def _get_types(cls, dct={}, instances=False, exclude=[]):
dct['available'] = True
if not instances:
yield ('', '--')
- for item in cls.objects.filter(**dct).all():
+ items = cls.objects.filter(**dct)
+ if exclude:
+ items = items.exclude(txt_idx__in=exclude)
+ for item in items.all():
if instances:
item.rank = 0
yield item
@@ -196,10 +200,12 @@ class GeneralType(models.Model):
PREFIX = "› "
@classmethod
- def _get_childs(cls, item, dct, prefix=0, instances=False):
+ def _get_childs(cls, item, dct, prefix=0, instances=False, exclude=[]):
prefix += 1
dct['parent'] = item
childs = cls.objects.filter(**dct)
+ if exclude:
+ childs = childs.exclude(txt_idx__in=exclude)
if hasattr(cls, 'order'):
childs = childs.order_by('order')
for child in childs.all():
@@ -209,16 +215,19 @@ class GeneralType(models.Model):
else:
yield (child.pk, SafeUnicode(prefix*cls.PREFIX + \
unicode(_(unicode(child))) ))
- for sub_child in cls._get_childs(child, dct, prefix, instances):
+ for sub_child in cls._get_childs(child, dct, prefix, instances,
+ exclude=exclude):
yield sub_child
@classmethod
- def _get_parent_types(cls, dct={}, instances=False):
+ def _get_parent_types(cls, dct={}, instances=False, exclude=[]):
dct['available'] = True
if not instances:
yield ('', '--')
dct['parent'] = None
items = cls.objects.filter(**dct)
+ if exclude:
+ items = items.exclude(txt_idx__in=exclude)
if hasattr(cls, 'order'):
items = items.order_by('order')
for item in items.all():
@@ -227,7 +236,7 @@ class GeneralType(models.Model):
yield item
else:
yield (item.pk, unicode(item))
- for child in cls._get_childs(item, dct, instances):
+ for child in cls._get_childs(item, dct, instances, exclude=exclude):
yield child
class HistoryError(Exception):
@@ -335,6 +344,10 @@ class LightHistorizedItem(BaseHistorizedItem):
class Meta:
abstract = True
+ def save(self, *args, **kwargs):
+ super(LightHistorizedItem, self).save(*args, **kwargs)
+ return True
+
class Departement(models.Model):
label = models.CharField(_(u"Label"), max_length=30)
number = models.CharField(_(u"Number"), unique=True, max_length=3)
@@ -1129,6 +1142,12 @@ class Container(LightHistorizedItem):
verbose_name = _(u"Container")
verbose_name_plural = _(u"Containers")
+ def __unicode__(self):
+ lbl = self.reference
+ lbl += u" - %s" % unicode(self.container_type)
+ lbl += u" (%s)" % unicode(self.location)
+ return lbl
+
if settings.COUNTRY == 'fr':
class Arrondissement(models.Model):
name = models.CharField(u"Nom", max_length=30)
diff --git a/ishtar/ishtar_base/urls.py b/ishtar/ishtar_base/urls.py
index a45211c8b..d313f1b76 100644
--- a/ishtar/ishtar_base/urls.py
+++ b/ishtar/ishtar_base/urls.py
@@ -108,8 +108,6 @@ urlpatterns = patterns('',
ishtar_forms.item_creation_wizard, name='item_creation'),
url(BASE_URL + r'item_modification/(?P<step>.+)$',
ishtar_forms.item_modification_wizard, name='item_modification'),
- url(BASE_URL + r'treatment_creation/(?P<step>.+)$',
- ishtar_forms.treatment_creation_wizard, name='treatment_creation'),
url(BASE_URL + r'item_source_creation/(?P<step>.+)$',
ishtar_forms.item_source_creation_wizard,
name='item_source_creation'),
@@ -119,6 +117,11 @@ urlpatterns = patterns('',
url(BASE_URL + r'item_source_deletion/(?P<step>.+)$',
ishtar_forms.item_source_deletion_wizard,
name='item_source_deletion'),
+ # Treatments
+ url(BASE_URL + r'treatment_creation/(?P<step>.+)$',
+ ishtar_forms.treatment_creation_wizard, name='treatment_creation'),
+ url(BASE_URL + r'warehouse_packaging/(?P<step>.+)$',
+ ishtar_forms.warehouse_packaging_wizard, name='warehouse_packaging'),
)
for section in menu.childs:
for menu_item in section.childs:
@@ -192,4 +195,9 @@ urlpatterns += patterns('ishtar.ishtar_base.views',
name='get-item'),
url(BASE_URL + r'get-itemsource/(?P<type>.+)?$',
'get_itemsource', name='get-itemsource'),
+ # Treatments
+ url(BASE_URL + r'autocomplete-container/?$',
+ 'autocomplete_container', name='autocomplete-container'),
+ url(BASE_URL + r'new-container/(?P<parent_name>.+)?/$',
+ 'new_container', name='new-container'),
)
diff --git a/ishtar/ishtar_base/views.py b/ishtar/ishtar_base/views.py
index a48912eeb..d4d82ac9f 100644
--- a/ishtar/ishtar_base/views.py
+++ b/ishtar/ishtar_base/views.py
@@ -549,6 +549,29 @@ def autocomplete_author(request):
for author in authors])
return HttpResponse(data, mimetype='text/plain')
+def autocomplete_container(request):
+ if not request.user.has_perm('ishtar_base.view_warehouse',
+ models.Warehouse)\
+ and not request.user.has_perm('ishtar_base.view_own_warehouse',
+ models.Warehouse):
+ return HttpResponse(mimetype='text/plain')
+ if not request.GET.get('term'):
+ return HttpResponse(mimetype='text/plain')
+ q = request.GET.get('term')
+ query = Q()
+ for q in q.split(' '):
+ extra = Q(container_type__label__icontains=q) | \
+ Q(container_type__reference__icontains=q) | \
+ Q(reference__icontains=q) | \
+ Q(location__name=q) | \
+ Q(location__town=q)
+ query = query & extra
+ limit = 15
+ containers = models.Container.objects.filter(query)[:limit]
+ data = json.dumps([{'id':container.pk, 'value':unicode(container)}
+ for container in containers])
+ return HttpResponse(data, mimetype='text/plain')
+
def new_item(model):
def func(request, parent_name):
model_name = model._meta.object_name
@@ -580,6 +603,7 @@ new_warehouse = new_item(models.Warehouse)
new_person = new_item(models.Person)
new_organization = new_item(models.Organization)
new_author = new_item(models.Author)
+new_container = new_item(models.Container)
def action(request, action_slug, obj_id=None, *args, **kwargs):
"""