Skip to content

Conversation

@BKM14
Copy link
Contributor

@BKM14 BKM14 commented Nov 11, 2025

Closes #15067

When filtering by a record's id using the "Is" operator in a workflow's Search Records action, the filter was ignored. The action returned all records for that object type instead of the single record matching the id.

Root cause

Inside computeRecordGqlOperationFilter.ts, all filters are iterated over and passed on to turnRecordFilterIntoRecordGqlOperationFilter. In turnRecordFilterIntoRecordGqlOperationFilter, in the case of uuid, recordIdsForUuid is required. But since it is undefined, it is early returned, causing the filter to be dropped.

case 'UUID': {
      const recordIds = recordIdsForUuid;
      if (!isDefined(recordIds) || recordIds.length === 0) return;

Solution

In the case where recordIdsForUuid, there is an additional check:

const uuidValue =
        typeof recordFilter.value === 'string' ? recordFilter.value : undefined;
if (isDefined(uuidValue) && uuidValue.trim() !== '')

If uuidValue is valid, then eq is used with uuidValue and returned.

Another potential solution could be to pass recordIdsForUuid as a singular array for each iteration in computeRecordGqlOperationFilter.

recordFilters
      .filter((filter) => !isDefined(filter.recordFilterGroupId))
      .map((regularFilter) => {
        return turnRecordFilterIntoRecordGqlOperationFilter({
          recordFilter: regularFilter,
          fieldMetadataItems: fields,
          filterValueDependencies,
          recordIdsForUuid: [regularFilter.value]
        });

Screenshot

image image

Note

  • New workflows: Will correctly filter by UUID when using the "Is" operator
  • Existing workflows: Workflows saved with the bug will need to be re-saved to regenerate the gqlOperationFilter

@greptile-apps
Copy link
Contributor

greptile-apps bot commented Nov 11, 2025

Greptile Overview

Greptile Summary

This PR fixes a bug where filtering records by UUID using the "Is" operator in workflow Search Records actions was ignored, returning all records instead of the matching one.

Key Changes:

  • Added fallback logic in the UUID filter case to use recordFilter.value directly when recordIdsForUuid is unavailable
  • Changed from early return to conditional checks, first attempting to use recordIdsForUuid with the in operator, then falling back to recordFilter.value with the eq operator
  • Import order adjusted (minor style issue)

Impact:

  • New workflows will correctly filter by UUID when using the "Is" operator
  • Existing workflows saved with the bug will need to be re-saved to regenerate the gqlOperationFilter

Confidence Score: 4/5

  • This PR is safe to merge with minor style improvements recommended
  • The fix correctly addresses the root cause by adding a fallback path when recordIdsForUuid is unavailable. The logic is sound and follows existing patterns in the codebase. Two minor style suggestions were made: using the isNonEmptyString utility function (aligns with custom rule) and fixing import ordering. The change is focused and doesn't introduce breaking changes, though existing workflows will need to be re-saved to benefit from the fix.
  • No files require special attention

Important Files Changed

File Analysis

Filename Score Overview
packages/twenty-shared/src/utils/filter/turnRecordFilterIntoGqlOperationFilter.ts 4/5 Adds fallback to use filter value directly for UUID filtering when recordIdsForUuid is unavailable. Minor style improvements needed for import ordering and utility function usage.

Sequence Diagram

sequenceDiagram
    participant WF as Workflow Engine
    participant CF as computeRecordGqlOperationFilter
    participant TF as turnRecordFilterIntoRecordGqlOperationFilter
    participant DB as Database

    WF->>CF: Filter by UUID with "Is" operator
    Note over WF,CF: recordFilter.value = "uuid-string"<br/>recordIdsForUuid = undefined
    
    CF->>TF: Process filter
    Note over CF,TF: No recordIdsForUuid provided
    
    TF->>TF: Check UUID case
    TF->>TF: recordIds = undefined
    TF->>TF: Extract uuidValue from recordFilter.value
    
    alt recordIds exists and has values
        TF->>DB: { id: { in: recordIds } }
    else uuidValue exists and is non-empty (NEW)
        TF->>DB: { id: { eq: uuidValue } }
        Note over TF,DB: This path is the fix
    else neither exists
        TF-->>CF: undefined (no filter)
    end
    
    DB-->>WF: Filtered records
Loading

Copy link
Contributor

@greptile-apps greptile-apps bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

1 file reviewed, 2 comments

Edit Code Review Agent Settings | Greptile

};
}

if (isDefined(uuidValue) && uuidValue.trim() !== '') {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

style: Use isNonEmptyString utility instead of manual validation.

Suggested change
if (isDefined(uuidValue) && uuidValue.trim() !== '') {
if (isNonEmptyString(uuidValue)) {

Context Used: Context from dashboard - Use the 'isNonEmptyString' utility function to check for non-empty strings instead of checking for e... (source)

Prompt To Fix With AI
This is a comment left during a code review.
Path: packages/twenty-shared/src/utils/filter/turnRecordFilterIntoGqlOperationFilter.ts
Line: 1320:1320

Comment:
**style:** Use `isNonEmptyString` utility instead of manual validation.

```suggestion
          if (isNonEmptyString(uuidValue)) {
```

**Context Used:** Context from `dashboard` - Use the 'isNonEmptyString' utility function to check for non-empty strings instead of checking for e... ([source](https://app.greptile.com/review/custom-context?memory=1553f120-8908-4962-bc22-796896959d06))

How can I resolve this? If you propose a fix, please make it concise.


import { type DateTimeFilter } from '@/types/RecordGqlOperationFilter';
import {
CustomError,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

style: Import order change for CustomError is inconsistent with alphabetical ordering.

Suggested change
CustomError,
checkIfShouldComputeEmptinessFilter,
checkIfShouldSkipFiltering,
CustomError,
Prompt To Fix With AI
This is a comment left during a code review.
Path: packages/twenty-shared/src/utils/filter/turnRecordFilterIntoGqlOperationFilter.ts
Line: 48:48

Comment:
**style:** Import order change for `CustomError` is inconsistent with alphabetical ordering.

```suggestion
  checkIfShouldComputeEmptinessFilter,
  checkIfShouldSkipFiltering,
  CustomError,
```

How can I resolve this? If you propose a fix, please make it concise.

@charlesBochet charlesBochet self-assigned this Nov 13, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Workflow: Search Records "where Id is <UUID>" Returns All Records

2 participants