Recoil: Question: Fetch atoms/selectors via "key"?

Created on 27 May 2020  路  7Comments  路  Source: facebookexperimental/Recoil

According to the docs, each atom/selector need to be given a unique key. Is it possible/planned to get an atom/selector by this key? If not, is there a way the library could generate a unique key without forcing the user to provide it?

// ...somewhere in the app...
const tempFahrenheit = atom({
  key: 'tempFahrenheit',
  default: 32,
});
//

const [tempF, setTempF] = useRecoilState('tempFahrenheit');

Just trying to get a better understanding of the library. Thanks :)

question

Most helpful comment

We've discussed this internally. There were some proposals to add Recoil "zones/contexts", which would help solve the key namespace concern and help with composability. Though, this isn't the highest priority at the moment. In the meantime, we use conventions for namespacing keys, e.g. 'Module/Key'.

No current plans to allow non-opaque strings as atom/selector handles in the API. Generally we want to enforce that you're actually working with the same shared atom/selector, provide protection from string typos, etc. It has worked pretty well to export shared atoms/selectors from shared modules that can be imported from the components or selectors that need them.

All 7 comments

If my understanding of the issue is right, this is something you can do with atomFactory (when it's released on npm, still waiting on #105)

const tempAtom = atomFactory({
  key: 'temp',
  default: () => 32,
})

function Component() {
  const [tempKey, setTempKey] = useState('tempFahrenheit')
  const temp = useRecoilValue(tempAtom(tempKey))
  // ...
}

I've been using a memoize function in the meantime, as mentioned in the library talk

@kingdaro - Not sure it's exactly the same thing. I may not have been clear enough. Let me try to expound. Essentially, my primary question is: Why do atom's and selector's have keys that are specified by the developer?

From that, two additional thoughts/questions emerged as alluded to in my original post:

  1. Is there a way to reference an atom/selector by the key alone? Most code examples either have the atom/selector in the same file or they import the atom/selector from a different file. Since the keys must be unique in the project, why can't I just provide the serialized key as the first argument to useRecoilState as I do in my original code example?

^ My hope here is to either get a better understanding of why the key is necessary or to see if this is a planned feature in a future release. Or maybe this already works? Like I said, just trying to better understand the library 馃憤

  1. If there are no plans to add the functionality above, why do I, the developer, need to provide a unique key at all? Can't the library figure out how to uniquely identify these things internally? Currently, the key doesn't seem to have any relevance to the developer other than the developer needs to ensure that the key is unique which feels like an unnecessary hassle. I'm sure there's a reason, I just wasn't sure why and thought I'd ask!

Hi @soluml ,

There is some information about the use of keys in #32

The main thing keys are used for is persistence
https://github.com/facebookexperimental/Recoil/issues/32#issuecomment-629400545

But, keys are intended to be used in a few use-cases where a persistent value is needed. For example, they are used to persist atom state in some way such as the URL, a backing store DB, etc. Another example is exposing the atom or selector in developer tools for debugging. (This hasn't been published yet)
https://github.com/facebookexperimental/Recoil/issues/32#issuecomment-629403087

@acutmore - Thanks for your reply! #32 helps a lot in clarifying things as to why we have keys. Have there been any discussions on making the key optional? As in, have the library generate the string when a unique key is not provided? I guess I personally see myself running into key conflicts (with a team of developers on large projects) more so than needing to persist the unique key of an atom.

And also, just to reiterate my first question above. Since we have unique keys, are there any plans to reference atoms/selectors by those keys like in the example above?

We've discussed this internally. There were some proposals to add Recoil "zones/contexts", which would help solve the key namespace concern and help with composability. Though, this isn't the highest priority at the moment. In the meantime, we use conventions for namespacing keys, e.g. 'Module/Key'.

No current plans to allow non-opaque strings as atom/selector handles in the API. Generally we want to enforce that you're actually working with the same shared atom/selector, provide protection from string typos, etc. It has worked pretty well to export shared atoms/selectors from shared modules that can be imported from the components or selectors that need them.

I'm not sure if it's considered a "best practice", but when implementing bind and map, I just took the key of the passed in value then appended /map (or /bind) + a hash of the function. Seems to work well so far, made composing/creating pipelines really nice.

Don't like fetch by key because could lead to weird behaviour where the atom itself isn't included in the bundle because no-one imports it because it's just being referenced by key name.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

tklepzig picture tklepzig  路  3Comments

adamkleingit picture adamkleingit  路  4Comments

pesterhazy picture pesterhazy  路  4Comments

ibnumusyaffa picture ibnumusyaffa  路  4Comments

yuantongkang picture yuantongkang  路  3Comments