14-dynsec-group.py 8.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191
  1. #!/usr/bin/env python3
  2. from mosq_test_helper import *
  3. import json
  4. import shutil
  5. def write_config(filename, port):
  6. with open(filename, 'w') as f:
  7. f.write("listener %d\n" % (port))
  8. f.write("allow_anonymous true\n")
  9. f.write("plugin ../../plugins/dynamic-security/mosquitto_dynamic_security.so\n")
  10. f.write("plugin_opt_config_file %d/dynamic-security.json\n" % (port))
  11. def command_check(sock, command_payload, expected_response, msg=""):
  12. command_packet = mosq_test.gen_publish(topic="$CONTROL/dynamic-security/v1", qos=0, payload=json.dumps(command_payload))
  13. sock.send(command_packet)
  14. response = json.loads(mosq_test.read_publish(sock))
  15. if response != expected_response:
  16. print(msg)
  17. print(expected_response)
  18. print(response)
  19. raise ValueError(response)
  20. port = mosq_test.get_port()
  21. conf_file = os.path.basename(__file__).replace('.py', '.conf')
  22. write_config(conf_file, port)
  23. create_client_command = { "commands": [{
  24. "command": "createClient", "username": "user_one",
  25. "password": "password", "clientid": "cid",
  26. "textname": "Name", "textdescription": "description",
  27. "rolename": "", "correlationData": "2" }]}
  28. create_client_response = {'responses':[{"command":"createClient","correlationData":"2"}]}
  29. create_client2_command = { "commands": [{
  30. "command": "createClient", "username": "user_two",
  31. "password": "password",
  32. "textname": "Name", "textdescription": "description",
  33. "rolename": "", "correlationData": "1" }]}
  34. create_client2_response = {'responses':[{"command":"createClient","correlationData":"1"}]}
  35. create_group_command = { "commands": [{
  36. "command": "createGroup", "groupname": "group_one",
  37. "textname": "Name", "textdescription": "description",
  38. "correlationData":"3"}]}
  39. create_group_response = {'responses':[{"command":"createGroup","correlationData":"3"}]}
  40. create_group_repeat_response = {'responses':[{"command":"createGroup","error":"Group already exists","correlationData":"3"}]}
  41. create_group2_command = { "commands": [{
  42. "command": "createGroup", "groupname": "group_two",
  43. "textname": "Name", "textdescription": "description",
  44. "correlationData":"30"}]}
  45. create_group2_response = {'responses':[{"command":"createGroup","correlationData":"30"}]}
  46. list_groups_command = { "commands": [{
  47. "command": "listGroups", "verbose": False, "correlationData": "10"}]}
  48. list_groups_response = {'responses':[{"command": "listGroups", "data":{"totalCount":2, "groups":["group_one","group_two"]},"correlationData":"10"}]}
  49. list_groups_verbose_command = { "commands": [{
  50. "command": "listGroups", "verbose": True, "correlationData": "15"}]}
  51. list_groups_verbose_response = {'responses':[{'command': 'listGroups', 'data': {"totalCount":2, 'groups':[
  52. {'groupname': 'group_one', 'textname': 'Name', 'textdescription': 'description', 'clients': [
  53. {"username":"user_one"}, {"username":"user_two"}], "roles":[]},
  54. {'groupname': 'group_two', 'textname': 'Name', 'textdescription': 'description', 'clients': [
  55. {"username":"user_one"}], "roles":[]}
  56. ]},
  57. 'correlationData': '15'}]}
  58. list_clients_verbose_command = { "commands": [{
  59. "command": "listClients", "verbose": True, "correlationData": "20"}]}
  60. list_clients_verbose_response = {'responses':[{"command": "listClients", "data":{"totalCount":3, "clients":[
  61. {'username': 'admin', 'textname': 'Dynsec admin user', 'roles': [{'rolename': 'admin'}], 'groups': []},
  62. {"username":"user_one", "clientid":"cid", "textname":"Name", "textdescription":"description",
  63. "groups":[{"groupname":"group_one"}, {"groupname":"group_two"}], "roles":[]},
  64. {"username":"user_two", "textname":"Name", "textdescription":"description",
  65. "groups":[{"groupname":"group_one"}], "roles":[]},
  66. ]}, "correlationData":"20"}]}
  67. get_group_command = { "commands": [{"command": "getGroup", "groupname":"group_one"}]}
  68. get_group_response = {'responses':[{'command': 'getGroup', 'data': {'group': {'groupname': 'group_one',
  69. 'textname':'Name', 'textdescription':'description', 'clients': [{"username":"user_one"}, {"username":"user_two"}], 'roles': []}}}]}
  70. add_client_to_group_command = {"commands": [{"command":"addGroupClient", "username":"user_one",
  71. "groupname": "group_one", "correlationData":"1234"}]}
  72. add_client_to_group_response = {'responses':[{'command': 'addGroupClient', 'correlationData': '1234'}]}
  73. add_duplicate_client_to_group_response = {'responses':[{'command': 'addGroupClient', 'error':'Client is already in this group', 'correlationData': '1234'}]}
  74. add_client_to_group2_command = {"commands": [{"command":"addGroupClient", "username":"user_one",
  75. "groupname": "group_two", "correlationData":"1234"}]}
  76. add_client_to_group2_response = {'responses':[{'command': 'addGroupClient', 'correlationData': '1234'}]}
  77. add_client2_to_group_command = {"commands": [{"command":"addGroupClient", "username":"user_two",
  78. "groupname": "group_one", "correlationData":"1235"}]}
  79. add_client2_to_group_response = {'responses':[{'command': 'addGroupClient', 'correlationData': '1235'}]}
  80. remove_client_from_group_command = {"commands": [{"command":"removeGroupClient", "username":"user_one",
  81. "groupname": "group_one", "correlationData":"4321"}]}
  82. remove_client_from_group_response = {'responses':[{'command': 'removeGroupClient', 'correlationData': '4321'}]}
  83. delete_group_command = {"commands": [{"command":"deleteGroup", "groupname":"group_one", "correlationData":"5678"}]}
  84. delete_group_response = {'responses':[{"command":"deleteGroup", "correlationData":"5678"}]}
  85. rc = 1
  86. keepalive = 10
  87. connect_packet = mosq_test.gen_connect("ctrl-test", keepalive=keepalive, username="admin", password="admin")
  88. connack_packet = mosq_test.gen_connack(rc=0)
  89. mid = 2
  90. subscribe_packet = mosq_test.gen_subscribe(mid, "$CONTROL/dynamic-security/#", 1)
  91. suback_packet = mosq_test.gen_suback(mid, 1)
  92. try:
  93. os.mkdir(str(port))
  94. shutil.copyfile("dynamic-security-init.json", "%d/dynamic-security.json" % (port))
  95. except FileExistsError:
  96. pass
  97. broker = mosq_test.start_broker(filename=os.path.basename(__file__), use_conf=True, port=port)
  98. try:
  99. sock = mosq_test.do_client_connect(connect_packet, connack_packet, timeout=5, port=port)
  100. mosq_test.do_send_receive(sock, subscribe_packet, suback_packet, "suback")
  101. # Add client
  102. command_check(sock, create_client_command, create_client_response)
  103. command_check(sock, create_client2_command, create_client2_response)
  104. # Add group
  105. command_check(sock, create_group2_command, create_group2_response)
  106. command_check(sock, create_group_command, create_group_response)
  107. # Add client to group
  108. command_check(sock, add_client_to_group_command, add_client_to_group_response)
  109. command_check(sock, add_client_to_group2_command, add_client_to_group2_response)
  110. command_check(sock, add_client2_to_group_command, add_client2_to_group_response)
  111. command_check(sock, add_client_to_group_command, add_duplicate_client_to_group_response)
  112. # Get group
  113. command_check(sock, get_group_command, get_group_response)
  114. # List groups non-verbose
  115. command_check(sock, list_groups_command, list_groups_response)
  116. # List groups verbose
  117. command_check(sock, list_groups_verbose_command, list_groups_verbose_response, "list groups")
  118. # List clients verbose
  119. command_check(sock, list_clients_verbose_command, list_clients_verbose_response)
  120. # Kill broker and restart, checking whether our changes were saved.
  121. broker.terminate()
  122. broker.wait()
  123. broker = mosq_test.start_broker(filename=os.path.basename(__file__), use_conf=True, port=port)
  124. sock = mosq_test.do_client_connect(connect_packet, connack_packet, timeout=5, port=port)
  125. mosq_test.do_send_receive(sock, subscribe_packet, suback_packet, "suback")
  126. # Add duplicate group
  127. command_check(sock, create_group_command, create_group_repeat_response)
  128. # Remove client from group
  129. command_check(sock, remove_client_from_group_command, remove_client_from_group_response)
  130. # Add client back to group
  131. command_check(sock, add_client_to_group_command, add_client_to_group_response)
  132. # Delete group entirely
  133. command_check(sock, delete_group_command, delete_group_response)
  134. rc = 0
  135. sock.close()
  136. except mosq_test.TestError:
  137. pass
  138. finally:
  139. os.remove(conf_file)
  140. try:
  141. os.remove(f"{port}/dynamic-security.json")
  142. except FileNotFoundError:
  143. pass
  144. os.rmdir(f"{port}")
  145. broker.terminate()
  146. broker.wait()
  147. (stdo, stde) = broker.communicate()
  148. if rc:
  149. print(stde.decode('utf-8'))
  150. exit(rc)