{"record":{"id":"0b3735091f515956","repo":"bevyengine/bevy","slug":"underlying-type-does-not-reflect-partialeq-and-h","errorCode":null,"errorMessage":"underlying type does not reflect `PartialEq` and hence doesn't support equality checks","messagePattern":"underlying type does not reflect `PartialEq` and hence doesn't support equality checks","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/bevy_reflect/src/map.rs","lineNumber":263,"sourceCode":"        self.represented_type = represented_type;\n    }\n\n    /// Inserts a typed key-value pair into the map.\n    pub fn insert<K: PartialReflect, V: PartialReflect>(&mut self, key: K, value: V) {\n        self.insert_boxed(Box::new(key), Box::new(value));\n    }\n\n    fn internal_hash(value: &dyn PartialReflect) -> u64 {\n        value.reflect_hash().expect(&hash_error!(value))\n    }\n\n    fn internal_eq(\n        key: &dyn PartialReflect,\n    ) -> impl FnMut(&(Box<dyn PartialReflect>, Box<dyn PartialReflect>)) -> bool + '_ {\n        |(other, _)| {\n            key\n            .reflect_partial_eq(&**other)\n            .expect(\"underlying type does not reflect `PartialEq` and hence doesn't support equality checks\")\n        }\n    }\n}\n\nimpl Map for DynamicMap {\n    fn get(&self, key: &dyn PartialReflect) -> Option<&dyn PartialReflect> {\n        self.hash_table\n            .find(Self::internal_hash(key), Self::internal_eq(key))\n            .map(|(_, value)| &**value)\n    }\n\n    fn get_mut(&mut self, key: &dyn PartialReflect) -> Option<&mut dyn PartialReflect> {\n        self.hash_table\n            .find_mut(Self::internal_hash(key), Self::internal_eq(key))\n            .map(|(_, value)| &mut **value)\n    }\n\n    fn len(&self) -> usize {","sourceCodeStart":245,"sourceCodeEnd":281,"githubUrl":"https://github.com/bevyengine/bevy/blob/396ca727080776bd313bb892423b7d94e03b81b4/crates/bevy_reflect/src/map.rs#L245-L281","documentation":"DynamicMap stores erased Box<dyn PartialReflect> keys in a hash table and looks them up by hashing and equality. internal_eq calls key.reflect_partial_eq(&**other) and expects the result: for types that do not reflect PartialEq, reflect_partial_eq returns None, and this expect panics with 'underlying type does not reflect `PartialEq`...'. Note DynamicMap::get/get_mut hash the key too, so key types also need reflected Hash.","triggerScenarios":"Calling DynamicMap::get/get_mut (or operations that look keys up) with a key whose type does not implement reflected PartialEq — e.g. a custom #[reflect_value] opaque type without #[reflect(PartialEq, Hash)], or a dynamic key that represents such a type.","commonSituations":"Custom opaque key types registered without PartialEq/Hash reflect data; building DynamicMap from user data with exotic keys; mirrors of typed maps where the key type changed into one lacking PartialEq.","solutions":["Add the missing reflect data to the key type: #[reflect(PartialEq, Hash)] (and derive/implement PartialEq + Hash) so reflect_partial_eq returns Some.","Use simple key types that already reflect PartialEq/Hash (String, integers, Entity) for dynamic map keys.","Check support before lookup: key.reflect_partial_eq(key.as_partial_reflect()).is_some() (and reflect_hash().is_some()) and fall back to iteration or rejection.","If the key is dynamic, set represented type info via set_represented_type so it converts to a PartialEq-supporting type before use."],"exampleFix":"// before\n#[derive(Reflect, TypePath)]\n#[reflect_value] // no PartialEq/Hash -> DynamicMap lookups panic\nstruct Key(u64);\n\n// after\n#[derive(Reflect, TypePath, PartialEq, Eq, Hash)]\n#[reflect_value(PartialEq, Hash)]\nstruct Key(u64);","handlingStrategy":"validation","validationCode":"fn key_supports_eq_and_hash(key: &dyn PartialReflect) -> bool {\n    key.reflect_hash().is_some() && key.reflect_partial_eq(key.as_partial_reflect()).is_some()\n}\n\nif key_supports_eq_and_hash(probe.as_ref()) {\n    let hit = dynamic_map.get(probe.as_ref());\n} else {\n    // iterate entries or reject the key type\n}","typeGuard":"fn safe_dynamic_key<K: PartialReflect + ?Sized>(k: &K) -> Option<&K> {\n    (k.reflect_partial_eq(k.as_partial_reflect()).is_some()).then_some(k)\n}","tryCatchPattern":null,"preventionTips":["Register #[reflect(PartialEq, Hash)] (plus the traits) on every type used as a dynamic map key.","Prefer String/integer/Entity keys for DynamicMap-driven lookups.","Unit-test key lookups for each custom key type you register."],"tags":["rust","bevy","bevy-reflect","dynamicmap","partialeq","hash","panic","key-lookup"],"backgroundTag":"missing-trait-implementation","analyzedSha":"396ca727080776bd313bb892423b7d94e03b81b4","analyzedAt":"2026-08-20T16:12:39.808Z","contentChangedAt":"2026-08-20T16:12:39.808Z","schemaVersion":2},"datasetVersion":"2026-09-09T11:17:12.671Z"}