Use RFC8040 URL for DAEXIM tests
[integration/test.git] / csit / libraries / ClusterStateLibrary.py
1 import SettingsLibrary
2 from time import sleep
3 import UtilLibrary
4 import json
5 import sys
6
7
8 __author__ = "Basheeruddin Ahmed"
9 __copyright__ = "Copyright(c) 2014, Cisco Systems, Inc."
10 __license__ = "New-style BSD"
11 __email__ = "syedbahm@cisco.com"
12
13
14 def getClusterRoles(
15     shardName, numOfShards=3, numOfTries=3, sleepBetweenRetriesInSecs=3, port=8181, *ips
16 ):
17     """Given a shardname (e.g. shard-inventory-config), number of shards and bunch of ips
18
19     determines what role each ip has in an Akka (Raft based) cluster
20     result would look like
21     {'10.194.126.118':'Leader', '10.194.126.118':'Follower', '10.194.126.117': None}
22     """
23     dict = {}
24     for ip in ips:
25         i = 1
26         dict[ip] = None
27         print("numOfShards => ", str(numOfShards))
28         while i <= numOfShards:
29             shardMemberName = "member-" + str(i) + "-" + shardName
30             j = 1
31             print("j => ", str(j))
32             print("numOfTries => ", str(numOfTries))
33             while int(j) <= int(numOfTries):
34                 print("Try number " + str(j))
35                 try:
36                     print(
37                         "getting role of " + ip + "  for shardName = " + shardMemberName
38                     )
39                     url = SettingsLibrary.getJolokiaURL(
40                         ip, str(port), str(i), shardName
41                     )
42                     print(url)
43                     resp = UtilLibrary.get(url)
44                     print(resp)
45                     if resp.status_code != 200:
46                         sleep(sleepBetweenRetriesInSecs)
47                         continue
48                     print(resp.text)
49                     data = json.loads(resp.text)
50                     if "value" in data:
51                         dataValue = data["value"]
52                         print("datavalue RaftState is", dataValue["RaftState"])
53                         dict[ip] = dataValue["RaftState"]
54                 except Exception:
55                     e = sys.exc_info()[0]
56                     print(
57                         "Try"
58                         + str(j)
59                         + ":An error occurred when finding leader on"
60                         + ip
61                         + " for shardName:"
62                         + shardMemberName
63                     )
64                     print(e)
65                     sleep(sleepBetweenRetriesInSecs)
66                     continue
67                 finally:
68                     j = j + 1
69             if dict[ip] is not None:
70                 break
71             i = i + 1
72     return dict
73
74
75 def isRole(
76     role, shardName, ipAddress, numOfShards=3, numOfRetries=1, sleepFor=3, port=8181
77 ):
78     """Given a role (Leader, Follower, Candidate, or IsolatedLeader),
79     shardname (e.g. shard-inventory-config), controller IP address,
80     and number of shards on the controller,this function determines if the controller,
81     has that role for the specified shard.
82     """
83     ip = getClusterRoles(
84         shardName, numOfShards, numOfRetries, sleepFor, port, ipAddress
85     )
86     print(ip)
87     if ip[ipAddress] == role:
88         return True
89     return False
90
91
92 def getLeader(
93     shardName, numOfShards=3, numOfTries=3, sleepBetweenRetriesInSecs=1, port=8181, *ips
94 ):
95     """Returns the leader of the shard given a set of IPs Or None"""
96     for i in range(3):  # Try 3 times to find a leader
97         dict = getClusterRoles(
98             shardName, numOfShards, numOfTries, sleepBetweenRetriesInSecs, port, *ips
99         )
100         for ip in dict.keys():
101             if dict[ip] == "Leader":
102                 return ip
103     return None
104
105
106 def getFollowers(
107     shardName, numOfShards=3, numOfTries=3, sleepBetweenRetriesInSecs=1, port=8181, *ips
108 ):
109     """Returns the follower list of a shard given a set of IPs Or []"""
110     for i in range(6):  # Try 6 times to find all followers
111         dict = getClusterRoles(
112             shardName, numOfShards, numOfTries, sleepBetweenRetriesInSecs, port, *ips
113         )
114         result = []
115
116         for ip in dict.keys():
117             if dict[ip] == "Follower":
118                 result.append(ip)
119         print("i=%s result=%s" % (i, result))
120         if len(result) == (len(ips) - 1):
121             break
122         sleep(1)
123     return result
124
125
126 def testGetClusterRoles():
127     dict = getClusterRoles(
128         "shard-inventory-config",
129         3,
130         1,
131         1,
132         8181,
133         "10.194.126.116",
134         "10.194.126.117",
135         "10.194.126.118",
136     )
137     print(dict)
138
139     for ip in dict.keys():
140         if isRole("Leader", "shard-inventory-config", 3, 1, 1, 8181, ip):
141             print(ip + " is Leader")
142         elif isRole("Follower", "shard-inventory-config", 3, 1, 1, 8181, ip):
143             print(ip + " is follower")
144         else:
145             print(ip + " seems to have value " + str(dict[ip]))
146
147
148 def testGetLeader():
149     leader = getLeader(
150         "shard-inventory-config",
151         3,
152         1,
153         1,
154         8181,
155         "10.194.126.116",
156         "10.194.126.117",
157         "10.194.126.118",
158     )
159     print(leader)
160     return leader
161
162
163 def testGetFollowers():
164     followers = getFollowers(
165         "shard-inventory-config",
166         3,
167         1,
168         1,
169         8181,
170         "10.194.126.116",
171         "10.194.126.117",
172         "10.194.126.118",
173     )
174     print(followers)
175     return followers
176
177
178 # testGetClusterRoles()
179 # testGetLeader()
180 # testGetFollowers()