std::unique_ptr MethodConstraint::from_json()

in source/model-generator/MethodConstraints.cpp [467:560]


std::unique_ptr<MethodConstraint> MethodConstraint::from_json(
    const Json::Value& constraint,
    Context& context) {
  JsonValidation::validate_object(constraint);

  std::string constraint_name =
      JsonValidation::string(constraint, "constraint");
  if (constraint_name == "name") {
    return std::make_unique<MethodNameConstraint>(
        JsonValidation::string(constraint, "pattern"));
  } else if (constraint_name == "parent") {
    return std::make_unique<ParentConstraint>(TypeConstraint::from_json(
        JsonValidation::object(constraint, /* field */ "inner")));
  } else if (constraint_name == "number_parameters") {
    return std::make_unique<NumberParametersConstraint>(
        IntegerConstraint::from_json(
            JsonValidation::object(constraint, /* field */ "inner")));
  } else if (constraint_name == "number_overrides") {
    return std::make_unique<NumberOverridesConstraint>(
        IntegerConstraint::from_json(
            JsonValidation::object(constraint, /* field */ "inner")),
        context);
  } else if (constraint_name == "is_static") {
    bool expected = constraint.isMember("value")
        ? JsonValidation::boolean(constraint, /* field */ "value")
        : true;
    return std::make_unique<IsStaticConstraint>(expected);
  } else if (constraint_name == "is_constructor") {
    bool expected = constraint.isMember("value")
        ? JsonValidation::boolean(constraint, /* field */ "value")
        : true;
    return std::make_unique<IsConstructorConstraint>(expected);
  } else if (constraint_name == "is_native") {
    bool expected = constraint.isMember("value")
        ? JsonValidation::boolean(constraint, /* field */ "value")
        : true;
    return std::make_unique<IsNativeConstraint>(expected);
  } else if (constraint_name == "parameter") {
    int index = JsonValidation::integer(constraint, /* field */ "idx");
    return std::make_unique<ParameterConstraint>(
        index,
        TypeConstraint::from_json(
            JsonValidation::object(constraint, /* field */ "inner")));
  } else if (constraint_name == "signature") {
    return std::make_unique<SignatureConstraint>(
        JsonValidation::string(constraint, /* field */ "pattern"));
  } else if (constraint_name == "any_of" || constraint_name == "all_of") {
    std::vector<std::unique_ptr<MethodConstraint>> constraints;
    for (const auto& inner :
         JsonValidation::null_or_array(constraint, /* field */ "inners")) {
      constraints.push_back(MethodConstraint::from_json(inner, context));
    }
    if (constraint_name == "any_of") {
      return std::make_unique<AnyOfMethodConstraint>(std::move(constraints));
    } else {
      return std::make_unique<AllOfMethodConstraint>(std::move(constraints));
    }
  } else if (constraint_name == "return") {
    return std::make_unique<ReturnConstraint>(TypeConstraint::from_json(
        JsonValidation::object(constraint, /* field */ "inner")));
  } else if (constraint_name == "visibility") {
    auto visibility_string =
        JsonValidation::string(constraint, /* field */ "is");
    auto visibility = string_to_visibility(visibility_string);
    if (!visibility) {
      throw JsonValidationError(
          constraint,
          /* field */ "is",
          /* expected */ "`public`, `private` or `protected`");
    }
    return std::make_unique<VisibilityMethodConstraint>(*visibility);
  } else if (constraint_name == "not") {
    return std::make_unique<NotMethodConstraint>(MethodConstraint::from_json(
        JsonValidation::object(constraint, /* field */ "inner"), context));
  } else if (constraint_name == "has_code") {
    bool expected = constraint.isMember("value")
        ? JsonValidation::boolean(constraint, /* field */ "value")
        : true;
    return std::make_unique<HasCodeConstraint>(expected);
  } else if (constraint_name == "has_annotation") {
    return std::make_unique<HasAnnotationMethodConstraint>(
        JsonValidation::string(constraint, "type"),
        constraint.isMember("pattern")
            ? std::optional<std::string>{JsonValidation::string(
                  constraint, "pattern")}
            : std::nullopt);
  } else {
    throw JsonValidationError(
        constraint,
        /* field */ "constraint",
        /* expected */ "valid constraint type");
    return nullptr;
  }
}