diff --git a/packages/core/client/src/schema-component/antd/association-field/AssociationSelect.tsx b/packages/core/client/src/schema-component/antd/association-field/AssociationSelect.tsx index 6c8f64137..4b7a0b51e 100644 --- a/packages/core/client/src/schema-component/antd/association-field/AssociationSelect.tsx +++ b/packages/core/client/src/schema-component/antd/association-field/AssociationSelect.tsx @@ -1,19 +1,45 @@ import { LoadingOutlined, PlusOutlined } from '@ant-design/icons'; import { RecursionField, connect, mapProps, observer, useField, useFieldSchema, useForm } from '@formily/react'; +import { onFieldChange, onFormInputChange } from '@formily/core'; +import { uid } from '@formily/shared'; import { Space, message } from 'antd'; import { isFunction } from 'mathjs'; -import React, { useState } from 'react'; +import React, { useState, useEffect } from 'react'; import { useTranslation } from 'react-i18next'; import { RecordProvider, useAPIClient } from '../../../'; import { isVariable } from '../../../variables/utils/isVariable'; import { RemoteSelect, RemoteSelectProps } from '../remote-select'; import useServiceOptions, { useAssociationFieldContext } from './hooks'; +import { getInnermostKeyAndValue } from '../../common/utils/uitls'; export type AssociationSelectProps
= RemoteSelectProps
& { action?: string; multiple?: boolean; }; +export const filterAnalyses = (filters): any[] => { + if (!filters) { + return; + } + const type = Object.keys(filters)[0] || '$and'; + const conditions = filters[type]; + const results = []; + conditions.map((c) => { + const jsonlogic = getInnermostKeyAndValue(c); + const operator = jsonlogic?.key; + + if (!operator) { + return true; + } + const regex = /\{\{\$(?:[a-zA-Z_]\w*)\.([a-zA-Z_]\w*)(?:\.id)?\}\}/; + const fieldName = jsonlogic?.value.match(regex)?.[1]; + if (fieldName) { + results.push(fieldName); + } + }); + return results; +}; + const InternalAssociationSelect = observer((props: AssociationSelectProps) => { const { objectValue = true } = props; const field: any = useField(); @@ -22,10 +48,8 @@ const InternalAssociationSelect = observer((props: AssociationSelectProps) => { const { options: collectionField } = useAssociationFieldContext(); const initValue = isVariable(props.value) ? undefined : props.value; const value = Array.isArray(initValue) ? initValue.filter(Boolean) : initValue; - // 因为通过 Schema 的形式书写的组件,在值变更的时候 `value` 的值没有改变,所以需要维护一个 `innerValue` 来变更值 const [innerValue, setInnerValue] = useState(value); - const addMode = fieldSchema['x-component-props']?.addMode; const isAllowAddNew = fieldSchema['x-add-new']; const { t } = useTranslation(); @@ -33,6 +57,26 @@ const InternalAssociationSelect = observer((props: AssociationSelectProps) => { const form = useForm(); const api = useAPIClient(); const resource = api.resource(collectionField.target); + const linkageFields = filterAnalyses(field.componentProps?.service?.params?.filter); + useEffect(() => { + const id = uid(); + form.addEffects(id, () => { + linkageFields?.forEach((v) => { + if (v) { + onFieldChange(v, () => { + if (field.value) { + props.onChange(null); + setInnerValue(null); + } + }); + } + }); + }); + + return () => { + form.removeEffects(id); + }; + }, []); const handleCreateAction = async (props) => { const { search: value, callBack } = props; diff --git a/packages/core/client/src/schema-component/antd/association-field/hooks.ts b/packages/core/client/src/schema-component/antd/association-field/hooks.ts index f2f0778bd..d9a920071 100644 --- a/packages/core/client/src/schema-component/antd/association-field/hooks.ts +++ b/packages/core/client/src/schema-component/antd/association-field/hooks.ts @@ -151,13 +151,13 @@ export default function useServiceOptions(props) { }, } : null, - params?.filter && value?.length - ? { - [fieldNames?.value]: { - ['$in']: value, - }, - } - : null, + // params?.filter && value?.length + // ? { + // [fieldNames?.value]: { + // ['$in']: value, + // }, + // } + // : null, ], '$or', ); diff --git a/packages/core/client/src/schema-component/antd/remote-select/RemoteSelect.tsx b/packages/core/client/src/schema-component/antd/remote-select/RemoteSelect.tsx index 9f1968f26..51a6bde9c 100644 --- a/packages/core/client/src/schema-component/antd/remote-select/RemoteSelect.tsx +++ b/packages/core/client/src/schema-component/antd/remote-select/RemoteSelect.tsx @@ -184,7 +184,7 @@ const InternalRemoteSelect = connect( } const valueOptions = (v != null && (Array.isArray(v) ? v : [{ ...v, [fieldNames.value]: v[fieldNames.value] || v }])) || []; - return uniqBy(data?.data?.concat(valueOptions) || [], fieldNames.value); + return uniqBy(data?.data?.concat(valueOptions ?? []), fieldNames.value); }, [value, defaultValue, data?.data, fieldNames.value]); const onDropdownVisibleChange = (visible) => { setOpen(visible);