You would be best served treating all incoming params as having string keys. If you must accept either atom or string keys, then using Map.get(“key”) || Map.get(:key) would be clearer than a case.
To elaborate a bit, the reason why map keys from external sources (like user input) are strings, is that atoms are not garbage collected and there is a set maximum amount of atoms available in the system. If you exceed that amount, the VM will crash. So that’s why you shouldn’t create atoms from user input for example.
But why is phx gen generating tests maps with keys?
I tried to put slider_id as string but I got this: expected params to be a map with atoms or string keys, got a map with mixed keys
So I should convert all pregenerated keys from atoms to string?
Example: @valid_attrs %{description: "some description"}
to @valid_attrs %{"description" "some description"}
The test maps should be automatically serialised to json by the phoenix test helpers, then deserialised to string-keyed maps in the Plug.Parsers plug declared in your endpoint module.
Params in contollers have string keys because anybody can send you any param and creating an atom for those would be a attack vector to crash the vm. It’s still generally adviced to work with atom keys in your business part of the app and to sanitize and atomize params before passing things forward into it.
This is interesting. In test that are generated by phx.gen.html the controller tests will have a fixture function that creates a test record with Ecto. But there is no changing of the atom keys to string keys. So if you do anything inside the context modules where you expect a string key from the controller your tests fail but the website works. Hmm, not great.