stanfordnlp/CoreNLP · error · RuntimeException
Invalid classifier type: ${relationExtractorClassifierType}
Error message
Invalid classifier type: ${relationExtractorClassifierType} What it means
In BasicRelationExtractor.trainMulticlass, the configured relationExtractorClassifierType selects a factory for training the relation classifier. Only "loglinear" (logistic) and "svm" branches exist; any other value (case-insensitive comparison) falls into the final else and throws RuntimeException. It is a configuration error: the chosen classifier family is not implemented/supported by this trainer.
Solutions
- Set the classifier-type property to exactly "loglinear" (logistic regression) or "svm" (SVMLight).
- Check for typos, extra whitespace, or wrong case-sensitivity assumptions in the config value.
- Read BasicRelationExtractor.java to confirm which types your version supports, and add a new factory branch if you need another learner.
- Log/echo the property value at startup so a misconfigured value surfaces before training starts.
Example fix
// before (properties) relation.extractor.classifierType = maxent // after relation.extractor.classifierType = loglinear
Defensive patterns
Strategy: validation
Validate before calling
String type = props.getProperty("relation.extractor.classifierType");
if (!"loglinear".equalsIgnoreCase(type) && !"svm".equalsIgnoreCase(type)) {
throw new IllegalArgumentException("classifierType must be 'loglinear' or 'svm', got: " + type);
} Prevention
- Whitelist the classifier type in a central config-validation step at startup.
- Compare with equalsIgnoreCase but still normalize/trim the value.
- Document the two supported values next to the property key.
When it happens
Trigger: Setting the classifier type property (relationExtractorClassifierType) to anything other than "loglinear" or "svm" (e.g. "naivebayes", "logistic", "SVM " with trailing whitespace, or a typo) before calling train()/trainMulticlass().
Common situations: Typing the classifier name by hand in the training properties file; copying a config from a different NLP pipeline that supports more classifier types; assuming case or synonyms like "maxent" are accepted; upgrading CoreNLP and renaming the option.
Understand the failure class
Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.
Related errors
- Unknown LogPriorType:
- Not sure if RVFDataset runs correctly in this method. Please
- minValue for feature
- maxValue for feature
- datum
AI-assisted analysis of stanfordnlp/CoreNLP@1b7edd19c4 (2026-09-10).
Data as JSON: /api/errors/152b6d41df0f5b30.
Report an issue: GitHub.
Appendix: source
Thrown at src/edu/stanford/nlp/ie/machinereading/BasicRelationExtractor.java:122
GeneralDataset<String, String> trainSet = createDataset(sentences);
trainMulticlass(trainSet);
}
public void trainMulticlass(GeneralDataset<String, String> trainSet) {
if (relationExtractorClassifierType.equalsIgnoreCase("linear")) {
LinearClassifierFactory<String, String> lcFactory = new LinearClassifierFactory<>(1e-4, false, sigma);
lcFactory.setVerbose(false);
// use in-place SGD instead of QN. this is faster but much worse!
// lcFactory.useInPlaceStochasticGradientDescent(-1, -1, 1.0);
// use a hybrid minimizer: start with in-place SGD, continue with QN
// lcFactory.useHybridMinimizerWithInPlaceSGD(50, -1, sigma);
classifier = lcFactory.trainClassifier(trainSet);
} else if (relationExtractorClassifierType.equalsIgnoreCase("svm")) {
SVMLightClassifierFactory<String, String> svmFactory = new SVMLightClassifierFactory<>();
svmFactory.setC(sigma);
classifier = svmFactory.trainClassifier(trainSet);
} else {
throw new RuntimeException("Invalid classifier type: " + relationExtractorClassifierType);
}
if (logger.isLoggable(Level.FINE)) {
reportWeights(classifier, null);
}
}
protected static void reportWeights(LinearClassifier<String, String> classifier, String classLabel) {
if (classLabel != null) logger.fine("CLASSIFIER WEIGHTS FOR LABEL " + classLabel);
Map<String, Counter<String>> labelsToFeatureWeights = classifier.weightsAsMapOfCounters();
List<String> labels = new ArrayList<>(labelsToFeatureWeights.keySet());
Collections.sort(labels);
for (String label: labels) {
Counter<String> featWeights = labelsToFeatureWeights.get(label);
List<Pair<String, Double>> sorted = Counters.toSortedListWithCounts(featWeights);
StringBuilder bos = new StringBuilder();
bos.append("WEIGHTS FOR LABEL ").append(label).append(':');
for (Pair<String, Double> feat: sorted) {
bos.append(' ').append(feat.first()).append(':').append(feat.second()+"\n");View on GitHub (pinned to 1b7edd19c4)