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

feat(findKey): add findKey #755

Merged
merged 8 commits into from
Nov 3, 2024
Merged

feat(findKey): add findKey #755

merged 8 commits into from
Nov 3, 2024

Conversation

Na-hyunwoo
Copy link
Contributor

Related issues: #715

Before implementing findKey in the compat layer, I preemptively worked on es-toolkit's findKey.

Hi!, @raon0211

There is something that needs your opinion.

There was a point where I was focused while implementing it, and that was how strictly to keep the type.

In the case of lodash's findKey, if an object is received as the first argument of findKey, the return value is a simple string.

However, in the case of findKey that I implemented, the key value of the object is specified as the return value.

Since this is not a compat layer, I think it is right to follow the principles of es-toolkit rather than lodash, so I need your opinion on that.

I believe that in order for TypeScript to be used meaningfully, it is right to strictly manage types.

As a maintainer, please tell me your opinion!

I have one more question.

After this work, I would like to implement the compat layer's findKey, findLastKey, and compat layer's findLastKey in that order. Is that okay?

findKey benchmark

Copy link

vercel bot commented Oct 26, 2024

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Comments Updated (UTC)
es-toolkit 🛑 Canceled (Inspect) Nov 3, 2024 8:02am

@@ -0,0 +1,31 @@
# findKey
Copy link
Collaborator

Choose a reason for hiding this comment

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

We actually generate documents in an automated way; you don't have to manually create them.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@raon0211 Oh, I see... I guess I won't have to write docs from next time.

Comment on lines 19 to 22
export function findKey<T extends PropertyKey, K>(
obj: Record<T, K>,
predicate: (value: K, key: T, obj: Record<T, K>) => boolean
): T | undefined {
Copy link
Collaborator

Choose a reason for hiding this comment

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

Suggested change
export function findKey<T extends PropertyKey, K>(
obj: Record<T, K>,
predicate: (value: K, key: T, obj: Record<T, K>) => boolean
): T | undefined {
export function findKey<T extends Record<any, any>>(
obj: T,
predicate: (value: T[keyof T], key: keyof T, obj: T) => boolean
): keyof T | undefined {

I guess this type signature is more accurate than the original one.


Note that foo is inferred as number | string in the first one, but is accurately inferred as number in the second one.

Old interface

declare function findKey<T extends PropertyKey, K>(
  obj: Record<T, K>,
  predicate: (value: K, key: T, obj: Record<T, K>) => boolean
): T | undefined

findKey({ foo: 1, bar: '1' }, (val, key, obj) => {
  // foo is string | number here
  obj.foo
})
image

New interface

declare function findKey<T extends Record<any, any>>(
  obj: T,
  predicate: (value: T[keyof T], key: keyof T, obj: T) => boolean
): T | undefined

findKey({ foo: 1, bar: '1' }, (val, key, obj) => {
  // foo is number here
  obj.foo
})
image

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@raon0211

Wow, thank you for the kind review.

In the case of the old interface, the type inference of the object's key and value is inferred independently, so accurate type inference is not possible.

I will commit again, reflecting your review!!

@raon0211
Copy link
Collaborator

raon0211 commented Nov 3, 2024

I would like to implement the compat layer's findKey, findLastKey, and compat layer's findLastKey in that order. Is that okay?

This will help a lot! 😃

raon0211
raon0211 previously approved these changes Nov 3, 2024
Copy link
Collaborator

@raon0211 raon0211 left a comment

Choose a reason for hiding this comment

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

Thanks for your contribution! ☺️

raon0211
raon0211 previously approved these changes Nov 3, 2024
@raon0211 raon0211 merged commit cbecb21 into toss:main Nov 3, 2024
7 of 8 checks passed
@Na-hyunwoo Na-hyunwoo deleted the feat/findKey branch November 11, 2024 22:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants