diff --git a/InvenTree/stock/serializers.py b/InvenTree/stock/serializers.py index c44dffe94f..e2781af12f 100644 --- a/InvenTree/stock/serializers.py +++ b/InvenTree/stock/serializers.py @@ -134,7 +134,7 @@ class StockItemSerializer(InvenTreeModelSerializer): tracking_items = serializers.IntegerField(source='tracking_info_count', read_only=True, required=False) - quantity = serializers.FloatField() + # quantity = serializers.FloatField() allocated = serializers.FloatField(source='allocation_count', required=False) @@ -142,20 +142,22 @@ class StockItemSerializer(InvenTreeModelSerializer): stale = serializers.BooleanField(required=False, read_only=True) - serial = serializers.CharField(required=False) + # serial = serializers.CharField(required=False) required_tests = serializers.IntegerField(source='required_test_count', read_only=True, required=False) purchase_price = InvenTreeMoneySerializer( label=_('Purchase Price'), max_digits=19, decimal_places=4, - allow_null=True + allow_null=True, + help_text=_('Purchase price of this stock item'), ) purchase_price_currency = serializers.ChoiceField( choices=currency_code_mappings(), default=currency_code_default, label=_('Currency'), + help_text=_('Purchase currency of this stock item'), ) purchase_price_string = serializers.SerializerMethodField() @@ -197,6 +199,7 @@ class StockItemSerializer(InvenTreeModelSerializer): 'belongs_to', 'build', 'customer', + 'delete_on_deplete', 'expired', 'expiry_date', 'in_stock', diff --git a/InvenTree/stock/templates/stock/item_base.html b/InvenTree/stock/templates/stock/item_base.html index b7019ff887..97b94bdd70 100644 --- a/InvenTree/stock/templates/stock/item_base.html +++ b/InvenTree/stock/templates/stock/item_base.html @@ -150,6 +150,7 @@
  • {% trans "Duplicate stock item" %}
  • {% endif %}
  • {% trans "Edit stock item" %}
  • +
  • {% trans "Edit stock item" %}
  • {% if user.is_staff or roles.stock.delete %} {% if item.can_delete %}
  • {% trans "Delete stock item" %}
  • @@ -520,6 +521,10 @@ $("#stock-edit").click(function () { ); }); +$('#stock-edit-2').click(function() { + editStockItem({{ item.pk }}); +}); + $('#stock-edit-status').click(function () { constructForm('{% url "api-stock-detail" item.pk %}', { diff --git a/InvenTree/templates/js/translated/forms.js b/InvenTree/templates/js/translated/forms.js index 1bfe196286..07e38565cd 100644 --- a/InvenTree/templates/js/translated/forms.js +++ b/InvenTree/templates/js/translated/forms.js @@ -179,6 +179,7 @@ function constructChangeForm(fields, options) { // Request existing data from the API endpoint $.ajax({ url: options.url, + data: options.params || {}, type: 'GET', contentType: 'application/json', dataType: 'json', @@ -194,6 +195,17 @@ function constructChangeForm(fields, options) { fields[field].value = data[field]; } } + + // An optional function can be provided to process the returned results, + // before they are rendered to the form + if (options.processResults) { + var processed = options.processResults(data, fields, options); + + // If the processResults function returns data, it will be stored + if (processed) { + data = processed; + } + } // Store the entire data object options.instance = data; diff --git a/InvenTree/templates/js/translated/stock.js b/InvenTree/templates/js/translated/stock.js index 67c50bffef..2f885477a5 100644 --- a/InvenTree/templates/js/translated/stock.js +++ b/InvenTree/templates/js/translated/stock.js @@ -68,6 +68,95 @@ function locationFields() { } +function stockItemFields(options={}) { + var fields = { + part: {}, + supplier_part: { + filters: { + part_detail: true, + supplier_detail: true, + }, + adjustFilters: function(query, opts) { + var part = getFormFieldValue('part', {}, opts); + + if (part) { + query.part = part; + } + + return query; + } + }, + serial: {}, + status: {}, + expiry_date: {}, + batch: {}, + purchase_price: {}, + purchase_price_currency: {}, + packaging: {}, + link: {}, + delete_on_deplete: {}, + // owner: {}, + }; + + // Remove stock expiry fields if feature is not enabled + if (!global_settings.STOCK_ENABLE_EXPIRY) { + delete fields['expiry_date']; + } + + return fields; +} + + +function stockItemGroups(options={}) { + return { + + }; +} + + +/* + * Launch a modal form to edit a given StockItem + */ +function editStockItem(pk, options={}) { + + var url = `/api/stock/${pk}/`; + + var fields = stockItemFields(options); + + // Prevent editing of the "part" + fields.part.hidden = true; + + var groups = stockItemGroups(options); + + constructForm(url, { + fields: fields, + groups: groups, + title: '{% trans "Edit Stock Item" %}', + params: { + part_detail: true, + supplier_part_detail: true, + }, + processResults: function(data, fields, options) { + // Callback when StockItem data is received from server + + if (data.part_detail.trackable) { + delete options.fields.delete_on_deplete; + } else { + // Remove serial number field if part is not trackable + delete options.fields.serial; + } + + // Remove pricing fields if part is not purchaseable + if (!data.part_detail.purchaseable) { + delete options.fields.supplier_part; + delete options.fields.purchase_price; + delete options.fields.purchase_price_currency; + } + } + }); +} + + /* Stock API functions * Requires api.js to be loaded first */