mirror of
https://github.com/inventree/InvenTree
synced 2024-08-30 18:33:04 +00:00
Build order rules (#7842)
* Add new global setting * Check if there are open children before completing a build * Adds management command to export settings definition * Fix settings export * Extract settings data into documentation * Add global settings spec * User settings * Revert strict mode * Tweak unit test * Remove unreachable code * Always export settings first * Remove unused macro * Remove old images * Re-add missing docs strings * Tweak docs * Remove unused import
This commit is contained in:
parent
556a3161e8
commit
42183a3a3f
1
.gitignore
vendored
1
.gitignore
vendored
@ -111,3 +111,4 @@ InvenTree/web/static
|
||||
docs/schema.yml
|
||||
docs/docs/api/*.yml
|
||||
docs/docs/api/schema/*.yml
|
||||
inventree_settings.json
|
||||
|
Binary file not shown.
Before Width: | Height: | Size: 56 KiB |
Binary file not shown.
Before Width: | Height: | Size: 84 KiB |
24
docs/docs/build/build.md
vendored
24
docs/docs/build/build.md
vendored
@ -265,18 +265,16 @@ Build orders may (optionally) have a target complete date specified. If this dat
|
||||
- Builds can be filtered by overdue status in the build list
|
||||
- Overdue builds will be displayed on the home page
|
||||
|
||||
## Build Order Restrictions
|
||||
## Build Order Settings
|
||||
|
||||
There are a number of optional restrictions which can be applied to build orders, which may be enabled or disabled in the system settings:
|
||||
The following [global settings](../settings/global.md) are available for adjusting the behavior of build orders:
|
||||
|
||||
### Require Active Part
|
||||
|
||||
If this option is enabled, build orders can only be created for parts which are marked as [Active](../part/part.md#active-parts).
|
||||
|
||||
### Require Locked Part
|
||||
|
||||
If this option is enabled, build orders can only be created for parts which are marked as [Locked](../part/part.md#locked-parts).
|
||||
|
||||
### Require Valid BOM
|
||||
|
||||
If this option is enabled, build orders can only be created for parts which have a valid [Bill of Materials](./bom.md) defined.
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("BUILDORDER_REFERENCE_PATTERN") }}
|
||||
{{ globalsetting("BUILDORDER_REQUIRE_RESPONSIBLE") }}
|
||||
{{ globalsetting("BUILDORDER_REQUIRE_ACTIVE_PART") }}
|
||||
{{ globalsetting("BUILDORDER_REQUIRE_LOCKED_PART") }}
|
||||
{{ globalsetting("BUILDORDER_REQUIRE_VALID_BOM") }}
|
||||
{{ globalsetting("BUILDORDER_REQUIRE_CLOSED_CHILDS") }}
|
||||
{{ globalsetting("PREVENT_BUILD_COMPLETION_HAVING_INCOMPLETED_TESTS") }}
|
||||
|
@ -139,3 +139,14 @@ This view can be accessed externally as an ICS calendar using a URL like the fol
|
||||
`http://inventree.example.org/api/order/calendar/purchase-order/calendar.ics`
|
||||
|
||||
by default, completed orders are not exported. These can be included by appending `?include_completed=True` to the URL.
|
||||
|
||||
## Purchase Order Settings
|
||||
|
||||
The following [global settings](../settings/global.md) are available for purchase orders:
|
||||
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("PURCHASEORDER_REFERENCE_PATTERN") }}
|
||||
{{ globalsetting("PURCHASEORDER_REQUIRE_RESPONSIBLE") }}
|
||||
{{ globalsetting("PURCHASEORDER_EDIT_COMPLETED_ORDERS") }}
|
||||
{{ globalsetting("PURCHASEORDER_AUTO_COMPLETE") }}
|
||||
|
@ -121,3 +121,14 @@ This view can be accessed externally as an ICS calendar using a URL like the fol
|
||||
`http://inventree.example.org/api/order/calendar/return-order/calendar.ics`
|
||||
|
||||
by default, completed orders are not exported. These can be included by appending `?include_completed=True` to the URL.
|
||||
|
||||
## Return Order Settings
|
||||
|
||||
The following [global settings](../settings/global.md) are available for return orders:
|
||||
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("RETURNORDER_ENABLED") }}
|
||||
{{ globalsetting("RETURNORDER_REFERENCE_PATTERN") }}
|
||||
{{ globalsetting("RETURNORDER_REQUIRE_RESPONSIBLE") }}
|
||||
{{ globalsetting("RETURNORDER_EDIT_COMPLETED_ORDERS") }}
|
||||
|
@ -183,3 +183,15 @@ All these fields can be edited by the user:
|
||||
{% with id="edit-shipment", url="order/edit_shipment.png", description="Edit shipment" %}
|
||||
{% include "img.html" %}
|
||||
{% endwith %}
|
||||
|
||||
## Sales Order Settings
|
||||
|
||||
The following [global settings](../settings/global.md) are available for sales orders:
|
||||
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("SALESORDER_REFERENCE_PATTERN") }}
|
||||
{{ globalsetting("SALESORDER_REQUIRE_RESPONSIBLE") }}
|
||||
{{ globalsetting("SALESORDER_DEFAULT_SHIPMENT") }}
|
||||
{{ globalsetting("SALESORDER_EDIT_COMPLETED_ORDERS") }}
|
||||
{{ globalsetting("SALESORDER_SHIP_COMPLETE") }}
|
||||
|
@ -24,12 +24,7 @@ If a different currency exchange backend is needed, or a custom implementation i
|
||||
|
||||
### Currency Settings
|
||||
|
||||
In the [settings screen](./global.md), under the *Pricing* section, the following currency settings are available:
|
||||
|
||||
| Setting | Description | Default Value |
|
||||
| --- | --- |
|
||||
| Default Currency | The selected *default* currency for the system. | USD |
|
||||
| Supported Currencies | The list of supported currencies for the system. | AUD, CAD, CNY, EUR, GBP, JPY, NZD, USD |
|
||||
Refer to the [global settings](./global.md#pricing-and-currency) documentation for more information on available currency settings.
|
||||
|
||||
#### Supported Currencies
|
||||
|
||||
|
@ -17,120 +17,139 @@ Global settings are arranged in the following categories:
|
||||
|
||||
### Server Settings
|
||||
|
||||
Configuration of basic server settings.
|
||||
Configuration of basic server settings:
|
||||
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("INVENTREE_BASE_URL") }}
|
||||
{{ globalsetting("INVENTREE_COMPANY_NAME") }}
|
||||
{{ globalsetting("INVENTREE_INSTANCE") }}
|
||||
{{ globalsetting("INVENTREE_INSTANCE_TITLE") }}
|
||||
{{ globalsetting("INVENTREE_RESTRICT_ABOUT") }}
|
||||
{{ globalsetting("DISPLAY_FULL_NAMES") }}
|
||||
{{ globalsetting("INVENTREE_UPDATE_CHECK_INTERVAL") }}
|
||||
{{ globalsetting("INVENTREE_DOWNLOAD_FROM_URL") }}
|
||||
{{ globalsetting("INVENTREE_DOWNLOAD_IMAGE_MAX_SIZE") }}
|
||||
{{ globalsetting("INVENTREE_DOWNLOAD_FROM_URL_USER_AGENT") }}
|
||||
{{ globalsetting("INVENTREE_REQUIRE_CONFIRM") }}
|
||||
{{ globalsetting("INVENTREE_STRICT_URLS") }}
|
||||
{{ globalsetting("INVENTREE_TREE_DEPTH") }}
|
||||
{{ globalsetting("INVENTREE_BACKUP_ENABLE") }}
|
||||
{{ globalsetting("INVENTREE_BACKUP_DAYS") }}
|
||||
{{ globalsetting("INVENTREE_DELETE_TASKS_DAYS") }}
|
||||
{{ globalsetting("INVENTREE_DELETE_ERRORS_DAYS") }}
|
||||
{{ globalsetting("INVENTREE_DELETE_NOTIFICATIONS_DAYS") }}
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| InvenTree Instance Name | String | String descriptor for the InvenTree server instance | InvenTree Server |
|
||||
| Use Instance Name | Boolean | Use instance name in title bars | False |
|
||||
| Restrict showing `about` | Boolean | Show the `about` modal only to superusers | False |
|
||||
| Base URL | String | Base URL for server instance | *blank* |
|
||||
| Company Name | String | Company name | My company name |
|
||||
| Download from URL | Boolean | Allow downloading of images from remote URLs | False |
|
||||
|
||||
### Login Settings
|
||||
|
||||
Change how logins, password-forgot, signups are handled.
|
||||
Change how logins, password-forgot, signups are handled:
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Enable registration | Boolean | Enable self-registration for users on the login-pages | False |
|
||||
| Enable SSO | Boolean | Enable SSO on the login-pages | False |
|
||||
| Enable SSO registration | Boolean | Enable self-registration for users via SSO on the login-pages | False |
|
||||
| Enable SSO group sync | Boolean | Enable synchronizing InvenTree groups directly from the IdP | False |
|
||||
| SSO group key | String | The name of the groups claim attribute provided by the IdP | |
|
||||
| SSO group map | String (JSON) | A mapping from SSO groups to local InvenTree groups | {} |
|
||||
| Remove groups outside of SSO | Boolean | Whether groups assigned to the user should be removed if they are not backend by the IdP. Disabling this setting might cause security issues | True |
|
||||
| Enable password forgot | Boolean | Enable password forgot function on the login-pages.<br><br>This will let users reset their passwords on their own. For this feature to work you need to configure E-mail | True |
|
||||
| E-Mail required | Boolean | Require user to supply e-mail on signup.<br><br>Without a way (e-mail) to contact the user notifications and security features might not work! | False |
|
||||
| Enforce MFA | Boolean | Users must use multifactor security.<br><br>This forces each user to setup MFA and use it on each authentication | False |
|
||||
| Mail twice | Boolean | On signup ask users twice for their mail | False |
|
||||
| Password twice | Boolean | On signup ask users twice for their password | True |
|
||||
| Auto-fill SSO users | Boolean | Automatically fill out user-details from SSO account-data.<br><br>If this feature is enabled the user is only asked for their username, first- and surname if those values can not be gathered from their SSO profile. This might lead to unwanted usernames bleeding over. | True |
|
||||
| Allowed domains | String | Restrict signup to certain domains (comma-separated, starting with @) | |
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("LOGIN_ENABLE_PWD_FORGOT") }}
|
||||
{{ globalsetting("LOGIN_MAIL_REQUIRED") }}
|
||||
{{ globalsetting("LOGIN_ENFORCE_MFA") }}
|
||||
{{ globalsetting("LOGIN_ENABLE_REG") }}
|
||||
{{ globalsetting("LOGIN_SIGNUP_MAIL_TWICE") }}
|
||||
{{ globalsetting("LOGIN_SIGNUP_PWD_TWICE") }}
|
||||
{{ globalsetting("SIGNUP_GROUP") }}
|
||||
{{ globalsetting("LOGIN_SIGNUP_MAIL_RESTRICTION") }}
|
||||
{{ globalsetting("LOGIN_ENABLE_SSO") }}
|
||||
{{ globalsetting("LOGIN_ENABLE_SSO_REG") }}
|
||||
{{ globalsetting("LOGIN_SIGNUP_SSO_AUTO") }}
|
||||
{{ globalsetting("LOGIN_ENABLE_SSO_GROUP_SYNC") }}
|
||||
{{ globalsetting("SSO_GROUP_MAP") }}
|
||||
{{ globalsetting("SSO_GROUP_KEY") }}
|
||||
{{ globalsetting("SSO_REMOVE_GROUPS") }}
|
||||
|
||||
#### Require User Email
|
||||
|
||||
If this setting is enabled, users must provide an email address when signing up. Note that some notification and security features require a valid email address.
|
||||
|
||||
#### Forgot Password
|
||||
|
||||
If this setting is enabled, users can reset their password via email. This requires a valid email address to be associated with the user account.
|
||||
|
||||
#### Enforce Multi-Factor Authentication
|
||||
|
||||
If this setting is enabled, users must have multi-factor authentication enabled to log in.
|
||||
|
||||
#### Auto Fil SSO Users
|
||||
|
||||
Automatically fill out user-details from SSO account-data. If this feature is enabled the user is only asked for their username, first- and surname if those values can not be gathered from their SSO profile. This might lead to unwanted usernames bleeding over.
|
||||
|
||||
### Barcodes
|
||||
|
||||
Configuration of barcode functionality
|
||||
Configuration of barcode functionality:
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Barcode Support | Boolean | Enable barcode functionality in web interface | True |
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("BARCODE_ENABLE") }}
|
||||
{{ globalsetting("BARCODE_INPUT_DELAY") }}
|
||||
{{ globalsetting("BARCODE_WEBCAM_SUPPORT") }}
|
||||
{{ globalsetting("BARCODE_SHOW_TEXT") }}
|
||||
{{ globalsetting("BARCODE_GENERATION_PLUGIN") }}
|
||||
|
||||
### Currencies
|
||||
### Pricing and Currency
|
||||
|
||||
Configuration of currency support
|
||||
Configuration of pricing data and currency support:
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Default Currency | Currency | Default currency | USD |
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("INVENTREE_DEFAULT_CURRENCY") }}
|
||||
{{ globalsetting("CURRENCY_CODES") }}
|
||||
{{ globalsetting("PART_INTERNAL_PRICE") }}
|
||||
{{ globalsetting("PART_BOM_USE_INTERNAL_PRICE") }}
|
||||
{{ globalsetting("PRICING_DECIMAL_PLACES_MIN") }}
|
||||
{{ globalsetting("PRICING_DECIMAL_PLACES") }}
|
||||
{{ globalsetting("PRICING_UPDATE_DAYS") }}
|
||||
{{ globalsetting("PRICING_USE_SUPPLIER_PRICING") }}
|
||||
{{ globalsetting("PRICING_PURCHASE_HISTORY_OVERRIDES_SUPPLIER") }}
|
||||
{{ globalsetting("PRICING_USE_STOCK_PRICING") }}
|
||||
{{ globalsetting("PRICING_STOCK_ITEM_AGE_DAYS") }}
|
||||
{{ globalsetting("PRICING_USE_VARIANT_PRICING") }}
|
||||
{{ globalsetting("PRICING_ACTIVE_VARIANTS") }}
|
||||
|
||||
### Reporting
|
||||
|
||||
Configuration of report generation
|
||||
Configuration of report generation:
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Enable Reports | Boolean | Enable report generation | False |
|
||||
| Page Size | String | Default page size | A4 |
|
||||
| Debug Mode | Boolean | Generate reports in debug mode (HTML output) | False |
|
||||
| Test Reports | Boolean | Enable generation of test reports | False |
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("REPORT_ENABLE") }}
|
||||
{{ globalsetting("REPORT_DEFAULT_PAGE_SIZE") }}
|
||||
{{ globalsetting("REPORT_DEBUG_MODE") }}
|
||||
{{ globalsetting("REPORT_LOG_ERRORS") }}
|
||||
{{ globalsetting("REPORT_ENABLE_TEST_REPORT") }}
|
||||
{{ globalsetting("REPORT_ATTACH_TEST_REPORT") }}
|
||||
|
||||
### Parts
|
||||
|
||||
#### Main Settings
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| IPN Regex | String | Regular expression pattern for matching Part IPN | *blank* |
|
||||
| Allow Duplicate IPN | Boolean | Allow multiple parts to share the same IPN | True |
|
||||
| Allow Editing IPN | Boolean | Allow changing the IPN value while editing a part | True |
|
||||
| Part Name Display Format | String | Format to display the part name | {% raw %}`{{ part.id if part.id }}{{ ' | ' if part.id }}{{ part.name }}{{ ' | ' if part.revision }}{{ part.revision if part.revision }}`{% endraw %} |
|
||||
| Show Price History | Boolean | Display historical pricing for Part | False |
|
||||
| Show Price in Forms | Boolean | Display part price in some forms | True |
|
||||
| Show Price in BOM | Boolean | Include pricing information in BOM tables | True |
|
||||
| Show related parts | Boolean | Display related parts for a part | True |
|
||||
| Create initial stock | Boolean | Create initial stock on part creation | True |
|
||||
|
||||
#### Creation Settings
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Template | Boolean | Parts are templates by default | False |
|
||||
| Assembly | Boolean | Parts can be assembled from other components by default | False |
|
||||
| Component | Boolean | Parts can be used as sub-components by default | True |
|
||||
| Trackable | Boolean | Parts are trackable by default | False |
|
||||
| Purchaseable | Boolean | Parts are purchaseable by default | True |
|
||||
| Salable | Boolean | Parts are salable by default | False |
|
||||
| Virtual | Boolean | Parts are virtual by default | False |
|
||||
|
||||
#### Copy Settings
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Copy Part BOM Data | Boolean | Copy BOM data by default when duplicating a part | True |
|
||||
| Copy Part Parameter Data | Boolean | Copy parameter data by default when duplicating a part | True |
|
||||
| Copy Part Test Data | Boolean | Copy test data by default when duplicating a part | True |
|
||||
| Copy Category Parameter Templates | Boolean | Copy category parameter templates when creating a part | True |
|
||||
|
||||
#### Internal Price Settings
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Internal Prices | Boolean | Enable internal prices for parts | False |
|
||||
| Internal Price as BOM-Price | Boolean | Use the internal price (if set) in BOM-price calculations | False |
|
||||
|
||||
#### Part Import Setting
|
||||
|
||||
This section of the part settings allows staff users to:
|
||||
|
||||
- import parts to InvenTree clicking the <span class="badge inventree add"><span class='fas fa-plus-circle'></span> Import Part</span> button
|
||||
- enable the ["Import Parts" tab in the part category view](../part/part.md#part-import).
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Show Import in Views | Boolean | Display the import wizard in some part views | True |
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("PART_IPN_REGEX") }}
|
||||
{{ globalsetting("PART_ALLOW_DUPLICATE_IPN") }}
|
||||
{{ globalsetting("PART_ALLOW_EDIT_IPN") }}
|
||||
{{ globalsetting("PART_ALLOW_DELETE_FROM_ASSEMBLY") }}
|
||||
{{ globalsetting("PART_ENABLE_REVISION") }}
|
||||
{{ globalsetting("PART_REVISION_ASSEMBLY_ONLY") }}
|
||||
{{ globalsetting("PART_NAME_FORMAT") }}
|
||||
{{ globalsetting("PART_SHOW_RELATED") }}
|
||||
{{ globalsetting("PART_CREATE_INITIAL") }}
|
||||
{{ globalsetting("PART_CREATE_SUPPLIER") }}
|
||||
{{ globalsetting("PART_TEMPLATE") }}
|
||||
{{ globalsetting("PART_ASSEMBLY") }}
|
||||
{{ globalsetting("PART_COMPONENT") }}
|
||||
{{ globalsetting("PART_TRACKABLE") }}
|
||||
{{ globalsetting("PART_PURCHASEABLE") }}
|
||||
{{ globalsetting("PART_SALABLE") }}
|
||||
{{ globalsetting("PART_VIRTUAL") }}
|
||||
{{ globalsetting("PART_COPY_BOM") }}
|
||||
{{ globalsetting("PART_COPY_PARAMETERS") }}
|
||||
{{ globalsetting("PART_COPY_TESTS") }}
|
||||
{{ globalsetting("PART_CATEGORY_PARAMETERS") }}
|
||||
{{ globalsetting("PART_CATEGORY_DEFAULT_ICON") }}
|
||||
|
||||
#### Part Parameter Templates
|
||||
|
||||
@ -153,45 +172,48 @@ After a list of parameters is added to a part category and upon creation of a ne
|
||||
|
||||
Configuration of stock item options
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Stock Expiry | Boolean | Enable stock expiry functionality | False |
|
||||
| Stock Stale Time | Days | Number of days stock items are considered stale before expiring | 90 |
|
||||
| Sell Expired Stock | Boolean | Allow sale of expired stock | False |
|
||||
| Build Expired Stock | Boolean | Allow building with expired stock | False |
|
||||
| Stock Ownership Control | Boolean | Enable ownership control functionality | False |
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("SERIAL_NUMBER_GLOBALLY_UNIQUE") }}
|
||||
{{ globalsetting("SERIAL_NUMBER_AUTOFILL") }}
|
||||
{{ globalsetting("STOCK_DELETE_DEPLETED_DEFAULT") }}
|
||||
{{ globalsetting("STOCK_BATCH_CODE_TEMPLATE") }}
|
||||
{{ globalsetting("STOCK_ENABLE_EXPIRY") }}
|
||||
{{ globalsetting("STOCK_STALE_DAYS") }}
|
||||
{{ globalsetting("STOCK_ALLOW_EXPIRED_SALE") }}
|
||||
{{ globalsetting("STOCK_ALLOW_EXPIRED_BUILD") }}
|
||||
{{ globalsetting("STOCK_OWNERSHIP_CONTROL") }}
|
||||
{{ globalsetting("STOCK_LOCATION_DEFAULT_ICON") }}
|
||||
{{ globalsetting("STOCK_SHOW_INSTALLED_ITEMS") }}
|
||||
{{ globalsetting("STOCK_ENFORCE_BOM_INSTALLATION") }}
|
||||
{{ globalsetting("STOCK_ALLOW_OUT_OF_STOCK_TRANSFER") }}
|
||||
{{ globalsetting("TEST_STATION_DATA") }}
|
||||
|
||||
### Build Orders
|
||||
|
||||
Options for build orders
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Reference Pattern | String | Pattern for defining Build Order reference values | {% raw %}BO-{ref:04d}{% endraw %} |
|
||||
Refer to the [build order settings](../build/build.md#build-order-settings).
|
||||
|
||||
### Purchase Orders
|
||||
|
||||
Options for purchase orders
|
||||
Refer to the [purchase order settings](../order/purchase_order.md#purchase-order-settings).
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Reference Pattern | String | Pattern for defining Purchase Order reference values | {% raw %}PO-{ref:04d}{% endraw %} |
|
||||
### Sales Orders
|
||||
|
||||
### Sales orders
|
||||
Refer to the [sales order settings](../order/sales_order.md#sales-order-settings).
|
||||
|
||||
Options for sales orders
|
||||
### Return Orders
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Reference Pattern | String | Pattern for defining Sales Order reference values | {% raw %}SO-{ref:04d}{% endraw %} |
|
||||
Refer to the [return order settings](../order/return_order.md#return-order-settings).
|
||||
|
||||
### Plugin Settings
|
||||
|
||||
Change into what parts plugins can integrate into.
|
||||
|
||||
| Setting | Type | Description | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| Enable URL integration | Boolean | Enable plugins to add URL routes | False |
|
||||
| Enable navigation integration | Boolean | Enable plugins to integrate into navigation | False |
|
||||
| Enable setting integration | Boolean | Enable plugins to integrate into inventree settings | False |
|
||||
| Enable app integration | Boolean | Enable plugins to add apps | False |
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ globalsetting("PLUGIN_ON_STARTUP") }}
|
||||
{{ globalsetting("PLUGIN_UPDATE_CHECK") }}
|
||||
{{ globalsetting("ENABLE_PLUGINS_URL") }}
|
||||
{{ globalsetting("ENABLE_PLUGINS_NAVIGATION") }}
|
||||
{{ globalsetting("ENABLE_PLUGINS_APP") }}
|
||||
{{ globalsetting("ENABLE_PLUGINS_SCHEDULE") }}
|
||||
{{ globalsetting("ENABLE_PLUGINS_EVENTS") }}
|
||||
|
@ -32,24 +32,44 @@ This screen allows the user to customize display of items on the InvenTree home
|
||||
|
||||
### Search Settings
|
||||
|
||||
Customize settings for search results
|
||||
Customize settings for search results:
|
||||
|
||||
{% with id="user-search", url="settings/user_search.png", description="User Search Settings" %}
|
||||
{% include 'img.html' %}
|
||||
{% endwith %}
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ usersetting("SEARCH_WHOLE") }}
|
||||
{{ usersetting("SEARCH_REGEX") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_RESULTS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_PARTS") }}
|
||||
{{ usersetting("SEARCH_HIDE_INACTIVE_PARTS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_SUPPLIER_PARTS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_MANUFACTURER_PARTS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_CATEGORIES") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_STOCK") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_HIDE_UNAVAILABLE_STOCK") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_LOCATIONS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_COMPANIES") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_BUILD_ORDERS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_PURCHASE_ORDERS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_EXCLUDE_INACTIVE_PURCHASE_ORDERS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_SALES_ORDERS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_EXCLUDE_INACTIVE_SALES_ORDERS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_SHOW_RETURN_ORDERS") }}
|
||||
{{ usersetting("SEARCH_PREVIEW_EXCLUDE_INACTIVE_RETURN_ORDERS") }}
|
||||
|
||||
### Notifications
|
||||
|
||||
Settings related to notification messages
|
||||
Settings related to notification messages:
|
||||
|
||||
{% with id="user-notification", url="settings/user_notifications.png", description="User Notification Settings" %}
|
||||
{% include 'img.html' %}
|
||||
{% endwith %}
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ usersetting("NOTIFICATION_ERROR_REPORT") }}
|
||||
|
||||
### Reporting
|
||||
|
||||
Settings for label printing and report generation
|
||||
Settings for label printing and report generation:
|
||||
|
||||
{% with id="user-reporting", url="settings/user_reporting.png", description="User Reporting Settings" %}
|
||||
{% include 'img.html' %}
|
||||
{% endwith %}
|
||||
| Name | Description | Default | Units |
|
||||
| ---- | ----------- | ------- | ----- |
|
||||
{{ usersetting("REPORT_INLINE") }}
|
||||
{{ usersetting("LABEL_INLINE") }}
|
||||
{{ usersetting("LABEL_DEFAULT_PRINTER") }}
|
||||
|
49
docs/main.py
49
docs/main.py
@ -1,5 +1,6 @@
|
||||
"""Main entry point for the documentation build process."""
|
||||
|
||||
import json
|
||||
import os
|
||||
import subprocess
|
||||
import textwrap
|
||||
@ -7,6 +8,20 @@ import textwrap
|
||||
import requests
|
||||
import yaml
|
||||
|
||||
# Cached settings dict values
|
||||
global GLOBAL_SETTINGS
|
||||
global USER_SETTINGS
|
||||
|
||||
# Read in the InvenTree settings file
|
||||
here = os.path.dirname(__file__)
|
||||
settings_file = os.path.join(here, 'inventree_settings.json')
|
||||
|
||||
with open(settings_file, 'r') as sf:
|
||||
settings = json.load(sf)
|
||||
|
||||
GLOBAL_SETTINGS = settings['global']
|
||||
USER_SETTINGS = settings['user']
|
||||
|
||||
|
||||
def get_repo_url(raw=False):
|
||||
"""Return the repository URL for the current project."""
|
||||
@ -219,3 +234,37 @@ def define_env(env):
|
||||
)
|
||||
|
||||
return includefile(fn, f'Template: {base}', format='html')
|
||||
|
||||
@env.macro
|
||||
def rendersetting(setting: dict):
|
||||
"""Render a provided setting object into a table row."""
|
||||
name = setting['name']
|
||||
description = setting['description']
|
||||
default = setting.get('default', None)
|
||||
units = setting.get('units', None)
|
||||
|
||||
return f'| {name} | {description} | {default if default is not None else ""} | {units if units is not None else ""} |'
|
||||
|
||||
@env.macro
|
||||
def globalsetting(key: str):
|
||||
"""Extract information on a particular global setting.
|
||||
|
||||
Arguments:
|
||||
- key: The name of the global setting to extract information for.
|
||||
"""
|
||||
global GLOBAL_SETTINGS
|
||||
setting = GLOBAL_SETTINGS[key]
|
||||
|
||||
return rendersetting(setting)
|
||||
|
||||
@env.macro
|
||||
def usersetting(key: str):
|
||||
"""Extract information on a particular user setting.
|
||||
|
||||
Arguments:
|
||||
- key: The name of the user setting to extract information for.
|
||||
"""
|
||||
global USER_SETTINGS
|
||||
setting = USER_SETTINGS[key]
|
||||
|
||||
return rendersetting(setting)
|
||||
|
@ -17,5 +17,6 @@ build:
|
||||
- echo "Generating API schema file"
|
||||
- pip install -U invoke
|
||||
- invoke migrate
|
||||
- invoke export-settings-definitions --filename docs/inventree_settings.json --overwrite
|
||||
- invoke schema --filename docs/schema.yml --ignore-warnings
|
||||
- python docs/extract_schema.py docs/schema.yml
|
||||
|
@ -0,0 +1,53 @@
|
||||
"""Custom management command to export settings definitions.
|
||||
|
||||
This is used to generate a JSON file which contains all of the settings,
|
||||
so that they can be introspected by the InvenTree documentation system.
|
||||
|
||||
This in turn allows settings to be documented in the InvenTree documentation,
|
||||
without having to manually duplicate the information in multiple places.
|
||||
"""
|
||||
|
||||
import json
|
||||
|
||||
from django.core.management.base import BaseCommand
|
||||
|
||||
|
||||
class Command(BaseCommand):
|
||||
"""Extract settings information, and export to a JSON file."""
|
||||
|
||||
def add_arguments(self, parser):
|
||||
"""Add custom arguments for this command."""
|
||||
parser.add_argument(
|
||||
'filename', type=str, help='Output filename for settings definitions'
|
||||
)
|
||||
|
||||
def handle(self, *args, **kwargs):
|
||||
"""Export settings information to a JSON file."""
|
||||
from common.models import InvenTreeSetting, InvenTreeUserSetting
|
||||
|
||||
settings = {'global': {}, 'user': {}}
|
||||
|
||||
# Global settings
|
||||
for key, setting in InvenTreeSetting.SETTINGS.items():
|
||||
settings['global'][key] = {
|
||||
'name': str(setting['name']),
|
||||
'description': str(setting['description']),
|
||||
'default': str(InvenTreeSetting.get_setting_default(key)),
|
||||
'units': str(setting.get('units', '')),
|
||||
}
|
||||
|
||||
# User settings
|
||||
for key, setting in InvenTreeUserSetting.SETTINGS.items():
|
||||
settings['user'][key] = {
|
||||
'name': str(setting['name']),
|
||||
'description': str(setting['description']),
|
||||
'default': str(InvenTreeUserSetting.get_setting_default(key)),
|
||||
'units': str(setting.get('units', '')),
|
||||
}
|
||||
|
||||
filename = kwargs.get('filename', 'inventree_settings.json')
|
||||
|
||||
with open(filename, 'w') as f:
|
||||
json.dump(settings, f, indent=4)
|
||||
|
||||
print(f"Exported InvenTree settings definitions to '{filename}'")
|
@ -395,9 +395,9 @@ class Build(
|
||||
def sub_builds(self, cascade=True):
|
||||
"""Return all Build Order objects under this one."""
|
||||
if cascade:
|
||||
return Build.objects.filter(parent=self.pk)
|
||||
descendants = self.get_descendants(include_self=True)
|
||||
Build.objects.filter(parent__pk__in=[d.pk for d in descendants])
|
||||
return self.get_descendants(include_self=False)
|
||||
else:
|
||||
return self.get_children()
|
||||
|
||||
def sub_build_count(self, cascade=True):
|
||||
"""Return the number of sub builds under this one.
|
||||
@ -407,6 +407,11 @@ class Build(
|
||||
"""
|
||||
return self.sub_builds(cascade=cascade).count()
|
||||
|
||||
@property
|
||||
def has_open_child_builds(self):
|
||||
"""Return True if this build order has any open child builds."""
|
||||
return self.sub_builds().filter(status__in=BuildStatusGroups.ACTIVE_CODES).exists()
|
||||
|
||||
@property
|
||||
def is_overdue(self):
|
||||
"""Returns true if this build is "overdue".
|
||||
@ -576,6 +581,9 @@ class Build(
|
||||
- Untracked parts must be allocated
|
||||
"""
|
||||
|
||||
if get_global_setting('BUILDORDER_REQUIRE_CLOSED_CHILDS') and self.has_open_child_builds:
|
||||
return False
|
||||
|
||||
if self.status != BuildStatus.PRODUCTION.value:
|
||||
return False
|
||||
|
||||
@ -619,6 +627,10 @@ class Build(
|
||||
trim_allocated_stock = kwargs.pop('trim_allocated_stock', False)
|
||||
user = kwargs.pop('user', None)
|
||||
|
||||
# Prevent completion if there are open child builds
|
||||
if get_global_setting('BUILDORDER_REQUIRE_CLOSED_CHILDS') and self.has_open_child_builds:
|
||||
return
|
||||
|
||||
if self.incomplete_count > 0:
|
||||
return
|
||||
|
||||
@ -974,7 +986,10 @@ class Build(
|
||||
items_to_save = []
|
||||
items_to_delete = []
|
||||
|
||||
for build_line in self.untracked_line_items:
|
||||
lines = self.untracked_line_items
|
||||
lines = lines.prefetch_related('allocations')
|
||||
|
||||
for build_line in lines:
|
||||
|
||||
reduce_by = build_line.allocated_quantity() - build_line.quantity
|
||||
|
||||
|
@ -27,6 +27,7 @@ from stock.serializers import StockItemSerializerBrief, LocationBriefSerializer
|
||||
|
||||
import common.models
|
||||
from common.serializers import ProjectCodeSerializer
|
||||
from common.settings import get_global_setting
|
||||
from importer.mixins import DataImportExportSerializerMixin
|
||||
import company.serializers
|
||||
import part.filters
|
||||
@ -765,6 +766,9 @@ class BuildCompleteSerializer(serializers.Serializer):
|
||||
"""Perform validation of this serializer prior to saving"""
|
||||
build = self.context['build']
|
||||
|
||||
if get_global_setting('BUILDORDER_REQUIRE_CLOSED_CHILDS') and build.has_open_child_builds:
|
||||
raise ValidationError(_("Build order has open child build orders"))
|
||||
|
||||
if build.status != BuildStatus.PRODUCTION.value:
|
||||
raise ValidationError(_("Build order must be in production state"))
|
||||
|
||||
|
@ -1015,7 +1015,7 @@ class BuildOverallocationTest(BuildAPITest):
|
||||
'accept_overallocated': 'trim',
|
||||
},
|
||||
expected_code=201,
|
||||
max_query_count=555, # TODO: Come back and refactor this
|
||||
max_query_count=600, # TODO: Come back and refactor this
|
||||
)
|
||||
|
||||
self.build.refresh_from_db()
|
||||
|
@ -1838,6 +1838,14 @@ class InvenTreeSetting(BaseInvenTreeSetting):
|
||||
'default': False,
|
||||
'validator': bool,
|
||||
},
|
||||
'BUILDORDER_REQUIRE_CLOSED_CHILDS': {
|
||||
'name': _('Require Closed Child Orders'),
|
||||
'description': _(
|
||||
'Prevent build order completion until all child orders are closed'
|
||||
),
|
||||
'default': False,
|
||||
'validator': bool,
|
||||
},
|
||||
'PREVENT_BUILD_COMPLETION_HAVING_INCOMPLETED_TESTS': {
|
||||
'name': _('Block Until Tests Pass'),
|
||||
'description': _(
|
||||
|
@ -17,6 +17,7 @@
|
||||
{% include "InvenTree/settings/setting.html" with key="BUILDORDER_REQUIRE_ACTIVE_PART" %}
|
||||
{% include "InvenTree/settings/setting.html" with key="BUILDORDER_REQUIRE_LOCKED_PART" %}
|
||||
{% include "InvenTree/settings/setting.html" with key="BUILDORDER_REQUIRE_VALID_BOM" %}
|
||||
{% include "InvenTree/settings/setting.html" with key="BUILDORDER_REQUIRE_CLOSED_CHILDS" %}
|
||||
{% include "InvenTree/settings/setting.html" with key="PREVENT_BUILD_COMPLETION_HAVING_INCOMPLETED_TESTS" %}
|
||||
</tbody>
|
||||
</table>
|
||||
|
@ -244,6 +244,7 @@ export default function SystemSettings() {
|
||||
'BUILDORDER_REQUIRE_ACTIVE_PART',
|
||||
'BUILDORDER_REQUIRE_LOCKED_PART',
|
||||
'BUILDORDER_REQUIRE_VALID_BOM',
|
||||
'BUILDORDER_REQUIRE_CLOSED_CHILDS',
|
||||
'PREVENT_BUILD_COMPLETION_HAVING_INCOMPLETED_TESTS'
|
||||
]}
|
||||
/>
|
||||
|
15
tasks.py
15
tasks.py
@ -1074,6 +1074,16 @@ def schema(
|
||||
print('Schema export completed:', filename)
|
||||
|
||||
|
||||
@task
|
||||
def export_settings_definitions(c, filename='inventree_settings.json', overwrite=False):
|
||||
"""Export settings definition to a JSON file."""
|
||||
filename = Path(filename).resolve()
|
||||
check_file_existance(filename, overwrite)
|
||||
|
||||
print(f"Exporting settings definition to '{filename}'...")
|
||||
manage(c, f'export_settings_definitions {filename}', pty=True)
|
||||
|
||||
|
||||
@task(default=True)
|
||||
def version(c):
|
||||
"""Show the current version of InvenTree."""
|
||||
@ -1406,6 +1416,11 @@ via your signed in browser, or consider using a point release download via invok
|
||||
)
|
||||
def docs_server(c, address='localhost:8080', compile_schema=False):
|
||||
"""Start a local mkdocs server to view the documentation."""
|
||||
# Extract settings definitions
|
||||
export_settings_definitions(
|
||||
c, filename='docs/inventree_settings.json', overwrite=True
|
||||
)
|
||||
|
||||
if compile_schema:
|
||||
# Build the schema docs first
|
||||
schema(c, ignore_warnings=True, overwrite=True, filename='docs/schema.yml')
|
||||
|
Loading…
Reference in New Issue
Block a user