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

Can in React strips ForcedSubject #974

Closed
CodeLenny opened this issue Sep 23, 2024 · 2 comments
Closed

Can in React strips ForcedSubject #974

CodeLenny opened this issue Sep 23, 2024 · 2 comments
Labels

Comments

@CodeLenny
Copy link

CodeLenny commented Sep 23, 2024

Describe the bug
When using Can in React (via createContextualCan), most of the type definitions strip (via Extract) most subject types, which prevents using ForcedSubject.

Please see lines of Can.ts:

? { do: T[0], on: T[1], field?: string } |
{ I: T[0], a: Extract<T[1], SubjectType>, field?: string } |
{ I: T[0], an: Extract<T[1], SubjectType>, field?: string } |
{ I: T[0], this: Exclude<T[1], SubjectType>, field?: string }

Is this:

a. Intentional, and I'm doing something wrong by working around these types by using the only argument form (do/on) that doesn't Extract types, in which case

  1. Please let me know so I don't cause issues in my project (and potentially the docs should be updated for createContextualCan() and/or subject())
  2. Maybe the do/on arguments should also be updated to not allow ForcedSubject

or:

b. Unintentional and subject() should be usable with a/an/this, in which case, can Can.ts be updated to allow forced subjects?

To Reproduce
Reproduction in CodeSandbox, described below: https://codesandbox.io/p/sandbox/casl-can-replication-53tx88

Steps to reproduce the behavior:

  1. Define Ability types, based on the TypeScript guide - I've also defined a variant with ForcedSubject to allow typing
  2. Define contextual Can via createContextualCan based on the React guide, specifying the Actions and Subjects defined in (1)
  3. Use Can with subject(): <Can I="create" a={subject("Car", { make: "Ford", model: "Transit" })}>{/* ... */}</Can>

Expected behavior
No TypeScript errors when using ForcedSubjects with <Can I="" a={subject()} />

Interactive example (optional, but highly desirable)
https://codesandbox.io/p/sandbox/casl-can-replication-53tx88

CodeSandbox only warns about the TypeScript error (please hover over the last a statement), but my actual project fully crashes and rejects the error, causing even more dramatic and blocking issues.

Additional Note/Other Cases
As mentioned above, the do/on arguments do not use Extract<>, so it seems like I could write my code using them, but as the documentation says, they're not as elegant: "use do and on if you are bored and don't want to make your code more readable ;)"

@CodeLenny CodeLenny added the bug label Sep 23, 2024
@stalniy
Copy link
Owner

stalniy commented Jan 5, 2025

@CodeLenny thank you very much for detailed issue and example!

This was done by intention and explained in documentation -> https://github.com/stalniy/casl/tree/master/packages/casl-react#property-names-and-aliases

Basically when you use forced subject you need to use this property (i.e., Can I read this article? -> means can I read this particular article object). When you check permission on type, you need to use a or an property (i.e., Can I read an article? -> means at least one article)

@stalniy stalniy closed this as completed Jan 5, 2025
@stalniy
Copy link
Owner

stalniy commented Jan 5, 2025

and if you change a with this in codesandbox example, the error will disappear

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants