Khi quá trình deploy trở lên phức tạp và mất thời gian để làm nhiều thứ, lúc đó các bạn nên nghĩ đến giải pháp tự động deploy.

Bằng cách này, bạn không phải quan tâm tới việc deploy mỗi lần nữa mà mọi thay đổi sẽ được tự động deploy lên server cho bạn mỗi khi bạn thay đổi code của mình.

Ví dụ khi hệ thống của bạn sử dụng các dịch vụ của AWS như EC2, ECS, Cloudfront, S3,... thì sẽ rất mất nhiều thời gian để bạn deploy thủ công bằng tay. Tự động deploy giúp bạn không còn phải quan tâm gì nữa, hệ thống sẽ tự động làm cho bạn tất cả :))))

Quá trình deploy này sử dụng circleCI https://circleci.com/

1. Yêu cầu.

- Nắm được cách sử dụng cơ bản circleCI.

 

2. Thứ tự và ý tưởng.

 

Tùy vào từng hệ thống mà ý tưởng và cách làm khác nhau, mình sẽ giới thiệu cách làm mình biết. Ví dụ khi bạn muốn tạo một server tên là A với các thay đổi của code mới nhất, thứ tự như sau:

- Khi push code lên github thì github sẽ trigger circleCI để circleCI chạy deploy.

circleCI sẽ thực thi một file deploy (tên file là deploy.sh chẳng hạn) nằm trên deploy server S (S là server chứa môi trường đã được cài đặt sẵn để có thể thực thi file deploy.sh, S luôn luôn chạy và không bao giờ bị tắt dù có deploy xong đi chăng nữa).

- File deploy.sh này sẽ chứa script do bạn viết để deploy server A cho bạn, mọi thứ liên quan tới thiết lập deploy server sẽ được thực thi từ file này.

 

Để làm được quá trình trên thì cần phải:

- Thiết lập để github có thể gọi thực thi circleCI khi có code mới được push lên.

- Thiết lập để circleCI có thể gọi tới file deploy.sh trên deploy server S

- Trong quá trình deploy trên server SS cần phải pull code mới về nên phải thiết lập để server S có thể pull code trên github.

 

a. Thiết lập để github có thể gọi thực thi circleCI khi có code mới được push lên.

- Vào circleCI và add project tương ứng của bạn vào.

- Thêm file circle.yml vào root project của bạn. Nội dung file circle.yml là thiết lập môi trường trên circleCI và câu lệnh thực thi khi từ circleCI gọi tới deploy server S. Nội dung file đó có thể như sau:

machine:
  timezone: Asia/Tokyo
  environment:
    PATH: "$PATH:~/$CIRCLE_PROJECT_REPONAME/bin"
  ruby:
    version: 2.3.1
  services:
    - docker
dependencies:
  pre:
    - sudo pip install awscli
deployment:
  deploy:
    branch: [master, develop]
    commands:
      - ssh [email protected] deploy.sh "$CIRCLE_PROJECT_USERNAME/$CIRCLE_PROJECT_REPONAME" $CIRCLE_BRANCH $CIRCLE_SHA1

+ Thời gian timezone là Aisa/Tokyo

+ Export thư mục bin trong project

+ set version của ruby và set cho cirlceCI sử dụng docker.

+ Thiết lập git branch là master và develop để chỉ khi push code vào 2 nhánh này mới tự động deploy.

+ commands là lệnh để gọi thực thi file deploy.sh trên deploy server S (ở đây deploy server tên là daovanhung.com, username là ec2-user vì mình sử dụng deploy server là EC2 của AWS)

 

b. Thiết lập để circleCI có thể gọi tới file deploy.sh trên deploy server S

- Tạo file ssh để tạo kết nối giữa circleCI và server S

Bạn cần tạo một file ssh, có thể tạo bằng câu lệnh sau: 

ssh-keygen -t rsa -b 4096 -C "[email protected]"

 

Khi bị yêu cầu nhập passphrase thì bạn không gõ gì và ấn enter nhé.

Sẽ có 2 file được tạo ra cho bạn, một file là khóa bí mật id_rsa và một file là khóa công khai id_rsa.pub  . Bạn có thể đổi tên 2 file này theo ý muốn, ví dụ đổi thành your_private_key.pem và your_public_key.pem.pub 

- Bạn đưa file id_rsa đặt vào server S làm khóa bí mật. Trên circleCI trong phần setting cho project bạn tạo SSH Permission có title là tên deploy server "daovanhung.com" (từ nay S và daovanhung.com là giống nhau nhé :)))) và có value chính là nội dung file id_rsa

Chỉ cần thế thôi là circleCI đã có thể ssh vào deploy server daovanhung.com được rồi.

 

c. Thiết lập để server S có thể pull code trên github.

- Tạo file ssh khác như phần trên.

- Copy file id_rsa vào  ~/.ssh/your_private_key_abcxyz.pem trên server S

- Vào Add deploy keys trong phần setting -> Deploy keys trên github và thêm public key với title là your_private_key_abcxyz, value là nội dung file id_rsa.pub nhé.

 

3. Một số vấn đề.

Quá trình trên khó khăn nhất vẫn là công sức để bạn viết file deploy.sh . Nếu file deploy.sh đã ổn định thì bạn có thể đặt cố định trong server S nhưng sẽ thế nào nếu file deploy.sh này được sửa nhiều lần?

Trong trường hợp file deploy.sh và các file liên quan tới quá trình deploy trên S được sửa nhiều lần thì thay vì bạn phải copy bằng tay lên S, bạn nên tạo một project chứa các file deploy, project này cũng trigger circleCI. Mỗi khi các file deploy này được push lên git thì circleCI sẽ lại gọi tới server S thực thi để copy các file này lên aws S3. Khi các file deploy này được quản lý trên S3 rồi thì khi deploy các project khác, S phải download các file này về và thực thi chúng.

Có thể đơn giản bằng mô hình sau, giả sử task_scripts là project mình chứa các file liên quan tới deploy cho các server, project1 và project2 là 2 project mình cần tự động deploy (task_scripts cũng là project tự động deploy):

Edit task_scripts -> push github  -> trigger -> trên S: download task_scripts files from github -> upload task_scripts to private S3 bucket (named S3_scripts)

project1 -> push git -> trigger -> download project1 from github and download task_scripts files from S3_scripts -> exec task_scripts files

project2 -> push git -> trigger ->download project2 from github and download task_scripts files from S3_scripts -> exec task_scripts files