{"record":{"id":"1a1f862c69e8b59c","repo":"apache/flink","slug":"cannot-extract-typeinformation-from-class-alone-b","errorCode":null,"errorMessage":"Cannot extract TypeInformation from Class alone, because generic parameters are missing. Please use TypeInformation.of(TypeHint) instead, or another equivalent method in the API that accepts a TypeHint instead of a Class. For example for a Tuple2<Long, String> pass a 'new TypeHint<Tuple2<Long, String>>(){}'.","messagePattern":"Cannot extract TypeInformation from Class alone, because generic parameters are missing\\. Please use TypeInformation\\.of\\(TypeHint\\) instead, or another equivalent method in the API that accepts a TypeHint instead of a Class\\. For example for a Tuple2<Long, String> pass a 'new TypeHint<Tuple2<Long, String>>\\(\\)(.+?)'\\.","errorType":"exception","errorClass":"FlinkRuntimeException","httpStatus":null,"severity":"error","filePath":"flink-core/src/main/java/org/apache/flink/api/common/typeinfo/TypeInformation.java","lineNumber":212,"sourceCode":"    public abstract boolean canEqual(Object obj);\n\n    // ------------------------------------------------------------------------\n\n    /**\n     * Creates a TypeInformation for the type described by the given class.\n     *\n     * <p>This method only works for non-generic types. For generic types, use the {@link\n     * #of(TypeHint)} method.\n     *\n     * @param typeClass The class of the type.\n     * @param <T> The generic type.\n     * @return The TypeInformation object for the type described by the hint.\n     */\n    public static <T> TypeInformation<T> of(Class<T> typeClass) {\n        try {\n            return TypeExtractor.createTypeInfo(typeClass);\n        } catch (InvalidTypesException e) {\n            throw new FlinkRuntimeException(\n                    \"Cannot extract TypeInformation from Class alone, because generic parameters are missing. \"\n                            + \"Please use TypeInformation.of(TypeHint) instead, or another equivalent method in the API that \"\n                            + \"accepts a TypeHint instead of a Class. \"\n                            + \"For example for a Tuple2<Long, String> pass a 'new TypeHint<Tuple2<Long, String>>(){}'.\");\n        }\n    }\n\n    /**\n     * Creates a TypeInformation for a generic type via a utility \"type hint\". This method can be\n     * used as follows:\n     *\n     * <pre>{@code\n     * TypeInformation<Tuple2<String, Long>> info = TypeInformation.of(new TypeHint<Tuple2<String, Long>>(){});\n     * }</pre>\n     *\n     * @param typeHint The hint for the generic type.\n     * @param <T> The generic type.\n     * @return The TypeInformation object for the type described by the hint.","sourceCodeStart":194,"sourceCodeEnd":230,"githubUrl":"https://github.com/apache/flink/blob/2f3c205e9266cb30240eb7f4fdab15cad629a70f/flink-core/src/main/java/org/apache/flink/api/common/typeinfo/TypeInformation.java#L194-L230","documentation":"TypeInformation.of(Class<T>) delegates to TypeExtractor.createTypeInfo(typeClass), which only succeeds for non-generic types. If the class has generic parameters (e.g., Tuple2.class, List.class, Map.class, or a generic POJO), TypeExtractor throws InvalidTypesException, which is wrapped as a FlinkRuntimeException directing you to the TypeHint-based overload TypeInformation.of(TypeHint).","triggerScenarios":"Calling TypeInformation.of(Tuple2.class), TypeInformation.of(List.class), or TypeInformation.of(SomeGenericClass.class); passing a raw generic class where the parameters are erased.","commonSituations":"Building TypeInformation from a Class object obtained reflectively (e.g., from a field or method return type) that turns out to be generic; refactoring from a concrete type to a generic one without switching to TypeHint; serializing generic collections.","solutions":["Use TypeInformation.of(new TypeHint<Tuple2<Long,String>>(){}) with fully specified type arguments.","If you only have a java.lang.reflect.Type (ParameterizedType), use TypeExtractor.createTypeInfo(Type, ...) or build the TypeInformation from the TypeHint at a concrete call site.","For non-generic types, TypeInformation.of(Class) works as-is — only switch when the type is parameterized."],"exampleFix":"// before\nTypeInformation.of(Tuple2.class); // throws: generic params missing\n\n// after\nTypeInformation.of(new TypeHint<Tuple2<Long,String>>(){});","handlingStrategy":"type-guard","validationCode":"Class<?> c = ...;\nif (c.getTypeParameters().length > 0) {\n    throw new IllegalArgumentException(\n        \"Use TypeInformation.of(TypeHint) for generic type \" + c.getName());\n}\nTypeInformation<?> ti = TypeInformation.of(c);","typeGuard":"static boolean isNonGeneric(Class<?> c) {\n    return c.getTypeParameters().length == 0;\n}","tryCatchPattern":"try {\n    return TypeInformation.of(typeClass);\n} catch (FlinkRuntimeException e) {\n    throw new IllegalArgumentException(\n        \"Generic type \" + typeClass + \" requires a TypeHint\", e);\n}","preventionTips":["Use TypeInformation.of(TypeHint) whenever the type has generic parameters.","Check Class.getTypeParameters().length before using the Class overload.","Prefer TypeExtractor.createTypeInfo for reflective/generic dispatch."],"tags":["type-information","type-hint","generics","type-erasure"],"backgroundTag":null,"analyzedSha":"2f3c205e9266cb30240eb7f4fdab15cad629a70f","analyzedAt":"2026-08-14T08:48:24.518Z","schemaVersion":2},"datasetVersion":"2026-08-14T10:17:34.591Z"}