Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Preview feature feedback: Prisma field reference support (fieldReference) #15068

Closed
matthewmueller opened this issue Aug 29, 2022 · 22 comments
Closed
Labels
kind/feedback Issue for gathering feedback. team/client Issue for team Client. topic: fieldReference topic: previewFeatures Issue touches on an preview feature flag
Milestone

Comments

@matthewmueller
Copy link
Contributor

matthewmueller commented Aug 29, 2022

Please share your feedback about the fieldReference functionality released in v4.3.0 in this issue.

=> Documentation

  • If you encounter a bug, please open a bug report in this repo.
  • If the feature is working well for you, please share this in a comment below or leave a 👍 on this issue.

If you have any questions, don't hesitate to ask them in the #prisma-client channel in the Prisma Slack.

@matthewmueller matthewmueller added kind/feedback Issue for gathering feedback. topic: previewFeatures Issue touches on an preview feature flag team/client Issue for team Client. topic: fieldReference labels Aug 29, 2022
@matthewmueller
Copy link
Contributor Author

matthewmueller commented Aug 29, 2022

Request for references across tables from @danshapir:

Assume we have 2 tables.
Accounts and Transactions
We have a field on the Accounts called LinkTime, a datetime.
We want to find all transactions where their createdAt is larger than the LinkTime of their parent account.

That's for the simple query, just comparison of fields from a join.
For the more complex scenario, but something we all do a thousand times using SQL, we create a dynamic property as part of the select (computed of multiple fields or any other logic, or maybe aggregated SUM/MIN) and we want to only fetch items that are larger or equal to it.

@shtse8
Copy link

shtse8 commented Sep 2, 2022

hope it can do it with cross models.
A.updatedAt > B.updatedAt

@TomerAberbach
Copy link

@matthewmueller with this new feature is the following valid? See #11646 for context!

// For the given class (with ID `some-class-id`):
// - Get what school it's in
// - Get all classes in that school in the same year as the given class
prisma.db.class.findUnique({
  select: {
    year: true,
    name: true,
    school: {
      select: {
        name: true,
        classes: {
          select: { name: true },
          where: { year: { equals: prisma.class.fields.year } }
        }
      }
    }
  },
  where: { id: `some-class-id` } 
})

@tslater
Copy link

tslater commented Sep 20, 2022

As far as I can tell, this doesn't seem to work with NOT and not. I get an error thrown about an invalid type:

  'Argument originalBlockId: Got invalid value prisma.block.fields.id on prisma.findManyBlock. Provided BytesFieldRefInput<Block>, expected BytesFilter or Bytes.',
  'type BytesFilter {',
  '  equals?: Bytes | BytesFieldRefInput',
  '  in?: List<Bytes>',
  '  notIn?: List<Bytes>',
  '  not?: Bytes | NestedBytesFilter',
  '}',

@nikooiko
Copy link

nikooiko commented Dec 7, 2022

Any update for this feature?

@janpio
Copy link
Member

janpio commented Dec 7, 2022

It is in preview. You can use it. It is documented here: https://www.prisma.io/docs/reference/api-reference/prisma-client-reference#compare-columns-in-the-same-table

@nikooiko
Copy link

nikooiko commented Dec 8, 2022

It is in preview. You can use it. It is documented here: https://www.prisma.io/docs/reference/api-reference/prisma-client-reference#compare-columns-in-the-same-table

Thanks for the response! I meant to ask about using this feature for comparing columns in separate tables (as mentioned above). I guess this will be a separate issue/feature. Both are much needed.

@janpio
Copy link
Member

janpio commented Dec 8, 2022

Ahhh - optimally someone open a new issue for that please. Much easier for us to track then.

@nikolasburk
Copy link
Member

I think I found a bug: #16715

@kefniark
Copy link

kefniark commented Mar 29, 2023

Hum looks like fieldReference is not working with enums

enum Locale {
  en
  ja
  es
  fr
 ...
}

  // ...

  localeDefault Locale
  locale        Locale

if I try to match those

.findMany({
    where: {
      locale: { equals: db.table.fields.localeDefault  },
    }
})

/*
Argument equals: Provided value prisma.table.fields.localeDefault of type LocaleFieldRefInput<Table> on prisma.findManyTable is not a Locale.
*/

Looks like a field reference is not a valid enum value, or it doesn't pass some form of validation.
If I do exactly the same query with 2 strings, it works fine (I created a view which cast my fields from enum to string)

@aarbmx6s
Copy link

How about updating the value of a field from a referenced field?

For example, for the table:

model Table {
  id String @unique
  limit Int
  remains Int
}

set value from the limit field to the remains field, if remains is greater than limit:

await prisma.table.updateMany({
  where: {
    remains: {
      gt: prisma.table.fields.limit
    }
  },
  data: {
    remains: prisma.table.fields.limit
  }
});

It would be very helpful to update a such case.

@livthomas
Copy link

It looks like the value of a referenced field can only be used directly right now. But I would like to do something like this:

prisma.job.updateMany({
  data: {
    status: JobStatus.ABORTED,
    stoppedAt: new Date(),
  },
  where: {
    startedAt: {
      lt: Date.now() - prisma.job.fields.timeoutMs,
    },
    status: JobStatus.STARTED,
  }
});

Would it be possible to add support for such computations that make use of referenced fields?

@Weakky
Copy link
Member

Weakky commented May 24, 2023

Hum looks like fieldReference is not working with enums

@kefniark: Thanks for bringing this to our attention. It should be fixed in the next release.

How about updating the value of a field from a referenced field?

@aarbmx6s: We agree this is a valuable feature. While we don't plan on adding this feature just yet as we've got other priorities, feel free to persist this in a separate feature request so that it gets more visibility 🙏

As far as I can tell, this doesn't seem to work with NOT and not.

@tslater: It's hard for me to tell without A code snippet but the TS definition you've shared suggests to me that you're trying to do the following:

await prisma.model.findMany({
  where: { field: prisma.model.otherField }
})

But this is not supported (yet). Try using the explicit equals filter instead:

await prisma.model.findMany({
  where: { field: { equals: prisma.model.otherField } }
})

It looks like the value of a referenced field can only be used directly right now. But I would like to do something like this:

@livthomas: We agree this is a valuable feature. See similar issue here: #16715 (comment). While we don't plan on adding this feature just yet as we've got other priorities, feel free to persist this in a separate feature request so that it gets more visibility 🙏

@he-la
Copy link

he-la commented May 24, 2023

Simply adding fieldReference to my previewFeatures causes typescript to fail building my project with

RangeError: Maximum call stack size exceeded
    at recursiveTypeRelatedTo (/src/flike/node_modules/typescript/lib/typescript.js:66353:44)
    at isRelatedTo (/src/flike/node_modules/typescript/lib/typescript.js:65942:25)
    at eachTypeRelatedToType (/src/flike/node_modules/typescript/lib/typescript.js:66275:41)
    at unionOrIntersectionRelatedTo (/src/flike/node_modules/typescript/lib/typescript.js:66154:25)
    at structuredTypeRelatedToWorker (/src/flike/node_modules/typescript/lib/typescript.js:66549:34)
    at structuredTypeRelatedTo (/src/flike/node_modules/typescript/lib/typescript.js:66474:30)
    at recursiveTypeRelatedTo (/src/flike/node_modules/typescript/lib/typescript.js:66439:30)
    at isRelatedTo (/src/flike/node_modules/typescript/lib/typescript.js:65942:25)
    at isPropertySymbolTypeRelated (/src/flike/node_modules/typescript/lib/typescript.js:67205:24)
    at propertyRelatedTo (/src/flike/node_modules/typescript/lib/typescript.js:67248:31) {
  type: 'RangeError'

This is before making any other code changes.

Unfortunately I'm working with a large-ish project that makes it hard to distill this down into a minimal repro 😕

Does someone know how I would go about finding the root cause here so I can file an issue?

@Weakky
Copy link
Member

Weakky commented May 25, 2023

@he-la Is there any way you could share your Prisma Schema with us, even privately if needed?

@jonoc330
Copy link

const workflowsToTrigger = await db.workflow.findMany({
    where: {
      builderId: auditLog.builderId,
    },
    include: {
      steps: {
        where: {
          workflowVersion: {
            equals: db.workflow.fields.version,
          },
        },
      },
    },
  })

I am trying to do something like this, find steps in a workflow that match the workflow's version number.
It would be great to be able to reference the parent as that's where I see the most benefit.

Type 'FieldRef<"Workflow", "Int">' is not assignable to type 'number | FieldRef<"WorkflowStep", "Int">'. Type 'FieldRef<"Workflow", "Int">' is not assignable to type 'FieldRef<"WorkflowStep", "Int">'. Type '"Workflow"' is not assignable to type '"WorkflowStep"'.

@Jolg42
Copy link
Member

Jolg42 commented Jun 14, 2023

@he-la Could you tell us which version of Prisma & TypeScript caused the RangeError: Maximum call stack size exceeded error?
Also, are you using Next.js maybe?
More info would help here to be able to reproduce, the best would be to create a bug issue and fill in the details.

@vimtor
Copy link

vimtor commented Jun 19, 2023

It looks like the value of a referenced field can only be used directly right now. But I would like to do something like this:

prisma.job.updateMany({
  data: {
    status: JobStatus.ABORTED,
    stoppedAt: new Date(),
  },
  where: {
    startedAt: {
      lt: Date.now() - prisma.job.fields.timeoutMs,
    },
    status: JobStatus.STARTED,
  }
});

Would it be possible to add support for such computations that make use of referenced fields?

I would also love to be able to do this.

@Jolg42 Jolg42 added this to the 5.0.0 milestone Jul 6, 2023
@Jolg42
Copy link
Member

Jolg42 commented Jul 11, 2023

Thank you everyone for the feedback 🙌🏼

We’re excited to announce that the fieldReference Preview feature is now stable and Generally Available. This means you can use this feature without the Preview feature flag in your Prisma schema.

We first introduced this feature in 4.5.0 to add the ability to compare columns on the same table. For example, the following query returns records where the quantity value is less than the warnQuantity of a product:

await prisma.product.findMany({
  where: { 
		quantity: { lte: prisma.product.fields.warnQuantity } 
	},
})

See Prisma 5.0.0 release notes.

@Jolg42 Jolg42 closed this as completed Jul 11, 2023
@The-White-Fang
Copy link

The-White-Fang commented Oct 20, 2023

Does this feature work for a deeply related relation as well?
For ex

model A {
  field1 Int @id
  field2 Int @unique
  field3 Int
  field4 String @db.char(5)
  B      B[]
}

model B {
  fieldX Int @id
  fieldY Int
  fieldZ Int

  rel A @relation(fields: [fieldY], references: [field2])
}

Can I do

prisma.a.findMany({ where: { field4: x, B: { some: { fieldZ: prisma.A.field3 } } } })

@janpio
Copy link
Member

janpio commented Oct 27, 2023

Please open a discussion to ask this question. Thanks.

@ivosabev
Copy link

Is there a solution to the multiple column references through and operation problem?

For example:

SELECT *
FROM orders O
WHERE O.total - O.payment - O.credit > 0

I believe whereRaw would be best suited for such cases but it is stale as well #5560

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
kind/feedback Issue for gathering feedback. team/client Issue for team Client. topic: fieldReference topic: previewFeatures Issue touches on an preview feature flag
Projects
None yet
Development

No branches or pull requests