utils.py 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110
  1. # Copyright: (c) OpenSpug Organization. https://github.com/openspug/spug
  2. # Copyright: (c) <spug.dev@gmail.com>
  3. # Released under the AGPL-3.0 License.
  4. from django_redis import get_redis_connection
  5. from django.conf import settings
  6. from django.db import close_old_connections
  7. from libs.utils import AttrDict, human_time
  8. from apps.repository.models import Repository
  9. from apps.app.utils import fetch_repo
  10. from apps.config.utils import compose_configs
  11. from apps.deploy.helper import Helper
  12. import json
  13. import uuid
  14. import os
  15. REPOS_DIR = settings.REPOS_DIR
  16. BUILD_DIR = settings.BUILD_DIR
  17. def dispatch(rep: Repository, helper=None):
  18. rep.status = '1'
  19. alone_build = helper is None
  20. if not helper:
  21. rds = get_redis_connection()
  22. rds_key = f'{settings.BUILD_KEY}:{rep.spug_version}'
  23. helper = Helper(rds, rds_key)
  24. rep.save()
  25. try:
  26. api_token = uuid.uuid4().hex
  27. helper.rds.setex(api_token, 60 * 60, f'{rep.app_id},{rep.env_id}')
  28. helper.send_info('local', f'\033[32m完成√\033[0m\r\n{human_time()} 构建准备... ')
  29. env = AttrDict(
  30. SPUG_APP_NAME=rep.app.name,
  31. SPUG_APP_KEY=rep.app.key,
  32. SPUG_APP_ID=str(rep.app_id),
  33. SPUG_DEPLOY_ID=str(rep.deploy_id),
  34. SPUG_BUILD_ID=str(rep.id),
  35. SPUG_ENV_ID=str(rep.env_id),
  36. SPUG_ENV_KEY=rep.env.key,
  37. SPUG_VERSION=rep.version,
  38. SPUG_API_TOKEN=api_token,
  39. SPUG_REPOS_DIR=REPOS_DIR,
  40. )
  41. # append configs
  42. configs = compose_configs(rep.app, rep.env_id)
  43. configs_env = {f'_SPUG_{k.upper()}': v for k, v in configs.items()}
  44. env.update(configs_env)
  45. _build(rep, helper, env)
  46. rep.status = '5'
  47. except Exception as e:
  48. rep.status = '2'
  49. raise e
  50. finally:
  51. helper.local(f'cd {REPOS_DIR} && rm -rf {rep.spug_version}')
  52. close_old_connections()
  53. if alone_build:
  54. helper.clear()
  55. rep.save()
  56. return rep
  57. elif rep.status == '5':
  58. rep.save()
  59. def _build(rep: Repository, helper, env):
  60. extend = rep.deploy.extend_obj
  61. extras = json.loads(rep.extra)
  62. git_dir = os.path.join(REPOS_DIR, str(rep.deploy_id))
  63. build_dir = os.path.join(REPOS_DIR, rep.spug_version)
  64. tar_file = os.path.join(BUILD_DIR, f'{rep.spug_version}.tar.gz')
  65. env.update(SPUG_DST_DIR=extend.dst_dir)
  66. if extras[0] == 'branch':
  67. tree_ish = extras[2]
  68. env.update(SPUG_GIT_BRANCH=extras[1], SPUG_GIT_COMMIT_ID=extras[2])
  69. else:
  70. tree_ish = extras[1]
  71. env.update(SPUG_GIT_TAG=extras[1])
  72. fetch_repo(rep.deploy_id, extend.git_repo)
  73. helper.send_info('local', '\033[32m完成√\033[0m\r\n')
  74. if extend.hook_pre_server:
  75. helper.send_step('local', 1, f'{human_time()} 检出前任务...\r\n')
  76. helper.local(f'cd {git_dir} && {extend.hook_pre_server}', env)
  77. helper.send_step('local', 2, f'{human_time()} 执行检出... ')
  78. command = f'cd {git_dir} && git archive --prefix={rep.spug_version}/ {tree_ish} | (cd .. && tar xf -)'
  79. helper.local(command)
  80. helper.send_info('local', '\033[32m完成√\033[0m\r\n')
  81. if extend.hook_post_server:
  82. helper.send_step('local', 3, f'{human_time()} 检出后任务...\r\n')
  83. helper.local(f'cd {build_dir} && {extend.hook_post_server}', env)
  84. helper.send_step('local', 4, f'\r\n{human_time()} 执行打包... ')
  85. filter_rule, exclude, contain = json.loads(extend.filter_rule), '', rep.spug_version
  86. files = helper.parse_filter_rule(filter_rule['data'])
  87. if files:
  88. if filter_rule['type'] == 'exclude':
  89. excludes = []
  90. for x in files:
  91. if x.startswith('/'):
  92. excludes.append(f'--exclude={rep.spug_version}{x}')
  93. else:
  94. excludes.append(f'--exclude={x}')
  95. exclude = ' '.join(excludes)
  96. else:
  97. contain = ' '.join(f'{rep.spug_version}/{x}' for x in files)
  98. helper.local(f'mkdir -p {BUILD_DIR} && cd {REPOS_DIR} && tar zcf {tar_file} {exclude} {contain}')
  99. helper.send_step('local', 5, f'\033[32m完成√\033[0m')
  100. helper.send_step('local', 100, f'\r\n\r\n{human_time()} ** \033[32m构建成功\033[0m **')