def test_empty_plans_return_hal(app): url = url_for("plans.list_plans") with app.test_request_context(url): res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(data={"plans": []}).to_dict()
def test_executors_list_return_empty_array(app): url = url_for("executors.get_executors") with app.test_request_context(url): res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(embedded={"executors": []}).to_dict()
def test_empty_attack_store_return_hal(app, manager): url = url_for("attacks.list_attacks") attack_list = [] manager.attacks_store.set_modules(attack_list) with app.test_request_context(url): res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(data={"attacks": attack_list}).to_dict()
def test_empty_planners_store_return_hal(app, manager): url = url_for("planners.list_planners") planners_list = [] manager.planners_store.set_modules(planners_list) with app.test_request_context(url): res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(data={"planners": []}).to_dict()
def put_executor(executor_id): """ Update a executor to change its date. To provide a new date use the format in the example bellow. The format is used to create a `DateTrigger <https://github.com/agronholm/apscheduler/blob/master/apscheduler/triggers/date.py>`_ from the apscheduler. TODO: create more `Triggers <https://github.com/agronholm/apscheduler/blob/master/apscheduler/triggers>`_ Example request:: PUT /api/1/executors/3b373155577b4d1bbc62216ffea013a4 Body: { "type" : "date", "args" : { "date": "2017-10-23T19:19" } } Example response:: { "id": "3b373155577b4d1bbc62216ffea013a4", "plan_id": "3ec72048cab04b76bdf2cfd4bc81cd1e", "next_run_time": "2017-10-23T19:19:1508786354", "executed": false, "_links": { "self": { "href": "/api/1/executors/3b373155577b4d1bbc62216ffea013a4" }, "update":{ "href":"/api/1/executors/3b373155577b4d1bbc62216ffea013a4" }, "delete":{ "href":"/api/1/executors/3b373155577b4d1bbc62216ffea013a4" } } } :return: :meth:`chaosmonkey.api.hal.document` """ assert validate_payload(request, executor_trigger_schema) body = request.get_json() trigger = dict_to_trigger(body) try: executor = manager.update_executor_trigger(executor_id, trigger) except JobLookupError: return json.jsonify({"msg": "executor not found " + executor_id}), 404 else: return Document(data=executor.to_dict())
def list_planners(): """ Return a list with the available planners and its configuration. Example response:: { "_links": { "self": { "href": "/api/1/planners/" } }, "planners": [ { "example": { "args": { "times": 4, "max_time": "15:00", "min_time": "10:00" }, "ref": "simple_planner:SimplePlanner" }, "ref": "simple_planner:SimplePlanner", "schema": { "type": "object", "properties": { "args": { "type": "object", "properties": { "times": { "type": "number" }, "max_time": { "type": "string" }, "min_time": { "type": "string" } } }, "ref": { "type": "string" } } } } ] } :return: :meth:`chaosmonkey.api.hal.document` """ planners_list = manager.get_planner_list() return Document(data={"planners": planners_list})
def test_plan_list_return_hal(app, manager): url = url_for("plans.list_plans") plan = manager.add_plan("plan name") with app.test_request_context(url): plan_list = [plan.to_dict()] res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(data={"plans": plan_list}).to_dict()
def test_attack_list_return_hal(app, manager): url = url_for("attacks.list_attacks") module_list = [attack1_module, attack2_module] manager.attacks_store.set_modules(module_list) with app.test_request_context(url): attack_list = [attack1_module.Attack1(None).to_dict(), attack2_module.Attack2(None).to_dict()] res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(data={"attacks": attack_list}).to_dict()
def test_planners_list_return_hal(app, manager): url = url_for("planners.list_planners") module_list = [planner1_module, planner2_module] manager.planners_store.set_modules(module_list) with app.test_request_context(url): planner_list = [planner1_module.Planner1("planner1").to_dict(), planner2_module.Planner2("planner2").to_dict()] res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(data={"planners": planner_list}).to_dict()
def test_get_executors(app, manager, plan): """" Test that the endpoint returns an array of executors """ url = url_for("executors.get_executors") run_time = datetime.now() + timedelta(hours=10) executor = manager.add_executor(run_time, "executor name", {}, plan.id) with app.test_request_context(url): res = app.test_client().get(url) assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == Document(embedded={ "executors": [executor.to_dict()] }).to_dict()
def list_plans(): """ List all plans created Example request:: GET /api/1/plans/?all=true Example response:: { "_links": { "self": { "href": "/api/1/plans/" } }, "plans": [ { "id": "6890192d8b6c40e5af16f13aa036c7dc", "created": "2017-01-26T10:41:1485427282", "next_execution": "2017-01-26 13:14:07.583372", "name": "Terminate instances in Playground", "executors_count": 2, "_links": { "self": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dc" }, "update": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dc" }, "delete": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dc" } } } ] } :param: all. Control when to show all plans (true) or only not executed (false). Defaults to false :return: :meth:`chaosmonkey.api.hal.document` """ show_all_query = request.args.get("all", False) show_all = get_boolean(show_all_query) plan_list = [ plan.to_dict() for plan in manager.get_plans(show_all=show_all) ] return Document(data={"plans": plan_list})
def test_plan_get_return_hal_with_executors(app, manager): plan = manager.add_plan("plan name") run_time = datetime.now() + timedelta(hours=10) executor = manager.add_executor(run_time, "executor name", {}, plan.id) url = url_for("plans.get_plan", plan_id=plan.id) with app.test_request_context(url): res = app.test_client().get(url) expected = Document(data=plan.to_dict(), embedded={ "executors": [executor.to_dict()] }).to_dict() assert res.status_code == 200 assert res.mimetype == "application/hal+json" assert res.json == expected
def get_executors(): """ Get a list of scheduled executors Example response:: { "executors":[ { "_links":{ "self":{ "href":"/api/1/executors/3b373155577b4d1bbc62216ffea013a4" }, "update":{ "href":"/api/1/executors/3b373155577b4d1bbc62216ffea013a4" }, "delete":{ "href":"/api/1/executors/3b373155577b4d1bbc62216ffea013a4" } }, "id":"3b373155577b4d1bbc62216ffea013a4", "plan_id":"3ec72048cab04b76bdf2cfd4bc81cd1e", "next_run_time":"2017-01-25T10:12:1485339145", "executed": false } ] } :param: executed. Control when to show all executors (true) or only not executed (false). Defaults to false :return: :meth:`chaosmonkey.api.hal.document` """ executed_query = request.args.get("executed", False) executed = get_boolean(executed_query) executors_list = [ executor.to_dict() for executor in manager.get_executors(executed=executed) ] return Document(embedded={"executors": executors_list})
def get_plan(plan_id): """ Get a plan with all related executors Example request:: GET /api/1/plans/6890192d8b6c40e5af16f13aa036c7dc Example response:: { "id": "6890192d8b6c40e5af16f13aa036c7dc", "_embedded": { "executors": [ { "plan_id": "6890192d8b6c40e5af16f13aa036c7dc", "_links": { "self": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dcdd2530572fd04c5aa061f261f82743d3" }, "update": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dcdd2530572fd04c5aa061f261f82743d3" }, "delete": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dcdd2530572fd04c5aa061f261f82743d3" } }, "next_run_time": "2017-01-26T13:14:1485436447", "id": "dd2530572fd04c5aa061f261f82743d3" }, { "plan_id": "6890192d8b6c40e5af16f13aa036c7dc", "_links": { "self": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dc1dd3f0d392e545808edb74852213c1ae" }, "update": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dc1dd3f0d392e545808edb74852213c1ae" }, "delete": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dc1dd3f0d392e545808edb74852213c1ae" } }, "next_run_time": "2017-01-26T18:24:1485455082", "id": "1dd3f0d392e545808edb74852213c1ae" } ] }, "created": "2017-01-26T10:41:1485427282", "next_execution": null, "name": "Terminate instances in Playground", "executors_count": null, "_links": { "self": { "href": "/api/1/plans/6890192d8b6c40e5af16f13aa036c7dc" } } } :return: :meth:`chaosmonkey.api.hal.document` """ plan = manager.get_plan(plan_id) executor_list = [ executor.to_dict() for executor in manager.get_executors_for_plan(plan_id) ] return Document(data=plan.to_dict(), embedded={"executors": executor_list})
def list_attacks(): """ Return a list with the available attacks and its configuration. Example:: { "attacks": [ { "example": { "args": { "filters": { "tag:Name": "playground-asg" }, "region": "eu-west-1" }, "ref": "terminate_ec2_instance:TerminateEC2Instance" }, "ref": "terminate_ec2_instance:TerminateEC2Instance", "schema": { "type": "object", "properties": { "args": { "type": "object", "properties": { "filters": { "type": "object", "properties": { "tag:Name": { "type": "string" } }, "required": [ "tag:Name" ] }, "region": { "optional": true, "type": "string" } }, "required": [ "region", "filters" ] }, "ref": { "type": "string" } } } } ], "_links": { "self": { "href": "/api/1/attacks/" } } } :return: :meth:`chaosmonkey.api.hal.document` """ attack_list = manager.get_attack_list() return Document(data={"attacks": attack_list})