diff --git a/cmdb-api/api/lib/cmdb/ci_type.py b/cmdb-api/api/lib/cmdb/ci_type.py index bf936d4..bc50a7f 100644 --- a/cmdb-api/api/lib/cmdb/ci_type.py +++ b/cmdb-api/api/lib/cmdb/ci_type.py @@ -486,6 +486,8 @@ class CITypeAttributeGroupManager(object): return abort(400, "Group <{0}> duplicate".format(name)) if name is not None: group.update(name=name) + else: + name = group.name cls.create_or_update(group.type_id, name, attr_order, group_order) diff --git a/cmdb-api/tests/conftest.py b/cmdb-api/tests/conftest.py index fee9d8f..d2f0c04 100644 --- a/cmdb-api/tests/conftest.py +++ b/cmdb-api/tests/conftest.py @@ -21,7 +21,7 @@ class CMDBTestClient(FlaskClient): headers.setdefault("User-Agent", "py.test") kwargs["headers"] = headers - json_data = kwargs.pop("json") + json_data = kwargs.pop("json", None) if json_data is not None: kwargs["data"] = json.dumps(json_data) if not kwargs.get("content_type"): @@ -49,6 +49,7 @@ def app(): _app.config['SECRET_KEY'] = CMDBTestClient.TEST_APP_SECRET _app.test_client_class = CMDBTestClient _app.response_class = CMDBTestResponse + ctx = _app.test_request_context() ctx.push() yield _app @@ -99,7 +100,6 @@ def clean_db(): db.session.commit() if not User.get_by(email="test@xx.com"): - print("hello world xxxxx") u = User.create( flush=True, username="test", diff --git a/cmdb-api/tests/sample.py b/cmdb-api/tests/sample.py new file mode 100644 index 0000000..3bdc563 --- /dev/null +++ b/cmdb-api/tests/sample.py @@ -0,0 +1,49 @@ +# -*- coding: utf-8 -*- +"""provide some sample data in database""" +import uuid +import random + +from api.models.cmdb import Attribute, CIType, CITypeAttributeGroup, CITypeAttribute + + +def init_attributes(num=1): + attrs = [] + for i in range(num): + attrs.append(Attribute.create( + name=uuid.uuid4().hex[:8], + alias=uuid.uuid4().hex[:8], + value_type=str(random.randint(0, 100) % 7) + )) + return attrs + + +def init_ci_types(num=1): + attrs = init_attributes(num) + + ci_types = [] + for i in range(num): + ci_type = CIType.create( + name=uuid.uuid4().hex[:8], + alias=uuid.uuid4().hex[:8], + unique_id=attrs[i].id + ) + CITypeAttribute.create( + type_id=ci_type.id, + attr_id=attrs[i].id, + ) + ci_types.append(ci_type) + + return ci_types + + +def init_attribute_groups(num=1): + ci_types = init_ci_types(num) + + ags = [] + for i in range(num): + ags.append(CITypeAttributeGroup.create( + name=uuid.uuid4().hex[:8], + type_id=ci_types[i].id, + order=i + )) + return ags diff --git a/cmdb-api/tests/test_cmdb_attribute.py b/cmdb-api/tests/test_cmdb_attribute.py index fc754d9..eac93e0 100644 --- a/cmdb-api/tests/test_cmdb_attribute.py +++ b/cmdb-api/tests/test_cmdb_attribute.py @@ -1,6 +1,8 @@ # -*- coding: utf-8 -*- from api.models.cmdb import Attribute +from tests.sample import init_attributes + def test_create_attribute(session, client): url = "/api/v0.1/attributes" @@ -16,7 +18,7 @@ def test_create_attribute(session, client): assert resp.status_code == 200 assert resp.json["attr_id"] - # check there is a ci_types in database + # check there is a attribute in database attr_id = resp.json["attr_id"] attr_ins = Attribute.get_by_id(attr_id) assert attr_ins.id == attr_id @@ -24,3 +26,34 @@ def test_create_attribute(session, client): assert attr_ins.alias == "区域" +def test_update_attribute(session, client): + attr_ins = init_attributes(1)[0] + + url = "/api/v0.1/attributes/" + str(attr_ins.id) + payload = { + "name": "update", + } + + resp = client.put(url, json=payload) + + # check resp status code and content + assert resp.status_code == 200 + assert resp.json["attr_id"] == attr_ins.id + + # check attribute updated in database + attr_ins = Attribute.get_by_id(attr_ins.id) + assert attr_ins.name == "update" + + +def test_delete_attribute(session, client): + attr_ins = init_attributes(1)[0] + url = "/api/v0.1/attributes/" + str(attr_ins.id) + + resp = client.delete(url) + + assert resp.status_code == 200 + # attr should be soft delete + attr_ins = Attribute.get_by_id(attr_ins.id) + assert attr_ins.deleted is True + assert attr_ins.deleted_at + diff --git a/cmdb-api/tests/test_cmdb_ci.py b/cmdb-api/tests/test_cmdb_ci.py index 78a93f1..faaaf79 100644 --- a/cmdb-api/tests/test_cmdb_ci.py +++ b/cmdb-api/tests/test_cmdb_ci.py @@ -1,10 +1,3 @@ # -*- coding: utf-8 -*- -class TestCI: - - def test_ci_search_only_type_query(self, app): - with app.test_client() as c: - rv = c.get('/api/v0.1/ci/s?q=_type:server', json={}) - json_data = rv.get_json() - assert type(json_data.get("result")) is list diff --git a/cmdb-api/tests/test_cmdb_ci_type.py b/cmdb-api/tests/test_cmdb_ci_type.py index 40a96af..fb7c23b 100644 --- a/cmdb-api/tests/test_cmdb_ci_type.py +++ b/cmdb-api/tests/test_cmdb_ci_type.py @@ -1 +1,167 @@ # -*- coding: utf-8 -*- +from api.models.cmdb import ( + CIType, CITypeAttribute, + Attribute, CITypeAttributeGroup, + CITypeAttributeGroupItem) + +from tests.sample import ( + init_attributes, init_ci_types, + init_attribute_groups) + + +def test_create_ci_type(session, client): + attr = init_attributes(1)[0] + + url = "/api/v0.1/ci_types" + payload = { + "name": "test", + "alias": "测试", + "unique_key": attr.id + } + + resp = client.post(url, json=payload) + + # check resp status code and content + assert resp.status_code == 200 + assert resp.json["type_id"] + + # check there is a attribute in database + type_id = resp.json["type_id"] + ci_type_ins = CIType.get_by_id(type_id) + assert ci_type_ins.id == type_id + assert ci_type_ins.name == "test" + assert ci_type_ins.alias == "测试" + assert ci_type_ins.unique_id == attr.id + + +def test_update_ci_type(session, client): + ci_type_ins = init_ci_types(1)[0] + + url = "/api/v0.1/ci_types/" + str(ci_type_ins.id) + payload = { + "name": "update", + } + + resp = client.put(url, json=payload) + + # check resp status code and content + assert resp.status_code == 200 + assert resp.json["type_id"] == ci_type_ins.id + + # check ci_type updated in database + ci_type_ins = CIType.get_by_id(ci_type_ins.id) + assert ci_type_ins.name == "update" + + +def test_delete_ci_type(session, client): + ci_type_ins = init_ci_types(1)[0] + url = "/api/v0.1/ci_types/" + str(ci_type_ins.id) + + resp = client.delete(url) + + assert resp.status_code == 200 + # attr should be soft delete + ci_type_ins = CIType.get_by_id(ci_type_ins.id) + assert ci_type_ins.deleted is True + assert ci_type_ins.deleted_at + + +def test_bind_attributes_ci_type(session, client): + attrs = init_attributes(3) + ci_type = init_ci_types(1)[0] + + url = "/api/v0.1/ci_types/{}/attributes".format(ci_type.id) + payload = { + "attr_id": [str(x.id) for x in attrs] + } + + resp = client.post(url, json=payload) + + # check resp status code and content + assert resp.status_code == 200 + assert len(resp.json["attributes"]) == len(attrs) + + # check ci_type has 4 attributes + ci_type_attribute_ids = [x.attr_id for x in CITypeAttribute.query.filter_by(type_id=ci_type.id).all()] + for attr in attrs: + assert attr.id in ci_type_attribute_ids + + +def test_get_attributes_ci_type(session, client): + ci_type = init_ci_types(1)[0] + url = "/api/v0.1/ci_types/{}/attributes".format(ci_type.name) + + resp = client.get(url) + + assert resp.status_code == 200 + assert len(resp.json["attributes"]) == 1 + + +def test_update_attributes_ci_type(session, client): + ci_type = init_ci_types(1)[0] + attr = Attribute.query.first() + url = "/api/v0.1/ci_types/{}/attributes".format(ci_type.id) + + payload = { + "attributes": [ + {"attr_id": attr.id, "default_show": False, "is_required": True} + ] + } + resp = client.put(url, json=payload) + assert resp.status_code == 200 + + ci_type_attr_ins = CITypeAttribute.query.filter_by(type_id=ci_type.id).first() + assert ci_type_attr_ins + assert ci_type_attr_ins.is_required is True + assert ci_type_attr_ins.default_show is False + + +def test_create_attribute_group_ci_type(session, client): + ci_type = init_ci_types(1)[0] + + url = "/api/v0.1/ci_types/{}/attribute_groups".format(ci_type.id) + payload = { + "name": "A", + "order": 100, + } + + resp = client.post(url, json=payload) + + # check resp status code and content + assert resp.status_code == 200 + assert resp.json["group_id"] + + ins = CITypeAttributeGroup.query.filter_by(type_id=ci_type.id).first() + assert ins + assert ins.id == resp.json["group_id"] + assert ins.name == "A" + assert ins.order == 100 + + +def test_update_attribute_group_ci_type(session, client): + attribute_groups = init_attribute_groups(1)[0] + + url = "/api/v0.1/ci_types/attribute_groups/{}".format(attribute_groups.id) + payload = { + "attributes": [x.id for x in Attribute.query.all()] + } + + resp = client.put(url, json=payload) + assert resp.status_code == 200 + assert resp.json["group_id"] + + ag_items = CITypeAttributeGroupItem.query.filter_by(group_id=attribute_groups.id).all() + for a in Attribute.query.all(): + assert a.id in [x.attr_id for x in ag_items] + + +def test_delete_attribute_group_ci_type(session, client): + attribute_groups = init_attribute_groups(1)[0] + + url = "/api/v0.1/ci_types/attribute_groups/{}".format(attribute_groups.id) + resp = client.delete(url) + + assert resp.status_code == 200 + attribute_group_ins = CITypeAttributeGroup.query.filter_by(id=attribute_groups.id).first() + assert attribute_group_ins.deleted is True + assert attribute_group_ins.deleted_at