{"record":{"id":"b1dbc81286bb07ad","repo":"keras-team/keras","slug":"a-featurespace-can-only-be-called-with-a-dict-rec","errorCode":null,"errorMessage":"A FeatureSpace can only be called with a dict. Received: data={data} (of type {type(data)}","messagePattern":"A FeatureSpace can only be called with a dict\\. Received: data=(.+?) \\(of type (.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"keras/src/layers/preprocessing/feature_space.py","lineNumber":763,"sourceCode":"\n    def _check_if_built(self):\n        if not self._sublayers_built:\n            self._check_if_adapted()\n            # Finishes building\n            self.get_encoded_features()\n            self._sublayers_built = True\n\n    def _convert_input(self, x):\n        if not isinstance(x, (tf.Tensor, tf.SparseTensor, tf.RaggedTensor)):\n            if not isinstance(x, (list, tuple, int, float)):\n                x = backend.convert_to_numpy(x)\n            x = tf.convert_to_tensor(x)\n        return x\n\n    def __call__(self, data):\n        self._check_if_built()\n        if not isinstance(data, dict):\n            raise ValueError(\n                \"A FeatureSpace can only be called with a dict. \"\n                f\"Received: data={data} (of type {type(data)}\"\n            )\n\n        # Many preprocessing layers support all backends but many do not.\n        # Switch to TF to make FeatureSpace work universally.\n        data = {key: self._convert_input(value) for key, value in data.items()}\n        rebatched = False\n        for name, x in data.items():\n            if len(x.shape) == 0:\n                data[name] = tf.reshape(x, (1, 1))\n                rebatched = True\n            elif len(x.shape) == 1:\n                data[name] = tf.expand_dims(x, -1)\n\n        with backend_utils.TFGraphScope():\n            # This scope is to make sure that inner DataLayers\n            # will not convert outputs back to backend-native --","sourceCodeStart":745,"sourceCodeEnd":781,"githubUrl":"https://github.com/keras-team/keras/blob/7a34a03db60bf60042242d6a556fc3be119046a5/keras/src/layers/preprocessing/feature_space.py#L745-L781","documentation":"FeatureSpace is a multi-input layer keyed by feature name, so it can only be called with a dict mapping feature names to batch data. Any non-dict input (tensor, list, DataFrame, tuple) is rejected at call time.","triggerScenarios":"fs(numpy_array), fs(list_of_tensors), fs(pandas_dataframe), or any single-tensor call instead of fs({'feature': batch}).","commonSituations":"Calling fs(data) with a numpy array, a pandas DataFrame, or a list instead of a dict; feature-name mismatch after refactoring keys.","solutions":["Call fs({'feature_name': batch_array, ...}) with keys matching the features= spec","For DataFrames convert first: fs(dict(df)) or fs({c: df[c].values for c in df.columns})","When using tf.data, keep datasets yielding dicts"],"exampleFix":"// before\nraw_inputs = fs(x_array)  # wrong\n// after\nraw_inputs = fs({\"a\": a_array, \"b\": b_array})","handlingStrategy":"type-guard","validationCode":"assert isinstance(data, dict), \"FeatureSpace expects a dict of feature_name -> batch\"","typeGuard":"def is_feature_dict(d, feature_names):\n    return isinstance(d, dict) and set(d) == set(feature_names)","tryCatchPattern":"catch ValueError and convert data to a dict keyed by feature names before calling again","preventionTips":["Always call FeatureSpace with a dict {feature_name: batch_array}","Do not pass DataFrames, tuples, or single arrays directly to the FeatureSpace call"],"tags":["keras","feature-space","input-type","dict"],"backgroundTag":"invalid-input-type","analyzedSha":"7a34a03db60bf60042242d6a556fc3be119046a5","analyzedAt":"2026-08-25T21:25:25.994Z","schemaVersion":2},"datasetVersion":"2026-08-26T02:17:13.382Z"}