int main(int argc, char** argv) { if (argc != 2) { cerr << "Usage: " << argv[0] << " <master>" << endl; return -1; } // Find this executable's directory to locate executor. char buf[4096]; realpath(dirname(argv[0]), buf); string uri = string(buf) + "/long-lived-executor"; if (getenv("MESOS_BUILD_DIR")) { uri = string(getenv("MESOS_BUILD_DIR")) + "/src/long-lived-executor"; } ExecutorInfo executor; executor.mutable_executor_id()->set_value("default"); executor.mutable_command()->set_value(uri); LongLivedScheduler scheduler(executor); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Long Lived Framework (C++)"); MesosSchedulerDriver driver(&scheduler, framework, argv[1]); return driver.run() == DRIVER_STOPPED ? 0 : 1; }
// Not deriving from fixture...because we want to set specific expectations. // Specifically we simulate caching failure in FrameworksManager. TEST(FrameworksManagerTest, CacheFailure) { ASSERT_TRUE(GTEST_IS_THREADSAFE); MockFrameworksStorage storage; process::spawn(storage); Result<map<FrameworkID, FrameworkInfo> > errMsg = Result<map<FrameworkID, FrameworkInfo> >::error("Fake Caching Error."); EXPECT_CALL(storage, list()) .Times(2) .WillRepeatedly(Return(errMsg)); EXPECT_CALL(storage, add(_, _)) .WillOnce(Return(Result<bool>::some(true))); EXPECT_CALL(storage, remove(_)) .Times(0); FrameworksManager manager(&storage); process::spawn(manager); // Test if initially FrameworksManager returns error. Future<Result<map<FrameworkID, FrameworkInfo> > > future1 = process::dispatch(manager, &FrameworksManager::list); ASSERT_TRUE(future1.await(2.0)); ASSERT_TRUE(future1.get().isError()); EXPECT_EQ(future1.get().error(), "Error caching framework infos."); // Add framework should function normally despite caching failure. FrameworkID id; id.set_value("id"); FrameworkInfo info; info.set_name("test name"); info.set_user("test user"); // Add the framework. Future<Result<bool> > future2 = process::dispatch(manager, &FrameworksManager::add, id, info); ASSERT_TRUE(future2.await(2.0)); EXPECT_TRUE(future2.get().get()); // Remove framework should fail due to caching failure. Future<Result<bool> > future3 = process::dispatch(manager, &FrameworksManager::remove, id, seconds(0)); ASSERT_TRUE(future3.await(2.0)); ASSERT_TRUE(future3.get().isError()); EXPECT_EQ(future3.get().error(), "Error caching framework infos."); process::terminate(manager); process::wait(manager); process::terminate(storage); process::wait(storage); }
int main(int argc, char** argv) { if (argc != 2) { cerr << "Usage: " << argv[0] << " <master>" << endl; return -1; } DockerNoExecutorScheduler scheduler; FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Docker No Executor Framework (C++)"); framework.set_checkpoint(true); MesosSchedulerDriver* driver; if (os::getenv("MESOS_AUTHENTICATE_FRAMEWORKS").isSome()) { cout << "Enabling authentication for the framework" << endl; Option<string> value = os::getenv("DEFAULT_PRINCIPAL"); if (value.isNone()) { EXIT(EXIT_FAILURE) << "Expecting authentication principal in the environment"; } Credential credential; credential.set_principal(value.get()); framework.set_principal(value.get()); value = os::getenv("DEFAULT_SECRET"); if (value.isNone()) { EXIT(EXIT_FAILURE) << "Expecting authentication secret in the environment"; } credential.set_secret(value.get()); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1], credential); } else { framework.set_principal("no-executor-framework-cpp"); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1]); } int status = driver->run() == DRIVER_STOPPED ? 0 : 1; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
int main(int argc, char** argv) { if (argc != 2) { cerr << "Usage: " << argv[0] << " <master>" << endl; return -1; } NoExecutorScheduler scheduler; FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("No Executor Framework (C++)"); // TODO(vinod): Make checkpointing the default when it is default // on the slave. if (os::hasenv("MESOS_CHECKPOINT")) { cout << "Enabling checkpoint for the framework" << endl; framework.set_checkpoint(true); } MesosSchedulerDriver* driver; if (os::hasenv("MESOS_AUTHENTICATE")) { cout << "Enabling authentication for the framework" << endl; if (!os::hasenv("DEFAULT_PRINCIPAL")) { EXIT(1) << "Expecting authentication principal in the environment"; } if (!os::hasenv("DEFAULT_SECRET")) { EXIT(1) << "Expecting authentication secret in the environment"; } Credential credential; credential.set_principal(getenv("DEFAULT_PRINCIPAL")); credential.set_secret(getenv("DEFAULT_SECRET")); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1], credential); } else { driver = new MesosSchedulerDriver( &scheduler, framework, argv[1]); } int status = driver->run() == DRIVER_STOPPED ? 0 : 1; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
int main(int argc, char** argv) { // Find this executable's directory to locate executor. string path = os::realpath(dirname(argv[0])).get(); string uri = path + "/test-executor"; if (getenv("MESOS_BUILD_DIR")) { uri = string(getenv("MESOS_BUILD_DIR")) + "/src/test-executor"; } mesos::internal::logging::Flags flags; string role; flags.add(&role, "role", "Role to use when registering", "*"); Option<string> master; flags.add(&master, "master", "ip:port of master to connect"); Try<Nothing> load = flags.load(None(), argc, argv); if (load.isError()) { cerr << load.error() << endl; usage(argv[0], flags); exit(1); } else if (master.isNone()) { cerr << "Missing --master" << endl; usage(argv[0], flags); exit(1); } ExecutorInfo executor; executor.mutable_executor_id()->set_value("default"); executor.mutable_command()->set_value(uri); executor.set_name("Test Executor (C++)"); executor.set_source("cpp_test"); TestScheduler scheduler(executor, role); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Test Framework (C++)"); framework.set_role(role); MesosSchedulerDriver driver(&scheduler, framework, master.get()); return driver.run() == DRIVER_STOPPED ? 0 : 1; }
int main(int argc, char** argv) { if (argc != 2) { cerr << "Usage: " << argv[0] << " <master>" << endl; return -1; } NoExecutorScheduler scheduler; FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("No Executor Framework (C++)"); MesosSchedulerDriver driver(&scheduler, framework, argv[1]); return driver.run() == DRIVER_STOPPED ? 0 : 1; }
TEST_F(FrameworksManagerTestFixture, ResurrectInterspersedExpiringFrameworks) { // This is another crucial test. // Two remove messages are interspersed with a resurrect. // Only the second remove should actually remove the framework. // Add a dummy framework. FrameworkID id; id.set_value("id"); FrameworkInfo info; info.set_name("test name"); info.set_user("test user"); // Add the framework. process::dispatch(manager, &FrameworksManager::add, id, info); Clock::pause(); Future<Result<bool> > future1 = process::dispatch(manager, &FrameworksManager::remove, id, seconds(2.0)); // Resurrect in the meanwhile. Future<Result<bool> > future2 = process::dispatch(manager, &FrameworksManager::resurrect, id); // Remove again. Future<Result<bool> > future3 = process::dispatch(manager, &FrameworksManager::remove, id, seconds(1.0)); ASSERT_TRUE(future2.await(2.0)); EXPECT_TRUE(future2.get().get()); Clock::update(Clock::now(manager) + 1.0); ASSERT_TRUE(future3.await(2.0)); EXPECT_TRUE(future3.get().get()); Clock::update(Clock::now(manager) + 2.0); ASSERT_TRUE(future1.await(2.0)); EXPECT_FALSE(future1.get().get()); Clock::resume(); }
TEST_F(FrameworksManagerTestFixture, AddFramework) { // Test if initially FM returns empty list. Future<Result<map<FrameworkID, FrameworkInfo> > > future = process::dispatch(manager, &FrameworksManager::list); ASSERT_TRUE(future.await(2.0)); EXPECT_TRUE(future.get().get().empty()); // Add a dummy framework. FrameworkID id; id.set_value("id"); FrameworkInfo info; info.set_name("test name"); info.set_user("test user"); // Add the framework. Future<Result<bool> > future2 = process::dispatch(manager, &FrameworksManager::add, id, info); ASSERT_TRUE(future2.await(2.0)); EXPECT_TRUE(future2.get().get()); // Check if framework manager returns the added framework. Future<Result<map<FrameworkID, FrameworkInfo> > > future3 = process::dispatch(manager, &FrameworksManager::list); ASSERT_TRUE(future3.await(2.0)); map<FrameworkID, FrameworkInfo> result = future3.get().get(); ASSERT_EQ(1, result.count(id)); EXPECT_EQ("test name", result[id].name()); EXPECT_EQ("test user", result[id].user()); // Check if the framework exists. Future<Result<bool> > future4 = process::dispatch(manager, &FrameworksManager::exists, id); ASSERT_TRUE(future4.await(2.0)); EXPECT_TRUE(future4.get().get()); }
// TODO(vinod): Using a paused clock in the tests means that // future.await() may wait forever. This makes debugging hard. TEST_F(FrameworksManagerTestFixture, ResurrectExpiringFramework) { // This is the crucial test. // Resurrect an existing framework that is being removed,is being removed, // which should cause the remove to be unsuccessful. // Add a dummy framework. FrameworkID id; id.set_value("id"); FrameworkInfo info; info.set_name("test name"); info.set_user("test user"); // Add the framework. process::dispatch(manager, &FrameworksManager::add, id, info); Clock::pause(); // Remove after 2 secs. Future<Result<bool> > future1 = process::dispatch(manager, &FrameworksManager::remove, id, seconds(2.0)); // Resurrect in the meanwhile. Future<Result<bool> > future2 = process::dispatch(manager, &FrameworksManager::resurrect, id); ASSERT_TRUE(future2.await(2.0)); EXPECT_TRUE(future2.get().get()); Clock::update(Clock::now(manager) + 2.0); ASSERT_TRUE(future1.await(2.0)); EXPECT_FALSE(future1.get().get()); Clock::resume(); }
int main(int argc, char** argv) { string master = MASTER; string k3binary; string paramfile; int total_peers; YAML::Node k3vars; // Parse Command Line options string path = os::realpath(dirname(argv[0])).get(); namespace po = boost::program_options; vector <string> optionalVars; po::options_description desc("K3 Run options"); desc.add_options() ("program", po::value<string>(&k3binary)->required(), "K3 executable program filename") ("numpeers", po::value<int>(&total_peers)->required(), "# of K3 Peers to launch") ("help,h", "Print help message") ("param,p", po::value<string>(¶mfile)->required(), "YAML Formatted input file"); po::positional_options_description positionalOptions; positionalOptions.add("program", 1); positionalOptions.add("numpeers", 1); po::variables_map vm; try { po::store(po::command_line_parser(argc, argv).options(desc) .positional(positionalOptions).run(), vm); if (vm.count("help") || vm.empty()) { cout << "K3 Distributed program framework backed by Mesos cluser" << endl; cout << desc << endl; return 0; } po::notify(vm); k3vars = YAML::LoadFile(paramfile); } catch (boost::program_options::required_option& e) { cerr << " ERROR: " << e.what() << endl << endl; cout << desc << endl; return 1; } catch (boost::program_options::error& e) { cerr << " ERROR: " << e.what() << endl << endl; cout << desc << endl; return 1; } KDScheduler scheduler(k3binary, total_peers, k3vars, path); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name(k3binary + "-" + stringify(total_peers)); framework.mutable_id()->set_value(k3binary); if (os::hasenv("MESOS_CHECKPOINT")) { cout << "Enabling checkpoint for the framework" << endl; framework.set_checkpoint(true); } MesosSchedulerDriver* driver; if (os::hasenv("MESOS_AUTHENTICATE")) { cout << "Enabling authentication for the framework" << endl; if (!os::hasenv("DEFAULT_PRINCIPAL")) { EXIT(1) << "Expecting authentication principal in the environment"; } if (!os::hasenv("DEFAULT_SECRET")) { EXIT(1) << "Expecting authentication secret in the environment"; } Credential credential; credential.set_principal(getenv("DEFAULT_PRINCIPAL")); credential.set_secret(getenv("DEFAULT_SECRET")); framework.set_principal(getenv("DEFAULT_PRINCIPAL")); driver = new MesosSchedulerDriver( &scheduler, framework, master, credential); } else { framework.set_principal("k3-docker-no-executor-framework-cpp"); driver = new MesosSchedulerDriver(&scheduler, framework, master); } int status = driver->run() == DRIVER_STOPPED ? 0 : 1; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
int main(int argc, char** argv) { Flags flags; Try<Nothing> load = flags.load("MESOS_", argc, argv); if (load.isError()) { cerr << flags.usage(load.error()) << endl; return EXIT_FAILURE; } if (flags.help) { cout << flags.usage() << endl; return EXIT_SUCCESS; } if (flags.master.isNone()) { cerr << flags.usage( "Missing required option --master") << endl; return EXIT_FAILURE; } if (flags.qps.isNone()) { cerr << flags.usage("Missing required option --qps") << endl; return EXIT_FAILURE; } if (flags.qps.get() <= 0) { cerr << flags.usage("--qps needs to be greater than zero") << endl; return EXIT_FAILURE; } // We want the logger to catch failure signals. mesos::internal::logging::initialize(argv[0], flags, true); LoadGeneratorScheduler scheduler(flags.qps.get(), flags.duration); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Load Generator Framework (C++)"); const Option<string> checkpoint = os::getenv("MESOS_CHECKPOINT"); if (checkpoint.isSome()) { framework.set_checkpoint( numify<bool>(checkpoint.get()).get()); } MesosSchedulerDriver* driver; if (flags.authenticate) { cout << "Enabling authentication for the framework" << endl; if (flags.secret.isNone()) { cerr << "Expecting --secret when --authenticate is set" << endl; return EXIT_FAILURE; } string secret = flags.secret.get(); Credential credential; credential.set_principal(flags.principal); credential.set_secret(strings::trim(secret)); framework.set_principal(flags.principal); driver = new MesosSchedulerDriver( &scheduler, framework, flags.master.get(), credential); } else { framework.set_principal(flags.principal); driver = new MesosSchedulerDriver( &scheduler, framework, flags.master.get()); } int status = driver->run() == DRIVER_STOPPED ? EXIT_SUCCESS : EXIT_SUCCESS; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
int main(int argc, char** argv) { if (argc != 2) { cerr << "Usage: " << argv[0] << " <master>" << endl; return -1; } // Find this executable's directory to locate executor. string path = os::realpath(dirname(argv[0])).get(); string uri = path + "/long-lived-executor"; if (getenv("MESOS_BUILD_DIR")) { uri = string(getenv("MESOS_BUILD_DIR")) + "/src/long-lived-executor"; } ExecutorInfo executor; executor.mutable_executor_id()->set_value("default"); executor.mutable_command()->set_value(uri); executor.set_name("Long Lived Executor (C++)"); executor.set_source("cpp_long_lived_framework"); LongLivedScheduler scheduler(executor); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Long Lived Framework (C++)"); // TODO(vinod): Make checkpointing the default when it is default // on the slave. if (os::hasenv("MESOS_CHECKPOINT")) { cout << "Enabling checkpoint for the framework" << endl; framework.set_checkpoint(true); } MesosSchedulerDriver* driver; if (os::hasenv("MESOS_AUTHENTICATE")) { cout << "Enabling authentication for the framework" << endl; if (!os::hasenv("DEFAULT_PRINCIPAL")) { EXIT(1) << "Expecting authentication principal in the environment"; } if (!os::hasenv("DEFAULT_SECRET")) { EXIT(1) << "Expecting authentication secret in the environment"; } Credential credential; credential.set_principal(getenv("DEFAULT_PRINCIPAL")); credential.set_secret(getenv("DEFAULT_SECRET")); framework.set_principal(getenv("DEFAULT_PRINCIPAL")); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1], credential); } else { framework.set_principal("long-lived-framework-cpp"); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1]); } int status = driver->run() == DRIVER_STOPPED ? 0 : 1; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
// This test verifies that authorization based endpoint filtering // works correctly on the /state endpoint. // Both default users are allowed to view high level frameworks, but only // one is allowed to view the tasks. // After launching a single task per each framework, one for role "superhero" // and the other for role "muggle", this test verifies that each of two // default users can view resource allocations and resource reservations for // corresponding allowed roles only. TYPED_TEST(SlaveAuthorizerTest, FilterStateEndpoint) { ACLs acls; const string roleSuperhero = "superhero"; const string roleMuggle = "muggle"; { // Default principal can see all frameworks. mesos::ACL::ViewFramework* acl = acls.add_view_frameworks(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL.principal()); acl->mutable_users()->set_type(ACL::Entity::ANY); } { // Second default principal can see all frameworks. mesos::ACL::ViewFramework* acl = acls.add_view_frameworks(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL_2.principal()); acl->mutable_users()->set_type(ACL::Entity::ANY); } { // No other principal can see frameworks running under any user. ACL::ViewFramework* acl = acls.add_view_frameworks(); acl->mutable_principals()->set_type(ACL::Entity::ANY); acl->mutable_users()->set_type(ACL::Entity::NONE); } { // Default principal can see all executors. mesos::ACL::ViewExecutor* acl = acls.add_view_executors(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL.principal()); acl->mutable_users()->set_type(ACL::Entity::ANY); } { // No other principal can see executors running under any user. ACL::ViewExecutor* acl = acls.add_view_executors(); acl->mutable_principals()->set_type(ACL::Entity::ANY); acl->mutable_users()->set_type(ACL::Entity::NONE); } { // Default principal can see all tasks. mesos::ACL::ViewTask* acl = acls.add_view_tasks(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL.principal()); acl->mutable_users()->set_type(ACL::Entity::ANY); } { // No other principal can see tasks running under any user. ACL::ViewTask* acl = acls.add_view_tasks(); acl->mutable_principals()->set_type(ACL::Entity::ANY); acl->mutable_users()->set_type(ACL::Entity::NONE); } { // Default principal can view "superhero" role only. ACL::ViewRole* acl = acls.add_view_roles(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL.principal()); acl->mutable_roles()->add_values(roleSuperhero); acl = acls.add_view_roles(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL.principal()); acl->mutable_roles()->set_type(mesos::ACL::Entity::NONE); } { // Second default principal can view "muggle" role only. ACL::ViewRole* acl = acls.add_view_roles(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL_2.principal()); acl->mutable_roles()->add_values(roleMuggle); acl = acls.add_view_roles(); acl->mutable_principals()->add_values(DEFAULT_CREDENTIAL_2.principal()); acl->mutable_roles()->set_type(mesos::ACL::Entity::NONE); } // Create an `Authorizer` with the ACLs. Try<Authorizer*> create = TypeParam::create(parameterize(acls)); ASSERT_SOME(create); Owned<Authorizer> authorizer(create.get()); Try<Owned<cluster::Master>> master = this->StartMaster(authorizer.get()); ASSERT_SOME(master); // Register framework with user "bar" and role "superhero". FrameworkInfo frameworkSuperhero = DEFAULT_FRAMEWORK_INFO; frameworkSuperhero.set_name("framework-" + roleSuperhero); frameworkSuperhero.set_roles(0, roleSuperhero); frameworkSuperhero.set_user("bar"); // Create an executor with user "bar". ExecutorInfo executorSuperhero = createExecutorInfo("test-executor-" + roleSuperhero, "sleep 2"); executorSuperhero.mutable_command()->set_user("bar"); MockExecutor execSuperhero(executorSuperhero.executor_id()); // Register framework with user "foo" and role "muggle". FrameworkInfo frameworkMuggle = DEFAULT_FRAMEWORK_INFO; frameworkMuggle.set_name("framework-" + roleMuggle); frameworkMuggle.set_principal(DEFAULT_CREDENTIAL_2.principal()); frameworkMuggle.set_roles(0, roleMuggle); frameworkMuggle.set_user("foo"); // Create an executor with user "foo". ExecutorInfo executorMuggle = createExecutorInfo("test-executor-" + roleMuggle, "sleep 2"); executorMuggle.mutable_command()->set_user("foo"); MockExecutor execMuggle(executorMuggle.executor_id()); TestContainerizer containerizer( {{executorSuperhero.executor_id(), &execSuperhero}, {executorMuggle.executor_id(), &execMuggle}}); slave::Flags flags = this->CreateSlaveFlags(); // Statically reserve resources for each role. flags.resources = "cpus(" + roleSuperhero + "):2;" + "cpus(" + roleMuggle + "):3;mem(" + roleSuperhero + "):512;" + "mem(" + roleMuggle + "):1024;"; Owned<MasterDetector> detector = master.get()->createDetector(); Try<Owned<cluster::Slave>> slave = this->StartSlave( detector.get(), &containerizer, authorizer.get(), flags); ASSERT_SOME(slave); MockScheduler schedSuperhero; MesosSchedulerDriver driverSuperhero( &schedSuperhero, frameworkSuperhero, master.get()->pid, DEFAULT_CREDENTIAL); EXPECT_CALL(execSuperhero, registered(_, _, _, _)) .Times(AtMost(1)); Future<FrameworkID> frameworkIdSuperhero; EXPECT_CALL(schedSuperhero, registered(&driverSuperhero, _, _)) .WillOnce(FutureArg<1>(&frameworkIdSuperhero)); Future<vector<Offer>> offersSuperhero; EXPECT_CALL(schedSuperhero, resourceOffers(&driverSuperhero, _)) .WillOnce(FutureArg<1>(&offersSuperhero)) .WillRepeatedly(Return()); // Ignore subsequent offers. driverSuperhero.start(); AWAIT_READY(frameworkIdSuperhero); AWAIT_READY(offersSuperhero); ASSERT_FALSE(offersSuperhero->empty()); // Define a task which will run on executorSuperhero of frameworkSuperhero. TaskInfo taskSuperhero; taskSuperhero.set_name("test-" + roleSuperhero); taskSuperhero.mutable_task_id()->set_value("1"); taskSuperhero.mutable_slave_id()->MergeFrom( offersSuperhero.get()[0].slave_id()); taskSuperhero.mutable_resources()->MergeFrom( offersSuperhero.get()[0].resources()); taskSuperhero.mutable_executor()->MergeFrom(executorSuperhero); EXPECT_CALL(execSuperhero, launchTask(_, _)) .WillOnce(SendStatusUpdateFromTask(TASK_RUNNING)) .WillRepeatedly(Return()); Future<TaskStatus> statusSuperhero; EXPECT_CALL(schedSuperhero, statusUpdate(&driverSuperhero, _)) .WillOnce(FutureArg<1>(&statusSuperhero)); driverSuperhero.launchTasks(offersSuperhero.get()[0].id(), {taskSuperhero}); AWAIT_READY(statusSuperhero); EXPECT_EQ(TASK_RUNNING, statusSuperhero->state()); MockScheduler schedMuggle; MesosSchedulerDriver driverMuggle( &schedMuggle, frameworkMuggle, master.get()->pid, DEFAULT_CREDENTIAL_2); EXPECT_CALL(execMuggle, registered(_, _, _, _)) .Times(AtMost(1)); Future<FrameworkID> frameworkIdMuggle; EXPECT_CALL(schedMuggle, registered(&driverMuggle, _, _)) .WillOnce(FutureArg<1>(&frameworkIdMuggle)); Future<vector<Offer>> offersMuggle; EXPECT_CALL(schedMuggle, resourceOffers(&driverMuggle, _)) .WillOnce(FutureArg<1>(&offersMuggle)) .WillRepeatedly(Return()); // Ignore subsequent offers. driverMuggle.start(); AWAIT_READY(frameworkIdMuggle); AWAIT_READY(offersMuggle); ASSERT_FALSE(offersMuggle->empty()); // Define a task which will run on executorMuggle of frameworkMuggle. TaskInfo taskMuggle; taskMuggle.set_name("test-" + roleMuggle); taskMuggle.mutable_task_id()->set_value("2"); taskMuggle.mutable_slave_id()->MergeFrom( offersMuggle.get()[0].slave_id()); taskMuggle.mutable_resources()->MergeFrom( offersMuggle.get()[0].resources()); taskMuggle.mutable_executor()->MergeFrom(executorMuggle); EXPECT_CALL(execMuggle, launchTask(_, _)) .WillOnce(SendStatusUpdateFromTask(TASK_RUNNING)) .WillRepeatedly(Return()); Future<TaskStatus> statusMuggle; EXPECT_CALL(schedMuggle, statusUpdate(&driverMuggle, _)) .WillOnce(FutureArg<1>(&statusMuggle)); driverMuggle.launchTasks(offersMuggle.get()[0].id(), {taskMuggle}); AWAIT_READY(statusMuggle); ASSERT_EQ(TASK_RUNNING, statusMuggle->state()); // Retrieve endpoint with the user allowed to view the frameworks. // The default user allowed to view role "superhero" only. { Future<Response> response = http::get( slave.get()->pid, "state", None(), createBasicAuthHeaders(DEFAULT_CREDENTIAL)); AWAIT_EXPECT_RESPONSE_STATUS_EQ(OK().status, response); Try<JSON::Object> parse = JSON::parse<JSON::Object>(response->body); ASSERT_SOME(parse); JSON::Object state = parse.get(); ASSERT_TRUE(state.values["frameworks"].is<JSON::Array>()); JSON::Array frameworks = state.values["frameworks"].as<JSON::Array>(); EXPECT_EQ(2u, frameworks.values.size()); foreach (const JSON::Value& value, frameworks.values) { JSON::Object framework = value.as<JSON::Object>(); EXPECT_FALSE(framework.values.empty()); ASSERT_TRUE(framework.values["executors"].is<JSON::Array>()); JSON::Array executors = framework.values["executors"].as<JSON::Array>(); EXPECT_EQ(1u, executors.values.size()); JSON::Object executor = executors.values.front().as<JSON::Object>(); EXPECT_EQ(1u, executor.values["tasks"].as<JSON::Array>().values.size()); } ASSERT_TRUE(state.values["reserved_resources"].is<JSON::Object>()); JSON::Object reserved_resources = state.values["reserved_resources"].as<JSON::Object>(); EXPECT_TRUE(reserved_resources.values[roleSuperhero].is<JSON::Object>()); EXPECT_FALSE(reserved_resources.values[roleMuggle].is<JSON::Object>()); ASSERT_TRUE( state.values["reserved_resources_allocated"].is<JSON::Object>()); JSON::Object reserved_resources_allocated = state.values["reserved_resources_allocated"].as<JSON::Object>(); EXPECT_TRUE( reserved_resources_allocated.values[roleSuperhero].is<JSON::Object>()); EXPECT_FALSE( reserved_resources_allocated.values[roleMuggle].is<JSON::Object>()); ASSERT_TRUE(state.values["reserved_resources_full"].is<JSON::Object>()); JSON::Object reserved_resources_full = state.values["reserved_resources_full"].as<JSON::Object>(); EXPECT_TRUE( reserved_resources_full.values[roleSuperhero].is<JSON::Array>()); EXPECT_FALSE( reserved_resources_full.values[roleMuggle].is<JSON::Array>()); } // Retrieve endpoint with the user allowed to view the frameworks, // but not the executors. // The second default user allowed to view role "muggle" only. { Future<Response> response = http::get( slave.get()->pid, "state", None(), createBasicAuthHeaders(DEFAULT_CREDENTIAL_2)); AWAIT_EXPECT_RESPONSE_STATUS_EQ(OK().status, response); Try<JSON::Object> parse = JSON::parse<JSON::Object>(response->body); ASSERT_SOME(parse); JSON::Object state = parse.get(); ASSERT_TRUE(state.values["frameworks"].is<JSON::Array>()); JSON::Array frameworks = state.values["frameworks"].as<JSON::Array>(); EXPECT_EQ(2u, frameworks.values.size()); foreach (const JSON::Value& value, frameworks.values) { JSON::Object framework = value.as<JSON::Object>(); EXPECT_FALSE(framework.values.empty()); EXPECT_TRUE( framework.values["executors"].as<JSON::Array>().values.empty()); } ASSERT_TRUE(state.values["reserved_resources"].is<JSON::Object>()); JSON::Object reserved_resources = state.values["reserved_resources"].as<JSON::Object>(); EXPECT_TRUE(reserved_resources.values[roleMuggle].is<JSON::Object>()); EXPECT_FALSE(reserved_resources.values[roleSuperhero].is<JSON::Object>()); ASSERT_TRUE( state.values["reserved_resources_allocated"].is<JSON::Object>()); JSON::Object reserved_resources_allocated = state.values["reserved_resources_allocated"].as<JSON::Object>(); EXPECT_TRUE( reserved_resources_allocated.values[roleMuggle].is<JSON::Object>()); EXPECT_FALSE( reserved_resources_allocated.values[roleSuperhero].is<JSON::Object>()); ASSERT_TRUE(state.values["reserved_resources_full"].is<JSON::Object>()); JSON::Object reserved_resources_full = state.values["reserved_resources_full"].as<JSON::Object>(); EXPECT_TRUE( reserved_resources_full.values[roleMuggle].is<JSON::Array>()); EXPECT_FALSE( reserved_resources_full.values[roleSuperhero].is<JSON::Array>()); } EXPECT_CALL(execSuperhero, shutdown(_)) .Times(AtMost(1)); EXPECT_CALL(execMuggle, shutdown(_)) .Times(AtMost(1)); driverSuperhero.stop(); driverSuperhero.join(); driverMuggle.stop(); driverMuggle.join(); }
int main(int argc, char** argv) { // Find this executable's directory to locate executor. string path = os::realpath(dirname(argv[0])).get(); string uri = path + "/test-executor"; if (getenv("MESOS_BUILD_DIR")) { uri = string(getenv("MESOS_BUILD_DIR")) + "/src/test-executor"; } mesos::internal::logging::Flags flags; string role; flags.add(&role, "role", "Role to use when registering", "*"); Option<string> master; flags.add(&master, "master", "ip:port of master to connect"); Try<Nothing> load = flags.load(None(), argc, argv); if (load.isError()) { cerr << load.error() << endl; usage(argv[0], flags); exit(1); } else if (master.isNone()) { cerr << "Missing --master" << endl; usage(argv[0], flags); exit(1); } ExecutorInfo executor; executor.mutable_executor_id()->set_value("default"); executor.mutable_command()->set_value(uri); executor.set_name("Test Executor (C++)"); executor.set_source("cpp_test"); TestScheduler scheduler(executor, role); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Test Framework (C++)"); framework.set_role(role); // TODO(vinod): Make checkpointing the default when it is default // on the slave. if (os::hasenv("MESOS_CHECKPOINT")) { cout << "Enabling checkpoint for the framework" << endl; framework.set_checkpoint(true); } MesosSchedulerDriver* driver; if (os::hasenv("MESOS_AUTHENTICATE")) { cout << "Enabling authentication for the framework" << endl; if (!os::hasenv("DEFAULT_PRINCIPAL")) { EXIT(1) << "Expecting authentication principal in the environment"; } if (!os::hasenv("DEFAULT_SECRET")) { EXIT(1) << "Expecting authentication secret in the environment"; } Credential credential; credential.set_principal(getenv("DEFAULT_PRINCIPAL")); credential.set_secret(getenv("DEFAULT_SECRET")); driver = new MesosSchedulerDriver( &scheduler, framework, master.get(), credential); } else { driver = new MesosSchedulerDriver( &scheduler, framework, master.get()); } int status = driver->run() == DRIVER_STOPPED ? 0 : 1; delete driver; return status; }
int main(int argc, char** argv) { if (argc != 3) { std::cerr << "Usage: " << argv[0] << " <master> <balloon limit in MB>" << std::endl; return -1; } // Verify the balloon limit. Try<size_t> limit = numify<size_t>(argv[2]); if (limit.isError()) { std::cerr << "Balloon limit is not a valid number" << std::endl; return -1; } if (limit.get() < EXECUTOR_MEMORY_MB) { std::cerr << "Please use a balloon limit bigger than " << EXECUTOR_MEMORY_MB << " MB" << std::endl; } // Find this executable's directory to locate executor. std::string path = os::realpath(::dirname(argv[0])).get(); std::string uri = path + "/balloon-executor"; if (getenv("MESOS_BUILD_DIR")) { uri = std::string(::getenv("MESOS_BUILD_DIR")) + "/src/balloon-executor"; } ExecutorInfo executor; executor.mutable_executor_id()->set_value("default"); executor.mutable_command()->set_value(uri); executor.set_name("Balloon Executor"); executor.set_source("balloon_test"); Resource* mem = executor.add_resources(); mem->set_name("mem"); mem->set_type(Value::SCALAR); mem->mutable_scalar()->set_value(EXECUTOR_MEMORY_MB); BalloonScheduler scheduler(executor, limit.get()); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Balloon Framework (C++)"); // TODO(vinod): Make checkpointing the default when it is default // on the slave. if (os::hasenv("MESOS_CHECKPOINT")) { cout << "Enabling checkpoint for the framework" << endl; framework.set_checkpoint(true); } MesosSchedulerDriver* driver; if (os::hasenv("MESOS_AUTHENTICATE")) { cout << "Enabling authentication for the framework" << endl; if (!os::hasenv("DEFAULT_PRINCIPAL")) { EXIT(1) << "Expecting authentication principal in the environment"; } if (!os::hasenv("DEFAULT_SECRET")) { EXIT(1) << "Expecting authentication secret in the environment"; } Credential credential; credential.set_principal(getenv("DEFAULT_PRINCIPAL")); credential.set_secret(getenv("DEFAULT_SECRET")); framework.set_principal(getenv("DEFAULT_PRINCIPAL")); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1], credential); } else { framework.set_principal("balloon-framework-cpp"); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1]); } int status = driver->run() == DRIVER_STOPPED ? 0 : 1; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
int main(int argc, char** argv) { Flags flags; Try<flags::Warnings> load = flags.load("MESOS_EXAMPLE_", argc, argv); if (load.isError()) { std::cerr << flags.usage(load.error()) << std::endl; return EXIT_FAILURE; } if (flags.help) { std::cout << flags.usage() << std::endl; return EXIT_SUCCESS; } mesos::internal::logging::initialize(argv[0], false); // Log any flag warnings (after logging is initialized). foreach (const flags::Warning& warning, load->warnings) { LOG(WARNING) << warning.message; } if (flags.qps <= 0.0) { EXIT(EXIT_FAILURE) << "Flag '--qps' needs to be greater than zero"; } LoadGeneratorScheduler scheduler(flags.qps, flags.duration); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_principal(flags.principal); framework.set_name(FRAMEWORK_NAME); framework.set_checkpoint(flags.checkpoint); framework.add_roles(flags.role); framework.add_capabilities()->set_type( FrameworkInfo::Capability::RESERVATION_REFINEMENT); framework.set_checkpoint(flags.checkpoint); if (flags.master == "local") { // Configure master. os::setenv("MESOS_ROLES", flags.role); os::setenv("MESOS_AUTHENTICATE_FRAMEWORKS", stringify(flags.authenticate)); ACLs acls; ACL::RegisterFramework* acl = acls.add_register_frameworks(); acl->mutable_principals()->set_type(ACL::Entity::ANY); acl->mutable_roles()->add_values("*"); os::setenv("MESOS_ACLS", stringify(JSON::protobuf(acls))); } MesosSchedulerDriver* driver; if (flags.authenticate) { LOG(INFO) << "Enabling authentication for the framework"; Credential credential; credential.set_principal(flags.principal); if (flags.secret.isSome()) { credential.set_secret(flags.secret.get()); } driver = new MesosSchedulerDriver( &scheduler, framework, flags.master, credential); } else { driver = new MesosSchedulerDriver( &scheduler, framework, flags.master); } int status = driver->run() == DRIVER_STOPPED ? EXIT_SUCCESS : EXIT_FAILURE; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
int main(int argc, char** argv) { if (argc != 2) { cerr << "Usage: " << argv[0] << " <master>" << endl; return -1; } // Find this executable's directory to locate executor. string uri; Option<string> value = os::getenv("MESOS_BUILD_DIR"); if (value.isSome()) { uri = path::join(value.get(), "src", "long-lived-executor"); } else { uri = path::join( os::realpath(Path(argv[0]).dirname()).get(), "long-lived-executor"); } ExecutorInfo executor; executor.mutable_executor_id()->set_value("default"); executor.mutable_command()->set_value(uri); executor.set_name("Long Lived Executor (C++)"); executor.set_source("cpp_long_lived_framework"); LongLivedScheduler scheduler(executor); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Long Lived Framework (C++)"); value = os::getenv("MESOS_CHECKPOINT"); if (value.isSome()) { framework.set_checkpoint( numify<bool>(value.get()).get()); } MesosSchedulerDriver* driver; if (os::getenv("MESOS_AUTHENTICATE").isSome()) { cout << "Enabling authentication for the framework" << endl; value = os::getenv("DEFAULT_PRINCIPAL"); if (value.isNone()) { EXIT(1) << "Expecting authentication principal in the environment"; } Credential credential; credential.set_principal(value.get()); framework.set_principal(value.get()); value = os::getenv("DEFAULT_SECRET"); if (value.isNone()) { EXIT(1) << "Expecting authentication secret in the environment"; } credential.set_secret(value.get()); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1], credential); } else { framework.set_principal("long-lived-framework-cpp"); driver = new MesosSchedulerDriver( &scheduler, framework, argv[1]); } int status = driver->run() == DRIVER_STOPPED ? 0 : 1; // Ensure that the driver process terminates. driver->stop(); delete driver; return status; }
// This test verifies that a task is launched on the agent if the task // user is authorized based on `run_tasks` ACL configured on the agent // to only allow whitelisted users to run tasks on the agent. TYPED_TEST(SlaveAuthorizerTest, AuthorizeRunTaskOnAgent) { // Get the current user. Result<string> user = os::user(); ASSERT_SOME(user) << "Failed to get the current user name" << (user.isError() ? ": " + user.error() : ""); Try<Owned<cluster::Master>> master = this->StartMaster(); ASSERT_SOME(master); // Start a slave with `bar` and the current user being the only authorized // users to launch tasks on the agent. ACLs acls; acls.set_permissive(false); // Restrictive. mesos::ACL::RunTask* acl = acls.add_run_tasks(); acl->mutable_principals()->set_type(ACL::Entity::ANY); acl->mutable_users()->add_values("bar"); acl->mutable_users()->add_values(user.get()); slave::Flags slaveFlags = this->CreateSlaveFlags(); slaveFlags.acls = acls; Owned<MasterDetector> detector = master.get()->createDetector(); Try<Owned<cluster::Slave>> slave = this->StartSlave( detector.get(), slaveFlags); ASSERT_SOME(slave); // Create a framework with user `foo`. FrameworkInfo frameworkInfo = DEFAULT_FRAMEWORK_INFO; frameworkInfo.set_user("foo"); MockScheduler sched; MesosSchedulerDriver driver( &sched, frameworkInfo, master.get()->pid, DEFAULT_CREDENTIAL); Future<FrameworkID> frameworkId; EXPECT_CALL(sched, registered(&driver, _, _)) .WillOnce(FutureArg<1>(&frameworkId)); Future<vector<Offer>> offers; EXPECT_CALL(sched, resourceOffers(&driver, _)) .WillOnce(FutureArg<1>(&offers)) .WillRepeatedly(Return()); // Ignore subsequent offers. driver.start(); // Framework is registered since the master admits frameworks of any user. AWAIT_READY(frameworkId); AWAIT_READY(offers); ASSERT_FALSE(offers->empty()); Offer offer = offers.get()[0]; // Launch the first task with no user, so it defaults to the // framework user `foo`. TaskInfo task1 = createTask( offer.slave_id(), Resources::parse("cpus:1;mem:32").get(), "sleep 1000"); // Launch the second task as the current user. TaskInfo task2 = createTask( offer.slave_id(), Resources::parse("cpus:1;mem:32").get(), "sleep 1000"); task2.mutable_command()->set_user(user.get()); // The first task should fail since the task user `foo` is not an // authorized user that can launch a task. However, the second task // should succeed. Future<TaskStatus> status0; Future<TaskStatus> status1; Future<TaskStatus> status2; EXPECT_CALL(sched, statusUpdate(&driver, _)) .WillOnce(FutureArg<1>(&status0)) .WillOnce(FutureArg<1>(&status1)) .WillOnce(FutureArg<1>(&status2)); driver.acceptOffers( {offer.id()}, {LAUNCH({task1, task2})}); // Wait for TASK_ERROR for 1st task, and TASK_STARTING followed by // TASK_RUNNING for 2nd task. AWAIT_READY(status0); AWAIT_READY(status1); AWAIT_READY(status2); // Validate both the statuses. Note that the order of receiving the // status updates for the 2 tasks is not deterministic, but we know // that task2's TASK_RUNNING arrives after TASK_STARTING. hashmap<TaskID, TaskStatus> statuses; statuses[status0->task_id()] = status0.get(); statuses[status1->task_id()] = status1.get(); statuses[status2->task_id()] = status2.get(); ASSERT_TRUE(statuses.contains(task1.task_id())); EXPECT_EQ(TASK_ERROR, statuses.at(task1.task_id()).state()); EXPECT_EQ(TaskStatus::SOURCE_SLAVE, statuses.at(task1.task_id()).source()); EXPECT_EQ(TaskStatus::REASON_TASK_UNAUTHORIZED, statuses.at(task1.task_id()).reason()); ASSERT_TRUE(statuses.contains(task2.task_id())); EXPECT_EQ(TASK_RUNNING, statuses.at(task2.task_id()).state()); driver.stop(); driver.join(); }
int main(int argc, char** argv) { string execpath, master, remotecmd; uint64_t mem = 64; double cpus = -1.0, cores = -1.0; shift; while(true) { const string s = argc > 0 ? argv[0] : "--help"; if(argc > 1 && s == "--exec-uri") { execpath = argv[1]; shift; shift; } else if(argc > 1 && s == "--master") { master = argv[1]; shift; shift; } else if(argc > 1 && s == "--cpus") { cpus = (double)stof(argv[1]); assert(cpus > 0.0); shift; shift; } else if(argc > 1 && s == "--mem") { mem = Bytes::parse(argv[1]).get().megabytes(); shift; shift; } else if(argc > 1 && s == "--cores") { cores = (double)stof(argv[1]); assert(cores> -1.0); shift; shift; } else if(argc > 1 && s == "--remote-cmd") { remotecmd = argv[1]; shift; shift; } else { break; } } if(master.length() == 0 || execpath.length() == 0 || cpus == -1) { printf("Usage: chapel-scheduler --master <ip:port|required> --exec-uri <uri-to-the-location-of-a.out_real|required> --cpus <number-of-nodes|%N> --cores <number-of-cores to use|optional default is '2'> --mem <amt-of-ram-per-node|optional default is '64MB'> --remote-cmd %C\n"); exit(1); } const string& hostname = getHostname(); const uid_t uid = geteuid(); const struct passwd* pw = getpwuid(uid); // don't free this pointer! check the docs of this function to confirm! FrameworkInfo framework; framework.set_user(pw->pw_name); framework.set_name("Chapel Framework"); //framework.set_role(role); framework.set_principal("cpp"); ChapelScheduler scheduler(cpus, mem, cores, hostname, execpath, remotecmd, pw->pw_name); // set up signal handler for clean shutdown // struct sigaction action; action.sa_handler = SIGINTHandler; sigemptyset(&action.sa_mask); action.sa_flags = 0; sigaction(SIGINT, &action, NULL); sigaction(SIGHUP, &action, NULL); sigaction(SIGQUIT, &action, NULL); sigaction(SIGCHLD, &action, NULL); sigaction(SIGSTOP, &action, NULL); sigaction(SIGABRT, &action, NULL); schedulerDriver = new MesosSchedulerDriver(&scheduler, framework, master); const uint8_t status = schedulerDriver->run() == DRIVER_STOPPED ? 0 : 1; if(status) { cout << "Driver Stopped!" << endl; scheduler.terminateAllTasks(schedulerDriver); schedulerDriver.stop(); shutdown(); if(schedulerDriver != NULL) { delete schedulerDriver; schedulerDriver = NULL; } } return status; }
int main(int argc, char** argv) { string seedUrl, master; shift; while (true) { string s = argc>0 ? argv[0] : "--help"; if (argc > 1 && s == "--seedUrl") { seedUrl = argv[1]; shift; shift; } else if (argc > 1 && s == "--master") { master = argv[1]; shift; shift; } else { break; } } if (master.length() == 0 || seedUrl.length() == 0) { printf("Usage: rendler --seedUrl <URL> --master <ip>:<port>\n"); exit(1); } // Find this executable's directory to locate executor. string path = realpath(dirname(argv[0]), NULL); string crawlerURI = path + "/crawl_executor"; string rendererURI = path + "/render_executor"; cout << crawlerURI << endl; cout << rendererURI << endl; ExecutorInfo crawler; crawler.mutable_executor_id()->set_value("Crawler"); crawler.mutable_command()->set_value(crawlerURI); crawler.set_name("Crawl Executor (C++)"); crawler.set_source("cpp"); ExecutorInfo renderer; renderer.mutable_executor_id()->set_value("Renderer"); renderer.mutable_command()->set_value(rendererURI); renderer.set_name("Render Executor (C++)"); renderer.set_source("cpp"); Rendler scheduler(crawler, renderer, seedUrl); FrameworkInfo framework; framework.set_user(""); // Have Mesos fill in the current user. framework.set_name("Rendler Framework (C++)"); //framework.set_role(role); framework.set_principal("rendler-cpp"); // Set up the signal handler for SIGINT for clean shutdown. struct sigaction action; action.sa_handler = SIGINTHandler; sigemptyset(&action.sa_mask); action.sa_flags = 0; sigaction(SIGINT, &action, NULL); schedulerDriver = new MesosSchedulerDriver(&scheduler, framework, master); int status = schedulerDriver->run() == DRIVER_STOPPED ? 0 : 1; // Ensure that the driver process terminates. schedulerDriver->stop(); shutdown(); delete schedulerDriver; return status; }