void setupStandaloneMcrouter()

in mcrouter/StandaloneUtils.cpp [410:505]


void setupStandaloneMcrouter(
    const std::string& serviceName,
    const CmdLineOptions& cmdLineOpts,
    const std::unordered_map<std::string, std::string>& libmcrouterOptionsDict,
    const std::unordered_map<std::string, std::string>& standaloneOptionsDict,
    McrouterOptions& libmcrouterOptions,
    McrouterStandaloneOptions& standaloneOptions) {
  // From now on, we might be reporting errors, so first thing is to
  // setup the logging file, if one was provided.
  auto logFile = standaloneOptionsDict.find("log_file");
  if (logFile != standaloneOptionsDict.end() && !logFile->second.empty()) {
    auto fd = open(
        logFile->second.c_str(),
        O_CREAT | O_WRONLY | O_APPEND,
        S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH);
    if (fd == -1) {
      LOG(ERROR) << "Couldn't open log file " << logFile->second
                 << " for writing: " << strerror(errno);
    } else {
      LOG(INFO) << "Logging to " << logFile->second;
      PCHECK(dup2(fd, STDERR_FILENO));
    }
  }

  // Before parsing options from dictionary to objects, we need to setup
  // the log failure, because we can call MC_LOG_FAILURE when parsing the
  // dictionaries.
  failure::setServiceContext(
      "mcrouter",
      folly::to<std::string>(
          cmdLineOpts.programName, " ", cmdLineOpts.commandArgs));
  failure::setHandler(failure::handlers::logToStdError());

  auto libmcrouterErrors =
      libmcrouterOptions.updateFromDict(libmcrouterOptionsDict);
  auto standaloneErrors =
      standaloneOptions.updateFromDict(standaloneOptionsDict);

  if (libmcrouterOptions.enable_failure_logging) {
    initFailureLogger();
  }

  // now that we (maybe) called initFailureLogger(), we can report the errors
  // with the options.
  reportOptionsErrors(libmcrouterOptions, libmcrouterErrors);
  reportOptionsErrors(libmcrouterOptions, standaloneErrors);
  for (const auto& option : cmdLineOpts.unrecognizedOptions) {
    MC_LOG_FAILURE(
        libmcrouterOptions,
        failure::Category::kInvalidOption,
        "Unrecognized option: {}",
        option);
  }

  // finialize standalone options
  finalizeStandaloneOptions(standaloneOptions);

  // init a few things.
  initStandaloneSSL();
  srand(time(nullptr) + getpid());

  // check if the values to provided to the options are sane.
  if (!areOptionsValid(libmcrouterOptions, standaloneOptions)) {
    printUsageAndDie(
        cmdLineOpts.programName.c_str(),
        kExitStatusUnrecoverableError,
        cmdLineOpts.packageName);
  }

  LOG(INFO) << cmdLineOpts.packageName << " startup (" << getpid() << ")";

  // update service_name and router_name
  if (cmdLineOpts.serviceName.empty()) {
    libmcrouterOptions.service_name = serviceName;
  } else {
    libmcrouterOptions.service_name = cmdLineOpts.serviceName;
  }
  if (cmdLineOpts.flavor.empty()) {
    std::string port = "0";
    if (!standaloneOptions.ports.empty()) {
      port = folly::to<std::string>(standaloneOptions.ports.at(0));
    }
    libmcrouterOptions.router_name = port;
  }

  // setup additional failure handler if necessary.
  if (cmdLineOpts.validateConfigMode != ValidateConfigMode::None) {
    failure::addHandler(failure::handlers::throwLogicError());
  }

  // initialize the follwing only if we are not going to exit right away.
  if (cmdLineOpts.validateConfigMode != ValidateConfigMode::Exit) {
    standaloneInit(libmcrouterOptions, standaloneOptions);
    set_standalone_args(cmdLineOpts.commandArgs);
  }
}