languagetool-org/languagetool · critical · RuntimeException

https_server_start_failed_unknown_reason

Error message

https_server_start_failed_unknown_reason

What it means

The generic catch-all in HTTPSServer's constructor: any exception during server setup that is not a BindException is rethrown as a RuntimeException with the localized 'https_server_start_failed_unknown_reason' message. It indicates HTTPS server initialization failed for an unexpected reason.

Source

Thrown at languagetool-server/src/main/java/org/languagetool/server/HTTPSServer.java:85

      }
      SSLContext sslContext = getSslContext(config.getKeystore(), config.getKeyStorePassword());
      HttpsConfigurator configurator = getConfigurator(sslContext);
      ((HttpsServer)server).setHttpsConfigurator(configurator);
      RequestLimiter limiter = getRequestLimiterOrNull(config);
      ErrorRequestLimiter errorLimiter = getErrorRequestLimiterOrNull(config);
      executorService = getExecutorService(config);
      BlockingQueue<Runnable> workQueue = executorService.getQueue();
      httpHandler = new LanguageToolHttpHandler(config, allowedIps, runInternally, limiter, errorLimiter, workQueue, this);
      server.createContext("/", httpHandler);
      server.setExecutor(executorService);
    } catch (BindException e) {
      ResourceBundle messages = JLanguageTool.getMessageBundle();
      String message = Tools.i18n(messages, "https_server_start_failed", host, Integer.toString(port));
      throw new PortBindingException(message, e);
    } catch (Exception e) {
      ResourceBundle messages = JLanguageTool.getMessageBundle();
      String message = Tools.i18n(messages, "https_server_start_failed_unknown_reason", host, Integer.toString(port));
      throw new RuntimeException(message, e);
    }
  }

  private SSLContext getSslContext(File keyStoreFile, String passPhrase) {
    try (FileInputStream keyStoreStream = new FileInputStream(keyStoreFile)) {
      KeyStore keystore = KeyStore.getInstance("JKS");
      keystore.load(keyStoreStream, passPhrase.toCharArray());
      KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
      kmf.init(keystore, passPhrase.toCharArray());
      TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509");
      tmf.init(keystore);
      SSLContext sslContext = SSLContext.getInstance("TLS");
      sslContext.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);
      return sslContext;
    } catch (Exception e) {
      throw new RuntimeException("Could not set up SSL context", e);
    }
  }

View on GitHub (pinned to 2e990059ce)

Solutions

  1. Inspect the exception's cause (the wrapped 'e') for the real root cause.
  2. Verify keystore path, format (JKS) and password in the config property file.
  3. Validate the host/port configuration values.
  4. Check the server log output from startup for the stack trace preceding this message.

Example fix

// before
keystore = /etc/ssl/wrong.jks
password = notthepassword
// after
keystore = /etc/ssl/server.jks
password = correctPassword
Defensive patterns

Strategy: try-catch

Validate before calling

// sanity-check prerequisites before startup
if (!new File(keystorePath).canRead()) throw new IllegalStateException("keystore unreadable: " + keystorePath);
if (port <= 0) throw new IllegalStateException("invalid port");

Try / catch

try {
  httpsServer = new HTTPSServer(config, false, host, allowedIps);
} catch (RuntimeException e) {
  log.error("HTTPS startup failed: {}", e.getCause(), e); // always inspect cause
}

Prevention

When it happens

Trigger: Any non-bind failure during HTTPSServer construction: SSL/keystore problems, invalid config values, IO errors creating the listener, executor setup failures — anything except BindException.

Common situations: Keystore file missing or corrupt; wrong keystore password; insufficient privileges; misconfigured host string; earlier setup step throwing (check the wrapped cause 'e' for the real reason).

Related errors


AI-assisted analysis of languagetool-org/languagetool@2e990059ce (2026-09-06). Data as JSON: /api/errors/e3201c2066c9aea7. Report an issue: GitHub.