[DevOps] ec2-gazua 사용법 및 커스터마이징
안녕하세요? 정리하는 개발자 워니즈입니다. 이번 시간에는 재미있는 툴을 하나 소개할건데요. 바로 ec2-gazua
입니다. 이름부터가 너무 재밌지 않나요?
인프라 내부 서버에 접속하기 우해서는 보통 Bastion Host
를 통해서 접속하는 경우가 많습니다. 즉, 외부에서 접근 불가능한 Private Subnet에 접근하기 위해 Public Bastion Host를 두어 Bastion Host를 통해 Private Subnet에 접근합니다.
한곳에서 외부의 Input을 관리하고 방화벽도 Bastion Host
를 열어두면 되기때문에 관리적인 차원에서 굉장히 유용합니다.
- B astion Host란 무엇인가요?
배스천 호스는는 침입 차단 소프트웨어가 설치되어 내부와 외부 네트워크 사이에서 일종의 게이트 역할을 수행하는 호스트를 뜻합니다.
제가 수행하는 프로젝트에서도 위와같이 배스천 호스트
를 통해서 내부 서버에 접근을 하는데요. 여기서 귀찮은점이 발견되어 개선포인트를 찾게 되었습니다.
1. 내부 서버에 접근하기 위해..
서론에서 설명 드렸다시피, 내부서버에 접근하기 위해서는 배스천 호스트를 통한다고 했습니다. 보통의 경우는 다음과 같이 서버에 접속합니다.
> ssh 사용자ID@서버아이피 -p포트
위처럼 사용하게 되면, 서버에 대한 정보를 알고있어야 합니다. 수많은 서버를 관리하는 곳에서는 불가능하게 됩니다.
그래서 추가적으로 활용할 수 있는부분은 ~/.ssh/config
를 활용하는 것입니다.
Host disp_a01
HostName 10.0.11.11
User aemuser
Port 20022
PreferredAuthentications password
Host sudodisp_a01
HostName 10.0.11.11
User ec2-user
Port 20022
PreferredAuthentications publickey
IdentityFile /home/aemuser/pem/kp_prd_ap_disp.pem
위와 같이 설정을 하게 되면 다음과 같은 방식으로 접근이 가능합니다.
> ssh disp_a01
여기까지만해도 좀더 편해진 것 같지만, 각 Host에 지정된 이름을 알고있어야 하고, 매번 다시 config 파일을 뒤져서 들어가고 싶은 Host의 Name을 조회했습니다.
2. ec2-gazua 툴 소개
ec2-gazua는 이런부분을 좀더 편하게 개선해준 툴입니다. aws
의 접근 키
와 비밀 키
를 통해서 서버에 대한 정보를 가져오고 카테고라이징을 해줘서 손쉽게 접속할 수 있도록 도와줍니다.
위의 그림에서 보시면 아시겠지만, 모든 목록을 불러오고, 카테고라이징을 해줘서 해당 서버에 대해 선택하고 접속을 하면 손쉽게 들어갈 수 있습니다.
2-2. 설치 방법
- clone
git clone https://github.com/leejaycoke/ec2-gazua.git
cd ./ec2-gazua/
pip install --user -r requirements.txt
설치 요구사항
- tmux
- python 2.x, 3.x
- pip
- AccessKey & SecretKey 등록
앞서 설명 드렸듯이, 접근 키
와 비밀 키
로 접근이 가능합니다. 이를 위해서는 AWS IAM
을 통하여 사용자를 생성해줘야 합니다.
- 사용자 생성
AWS IAM 메뉴에 들어가서 사용자 추가
를 클릭해 줍니다.
- 세부 정보 추가
- 정책 연결
- 키 생성
이제 위에서 생성된 사용자에 대한 접큰 키
와 비밀 키
를 ec2-gazua 설정파일에 등록을 해주면됩니다.
> vi ~/.ec2-gz
파일 내용은 아래와 같고 여기서 aws_access_key_id
와 aws_secret_access_key
에 복사한 Key값을 등록하면 됩니다.
name: minor
ssh-path: ~/.ssh
credential:
aws_access_key_id: access-key # 요기
aws_secret_access_key: secret-key # 요기
region: ap-northeast-2
group-tag: Team
name-tag: Name
filter:
connectable: true
connect-ip:
default: private
key-file:
default: auto
user:
default: ec2-user
키 등록이 끝나셨다면 EC2 접속 권한을 얻기 위해 pem 키를 등록합니다
- pem 파일 등록
기존에 등록해놓은 .pem 파일들이 있어서 그 파일 역시 설정파일에 등록을 해줍니다. 위에서 보시는것처럼 ssh-path
라는 설정갑이 있는데 여기를 다음과 같이 셋팅했습니다.
ssh-path: /home/aemuser/ec2-gazua-pem
- 명령어 지정
> vi ~/.bashrc
접속 명령어는 위의 설정에서 바꾸시면 되고, 아래와 같이 등록을 합니다.
alias ec2system="python {ec2-gauza설치Path}/ec2-gz.py"
실제로는 python 소스를 실행하는 것이고, 해당 명령 내용에 대해서 alias
를 걸어주는 내용입니다.
source ~/.bashrc
이후의 내용을 위와 같이 반영해주고, 해당 명령어로 실행을 합니다.
3. customizing 내용
우선 위의 내용에서 소개 안한 부분이 카테고리를 지정하는 부분인데, 각 아마존 인스턴스 마다 그룹 태그
에 대한 내용이 들어가있어야 합니다.
필자가 속한 프로젝트에서는 Name
태그에 대한 내용만 있어서 실제로 카테고라이징이 정상적으로 되지 않는 문제점이 있었습니다. 그래서 이부분을 파이썬 소스에서 직접 수정 하였습니다.
3-1. 카테고리를 위한 내용 커스터마이징
/ec2-gazua-system/ec2gazua/ec2.py
위의 파일에서 다음부분을 수정하여 카테고리가 정상적으로 되도록 하였습니다.
@property
def group(self):
prd_ids='IDS'
prd_pub='PUB'
prd_dis='DIS'
prd_aut='AUT'
prd_search='_ES'
stg='STG'
etc='ETC'
if prd_ids in self.tags['Name']:
return 'PRD_IDS'
elif prd_aut in self.tags['Name']:
return 'PRD_AUTH'
elif prd_dis in self.tags['Name']:
return 'PRD_DIS'
elif prd_pub in self.tags['Name']:
return 'PRD_PUB'
elif stg in self.tags['Name']:
return stg
elif prd_search in self.tags['Name']:
return 'PRD_ES'
else:
return etc
return self.tags['Name']
@property
def type(self):
return self.instance['InstanceType']
실제로 Name
태그에 대한 내용을 분기하여 적절하게 카테고라이징을 해주는 내용입니다.
3-2. ID/PW 입력 방식 추가 커스터마이징
위의 내용을 시스템 엔지니어만 쓰는게 아니라 개발팀에서도 별도로 접속을 할 수 있도록 제공을 해주고 싶었습니다. 개발팀에서 실제로 운영
서버에 접속을 할때는 ID/PW
를 입력해야했고, 이기능을 추가해야했습니다.
상위의 내용을 그대로 복사하여 경로만 다른곳에 두었습니다.
/ec2-gazua-system/ => /ec2-gazua/
> vi /ec2-gazua/gazua.py
먼저 위의 파일을 열고 , 아래 부분을 수정합니다.
id = 'ec2-user'
=>
id = raw_input('input your id : ')
아이디/패스워드 입력방식으로 변경하기 위해서는 tmux.py
의 내용도 수정이 필요합니다.
> vi /ec2-gazua/tmux.py
def create_tmux_command(ssh_params):
session = create_session_name()
commands = [
"tmux new-session -s %s -d -x 2000 -y 2000" % session,
"tmux send-keys -t %s 'ssh %s@%s -p20022' C-m" % (
session,
ssh_params[0]['user'],
ssh_params[0]['ip_address'],
# ssh_params[0]['key_file'] if ssh_params[0]['key_file'] is not None else 'NOT_FOUND_KEY_FILE'
)
]
if len(ssh_params) > 1:
for i, ssh_param in enumerate(ssh_params[1:]):
commands += [
"tmux split-window -v -t %s" % session,
"tmux send-keys -t %s:0.%d 'ssh %s@%s -p20022' C-m" % (
session,
i + 1,
ssh_param['user'],
ssh_param['ip_address'],
# ssh_param['key_file'] if ssh_params[0]['key_file'] is not None else 'NOT_FOUND_KEY_FILE'
)
]
commands += [
"tmux select-layout 'tiled'",
"tmux set-window-option synchronize-panes on",
"tmux attach -t %s" % session
]
return commands
중간의 다음의 내용을 모두 주석처리합니다.
ssh_params[0]['key_file'] if ssh_params[0]['key_file'] is not None else 'NOT_FOUND_KEY_FILE'
그리고 마지막에 계정 체크를 위해 다음의 내용을 추가합니다.
def run(ssh_params):
if len(ssh_params) > 0 and ssh_params[0]['user'] == "ec2-user":
commands = create_tmux_command_root(ssh_params)
os.system("; ".join(commands))
sys.exit(0)
if len(ssh_params) > 0:
commands = create_tmux_command(ssh_params)
os.system("; ".join(commands))
sys.exit(0)
실제로 접속을 하게되면, 위와 같이 아이디를 입력하게 되고 패스워드를 묻습니다. 최종 적으로 해당 아이디/패스워드로 ssh 접속 명령어를 하게되고, 틀리게되면 접속이 안됩니다.