gateway-update.py 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180
  1. #!/bin/env python
  2. #coding=utf-8
  3. #edite panwang
  4. #旧版发布脚本 添加到git
  5. import docker
  6. import sys
  7. import requests
  8. import json
  9. import queue
  10. import threading
  11. from aliyunsdkcore import client
  12. from aliyunsdkecs.request.v20140526.DescribeNetworkInterfacesRequest import DescribeNetworkInterfacesRequest
  13. from aliyunsdkcore.request import CommonRequest
  14. from aliyunsdkslb.request.v20140515.DescribeLoadBalancerAttributeRequest import DescribeLoadBalancerAttributeRequest
  15. import time
  16. AccessKey = 'LTAIuPbTPL3LDDKN'
  17. AccessSecret = 'ORcNedKwWuwVtcq4IRFtUDZgS0b1le'
  18. RegionId = 'cn-hangzhou'
  19. version = sys.argv[1]
  20. # slbIDs = ['lb-bp1jtzhp9krunyv3mim2q','lb-bp1mfk1gmd47twfh6bgwv']
  21. slbIDs = ["lb-bp1mfk1gmd47twfh6bgwv", "lb-bp1jtzhp9krunyv3mim2q", "lb-bp1jijiyb925dk26ofm8h","lb-bp19a14ptmw1b7nwejvej","lb-bp15xf7asp620927z3lgr","lb-bp1i24x4sdfjbbuo8n1be","lb-bp153yk5n4szt6q8wzloy","lb-bp1s5c004pwnfu1beebye"]
  22. apps = 'piaoquan-gateway'
  23. repository = 'registry-vpc.cn-hangzhou.aliyuncs.com/stuuudy/{}'.format(apps)
  24. registry = 'registry-vpc.cn-hangzhou.aliyuncs.com/stuuudy/{}:{}'.format(apps, version)
  25. clt = client.AcsClient (AccessKey, AccessSecret, RegionId)
  26. class MyThread (threading.Thread):
  27. def __init__(self, func):
  28. threading.Thread.__init__ (self)
  29. self.func = func
  30. def run(self):
  31. self.func ()
  32. def checkHealth(ipadd):
  33. while True:
  34. health_url = 'http://%s:9000/healthcheck' %(ipadd)
  35. header = {"Content-Type":"application/json"}
  36. try:
  37. health_code = requests.get(health_url).status_code
  38. except Exception as e:
  39. continue
  40. if health_code == 200:
  41. print("httpcode 200,开始挂载流量")
  42. return False
  43. #服务更新完之后逐步修改服务器的权重值,直接加载100会出现502。权重值每次增加10,每2s修改一次
  44. def setInstanceWeightProcess(slb_id, instance_id):
  45. for i in range(1,6):
  46. weight = i*20
  47. setWeight(slb_id,instance_id,weight)
  48. print("slb_id:"+slb_id+",当前权重:", weight)
  49. time.sleep(5)
  50. #设置权重 instance_id :服务器id,weight:权重值
  51. def setWeight(slb_id,instance_id ,weight):
  52. BackendServers = [{"ServerId": instance_id, "Weight": weight}]
  53. request = CommonRequest ()
  54. request.set_accept_format ('json')
  55. request.set_domain ('slb.aliyuncs.com')
  56. request.set_version ('2014-05-15')
  57. request.set_method ('POST')
  58. request.set_action_name ('SetBackendServers')
  59. request.add_query_param ('BackendServers', BackendServers)
  60. request.add_query_param ('LoadBalancerId', slb_id)
  61. try:
  62. response = clt.do_action (request)
  63. except Exception as e:
  64. print (e)
  65. def getInstanceId(slb_id):
  66. request = DescribeLoadBalancerAttributeRequest()
  67. request.set_accept_format('json')
  68. request.set_LoadBalancerId(slb_id)
  69. response = clt.do_action_with_exception(request)
  70. return json.loads (response)
  71. #获取实例IP地址
  72. def getIpadd(instance_id):
  73. request = DescribeNetworkInterfacesRequest()
  74. request.set_accept_format('json')
  75. request.set_InstanceId(instance_id)
  76. response = clt.do_action_with_exception(request)
  77. request_content = json.loads(response)
  78. IpAddr = request_content['NetworkInterfaceSets']['NetworkInterfaceSet'][0]['PrivateIpAddress']
  79. return IpAddr
  80. #更新服务
  81. def update(instance_id):
  82. time.sleep(10)
  83. global success_count
  84. ipadd = getIpadd(instance_id)
  85. print("服务器信息:" + "%s/%s" %(instance_id, ipadd))
  86. client = docker.DockerClient(base_url='tcp://%s:2375' %(ipadd),timeout=60 )
  87. try:
  88. #更新前移除旧的容器
  89. id = client.containers.get(apps)
  90. id.remove(force = True)
  91. except Exception as e:
  92. print("容器不存在或者无法删除当前容器")
  93. try:
  94. #登录镜像仓库
  95. client.login(username='stuuudys' ,password='Qingqu@2019', registry='registry-vpc.cn-hangzhou.aliyuncs.com')
  96. #启动一个容器
  97. client.containers.run(registry, detach = True, cap_add = 'SYS_PTRACE', network_mode = 'host', name = apps,volumes={'/datalog/': {'bind': '/datalog/', 'mode': 'rw'}})
  98. print("开始健康检查")
  99. checkHealth(ipadd)
  100. print("%s :权重修改中......" %(ipadd))
  101. for slbID in slbIDs:
  102. setInstanceWeightProcess(slbID, instance_id)
  103. success_count = success_count + 1
  104. print("更新进度" + "%s/%s" %(success_count, total))
  105. except Exception as e:
  106. print(e)
  107. sys.exit()
  108. #容器启动失败立即退出更新
  109. def pull_image():
  110. instanceId = q1.get()
  111. ipaddr = getIpadd(instanceId)
  112. cd_url = "tcp://{}:2375".format(ipaddr)
  113. client = docker.DockerClient(base_url=cd_url, timeout=30)
  114. try:
  115. client.images.pull(repository, tag=version)
  116. print(ipaddr, "pull images success ")
  117. return True
  118. except Exception as e:
  119. print(e, "images pull fail")
  120. return False
  121. if __name__ == '__main__':
  122. #更新完成计数
  123. success_count = 0
  124. threads = []
  125. res = getInstanceId (slbIDs[0])
  126. #slb下服务器总数
  127. total = len(res["BackendServers"]["BackendServer"])
  128. InstanceIDs = []
  129. q1 = queue.Queue()
  130. if res["BackendServers"]["BackendServer"]:
  131. for i in range ((len (res["BackendServers"]["BackendServer"]))):
  132. InstanceID = res["BackendServers"]["BackendServer"][i]["ServerId"]
  133. InstanceIDs.append(InstanceID)
  134. q1.put(InstanceID)
  135. print(InstanceIDs)
  136. #多线程预先pull images
  137. for i in range (len(InstanceIDs)):
  138. thread = MyThread (pull_image)
  139. thread.start ()
  140. threads.append(thread)
  141. for thread in threads:
  142. thread.join ()
  143. #单线程更新
  144. for instanceID in InstanceIDs:
  145. for slbID in slbIDs:
  146. setWeight(slbID,instanceID,0)
  147. update(instanceID)