공부하기싫어
article thumbnail

 

1. cdk 컨테이너 초기화 후 정상 실행 확인 (간단한 lambda 함수 하나)

2. jenkins-container 연결 (ansible 연결 + ssh 설치 + 인벤토리 등록)

3. pipeline 생성

4. jenkinsfile 작성 후 commit - hook - deploy 확인

 

 

1. cdk 컨테이너 초기화 후 정상 실행 확인 (간단한 lambda 함수 하나)

이전에 만들었던 dockerfile 로 빌드한 cdk 컨테이너에서 작업할꺼다

bootstrapping 까지 확인해보고 이후 dynamoDB 아이템을 수정하는 간단한 람다 함수를 넣어서 deploy 해보고

jenkins 컨테이너와 pipeline 으로 연결한 뒤

항목 값을 바꿔서 commit test 를 진행해볼 예정

 

docker run

ubuntu@jenkins-server:~$ docker run -it -d --name CDK cyaninn/awscdk_python:23.03.v1
9cef21a7593193cd0005def4febbed8c50a67ee586efe78a07173761a6e1434a

이전에 만든 이미지로 빌드해줬다.

aws-cli, aws-cdk 가 설치되어있고 ethereum_autotrade 디렉토리 안에 python 으로 cdk 가 초기화되어있는 상태이다.

 

aws configure 를 해줬다

 

 

dynamoDB table

간단하게 하나 만들어주고 현재 날자와 시간으로 값을 넣어줬다

 

 

 

demo_function_stack.py

from aws_cdk import (
    aws_lambda as lambda_,
    aws_dynamodb as dynamodb,
    aws_iam as iam,
    Duration, Stack
)
from constructs import Construct

class EthereumAutotradeStack(Stack):

    def __init__(self, scope: Construct, id: str, **kwargs) -> None:
        super().__init__(scope, id, **kwargs)

        table_name='dev-general-table'
        # Get a reference to the existing DynamoDB table
        table = dynamodb.Table.from_table_name(self, "DemoTable", table_name)

        # Create Lambda function
        function = lambda_.Function(self, "DemoFunction",
                                    runtime=lambda_.Runtime.PYTHON_3_8,
                                    code=lambda_.Code.from_asset("lambda"),
                                    handler="handler.main",
                                    timeout=Duration.seconds(10),
                                    memory_size=256,
                                    environment={
                                        'TABLE_NAME': table.table_name
                                    })

        # Grant necessary permissions to Lambda function to update DynamoDB table
        table.grant_write_data(function)

        # Grant necessary permissions for Lambda execution role
        function_role = function.role
        function_role.add_managed_policy(iam.ManagedPolicy.from_aws_managed_policy_name('service-role/AWSLambdaBasicExecutionRole'))
        function_role.add_managed_policy(iam.ManagedPolicy.from_aws_managed_policy_name('AmazonDynamoDBFullAccess'))

chatGPT 로 생성해보려고 했으나 계속 cdk verison1 으로 생성해줘서 그냥 aws github 를 보면서 대충 만들었다.

chatGPT 가 aws-cdk python 을 잘 모르는것 같다

 

demo_function_lambda.py from chatGPT

import boto3

def handler(event, context):
    # Get a reference to the DynamoDB table
    table_name = 'dev-general-table'
    partition_key_value = 'ethereum_autotrade'

    dynamodb = boto3.resource('dynamodb')
    table = dynamodb.Table(table_name)

    # Update the attribute value for the specified entry
    response = table.update_item(
        Key={
            'id': partition_key_value
        },
        UpdateExpression='SET demo_value = :val',
        ExpressionAttributeValues={
            ':val': 2303231043
        }
    )

    return {
        'statusCode': 200,
        'body': 'Attribute value updated successfully'
    }

이렇게 함수를 띄워서 bootstrap 후 deploy 해봤더니 스택은 잘 생성이 되었는데

함수 테스트를 해보니 실행이 안됬다

 

 

Response
{
  "errorMessage": "Unable to import module 'handler': No module named 'handler'",
  "errorType": "Runtime.ImportModuleError",
  "stackTrace": []
}

 

 

진짜 왜 이러는지 모르겠다

 

 

 

 

2. jenkins container 연결

jenkins 비밀번호 찾기

jenkins server 비밀번호를 까먹어서 재설정해주려고 한다

ubuntu container 로 jenkins 를 사용하고 있다

경로는 /var/jenkins-home/config.xml

<?xml version='1.1' encoding='UTF-8'?>
<hudson>
  <disabledAdministrativeMonitors>
    <string>jenkins.diagnostics.ControllerExecutorsNoAgents</string>
  </disabledAdministrativeMonitors>
  <version>2.381</version>
  <numExecutors>2</numExecutors>
  <mode>NORMAL</mode>
  <useSecurity>false</useSecurity>

false 로 바꿔주고

 

ip:8080 으로 들어가면 비밀번호 없이 들어갈 수 있다

보안설정으로 들어가서

 

security realm

jenkins' own user database 로 바꿔주고

manage users

여기로 들어가서 admin 비밀번호를 바꿔줬다

임시 비밀번호로 되어있었나보다

 

 

Ansible 연결

현재 jenkins-server instance 안에 jenkins-conatiner 와 cdk-container 가 있다.

jenkins container 에는 ansible 이 이미 설치되어있기 때문에 새로 생성된 cdk 에 ssh 를 허용해주고 비밀번호로 접근할 수 있게 했다

 

apt-get install -y openssh-server

passwd
vim /etc/ssh/sshd_config
Include /etc/ssh/sshd_config.d/*.conf

Port 22
#AddressFamily any
#ListenAddress 0.0.0.0
#ListenAddress ::

#HostKey /etc/ssh/ssh_host_rsa_key
#HostKey /etc/ssh/ssh_host_ecdsa_key
#HostKey /etc/ssh/ssh_host_ed25519_key

# Ciphers and keying
#RekeyLimit default none

# Logging
#SyslogFacility AUTH
#LogLevel INFO

# Authentication:

#LoginGraceTime 2m
PermitRootLogin yes

위처럼 config 파일을 수정해주고

 

service ssh status
service ssh restart

ssh 를 실행해줬다

 

jenkins-server 에서 CDK 컨테이너의 ip 를 확인해줘야 한다

ubuntu@jenkins-server:~$ docker inspect -f "{{ .NetworkSettings.IPAddress }}" CDK
172.17.0.2

 

ansible 명령을 위해 인벤토리 파일을 jenkins-container 의 home 디렉토리 아래에 생성해줫다.

[serverless]
ansible_host=172.17.0.2

 

jenkins-container 에서 ssh key 를 만들어주고 cdk-container 로 붙여줬다

root@e983e40cb20b:/# ssh-copy-id 172.17.0.2
/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/root/.ssh/id_rsa.pub"
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed
/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted now it is to install the new keys
root@172.17.0.2's password: 
Permission denied, please try again.
root@172.17.0.2's password: 

Number of key(s) added: 1

Now try logging into the machine, with:   "ssh '172.17.0.2'"
and check to make sure that only the key(s) you wanted were added.

 

이후 간단히 핑테스트

root@e983e40cb20b:/home# ansible -m ping serverless -i Inventory.ini
[WARNING]: Invalid characters were found in group names but not replaced, use -vvvv to see details
172.17.0.2 | SUCCESS => {
    "ansible_facts": {
        "discovered_interpreter_python": "/usr/bin/python3"
    },
    "changed": false,
    "ping": "pong"
}
root@e983e40cb20b:/home#

 

 

 

3. jenkins pipeline 생성

cdk container 와 git repo 간의 pipeline 을 만들자

 

github credential 생성

pipeline 생성

pipeline
definition

credentials 을 설정해주고 브랜치를 main 으로 바꿔줫다

github-webhook

jenkins 서버 ip 와 port 로 접근하게 해줬다

trigger

트리거도 github hook 으로 설정

 

 

 

4. Jenkinsfile 작성 후 build 확인

Jenkinsfile

3개의 스테이지를 만들어서 해볼 예정이다

github 로 push 되면 hook 을 트리거 시켜서 jenkins container 에서 cdk container 로 ansible 을 전달할꺼다

 

pipeline {
  agent any

  stages {
    // cdk container 에서 github repo 를 클론한다.
    stage('Git pull') {
      steps {
        dir("/home") {
            sh "pwd"
            sh 'ansible serverless -a "chdir=/home"'
            sh 'ansible serverless -i Inventory.ini -m shell -a "pwd"'
            sh 'ansible serverless -i Inventory.ini -m shell -a "rm -rf /home/Cryptocurrency-autotrade-pyupbit-prod-cicd-CDK && git clone https://github.com/cyaninn-entj/Cryptocurrency-autotrade-pyupbit-prod-cicd-CDK.git"'
        }
      }
      post {
        failure {
          echo 'Git pull failure'
        }
        success {
          echo 'Git pull success'
        }
      }
    }

    // 클론한 stack.py 와 lambda.py 들을 각각의 디렉토리로 이동
    stage('moving files into a directory') {
      steps {
        dir("/home") {
            sh 'ansible serverless -i Inventory.ini -m shell -a "mv /home/Cryptocurrency-autotrade-pyupbit-prod-cicd-CDK/ethereum_autotrade_stack.py /home/ethereum_autotrade/ethereum_autotrade/"'
            sh 'ansible serverless -i Inventory.ini -m shell -a mv /home/Cryptocurrency-autotrade-pyupbit-prod-cicd-CDK/demo_function.py /home/ethereum_autotrade/lambda/ "'
        }
      }
      post {
        failure {
          echo 'moving files into a directory failure'
        }
        success {
          echo 'moving files into a directory success'
        }
      }
    }  

    // cdk deploy 실행
    stage('cdk deploy') {
      steps {
        dir("/home") {
            sh 'ansible serverless -i Inventory.ini -m shell -a "cdk deploy" -u remote_user --become-user=root --chdir=/home/ethereum_autotrade'
        }
      }
      post {
        failure {
          echo 'cdk deploy failure'
        }
        success {
          echo 'cdk deploy success'
        }
      }
    }


  }//stages end
}//pipeline end

 

이렇게 저렇게 해보는데 잘 안된다

ansible ad-hoc 으로 해보려고 했는데 작업디렉토리 지정하는 것에서 막혔다.