"text/foo,\ttext/*;q=0.1", "*/*", "*/*, text/bar", "*/*, foo/*" }; foreach (const string& accept, headers) { http::Request request; request.headers["Accept"] = accept; EXPECT_TRUE(request.acceptsMediaType("text/html")) << "Expecting '" << accept << "' to match 'text/html'"; } // Missing header should accept all media types. http::Request empty; EXPECT_TRUE(empty.acceptsMediaType("text/html")); } // TODO(evelinad): Add URLTest for IPv6. TEST(URLTest, Stringification) { EXPECT_EQ("http://mesos.apache.org:80/", stringify(URL("http", "mesos.apache.org"))); EXPECT_EQ("https://mesos.apache.org:8080/", stringify(URL("https", "mesos.apache.org", 8080))); Try<net::IP> ip = net::IP::parse("172.158.1.23", AF_INET); ASSERT_SOME(ip);
Future<http::Response> ResourceProviderManagerProcess::api( const http::Request& request, const Option<Principal>& principal) { if (request.method != "POST") { return MethodNotAllowed({"POST"}, request.method); } v1::resource_provider::Call v1Call; // TODO(anand): Content type values are case-insensitive. Option<string> contentType = request.headers.get("Content-Type"); if (contentType.isNone()) { return BadRequest("Expecting 'Content-Type' to be present"); } if (contentType.get() == APPLICATION_PROTOBUF) { if (!v1Call.ParseFromString(request.body)) { return BadRequest("Failed to parse body into Call protobuf"); } } else if (contentType.get() == APPLICATION_JSON) { Try<JSON::Value> value = JSON::parse(request.body); if (value.isError()) { return BadRequest("Failed to parse body into JSON: " + value.error()); } Try<v1::resource_provider::Call> parse = ::protobuf::parse<v1::resource_provider::Call>(value.get()); if (parse.isError()) { return BadRequest("Failed to convert JSON into Call protobuf: " + parse.error()); } v1Call = parse.get(); } else { return UnsupportedMediaType( string("Expecting 'Content-Type' of ") + APPLICATION_JSON + " or " + APPLICATION_PROTOBUF); } Call call = devolve(v1Call); Option<Error> error = validate(call); if (error.isSome()) { return BadRequest( "Failed to validate resource_provider::Call: " + error->message); } ContentType acceptType; if (request.acceptsMediaType(APPLICATION_JSON)) { acceptType = ContentType::JSON; } else if (request.acceptsMediaType(APPLICATION_PROTOBUF)) { acceptType = ContentType::PROTOBUF; } else { return NotAcceptable( string("Expecting 'Accept' to allow ") + "'" + APPLICATION_PROTOBUF + "' or '" + APPLICATION_JSON + "'"); } switch(call.type()) { case Call::UNKNOWN: { return NotImplemented(); } case Call::SUBSCRIBE: { Pipe pipe; OK ok; ok.headers["Content-Type"] = stringify(acceptType); ok.type = http::Response::PIPE; ok.reader = pipe.reader(); HttpConnection http(pipe.writer(), acceptType); subscribe(http, call.subscribe()); return ok; } case Call::UPDATE: { if (!resourceProviders.contains(call.resource_provider_id())) { return BadRequest("Resource provider cannot be found"); } auto resourceProvider = resourceProviders.at(call.resource_provider_id()); update(&resourceProvider, call.update()); return Accepted(); } } UNREACHABLE(); }