2
0
mirror of https://github.com/inventree/InvenTree.git synced 2025-04-28 19:46:46 +00:00

Created by (#8848)

* Add 'created_by' field to order API endpoints

* Add 'created_by' filter

* Allow ordering by 'created_by' field

* Update UI tables

- Show "Created By" column
- Column sorting
- Column filtering

* Cleanup order detail pages

* Bump API version

* Refactor table filters

* Fix BuildOrderTable filters
This commit is contained in:
Oliver 2025-01-08 10:07:38 +11:00 committed by GitHub
parent 296c54a1d7
commit 9138e31e58
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
12 changed files with 185 additions and 114 deletions

View File

@ -1,13 +1,18 @@
"""InvenTree API version information.""" """InvenTree API version information."""
# InvenTree API version # InvenTree API version
INVENTREE_API_VERSION = 297 INVENTREE_API_VERSION = 298
"""Increment this API version number whenever there is a significant change to the API that any clients need to know about.""" """Increment this API version number whenever there is a significant change to the API that any clients need to know about."""
INVENTREE_API_TEXT = """ INVENTREE_API_TEXT = """
v298 - 2025-01-07 - https://github.com/inventree/InvenTree/pull/8848
- Adds 'created_by' field to PurchaseOrder API endpoints
- Adds 'created_by' field to SalesOrder API endpoints
- Adds 'created_by' field to ReturnOrder API endpoints
v297 - 2024-12-29 - https://github.com/inventree/InvenTree/pull/8438 v297 - 2024-12-29 - https://github.com/inventree/InvenTree/pull/8438
- Adjustments to the CustomUserState API endpoints and serializers - Adjustments to the CustomUserState API endpoints and serializers

View File

@ -5,6 +5,7 @@ from typing import cast
from django.conf import settings from django.conf import settings
from django.contrib.auth import authenticate, login from django.contrib.auth import authenticate, login
from django.contrib.auth.models import User
from django.db.models import F, Q from django.db.models import F, Q
from django.http.response import JsonResponse from django.http.response import JsonResponse
from django.urls import include, path, re_path from django.urls import include, path, re_path
@ -168,6 +169,10 @@ class OrderFilter(rest_filters.FilterSet):
queryset=Owner.objects.all(), field_name='responsible', label=_('Responsible') queryset=Owner.objects.all(), field_name='responsible', label=_('Responsible')
) )
created_by = rest_filters.ModelChoiceFilter(
queryset=User.objects.all(), field_name='created_by', label=_('Created By')
)
created_before = InvenTreeDateFilter( created_before = InvenTreeDateFilter(
label=_('Created Before'), field_name='creation_date', lookup_expr='lt' label=_('Created Before'), field_name='creation_date', lookup_expr='lt'
) )
@ -328,6 +333,7 @@ class PurchaseOrderList(
ordering_fields = [ ordering_fields = [
'creation_date', 'creation_date',
'created_by',
'reference', 'reference',
'supplier__name', 'supplier__name',
'target_date', 'target_date',
@ -785,6 +791,7 @@ class SalesOrderList(
ordering_fields = [ ordering_fields = [
'creation_date', 'creation_date',
'created_by',
'reference', 'reference',
'customer__name', 'customer__name',
'customer_reference', 'customer_reference',
@ -1369,6 +1376,7 @@ class ReturnOrderList(
ordering_fields = [ ordering_fields = [
'creation_date', 'creation_date',
'created_by',
'reference', 'reference',
'customer__name', 'customer__name',
'customer_reference', 'customer_reference',

View File

@ -50,6 +50,7 @@ from InvenTree.serializers import (
InvenTreeModelSerializer, InvenTreeModelSerializer,
InvenTreeMoneySerializer, InvenTreeMoneySerializer,
NotesFieldMixin, NotesFieldMixin,
UserSerializer,
) )
from order.status_codes import ( from order.status_codes import (
PurchaseOrderStatusGroups, PurchaseOrderStatusGroups,
@ -158,6 +159,8 @@ class AbstractOrderSerializer(DataImportExportSerializerMixin, serializers.Seria
required=False, allow_null=True, label=_('Creation Date') required=False, allow_null=True, label=_('Creation Date')
) )
created_by = UserSerializer(read_only=True)
duplicate = DuplicateOrderSerializer( duplicate = DuplicateOrderSerializer(
label=_('Duplicate Order'), label=_('Duplicate Order'),
help_text=_('Specify options for duplicating this order'), help_text=_('Specify options for duplicating this order'),
@ -174,6 +177,7 @@ class AbstractOrderSerializer(DataImportExportSerializerMixin, serializers.Seria
def annotate_queryset(queryset): def annotate_queryset(queryset):
"""Add extra information to the queryset.""" """Add extra information to the queryset."""
queryset = queryset.annotate(line_items=SubqueryCount('lines')) queryset = queryset.annotate(line_items=SubqueryCount('lines'))
queryset = queryset.select_related('created_by')
return queryset return queryset
@ -183,6 +187,7 @@ class AbstractOrderSerializer(DataImportExportSerializerMixin, serializers.Seria
return [ return [
'pk', 'pk',
'creation_date', 'creation_date',
'created_by',
'target_date', 'target_date',
'description', 'description',
'line_items', 'line_items',

View File

@ -217,6 +217,13 @@ export default function PurchaseOrderDetail() {
icon: 'reference', icon: 'reference',
copy: true, copy: true,
hidden: !order.project_code hidden: !order.project_code
},
{
type: 'text',
name: 'responsible',
label: t`Responsible`,
badge: 'owner',
hidden: !order.responsible
} }
]; ];
@ -225,6 +232,7 @@ export default function PurchaseOrderDetail() {
type: 'date', type: 'date',
name: 'creation_date', name: 'creation_date',
label: t`Creation Date`, label: t`Creation Date`,
copy: true,
icon: 'calendar' icon: 'calendar'
}, },
{ {
@ -240,6 +248,7 @@ export default function PurchaseOrderDetail() {
name: 'target_date', name: 'target_date',
label: t`Target Date`, label: t`Target Date`,
icon: 'calendar', icon: 'calendar',
copy: true,
hidden: !order.target_date hidden: !order.target_date
}, },
{ {
@ -249,13 +258,6 @@ export default function PurchaseOrderDetail() {
label: t`Completion Date`, label: t`Completion Date`,
copy: true, copy: true,
hidden: !order.complete_date hidden: !order.complete_date
},
{
type: 'text',
name: 'responsible',
label: t`Responsible`,
badge: 'owner',
hidden: !order.responsible
} }
]; ];

View File

@ -187,6 +187,13 @@ export default function ReturnOrderDetail() {
icon: 'reference', icon: 'reference',
copy: true, copy: true,
hidden: !order.project_code hidden: !order.project_code
},
{
type: 'text',
name: 'responsible',
label: t`Responsible`,
badge: 'owner',
hidden: !order.responsible
} }
]; ];
@ -221,13 +228,6 @@ export default function ReturnOrderDetail() {
label: t`Completion Date`, label: t`Completion Date`,
copy: true, copy: true,
hidden: !order.complete_date hidden: !order.complete_date
},
{
type: 'text',
name: 'responsible',
label: t`Responsible`,
badge: 'owner',
hidden: !order.responsible
} }
]; ];

View File

@ -199,6 +199,13 @@ export default function SalesOrderDetail() {
icon: 'reference', icon: 'reference',
copy: true, copy: true,
hidden: !order.project_code hidden: !order.project_code
},
{
type: 'text',
name: 'responsible',
label: t`Responsible`,
badge: 'owner',
hidden: !order.responsible
} }
]; ];
@ -231,13 +238,6 @@ export default function SalesOrderDetail() {
label: t`Completion Date`, label: t`Completion Date`,
hidden: !order.shipment_date, hidden: !order.shipment_date,
copy: true copy: true
},
{
type: 'text',
name: 'responsible',
label: t`Responsible`,
badge: 'owner',
hidden: !order.responsible
} }
]; ];

View File

@ -9,7 +9,7 @@ import { YesNoButton } from '../components/buttons/YesNoButton';
import { Thumbnail } from '../components/images/Thumbnail'; import { Thumbnail } from '../components/images/Thumbnail';
import { ProgressBar } from '../components/items/ProgressBar'; import { ProgressBar } from '../components/items/ProgressBar';
import { TableStatusRenderer } from '../components/render/StatusRenderer'; import { TableStatusRenderer } from '../components/render/StatusRenderer';
import { RenderOwner } from '../components/render/User'; import { RenderOwner, RenderUser } from '../components/render/User';
import { formatCurrency, formatDate } from '../defaults/formatters'; import { formatCurrency, formatDate } from '../defaults/formatters';
import type { ModelType } from '../enums/ModelType'; import type { ModelType } from '../enums/ModelType';
import { resolveItem } from '../functions/conversion'; import { resolveItem } from '../functions/conversion';
@ -202,6 +202,18 @@ export function StatusColumn({
}; };
} }
export function CreatedByColumn(props: TableColumnProps): TableColumn {
return {
accessor: 'created_by',
title: t`Created By`,
sortable: true,
switchable: true,
render: (record: any) =>
record.created_by && RenderUser({ instance: record.created_by }),
...props
};
}
export function ResponsibleColumn(props: TableColumnProps): TableColumn { export function ResponsibleColumn(props: TableColumnProps): TableColumn {
return { return {
accessor: 'responsible', accessor: 'responsible',

View File

@ -205,3 +205,47 @@ export function HasProjectCodeFilter(): TableFilter {
description: t`Show orders with an assigned project code` description: t`Show orders with an assigned project code`
}; };
} }
export function OrderStatusFilter({
model
}: { model: ModelType }): TableFilter {
return {
name: 'status',
label: t`Status`,
description: t`Filter by order status`,
choiceFunction: StatusFilterOptions(model)
};
}
export function ProjectCodeFilter({
choices
}: { choices: TableFilterChoice[] }): TableFilter {
return {
name: 'project_code',
label: t`Project Code`,
description: t`Filter by project code`,
choices: choices
};
}
export function ResponsibleFilter({
choices
}: { choices: TableFilterChoice[] }): TableFilter {
return {
name: 'assigned_to',
label: t`Responsible`,
description: t`Filter by responsible owner`,
choices: choices
};
}
export function CreatedByFilter({
choices
}: { choices: TableFilterChoice[] }): TableFilter {
return {
name: 'created_by',
label: t`Created By`,
description: t`Filter by user who created the order`,
choices: choices
};
}

View File

@ -8,7 +8,11 @@ import { ApiEndpoints } from '../../enums/ApiEndpoints';
import { ModelType } from '../../enums/ModelType'; import { ModelType } from '../../enums/ModelType';
import { UserRoles } from '../../enums/Roles'; import { UserRoles } from '../../enums/Roles';
import { useBuildOrderFields } from '../../forms/BuildForms'; import { useBuildOrderFields } from '../../forms/BuildForms';
import { useOwnerFilters, useProjectCodeFilters } from '../../hooks/UseFilter'; import {
useOwnerFilters,
useProjectCodeFilters,
useUserFilters
} from '../../hooks/UseFilter';
import { useCreateApiFormModal } from '../../hooks/UseForm'; import { useCreateApiFormModal } from '../../hooks/UseForm';
import { useTable } from '../../hooks/UseTable'; import { useTable } from '../../hooks/UseTable';
import { apiUrl } from '../../states/ApiState'; import { apiUrl } from '../../states/ApiState';
@ -32,8 +36,11 @@ import {
HasProjectCodeFilter, HasProjectCodeFilter,
MaxDateFilter, MaxDateFilter,
MinDateFilter, MinDateFilter,
OrderStatusFilter,
OutstandingFilter,
OverdueFilter, OverdueFilter,
StatusFilterOptions, ProjectCodeFilter,
ResponsibleFilter,
type TableFilter, type TableFilter,
TargetDateAfterFilter, TargetDateAfterFilter,
TargetDateBeforeFilter TargetDateBeforeFilter
@ -117,21 +124,12 @@ export function BuildOrderTable({
const projectCodeFilters = useProjectCodeFilters(); const projectCodeFilters = useProjectCodeFilters();
const ownerFilters = useOwnerFilters(); const ownerFilters = useOwnerFilters();
const userFilters = useUserFilters();
const tableFilters: TableFilter[] = useMemo(() => { const tableFilters: TableFilter[] = useMemo(() => {
const filters: TableFilter[] = [ const filters: TableFilter[] = [
{ OutstandingFilter(),
name: 'outstanding', OrderStatusFilter({ model: ModelType.build }),
type: 'boolean',
label: t`Outstanding`,
description: t`Show outstanding orders`
},
{
name: 'status',
label: t`Status`,
description: t`Filter by order status`,
choiceFunction: StatusFilterOptions(ModelType.build)
},
OverdueFilter(), OverdueFilter(),
AssignedToMeFilter(), AssignedToMeFilter(),
MinDateFilter(), MinDateFilter(),
@ -142,25 +140,15 @@ export function BuildOrderTable({
TargetDateAfterFilter(), TargetDateAfterFilter(),
CompletedBeforeFilter(), CompletedBeforeFilter(),
CompletedAfterFilter(), CompletedAfterFilter(),
{ ProjectCodeFilter({ choices: projectCodeFilters.choices }),
name: 'project_code',
label: t`Project Code`,
description: t`Filter by project code`,
choices: projectCodeFilters.choices
},
HasProjectCodeFilter(), HasProjectCodeFilter(),
{ {
name: 'issued_by', name: 'issued_by',
label: t`Issued By`, label: t`Issued By`,
description: t`Filter by user who issued this order`, description: t`Filter by user who issued this order`,
choices: ownerFilters.choices choices: userFilters.choices
}, },
{ ResponsibleFilter({ choices: ownerFilters.choices })
name: 'assigned_to',
label: t`Responsible`,
description: t`Filter by responsible owner`,
choices: ownerFilters.choices
}
]; ];
// If we are filtering on a specific part, we can include the "include variants" filter // If we are filtering on a specific part, we can include the "include variants" filter
@ -174,7 +162,12 @@ export function BuildOrderTable({
} }
return filters; return filters;
}, [partId, projectCodeFilters.choices, ownerFilters.choices]); }, [
partId,
projectCodeFilters.choices,
ownerFilters.choices,
userFilters.choices
]);
const user = useUserState(); const user = useUserState();

View File

@ -8,13 +8,18 @@ import { ApiEndpoints } from '../../enums/ApiEndpoints';
import { ModelType } from '../../enums/ModelType'; import { ModelType } from '../../enums/ModelType';
import { UserRoles } from '../../enums/Roles'; import { UserRoles } from '../../enums/Roles';
import { usePurchaseOrderFields } from '../../forms/PurchaseOrderForms'; import { usePurchaseOrderFields } from '../../forms/PurchaseOrderForms';
import { useOwnerFilters, useProjectCodeFilters } from '../../hooks/UseFilter'; import {
useOwnerFilters,
useProjectCodeFilters,
useUserFilters
} from '../../hooks/UseFilter';
import { useCreateApiFormModal } from '../../hooks/UseForm'; import { useCreateApiFormModal } from '../../hooks/UseForm';
import { useTable } from '../../hooks/UseTable'; import { useTable } from '../../hooks/UseTable';
import { apiUrl } from '../../states/ApiState'; import { apiUrl } from '../../states/ApiState';
import { useUserState } from '../../states/UserState'; import { useUserState } from '../../states/UserState';
import { import {
CompletionDateColumn, CompletionDateColumn,
CreatedByColumn,
CreationDateColumn, CreationDateColumn,
DescriptionColumn, DescriptionColumn,
LineItemsProgressColumn, LineItemsProgressColumn,
@ -30,12 +35,15 @@ import {
CompletedBeforeFilter, CompletedBeforeFilter,
CreatedAfterFilter, CreatedAfterFilter,
CreatedBeforeFilter, CreatedBeforeFilter,
CreatedByFilter,
HasProjectCodeFilter, HasProjectCodeFilter,
MaxDateFilter, MaxDateFilter,
MinDateFilter, MinDateFilter,
OrderStatusFilter,
OutstandingFilter, OutstandingFilter,
OverdueFilter, OverdueFilter,
StatusFilterOptions, ProjectCodeFilter,
ResponsibleFilter,
type TableFilter, type TableFilter,
TargetDateAfterFilter, TargetDateAfterFilter,
TargetDateBeforeFilter TargetDateBeforeFilter
@ -57,15 +65,11 @@ export function PurchaseOrderTable({
const projectCodeFilters = useProjectCodeFilters(); const projectCodeFilters = useProjectCodeFilters();
const responsibleFilters = useOwnerFilters(); const responsibleFilters = useOwnerFilters();
const createdByFilters = useUserFilters();
const tableFilters: TableFilter[] = useMemo(() => { const tableFilters: TableFilter[] = useMemo(() => {
return [ return [
{ OrderStatusFilter({ model: ModelType.purchaseorder }),
name: 'status',
label: t`Status`,
description: t`Filter by order status`,
choiceFunction: StatusFilterOptions(ModelType.purchaseorder)
},
OutstandingFilter(), OutstandingFilter(),
OverdueFilter(), OverdueFilter(),
AssignedToMeFilter(), AssignedToMeFilter(),
@ -77,21 +81,16 @@ export function PurchaseOrderTable({
TargetDateAfterFilter(), TargetDateAfterFilter(),
CompletedBeforeFilter(), CompletedBeforeFilter(),
CompletedAfterFilter(), CompletedAfterFilter(),
{ ProjectCodeFilter({ choices: projectCodeFilters.choices }),
name: 'project_code',
label: t`Project Code`,
description: t`Filter by project code`,
choices: projectCodeFilters.choices
},
HasProjectCodeFilter(), HasProjectCodeFilter(),
{ ResponsibleFilter({ choices: responsibleFilters.choices }),
name: 'assigned_to', CreatedByFilter({ choices: createdByFilters.choices })
label: t`Responsible`,
description: t`Filter by responsible owner`,
choices: responsibleFilters.choices
}
]; ];
}, [projectCodeFilters.choices, responsibleFilters.choices]); }, [
projectCodeFilters.choices,
responsibleFilters.choices,
createdByFilters.choices
]);
const tableColumns = useMemo(() => { const tableColumns = useMemo(() => {
return [ return [
@ -120,6 +119,7 @@ export function PurchaseOrderTable({
StatusColumn({ model: ModelType.purchaseorder }), StatusColumn({ model: ModelType.purchaseorder }),
ProjectCodeColumn({}), ProjectCodeColumn({}),
CreationDateColumn({}), CreationDateColumn({}),
CreatedByColumn({}),
TargetDateColumn({}), TargetDateColumn({}),
CompletionDateColumn({ CompletionDateColumn({
accessor: 'complete_date' accessor: 'complete_date'

View File

@ -8,13 +8,18 @@ import { ApiEndpoints } from '../../enums/ApiEndpoints';
import { ModelType } from '../../enums/ModelType'; import { ModelType } from '../../enums/ModelType';
import { UserRoles } from '../../enums/Roles'; import { UserRoles } from '../../enums/Roles';
import { useReturnOrderFields } from '../../forms/ReturnOrderForms'; import { useReturnOrderFields } from '../../forms/ReturnOrderForms';
import { useOwnerFilters, useProjectCodeFilters } from '../../hooks/UseFilter'; import {
useOwnerFilters,
useProjectCodeFilters,
useUserFilters
} from '../../hooks/UseFilter';
import { useCreateApiFormModal } from '../../hooks/UseForm'; import { useCreateApiFormModal } from '../../hooks/UseForm';
import { useTable } from '../../hooks/UseTable'; import { useTable } from '../../hooks/UseTable';
import { apiUrl } from '../../states/ApiState'; import { apiUrl } from '../../states/ApiState';
import { useUserState } from '../../states/UserState'; import { useUserState } from '../../states/UserState';
import { import {
CompletionDateColumn, CompletionDateColumn,
CreatedByColumn,
CreationDateColumn, CreationDateColumn,
DescriptionColumn, DescriptionColumn,
LineItemsProgressColumn, LineItemsProgressColumn,
@ -30,12 +35,15 @@ import {
CompletedBeforeFilter, CompletedBeforeFilter,
CreatedAfterFilter, CreatedAfterFilter,
CreatedBeforeFilter, CreatedBeforeFilter,
CreatedByFilter,
HasProjectCodeFilter, HasProjectCodeFilter,
MaxDateFilter, MaxDateFilter,
MinDateFilter, MinDateFilter,
OrderStatusFilter,
OutstandingFilter, OutstandingFilter,
OverdueFilter, OverdueFilter,
StatusFilterOptions, ProjectCodeFilter,
ResponsibleFilter,
type TableFilter, type TableFilter,
TargetDateAfterFilter, TargetDateAfterFilter,
TargetDateBeforeFilter TargetDateBeforeFilter
@ -54,15 +62,11 @@ export function ReturnOrderTable({
const projectCodeFilters = useProjectCodeFilters(); const projectCodeFilters = useProjectCodeFilters();
const responsibleFilters = useOwnerFilters(); const responsibleFilters = useOwnerFilters();
const createdByFilters = useUserFilters();
const tableFilters: TableFilter[] = useMemo(() => { const tableFilters: TableFilter[] = useMemo(() => {
const filters: TableFilter[] = [ const filters: TableFilter[] = [
{ OrderStatusFilter({ model: ModelType.returnorder }),
name: 'status',
label: t`Status`,
description: t`Filter by order status`,
choiceFunction: StatusFilterOptions(ModelType.returnorder)
},
OutstandingFilter(), OutstandingFilter(),
OverdueFilter(), OverdueFilter(),
AssignedToMeFilter(), AssignedToMeFilter(),
@ -74,19 +78,10 @@ export function ReturnOrderTable({
TargetDateAfterFilter(), TargetDateAfterFilter(),
CompletedBeforeFilter(), CompletedBeforeFilter(),
CompletedAfterFilter(), CompletedAfterFilter(),
{
name: 'project_code',
label: t`Project Code`,
description: t`Filter by project code`,
choices: projectCodeFilters.choices
},
HasProjectCodeFilter(), HasProjectCodeFilter(),
{ ProjectCodeFilter({ choices: projectCodeFilters.choices }),
name: 'assigned_to', ResponsibleFilter({ choices: responsibleFilters.choices }),
label: t`Responsible`, CreatedByFilter({ choices: createdByFilters.choices })
description: t`Filter by responsible owner`,
choices: responsibleFilters.choices
}
]; ];
if (!!partId) { if (!!partId) {
@ -99,7 +94,12 @@ export function ReturnOrderTable({
} }
return filters; return filters;
}, [partId, projectCodeFilters.choices, responsibleFilters.choices]); }, [
partId,
projectCodeFilters.choices,
responsibleFilters.choices,
createdByFilters.choices
]);
const tableColumns = useMemo(() => { const tableColumns = useMemo(() => {
return [ return [
@ -128,6 +128,7 @@ export function ReturnOrderTable({
StatusColumn({ model: ModelType.returnorder }), StatusColumn({ model: ModelType.returnorder }),
ProjectCodeColumn({}), ProjectCodeColumn({}),
CreationDateColumn({}), CreationDateColumn({}),
CreatedByColumn({}),
TargetDateColumn({}), TargetDateColumn({}),
CompletionDateColumn({ CompletionDateColumn({
accessor: 'complete_date' accessor: 'complete_date'

View File

@ -9,12 +9,17 @@ import { ApiEndpoints } from '../../enums/ApiEndpoints';
import { ModelType } from '../../enums/ModelType'; import { ModelType } from '../../enums/ModelType';
import { UserRoles } from '../../enums/Roles'; import { UserRoles } from '../../enums/Roles';
import { useSalesOrderFields } from '../../forms/SalesOrderForms'; import { useSalesOrderFields } from '../../forms/SalesOrderForms';
import { useOwnerFilters, useProjectCodeFilters } from '../../hooks/UseFilter'; import {
useOwnerFilters,
useProjectCodeFilters,
useUserFilters
} from '../../hooks/UseFilter';
import { useCreateApiFormModal } from '../../hooks/UseForm'; import { useCreateApiFormModal } from '../../hooks/UseForm';
import { useTable } from '../../hooks/UseTable'; import { useTable } from '../../hooks/UseTable';
import { apiUrl } from '../../states/ApiState'; import { apiUrl } from '../../states/ApiState';
import { useUserState } from '../../states/UserState'; import { useUserState } from '../../states/UserState';
import { import {
CreatedByColumn,
CreationDateColumn, CreationDateColumn,
DescriptionColumn, DescriptionColumn,
LineItemsProgressColumn, LineItemsProgressColumn,
@ -31,12 +36,15 @@ import {
CompletedBeforeFilter, CompletedBeforeFilter,
CreatedAfterFilter, CreatedAfterFilter,
CreatedBeforeFilter, CreatedBeforeFilter,
CreatedByFilter,
HasProjectCodeFilter, HasProjectCodeFilter,
MaxDateFilter, MaxDateFilter,
MinDateFilter, MinDateFilter,
OrderStatusFilter,
OutstandingFilter, OutstandingFilter,
OverdueFilter, OverdueFilter,
StatusFilterOptions, ProjectCodeFilter,
ResponsibleFilter,
type TableFilter, type TableFilter,
TargetDateAfterFilter, TargetDateAfterFilter,
TargetDateBeforeFilter TargetDateBeforeFilter
@ -55,15 +63,11 @@ export function SalesOrderTable({
const projectCodeFilters = useProjectCodeFilters(); const projectCodeFilters = useProjectCodeFilters();
const responsibleFilters = useOwnerFilters(); const responsibleFilters = useOwnerFilters();
const createdByFilters = useUserFilters();
const tableFilters: TableFilter[] = useMemo(() => { const tableFilters: TableFilter[] = useMemo(() => {
const filters: TableFilter[] = [ const filters: TableFilter[] = [
{ OrderStatusFilter({ model: ModelType.salesorder }),
name: 'status',
label: t`Status`,
description: t`Filter by order status`,
choiceFunction: StatusFilterOptions(ModelType.salesorder)
},
OutstandingFilter(), OutstandingFilter(),
OverdueFilter(), OverdueFilter(),
AssignedToMeFilter(), AssignedToMeFilter(),
@ -75,19 +79,10 @@ export function SalesOrderTable({
TargetDateAfterFilter(), TargetDateAfterFilter(),
CompletedBeforeFilter(), CompletedBeforeFilter(),
CompletedAfterFilter(), CompletedAfterFilter(),
{
name: 'project_code',
label: t`Project Code`,
description: t`Filter by project code`,
choices: projectCodeFilters.choices
},
HasProjectCodeFilter(), HasProjectCodeFilter(),
{ ProjectCodeFilter({ choices: projectCodeFilters.choices }),
name: 'assigned_to', ResponsibleFilter({ choices: responsibleFilters.choices }),
label: t`Responsible`, CreatedByFilter({ choices: createdByFilters.choices })
description: t`Filter by responsible owner`,
choices: responsibleFilters.choices
}
]; ];
if (!!partId) { if (!!partId) {
@ -100,7 +95,12 @@ export function SalesOrderTable({
} }
return filters; return filters;
}, [partId, projectCodeFilters.choices, responsibleFilters.choices]); }, [
partId,
projectCodeFilters.choices,
responsibleFilters.choices,
createdByFilters.choices
]);
const salesOrderFields = useSalesOrderFields({}); const salesOrderFields = useSalesOrderFields({});
@ -165,6 +165,7 @@ export function SalesOrderTable({
StatusColumn({ model: ModelType.salesorder }), StatusColumn({ model: ModelType.salesorder }),
ProjectCodeColumn({}), ProjectCodeColumn({}),
CreationDateColumn({}), CreationDateColumn({}),
CreatedByColumn({}),
TargetDateColumn({}), TargetDateColumn({}),
ShipmentDateColumn({}), ShipmentDateColumn({}),
ResponsibleColumn({}), ResponsibleColumn({}),