Add endpoint for dynamic javascript files

This commit is contained in:
Oliver Walters 2020-05-02 21:19:34 +10:00
parent e998098e4f
commit 5160165669
5 changed files with 243 additions and 242 deletions

View File

@ -2,22 +2,6 @@
* Requires api.js to be loaded first
*/
function getPartCategoryList(filters={}, options={}) {
return inventreeGet('/api/part/category/', filters, options);
}
function getSupplierPartList(filters={}, options={}) {
return inventreeGet('/api/part/supplier/', filters, options);
}
function getPartList(filters={}, options={}) {
return inventreeGet('/api/part/', filters, options);
}
function getBomList(filters={}, options={}) {
return inventreeGet('/api/bom/', filters, options);
}
function toggleStar(options) {
/* Toggle the 'starred' status of a part.
* Performs AJAX queries and updates the display on the button.
@ -72,230 +56,4 @@ function toggleStar(options) {
},
}
);
}
function loadPartTable(table, url, options={}) {
/* Load part listing data into specified table.
*
* Args:
* - table: HTML reference to the table
* - url: Base URL for API query
* - options: object containing following (optional) fields
* checkbox: Show the checkbox column
* query: extra query params for API request
* buttons: If provided, link buttons to selection status of this table
* disableFilters: If true, disable custom filters
*/
// Ensure category detail is included
options.params['category_detail'] = true;
var params = options.params || {};
var filters = {};
if (!options.disableFilters) {
filters = loadTableFilters("parts");
}
for (var key in params) {
filters[key] = params[key];
}
setupFilterList("parts", $(table));
var columns = [
{
field: 'pk',
title: 'ID',
visible: false,
}
];
if (options.checkbox) {
columns.push({
checkbox: true,
title: 'Select',
searchable: false,
});
}
columns.push({
field: 'name',
title: 'Part',
sortable: true,
formatter: function(value, row, index, field) {
var name = '';
if (row.IPN) {
name += row.IPN;
name += ' | ';
}
name += value;
if (row.revision) {
name += ' | ';
name += row.revision;
}
if (row.is_template) {
name = '<i>' + name + '</i>';
}
var display = imageHoverIcon(row.thumbnail) + renderLink(name, '/part/' + row.pk + '/');
if (row.is_template) {
display += `<span class='fas fa-clone label-right' title='Template part'></span>`;
}
if (row.assembly) {
display += `<span class='fas fa-tools label-right' title='Assembled part'></span>`;
}
if (row.starred) {
display += `<span class='fas fa-star label-right' title='Starred part'></span>`;
}
if (row.salable) {
display += `<span class='fas fa-dollar-sign label-right' title='Salable part'></span>`;
}
/*
if (row.component) {
display = display + `<span class='fas fa-cogs label-right' title='Component part'></span>`;
}
*/
if (!row.active) {
display += `<span class='label label-warning label-right'>INACTIVE</span>`;
}
return display;
}
});
columns.push({
sortable: true,
field: 'description',
title: 'Description',
formatter: function(value, row, index, field) {
if (row.is_template) {
value = '<i>' + value + '</i>';
}
return value;
}
});
columns.push({
sortable: true,
field: 'category_detail',
title: 'Category',
formatter: function(value, row, index, field) {
if (row.category) {
return renderLink(value.pathstring, "/part/category/" + row.category + "/");
}
else {
return 'No category';
}
}
});
columns.push({
field: 'in_stock',
title: 'Stock',
searchable: false,
sortable: true,
formatter: function(value, row, index, field) {
var link = "stock";
if (value) {
// There IS stock available for this part
// Is stock "low" (below the 'minimum_stock' quantity)?
if (row.minimum_stock && row.minimum_stock > value) {
value += "<span class='label label-right label-warning'>Low stock</span>";
}
} else if (row.on_order) {
// There is no stock available, but stock is on order
value = "0<span class='label label-right label-primary'>On Order : " + row.on_order + "</span>";
link = "orders";
} else if (row.building) {
// There is no stock available, but stock is being built
value = "0<span class='label label-right label-info'>Building : " + row.building + "</span>";
link = "builds";
} else {
// There is no stock available
value = "0<span class='label label-right label-danger'>No Stock</span>";
}
return renderLink(value, '/part/' + row.pk + "/" + link + "/");
}
});
$(table).inventreeTable({
url: url,
sortName: 'name',
method: 'get',
queryParams: filters,
groupBy: false,
original: params,
formatNoMatches: function() { return "No parts found"; },
columns: columns,
});
if (options.buttons) {
linkButtonsToSelection($(table), options.buttons);
}
/* Button callbacks for part table buttons */
$("#multi-part-order").click(function() {
var selections = $(table).bootstrapTable("getSelections");
var parts = [];
selections.forEach(function(item) {
parts.push(item.pk);
});
launchModalForm("/order/purchase-order/order-parts/", {
data: {
parts: parts,
},
});
});
$("#multi-part-category").click(function() {
var selections = $(table).bootstrapTable("getSelections");
var parts = [];
selections.forEach(function(item) {
parts.push(item.pk);
});
launchModalForm("/part/set-category/", {
data: {
parts: parts,
},
reload: true,
});
});
$('#multi-part-export').click(function() {
var selections = $(table).bootstrapTable("getSelections");
var parts = '';
selections.forEach(function(item) {
parts += item.pk;
parts += ',';
});
location.href = '/part/export/?parts=' + parts;
});
}

View File

@ -35,6 +35,7 @@ from rest_framework.documentation import include_docs_urls
from .views import IndexView, SearchView, DatabaseStatsView
from .views import SettingsView, EditUserView, SetPasswordView
from .views import DynamicJsView
from .api import InfoView, BarcodePluginView, ActionPluginView
@ -74,6 +75,7 @@ settings_urls = [
]
dynamic_javascript_urls = [
url(r'^part.js', DynamicJsView.as_view(template_name='js/part.js'), name='part.js'),
]
urlpatterns = [

View File

@ -514,6 +514,18 @@ class SearchView(TemplateView):
return super(TemplateView, self).render_to_response(context)
class DynamicJsView(TemplateView):
"""
View for returning javacsript files,
which instead of being served dynamically,
are passed through the django translation engine!
"""
template_name = ""
content_type = 'text/javascript'
class SettingsView(TemplateView):
""" View for configuring User settings
"""

View File

@ -114,6 +114,8 @@ InvenTree
<script type='text/javascript' src="{% static 'script/inventree/notification.js' %}"></script>
<script type='text/javascript' src="{% static 'script/inventree/sidenav.js' %}"></script>
<script type='text/javascript' src="{% url 'part.js' %}"></script>
<script type='text/javascript' src="{% static 'fontawesome/js/solid.js' %}"></script>
<script type='text/javascript' src="{% static 'fontawesome/js/brands.js' %}"></script>
<script type='text/javascript' src="{% static 'fontawesome/js/fontawesome.js' %}"></script>

View File

@ -0,0 +1,227 @@
{% load i18n %}
function loadPartTable(table, url, options={}) {
/* Load part listing data into specified table.
*
* Args:
* - table: HTML reference to the table
* - url: Base URL for API query
* - options: object containing following (optional) fields
* checkbox: Show the checkbox column
* query: extra query params for API request
* buttons: If provided, link buttons to selection status of this table
* disableFilters: If true, disable custom filters
*/
// Ensure category detail is included
options.params['category_detail'] = true;
var params = options.params || {};
var filters = {};
if (!options.disableFilters) {
filters = loadTableFilters("parts");
}
for (var key in params) {
filters[key] = params[key];
}
setupFilterList("parts", $(table));
var columns = [
{
field: 'pk',
title: 'ID',
visible: false,
}
];
if (options.checkbox) {
columns.push({
checkbox: true,
title: 'Select',
searchable: false,
});
}
columns.push({
field: 'name',
title: 'Part',
sortable: true,
formatter: function(value, row, index, field) {
var name = '';
if (row.IPN) {
name += row.IPN;
name += ' | ';
}
name += value;
if (row.revision) {
name += ' | ';
name += row.revision;
}
if (row.is_template) {
name = '<i>' + name + '</i>';
}
var display = imageHoverIcon(row.thumbnail) + renderLink(name, '/part/' + row.pk + '/');
if (row.is_template) {
display += `<span class='fas fa-clone label-right' title='Template part'></span>`;
}
if (row.assembly) {
display += `<span class='fas fa-tools label-right' title='Assembled part'></span>`;
}
if (row.starred) {
display += `<span class='fas fa-star label-right' title='Starred part'></span>`;
}
if (row.salable) {
display += `<span class='fas fa-dollar-sign label-right' title='Salable part'></span>`;
}
/*
if (row.component) {
display = display + `<span class='fas fa-cogs label-right' title='Component part'></span>`;
}
*/
if (!row.active) {
display += `<span class='label label-warning label-right'>INACTIVE</span>`;
}
return display;
}
});
columns.push({
sortable: true,
field: 'description',
title: 'Description',
formatter: function(value, row, index, field) {
if (row.is_template) {
value = '<i>' + value + '</i>';
}
return value;
}
});
columns.push({
sortable: true,
field: 'category_detail',
title: 'Category',
formatter: function(value, row, index, field) {
if (row.category) {
return renderLink(value.pathstring, "/part/category/" + row.category + "/");
}
else {
return 'No category';
}
}
});
columns.push({
field: 'in_stock',
title: 'Stock',
searchable: false,
sortable: true,
formatter: function(value, row, index, field) {
var link = "stock";
if (value) {
// There IS stock available for this part
// Is stock "low" (below the 'minimum_stock' quantity)?
if (row.minimum_stock && row.minimum_stock > value) {
value += "<span class='label label-right label-warning'>Low stock</span>";
}
} else if (row.on_order) {
// There is no stock available, but stock is on order
value = "0<span class='label label-right label-primary'>On Order : " + row.on_order + "</span>";
link = "orders";
} else if (row.building) {
// There is no stock available, but stock is being built
value = "0<span class='label label-right label-info'>Building : " + row.building + "</span>";
link = "builds";
} else {
// There is no stock available
value = "0<span class='label label-right label-danger'>No Stock</span>";
}
return renderLink(value, '/part/' + row.pk + "/" + link + "/");
}
});
$(table).inventreeTable({
url: url,
sortName: 'name',
method: 'get',
queryParams: filters,
groupBy: false,
original: params,
formatNoMatches: function() { return "No parts found"; },
columns: columns,
});
if (options.buttons) {
linkButtonsToSelection($(table), options.buttons);
}
/* Button callbacks for part table buttons */
$("#multi-part-order").click(function() {
var selections = $(table).bootstrapTable("getSelections");
var parts = [];
selections.forEach(function(item) {
parts.push(item.pk);
});
launchModalForm("/order/purchase-order/order-parts/", {
data: {
parts: parts,
},
});
});
$("#multi-part-category").click(function() {
var selections = $(table).bootstrapTable("getSelections");
var parts = [];
selections.forEach(function(item) {
parts.push(item.pk);
});
launchModalForm("/part/set-category/", {
data: {
parts: parts,
},
reload: true,
});
});
$('#multi-part-export').click(function() {
var selections = $(table).bootstrapTable("getSelections");
var parts = '';
selections.forEach(function(item) {
parts += item.pk;
parts += ',';
});
location.href = '/part/export/?parts=' + parts;
});
}