.deb File 설치방법

.deb File 설치방법

확장자가 .deb 인 파일은 debian 리눅스에서의 설치파일로, 같은 계열인 ubuntu 에서 손 쉽게 설치 가능합니다.

설치

$ sudo dpkg -i filename.deb 

제거

$ sudo dpkg -r PACKAGE_NAME

보통은 apt-get 을 이용하지만 .deb 파일을 직접 설치할 경우 유용한 명령입니다.

iptables 명령어

iptables 명령어

현재 목록 확인

$ sudo iptables -L

규칙 추가

$ sudo iptables -A INPUT -s 127.0.0.1 -p icmp -j DROP

설명: 들어오는 패킷이 127.0.0.1 의 아이피를 가지고 있고 protocol 이 icmp 면 버려라.

 

번호 확인

$ sudo iptables -L --line-numbers

삭제

$ sudo iptables -D INPUT 3

#iptables #command

iwinv(가상호스팅)에 docker 적용하기

iwinv(가상호스팅)에 docker 적용하기

iwinv 제가 호스팅을 이전했다는 사실은 지난 글에서 이미 언급한 적이 있습니다.

오늘은 iwinv 로 이전하면서 엄청난 고생을 했던 경험에 대한 이야기 및 해결책에 대한 이야기를 적어 보려 합니다.

Environment

  • Ubuntu 16.04 xenial

삽질의 시작

IwinV Manual

iwinv 홈페이지를 가면 이렇게 도커 적용을 하는 것에 대한 매뉴얼이 있습니다만…

가격의 매리트와 docker 적용에 대한 호기심으로 시작한 이 작업이 이렇게 크나큰 고통을 안겨 줄 것이라는 것을 이 때는 몰랐습니다.

사실 저 메뉴얼이 있는걸 확인 하고 docker 적용에 별 어려움이 없을 것이라고 판단했던 것이 제가 서버 이전을 마음 먹은 것에 큰 이유 중 하나이기도 합니다.
물론 iwinv의 메뉴얼은 저를 속였습니다. (물론 회사가 의도친 않았지만…)ㅎㅎㅎ

이유인 즉, 저 매뉴얼은 반 쪽짜리 매뉴얼 이었기 때문입니다.

물론 간단히 하나의 도커파일만으로 사용할 경우는 별 문제가 없을 지도 모르겠습니다만,
도커 이미지간에 네트웍 통신에는 치명적 문제가 있었습니다.

MTU

위의 매뉴얼 링크를 클릭해보시면 아시겠지만, iwinv는 내부적으로 MTU1450으로 사용하고 있다고 합니다. 이리하여 도커의 MTU 설정을 변경해줘야 한다는 것이 저 글의 요지입니다.

자, 그럼 MTU가 무엇이냐하면,

컴퓨터 네트워킹에서, 레이어의 커뮤니케이션 프로토콜의 최대 전송 단위(maximum transmission unit, MTU)란 해당 레이어가 전송할 수 있는 최대 프로토콜 데이터 단위의 크기(바이트)이다.

최대 전송 단위 – 위키백과, 우리 모두의 백과사전

간단히 말해 네트워크 통신에서의 패킷 사이즈를 결정하는 단위라고 생각하면 될 듯 합니다.

이때는 “아 패킷 사이즈를 iwinv가 적게 쓰는 구나.” 하고 넘어갔습니다.

Docker 설치

매뉴얼대로 도커를 설치합니다.
물론 이 포스팅에서는 매뉴얼과 docker 홈페이지를 적절히 이용해서 설치하겠습니다.
현 시점에서의 설치방법입니다. (2017.6)

먼저 apt-get 업데이트를 합니다.

$ sudo apt-get update
$ sudo apt-get upgrade

도커 설치는 공식페이지를 참고합니다.

오래된 버전의 docker 가 있다면 지웁니다.

$ sudo apt-get remove docker docker-engine

docker 설치에 필요한 패키지를 설치합니다.

$ sudo apt-get install \
apt-transport-https \
ca-certificates \
curl \
software-properties-common

docker 의 공식 GPG key를 추가합니다.

$ curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -

키를 확인합니다.
9DC8 5822 9FC7 DD38 854A E2D8 8D81 803C 0EBF CD88

$ sudo apt-key fingerprint 0EBFCD88

pub 4096R/0EBFCD88 2017-02-22
Key fingerprint = 9DC8 5822 9FC7 DD38 854A E2D8 8D81 803C 0EBF CD88
uid Docker Release (CE deb) <docker@docker.com>
sub 4096R/F273FCD8 2017-02-22

amd64 architecture 를 사용하는 docker 를 설치하겠습니다.

$ sudo add-apt-repository \
"deb [arch=amd64] https://download.docker.com/linux/ubuntu \
$(lsb_release -cs) \
stable"

Docker 가 설치가 잘 되었는지 확인

$ sudo docker run hello-world

...
Hello from Docker!
This message shows that your installation appears to be working correctly.

여기서부터 iwinv의 메뉴얼을 따릅니다.

$ sudo docker pull ubuntu
$ sudo docker run -it ubuntu

※ update가 진행이 안되는 문제 발생하며 ftp 등 일부 서비스에서 문제 발생.

위 증상은 MTU 때문입니다.
이제 MTU를 1450으로 세팅합니다.

$ cp /lib/systemd/system/docker.service /etc/systemd/system/docker.service
$ vi /etc/systemd/system/docker.service

/etc/systemd/system/docker.service

[Unit]
Description=Docker Application Container Engine
Documentation=https://docs.docker.com
After=network.target docker.socket firewalld.service
Requires=docker.socket

[Service]
Type=notify
# the default is not to use systemd for cgroups because the delegate issues still
# exists and systemd currently does not support the cgroup feature set required
# for containers run by docker
ExecStart=/usr/bin/dockerd -H fd:// --mtu=1450
#-H fd://
ExecReload=/bin/kill -s HUP $MAINPID
LimitNOFILE=1048576
# Having non-zero Limit*s causes performance problems due to accounting overhead
# in the kernel. We recommend using cgroups to do container-local accounting.
LimitNPROC=infinity
LimitCORE=infinity
# Uncomment TasksMax if your systemd version supports it.
# Only systemd 226 and above support this version.
TasksMax=infinity
TimeoutStartSec=0
# set delegate yes so that systemd does not reset the cgroups of docker containers
Delegate=yes
# kill only the docker process, not all processes in the cgroup
KillMode=process

[Install]
WantedBy=multi-user.target

ExecStart=/usr/bin/dockerd -H fd:// —mtu=1450

이렇게 변경 후에 아래 명령 실행합니다.

$ sudo systemctl daemon-reload
$ sudo service docker restart

이제 이 전의 명령을 다시 실행해봅니다.

$ sudo docker run -it ubuntu

진행이 정상적으로 되는 것을 확인 할 수 있습니다.

Docker compose

여기까지 설치했다면 iwinv의 메뉴얼 대로 잘 설치된 상황입니다.

허나 함정이 있습니다.
바로 docker-compose를 사용하게 될 때의 문제인데요.

먼저 docker-compose를 알아봅시다.

docker compose 란 간단히 말해서 docker application을 이용한 서비스 환경 구축을 손쉽게 도와주는 tool 이라고 생각하시면 됩니다.

일반적으로 web service 구축을 위해선 web application 과 database 가 필요할 것입니다.
docker compose 는 이 둘을 한번에 구성하기 위한 툴로 보시면 됩니다.

설치방법은 아래 링크를 참고하세요.
docker-compose 설치

docker compose를 설치하고 docker-compose.yml 파일을 작성 후 docker로 서비스를 구축합니다. 여기서는 wordpress 를 구축했습니다.

docker-wordpress-nginx/docker-compose.yml at master · 9to6/docker-wordpress-nginx · GitHub

깃허브 소스를 참고하시면 됩니다.

docker-compose.yml

version: "3.2"
services:
web:
build: .
ports:
- "80:80"
volumes:
- wordpress:/var/www/html
depends_on:
- php
php:
image: wordpress:4.8-php7.1-fpm-alpine
depends_on:
- db
restart: always
ports:
- "9000:9000"
volumes:
- wordpress:/var/www/html
db:
image: mariadb:10.2.6
volumes:
- db_data:/var/lib/mysql
restart: always
ports:
- "3306:3306"

docker compose의 파일을 보면 wordpressmariadb 와 함께 설치해서 wordpress web service 를 구성하게 됩니다.

이제 wordpress 설치를 시작하게 되고 첫 화면이 뜨고 난뒤, plugin 이나 theme 를 추가하기 위해 들어가보면 목록이 나오지 않습니다.
에러가 났다고 나오고, (wp-setting.php ?? 기억이 명확하지 않네요..)의 어떤 부분에서 에러가 났다고 합니다.
이제부터 문제 해결 과정입니다.

docker compose 문제 해결 과정

extra_hosts 추가

위의 에러난 부분을 찾아가서 php 소스를 수정, echo 로 확인해봤습니다.
wordpress 내부에서 https 를 이용 api.wordpress.org 에 request 를 보내는 부분에서 계속 에러가 납니다.

구글링을 해봤더니, wordpress docker 내부에서 api.wordpress.org 의 도메인을 lookup을 못해서 일 것이라는 글을 보고 host를 추가해봤는데,

php:
image: wordpress:4.8-php7.1-fpm-alpine
depends_on:
- db
restart: always
ports:
- "9000:9000"
volumes:
- wordpress:/var/www/html
extra_hosts:
- "api.wordpress.org:66.155.40.202"

같은 증상이었습니다…

iptables 추가

전혀 해결이 되지 않아서 또다른 방법을 찾던 중 나온 방법이 iptables를 수정하는 것이 었습니다.
현재 상황이 패킷이 나가지 않는 문제라고 판단했을 때, iptables 를 이용해서 해결 할 수 있을 것이라고 판단하고 적용해봤습니다.

docker 1.10, 1.11 do not infer MTU from eth0; docker 1.9 does · Issue #22028 · moby/moby · GitHub

좋아요도 두개나 받은 내용으로 적용을 해봤는데…

실행이 되었습니다.

이렇게 해결되었다는 기쁨(?)을 느끼고 이제 마무리를 지었는데…

또다른 문제. 다시 원점으로…

제가 모바일 어플의 서버로 사용하던 rails application을 또다른 docker 파일로 실행했는데, 메일이 나가지 않는 문제를 확인했습니다. 이 rails 앱은 smtp 를 사용해서 메일을 보내는 기능이 있었는데 메일이 나가지 않아서 ruby library 파일을 직접 수정하면서 디버깅을 시작했습니다.

문제는 smtp 를 보내는 부분에서 났기 때문에 네트워크 문제로 판단, 결국 다시 원점으로 돌아갔습니다. ㅠㅠ

이렇게 또다시 하루정도 iptables 룰 도 바꿔보고 구글링도 해보고 이것저것 해보게 되었습니다.

이때쯤 iwinv 서비스 이용을 포기할 생각을 잠시 하게 되었습니다…만, 심기일전 하고 다시 구글링.

결국 찾은 해결책과 원인

마침내 찾은 해결책.
containers in docker 1.11 does not get same MTU as host · Issue #22297 · moby/moby · GitHub

docker network 를 구성할 때 mtu 설정을 별도로 해줘야한다는 것이 었습니다.

이제 뭔가 이해되는 느낌…
docker compose 로 docker application을 실행하게 되면,
docker 엔진이 별도의 sub network 를 구성하게 되고, wordpress web app 과 mariadb는 sub network 안에서 통신을 하게 됩니다.
이 때 mtu 사이즈가 1450 이상이었기 때문에 문제가 발생했던 것입니다.

해결을 위해서는
1. 첫번째로, docker-compose 안에 이렇게 network 구성을 해주는 방법이나,

networks:
default:
driver: bridge
driver_opts:
com.docker.network.driver.mtu: 1450
  1. 두번째로는, 미리 생성된 network를 이용하는 방법입니다.
$ suod docker network create -o "com.docker.network.driver.mtu"="1450"
networks:
default:
external:
name:

이 해결책을 찾아보고 다시 두번째 해결책이었던 iptables의 명령어에 대해 찾아봤는데,

TCPMSS target

Under normal circumstances, this means the size of the MTU (Maximum Transfer Unit) value, minus 40 bytes.

정상적 상황에서 MTU 사이즈에서 40바이트를 빼주는 것이라고 하네요.
아마 이래서 잘 작동했었나 봅니다. SMTP 의 패킷은 40을 빼줘도 더 1450보다 더 패킷 사이즈가 컸나 봅니다.

하지만 보다 정확한 해결책은 MTU사이즈 수정입니다.

이제 다시 SMTP 로 메일을 보내봅니다. 정상적으로 동작합니다.

결론

  • iwinvdocker 를 사용은 비추
  •  그러나 이 글을 읽어봤다면 추천;;;
  • docker 를 사용하지 않으면 손쉽게 사용가능 하니 좋은 서비스 저렴하게 사용 가능
  • docker 사용을 하시겠다면 매뉴얼의 MTU 설정과 별도 docker networkMTU 설정도 유념해야 함

서버 이전 경험 공유기 – 2. Let’s Encrypt

서버 이전 경험 공유기 – 2. Let’s Encrypt

이번에 서버이전을 하면서 이것저것 알게된 지식 및 경험을 공유하고자 이 글을 작성합니다.

이전 글은 여기서 볼수 있습니다.

Let’s Encrypt

이 전 글에서 간단히 언급했지만, Let’s Encrypt 라는 https 보급 확산을 위한, 무료 인증서 발급 프로젝트 입니다.

사실 예전부터 개인 서버에 https 를 적용하고 싶었지만, 비용이 개인이 부담하기엔 적은 금액이 아니라서 도입을 망설이고 있었습니다.
이런 찰나에 이런 프로젝트가 있다는 사실을 알게 되어 제 서버에 도입을 하지 않을 수가 없었습니다.

설치

Let’s Encrypt 를 설치하기 위해서는 Certbot 이라는 클라이언트가 필요합니다.

Install Certbot

위의 사이트를 들어가면 certbot 을 설치하는 법이 자세히 나옵니다.

간단히 정리하면,

$ wget https://dl.eff.org/certbot-auto
$ chmod a+x ./certbot-auto
$ ./certbot-auto --help

wget 으로 다운로드 받은 뒤, 실행권한 주면 끝입니다. 간단합니다.

certbot-auto 는 현재(version 0.15.0) nginxapache를 지원하고 있습니다. 만약 nginxapache 를 직접(apt-get or yum) 설치했다면 plugin 을 이용해서 연동할 수 있을 것입니다.

–apache Use the Apache plugin for authentication & installation
–standalone Run a standalone webserver for authentication
–nginx Use the Nginx plugin for authentication & installation

하지만, 저는 docker 를 이용한 관계로 그렇게 하지 못하고 다른 방식으로 설치 진행했습니다.

GitHub – 9to6/docker-nginx: Docker for nginx

githubdockerfilereadme 를 참고 하시면 되겠습니다.

핵심은 certbot 설치 후,

$ ./certbot-auto certonly --standalone --email your@email.com -d example.com -d www.example.com

위 명령 실행입니다. example.com 대신 본인의 도메인을 입력하시면 됩니다.

처음으로 실행하셨다면, 본인 이메일 입력하는 란이 나오고,
이메일을 입력 한 뒤에는,
기꺼이 본인의 이메일을 EFF(Electronic Frontier Foundation) 에 제공하겠냐고 물어보는데 저는 그냥 제공해드렸습니다. ㅎㅎㅎㅎ

Let’s Encrypt3개월 마다 한번씩 갱신해야합니다.

매번 신경 쓰기 힘드므로 crontab 에 등록해줍니다.

아래 내용은 매일 새벽 1시에 renew 를 시도하고, 성공시 nginx-simple 이라는 docker container 내부의 nginx의 설정을 다시 reload 하라는 뜻 입니다.

$ sudo echo "0 1 * * * /home/user/certbot-auto renew --quiet --renew-hook \"/usr/bin/docker exec nginx-simple nginx -s reload\"" | sudo tee -a /var/spool/cron/crontabs/root

결론

https 설치가 무사히 완료되었습니다.
이제 appstore application 의 adhoc 버전 배포할 때 굳이 dropbox를 써야하는 번거로움도 사라지겠네요. (다만 요즘 앱개발 할 일이 전혀 없습니다…)

https 적용으로 보안성도 강화되었습니다.
SSL Server Test (Powered by Qualys SSL Labs) 기념으로 이곳에서 보안성 테스트도 해줬습니다.
점수가 괜찮은 듯 합니다.

만족스럽습니다. 여러분들도 https 적용하시고 https 의 빠른 보급에 작은 기여를 해주셨으면 합니다.

서버 이전 경험 공유기 – 1. Dockerizing

이번에 서버이전을 하면서 이것저것 알게된 지식 및 경험을 공유하고자 이 글을 작성합니다.

서버 이전

서버 이전을 하게 되었습니다.
기존엔 cloudv 를 쓰고 있었는데, 같은 회사에서 나온 iwinv 가 한국형 AWS가 되겠다고 하고 과감하게 출사표를 던저서 가격을 보던 중, iwinv 가 압도적으로 좋다고 판단해서 서버이전을 마음먹었습니다.

기존 cloudv 사양

1core, 3G memory, 100G ssd -> 월 31900원

이전 iwinv 사양

2core, 6G memory, 25G ssd -> 월 20900원

iwinv 는 블록스토리지 20g 추가 당 2000원.

굳이 이전하지 않을 이유가 없었습니다.

아무튼…

이전하는 김에 제 개인 서버를 모두 Dockerizing 하기로 마음을 먹고, 작업을 진행하던 중에, 요즘 무료로 https 를 발급해주는 Let’s Encrypt 라는 프로젝트가 있다는 사실을 알게 되었습니다.

그래서 이것도한 시도를 하겠다는 마음을 덜컥 먹어버린…

이런 이유로 시작한 설치 경험을 공유합니다.

Docker

소개

Docker 는 요즘 모르는 사람이 별로 없을 것 같습니다만, 상세소개는 페이지 링크로 대체합니다.

Official Site Overview
nacyot의 프로그래밍 이야기 :: 도커(Docker) 튜토리얼 : 깐 김에 배포까지

간단히 Docker 에 대해 설명하자면 아래 아키택트 이미지로 쉽게 표현이 가능할 것이라고 생각합니다.

Docker Architecture vs Virtual machine

Docker 를 이해하기 위해선 가상 머신(Virtual machine)과의 비교는 필수라고 생각합니다.

한마디로 제게 Docker 를 표현하라고 한다면, Virtual machine 의 장점(isolation, distribution)을 취했으나, 훨씬 더 비용이 적게드는 시스템이 아닐까합니다.

Docker 를 적용하는 이유

이런 도커를 이용해서 제 블로그 및 서버를 구성하기로 마음먹은 겁니다.

이유는 여러가지가 있지만 가장 큰 이유는, 개인서버는 형편상 이사갈 일이 많습니다.
좀 더 저렴하고 좋은 서비스가 나오면 이사를 가야하기 때문이죠.
적고보니 회사든 개인이든 비용문제는 같은 거군요..

Docker를 적용한다면 앞으로 다른 더 좋은 호스팅 서비스가 나올 경우, 쉽게 갈아탈 수 있게 하기 위함입니다. 도커 이미지만 Download 받고 실행하면 그만이거든요.

Dockerizing 본격 시작

이 블로그는 블로그계의 원탑 wordpress 로 이뤄져있고, 워드프레스는 역시 유명한 만큼 자료가 많더군요.

Quickstart: Compose and WordPress

Docker 공식 사이트에 이렇게 docker compose 로 결합하는게 나옵니다.

하지만 부족합니다…
이유는 저는 일단 mysql 을 사용하지 싫고, mariadb를 사용하고 싶기 때문이며,
하나는 역시나 이것또한 비용 문제로 docker image size 를 조금이라도 줄이고 싶기 때문입니다.

그러기에 저는 Alpine Linux 를 쓸 생각을 하게 됩니다.

Using docker compose

GitHub – 9to6/docker-wordpress-nginx: Docker compose for WordPress

docker compose 를 이용해서 워드프래스를 구성하실 분은 위 링크를 참고하시면 좋을 듯합니다.

구성은,

nginx 1.13 alpine, mariadb 10.2.6, wordpress 4.8 alpine

으로 구성했으며, wordpress Plugin인 duplicator 의 손쉬운 사용을 위해, 기본 Dockerfile에서 zip 라이브러리를 추가했습니다.

Using only Dockerfile

심플하기는 위에 것보다 아래 링크가 더 심플합니다.
GitHub – 9to6/docker-wordpress: docker + nginx + mariadb + supervisor + php7

이건 docker compose 를 사용하지 않고, 하나의 도커파일에 nginx + mariadb + wordpress + supervisor 를 한번에 담은 것으로 단순 wordpress 를 호스팅하길 원하시는 분은 이것이 훨씬 단순할 것입니다.

$ sudo docker pull 9to5/wordpress

Docker hub 에 이미지도 올려놓았으니 필요한 분들은 사용하시면 됩니다.

결론

이렇게 해서 도커를 이용해서 워드프레스 서버 구성을 끝냈습니다.
여러분이 보고 있는 이 화면이 결과물입니다.

다음 글은 wordpress 블로그에 무료 https 적용하는 방법을 기술하겠습니다.

ubuntu 14.04(trusty)에 docker install

Ubuntu 우분투 14.04 docker 설치

$ sudo apt-get update
$ sudo apt-get install -y docker-engine

을 하면 에러가 나고 아래와 같은 메시지를 만나게 됩니다.

Reading package lists... Done
Building dependency tree
Reading state information... Done
docker-engine is already the newest version.
You might want to run 'apt-get -f install' to correct these:
The following packages have unmet dependencies:
docker-engine : Depends: libsystemd-journal0 (>= 201) but it is not going to be installed
Recommends: aufs-tools but it is not going to be installed
Recommends: cgroupfs-mount but it is not installable or
cgroup-lite but it is not going to be installed
Recommends: git but it is not going to be installed
E: Unmet dependencies. Try 'apt-get -f install' with no packages (or specify a solution).

보면 dockerlibsystemd-journal0에 의존성이 걸려있어서 그런데요.
설치가 안되는 이유는 잘 모르겠으나, 그냥 수동으로 설치해줬습니다.

파일을 찾아보다가 나중에 또 이런일이 생길 듯하여 기록에 남겨둡니다.

$ wget http://kr.archive.ubuntu.com/ubuntu/pool/main/s/systemd/libsystemd-journal0_204-5ubuntu20_amd64.deb

위 명령으로 *.deb 파일을 다운로드 받은 뒤에 수동 설치합니다.

$ sudo dpkg -I libsystemd-journal0_204-5ubuntu20_amd64.deb

설치 후 다시 docker install 을 시도합니다.

$ sudo apt-get install -y docker-engine

정상 설치가 되었습니다.

Reading package lists... Done
Building dependency tree
Reading state information... Done
docker-engine is already the newest version.
0 upgraded, 0 newly installed, 0 to remove and 29 not upgraded.
1 not fully installed or removed.
After this operation, 0 B of additional disk space will be used.
Setting up docker-engine (17.05.0~ce~rc3-0~ubuntu-trusty) ...
docker start/running, process 3434
Processing triggers for ureadahead (0.100.0-16) ...

설치가 잘 되었는지 확인합니다.

$ docker

정상 설치되었다면 usage가 나옵니다.

잘 설치되었다면 이제 docker를 잘 이용하시면 됩니다.

p80.pool.sks-keyservers.net: Host not found

AWS의 Opsworks에서 새로운 instances를 만들다가 만난 에러를 정리해둡니다.

AWS의 Opsworks 는 인스턴스를 새로 생성하면 등록되어있는 Chef Recipe 들을 자동으로 실행해주는 툴입니다.

이번에 Instance 한개를 추가로 생성하고, 그 Instance에 하나의 App 을 배포하려고 기존 Layer에서 추가로 Instance 를 생성하게 되었습니다.

그런데 갑자기 에러가 발생해서 로그를 봤더니 이런 로그가 있었습니다.

Mixlib::ShellOut::ShellCommandFailed
------------------------------------
execute[install-key 58118E89F3A912897C070ADBF76221572C52609D] (/var/lib/aws/opsworks/cache.stage2/cookbooks/apt/providers/repository.rb line 28) had an error: Mixlib::ShellOut::ShellCommandFailed: Expected process to exit with [0], but received '2'
---- Begin output of apt-key adv --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D ----
STDOUT: Executing: gpg --ignore-time-conflict --no-options --no-default-keyring --homedir /tmp/tmp.YjqEGDmda9 --no-auto-check-trustdb --trust-model always --keyring /etc/apt/trusted.gpg --primary-keyring /etc/apt/trusted.gpg --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D
?: p80.pool.sks-keyservers.net: Host not found
gpgkeys: HTTP fetch error 7: couldn't connect: Success
STDERR: gpg: requesting key 2C52609D from hkp server p80.pool.sks-keyservers.net
gpg: no valid OpenPGP data found.
gpg: Total number processed: 0
---- End output of apt-key adv --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D ----
Ran apt-key adv --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D returned 2

Resource Declaration:
---------------------
# In /var/lib/aws/opsworks/cache.stage2/cookbooks/ops-docker/recipes/install.rb

4: apt_repository 'docker' do
5: uri node['docker']['package']['repo_url']
6: distribution node['docker']['package']['distribution']
7: components ['main']
8: keyserver node['docker']['package']['repo_keyserver']
9: key node['docker']['package']['repo_key']
10: end
11:

Compiled Resource:
------------------
# Declared in /var/lib/aws/opsworks/cache.stage2/cookbooks/ops-docker/recipes/install.rb:4:in `from_file'

apt_repository("docker") do
action :add
retries 0
retry_delay 2
cookbook_name "ops-docker"
recipe_name "install"
uri "https://apt.dockerproject.org/repo"
distribution "ubuntu-trusty"
components ["main"]
keyserver "hkp://p80.pool.sks-keyservers.net:80"
key "58118E89F3A912897C070ADBF76221572C52609D"
cache_rebuild true
end

[2017-05-03T09:17:52+00:00] INFO: Running queued delayed notifications before re-raising exception
[2017-05-03T09:17:52+00:00] ERROR: Running exception handlers
[2017-05-03T09:17:52+00:00] ERROR: Exception handlers complete
[2017-05-03T09:17:52+00:00] FATAL: Stacktrace dumped to /var/lib/aws/opsworks/cache.stage2/chef-stacktrace.out
[2017-05-03T09:17:52+00:00] ERROR: apt_repository[docker] (ops-docker::install line 4) had an error: Mixlib::ShellOut::ShellCommandFailed: execute[install-key 58118E89F3A912897C070ADBF76221572C52609D] (/var/lib/aws/opsworks/cache.stage2/cookbooks/apt/providers/repository.rb line 28) had an error: Mixlib::ShellOut::ShellCommandFailed: Expected process to exit with [0], but received '2'
---- Begin output of apt-key adv --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D ----
STDOUT: Executing: gpg --ignore-time-conflict --no-options --no-default-keyring --homedir /tmp/tmp.YjqEGDmda9 --no-auto-check-trustdb --trust-model always --keyring /etc/apt/trusted.gpg --primary-keyring /etc/apt/trusted.gpg --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D
?: p80.pool.sks-keyservers.net: Host not found
gpgkeys: HTTP fetch error 7: couldn't connect: Success
STDERR: gpg: requesting key 2C52609D from hkp server p80.pool.sks-keyservers.net
gpg: no valid OpenPGP data found.
gpg: Total number processed: 0
---- End output of apt-key adv --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D ----
Ran apt-key adv --keyserver hkp://p80.pool.sks-keyservers.net:80 --recv 58118E89F3A912897C070ADBF76221572C52609D returned 2
[2017-05-03T09:17:53+00:00] FATAL: Chef::Exceptions::ChildConvergeError: Chef run process exited unsuccessfully (exit code 1)

해서 검색을 시작했습니다.
저는 OpsWorksDocker에 서툴러서 뭔 실수를 했나 싶었는데 결과는…
그냥 단순히 서버 다운… OTL.

p80.pool.sks-keyservers.net: Host not found
gpgkeys: HTTP fetch error 7: couldn’t connect: Success

그냥 저 서버가 죽은거 였네요.

저 서버가 Docker설치시 기본으로 바로보는 PGP key server인 듯..
아래 링크가 이 에러와 관련된 Thread입니다.

Key server down for get.docker.com · Issue #13555 · moby/moby · GitHub

여기 가보면 kris라는 사람이
기존 Docker가 사용하는 서버주소를
From,

p80.pool.sks-keyservers.net

To,

hkp://keyserver.ubuntu.com:80

로 변경해주라고 답을 달아놨더군요.

 

결론

아무튼 이 버그의 결론은,
잠시뒤에 다시 시도 해본다;;;;

서버가 살아날 시간을 주는 것입니다;;

[centos] svn server(subversion) 아파치 https 연동하기

예전부터 종종 해오면서 “해야지, 해야지”했던 svn 서버 설정에 대해 블로깅하려 한다.

지금은 git가 대세라서 git도 좀 써보려하지만 일단 친숙한 svn서버 설정부터 해놓으려는게 목적이다.

서버 환경은 Centos 6.5 이고 minimun을 다운받아서 기본만 설치한 상태이다.

1. 아파치 설치

$> sudo yum install httpd

a. 정상설치 확인

$> rpm -qa httpd
httpd-2.2.15-39.el6.centos.x86_64

b. 아파치 iptables 예외 설정

$>sudo vi /etc/sysconfig/iptables

아래 내용 추가

-A INPUT -m state --state NEW -m tcp -p tcp --dport 80 -j ACCEPT
-A INPUT -m state --state NEW -m tcp -p tcp --dport 443 -j ACCEPT

아파치 svn연동 모듈 설치

$> sudo yum install mod_dav_svn mod_ssl

 

2. 아파치 https 설정

https 키생성(self signing)

$> openssl genrsa -des3 -out cert.key 1024
$> openssl req -new -key cert.key -out cert.csr
$> openssl x509 -req -days 3650 -in cert.csr -signkey cert.key -out cert.crt

키를 특정 경로에 저장, 여기서는 /etc/httpd폴더에 cert폴더를 만듬

$> mkdir /etc/httpd/cert

httpd-svn.conf파일을 /etc/httpd/conf.d/ 경로에 생성 한 뒤,

$> vi /etc/httpd/conf.d/httpd-svn.conf

 

아래 내용을 자신에게 맞도록 설정을 변경한다.

ServerName: 본인의 서버 이름

ServerAlias: 서버의 약칭

AuthUserFile: svn의 repository의 유저 패스워드 파일(뒤에 생성)

AuthzSVNAccessFile: svn의 repository 각 프로젝트의 권한 설정 파일(뒤에 생성)

SSLCertificateFile: 생성한 인증서파일

SSLCertificateKeyFile: 생성한 개인키

<VirtualHost *:443>

ServerName weeppp.com
ServerAlias weeppp.com
DocumentRoot "/var/www/svn"

<Location /test>
    DAV                svn
#   SVNPath             "/repository/sample"
    SVNParentPath      "/repository"
    SVNListParentPath  On
    SVNIndexXSLT       "/repos-web/view/repos.xsl"

    AuthType           Basic
    AuthName           "SVN Repository"
    AuthUserFile       "/repository/.passwd"
    AuthzSVNAccessFile "/repository/.authz"
    Require            valid-user
</Location>

# Use separate log files for the SSL virtual host; note that LogLevel
# is not inherited from httpd.conf.
ErrorLog logs/ssl_error_log
TransferLog logs/ssl_access_log
LogLevel warn

#   SSL Engine Switch:
#   Enable/Disable SSL for this virtual host.
SSLEngine on

#   SSL Protocol support:
# List the enable protocol levels with which clients will be able to
# connect.  Disable SSLv2 access by default:
SSLProtocol all -SSLv2

#   SSL Cipher Suite:
# List the ciphers that the client is permitted to negotiate.
# See the mod_ssl documentation for a complete list.
SSLCipherSuite ALL:!ADH:!EXPORT:!SSLv2:RC4+RSA:+HIGH:+MEDIUM:+LOW

#   Server Certificate:
# Point SSLCertificateFile at a PEM encoded certificate.  If
# the certificate is encrypted, then you will be prompted for a
# pass phrase.  Note that a kill -HUP will prompt again.  A new
# certificate can be generated using the genkey(1) command.
#SSLCertificateFile /etc/pki/tls/certs/localhost.crt
SSLCertificateFile /etc/cert/server.crt

#   Server Private Key:
#   If the key is not combined with the certificate, use this
#   directive to point at the key file.  Keep in mind that if
#   you've both a RSA and a DSA private key you can configure
#   both in parallel (to also allow the use of DSA ciphers, etc.)
#SSLCertificateKeyFile /etc/pki/tls/private/localhost.key
SSLCertificateKeyFile /etc/cert/server.key

#   Server Certificate Chain:
#   Point SSLCertificateChainFile at a file containing the
#   concatenation of PEM encoded CA certificates which form the
#   certificate chain for the server certificate. Alternatively
#   the referenced file can be the same as SSLCertificateFile
#   when the CA certificates are directly appended to the server
#   certificate for convinience.
#SSLCertificateChainFile /etc/pki/tls/certs/server-chain.crt

#   Certificate Authority (CA):
#   Set the CA certificate verification path where to find CA
#   certificates for client authentication or alternatively one
#   huge file containing all of them (file must be PEM encoded)
#SSLCACertificateFile /etc/pki/tls/certs/ca-bundle.crt

#   Client Authentication (Type):
#   Client certificate verification type and depth.  Types are
#   none, optional, require and optional_no_ca.  Depth is a
#   number which specifies how deeply to verify the certificate
#   issuer chain before deciding the certificate is not valid.
#SSLVerifyClient require
#SSLVerifyDepth  10

#   Access Control:
#   With SSLRequire you can do per-directory access control based
#   on arbitrary complex boolean expressions containing server
#   variable checks and other lookup directives.  The syntax is a
#   mixture between C and Perl.  See the mod_ssl documentation
#   for more details.
#<Location />
#SSLRequire (    %{SSL_CIPHER} !~ m/^(EXP|NULL)/ \
#            and %{SSL_CLIENT_S_DN_O} eq "Snake Oil, Ltd." \
#            and %{SSL_CLIENT_S_DN_OU} in {"Staff", "CA", "Dev"} \
#            and %{TIME_WDAY} >= 1 and %{TIME_WDAY} <= 5 \
#            and %{TIME_HOUR} >= 8 and %{TIME_HOUR} <= 20       ) \
#           or %{REMOTE_ADDR} =~ m/^192\.76\.162\.[0-9]+$/
#</Location>

#   SSL Engine Options:
#   Set various options for the SSL engine.
#   o FakeBasicAuth:
#     Translate the client X.509 into a Basic Authorisation.  This means that
#     the standard Auth/DBMAuth methods can be used for access control.  The
#     user name is the `one line' version of the client's X.509 certificate.
#     Note that no password is obtained from the user. Every entry in the user
#     file needs this password: `xxj31ZMTZzkVA'.
#   o ExportCertData:
#     This exports two additional environment variables: SSL_CLIENT_CERT and
#     SSL_SERVER_CERT. These contain the PEM-encoded certificates of the
#     server (always existing) and the client (only existing when client
#     authentication is used). This can be used to import the certificates
#     into CGI scripts.
#   o StdEnvVars:
#     This exports the standard SSL/TLS related `SSL_*' environment variables.
#     Per default this exportation is switched off for performance reasons,
#     because the extraction step is an expensive operation and is usually
#     useless for serving static content. So one usually enables the
#     exportation for CGI and SSI requests only.
#   o StrictRequire:
#     This denies access when "SSLRequireSSL" or "SSLRequire" applied even
#     under a "Satisfy any" situation, i.e. when it applies access is denied
#     and no other module can change it.
#   o OptRenegotiate:
#     This enables optimized SSL connection renegotiation handling when SSL
#     directives are used in per-directory context.
#SSLOptions +FakeBasicAuth +ExportCertData +StrictRequire
<Files ~ "\.(cgi|shtml|phtml|php3?)$">
    SSLOptions +StdEnvVars
</Files>
<Directory "/var/www/cgi-bin">
    SSLOptions +StdEnvVars
</Directory>

#   SSL Protocol Adjustments:
#   The safe and default but still SSL/TLS standard compliant shutdown
#   approach is that mod_ssl sends the close notify alert but doesn't wait for
#   the close notify alert from client. When you need a different shutdown
#   approach you can use one of the following variables:
#   o ssl-unclean-shutdown:
#     This forces an unclean shutdown when the connection is closed, i.e. no
#     SSL close notify alert is send or allowed to received.  This violates
#     the SSL/TLS standard but is needed for some brain-dead browsers. Use
#     this when you receive I/O errors because of the standard approach where
#     mod_ssl sends the close notify alert.
#   o ssl-accurate-shutdown:
#     This forces an accurate shutdown when the connection is closed, i.e. a
#     SSL close notify alert is send and mod_ssl waits for the close notify
#     alert of the client. This is 100% SSL/TLS standard compliant, but in
#     practice often causes hanging connections with brain-dead browsers. Use
#     this only for browsers where you know that their SSL implementation
#     works correctly.
#   Notice: Most problems of broken clients are also related to the HTTP
#   keep-alive facility, so you usually additionally want to disable
#   keep-alive for those clients, too. Use variable "nokeepalive" for this.
#   Similarly, one has to force some clients to use HTTP/1.0 to workaround
#   their broken HTTP/1.1 implementation. Use variables "downgrade-1.0" and
#   "force-response-1.0" for this.
SetEnvIf User-Agent ".*MSIE.*" \
         nokeepalive ssl-unclean-shutdown \
         downgrade-1.0 force-response-1.0

#   Per-Server Logging:
#   The home of a custom SSL log file. Use this when you want a
#   compact non-error SSL logfile on a virtual host basis.
CustomLog logs/ssl_request_log \
          "%t %h %{SSL_PROTOCOL}x %{SSL_CIPHER}x \"%r\" %b"

</VirtualHost>

 

 

아파치 설정 폴더로 이동

$> cd /etc/httpd/conf

설정 파일 오픈 및 내용 변경

  • 서버이름은 해당 도메인이나 아이피등으로 변경
  • User와 Group은 아래와 같이 아파치로 변경
ServerName weeppp.com
User apache
Group apache

/etc/httpd/conf 디렉토리에 extra 폴더 생성 및 파일 생성

$> mkdir extra
$> cd extra
$> vi httpd-svn.conf

httpd-svn.conf 파일안에 아래 내용 복사

##############################################################
# SVN
##############################################################

LoadModule dav_svn_module   modules/mod_dav_svn.so
LoadModule authz_svn_module modules/mod_authz_svn.so

<VirtualHost *:443>
    ServerName  weeppp.com
    ServerAlias  weeppp.com
    DocumentRoot "/data/webapps/svn/public_html"
    ServerAdmin  admin@gmail.com

    SetEnvIf Request_URI "\.(gif)|(jpg)|(swf)|(png)$" image_log

    CustomLog    "logs/svn_access_log.log"       common env=!image_log
    CustomLog    "logs/svn_access_image_log.log" common env=image_log
    ErrorLog     "logs/svn_error_log.log"

    <Location /svn>
        DAV                svn
        #SVNPath             "/repository/svn/repo/devsample"
        SVNParentPath /repository
#        SVNParentPath      "/repository/svn/devsample"
#        SVNListParentPath  On
        SVNIndexXSLT       "/repos-web/view/repos.xsl"

        AuthType           Basic
        AuthName           "Weep SVN Repository"
        AuthUserFile       "/repository/.passwd"
        AuthzSVNAccessFile "/repository/.authz"
        Require            valid-user
    </Location>
</VirtualHost>

여기서는 SVNParentPath를 설정해줘서 루트아래의 모든 프로젝트를 접근 가능하도록 함

3. SVN 설정

svn 저장소를 원하는 경로에 생성 및 이동

$> mkdir /repository
$> cd /repository

svn 저장소 소유자 변경

$> chown -R apache.apache /repository

sample프로젝트 생성

$> svnadmin create /repository/sample

프로젝트 소유자 및 권한 변경

$> chown -R apache.apache sample
$> chcon -R -t httpd_sys_content_t sample

svn 계정생성

$> htpasswd -c -m .passwd USER

.authz파일 생성

$> vi /repository/.authz

.authz파일에 하단 내용 추가

admin 그룹에 속한 계정(현재는 weeppp)에게 sample 프로젝트의 read/write 권한을 모두 주는것을 의미한다.

[groups]
admin=weeppp

[sample:/]
@admin = rw

 

.passwd 파일과 .authz파일 소유자를 apache로 변경한다

$> chown apache.apache .passwd
$> chown apache.apache .authz

problems with SELinux context/lables 요 문제가 있으므로 아래 명령을 실행한다.

$> chcon -t httpd_sys_content_t .authz
$> chcon -t httpd_sys_content_t .passwd

위의 명령어들을 잊지 않도록 /repository 폴더안에 ReadMe 파일로 저장해둔다.

#user create
htpasswd -c -m .passwd USER
#user add
htpasswd -m .passwd USER

#create svn repository
svnadmin create /repository/sample
chown -R apache.apache sample
chcon -R -t httpd_sys_content_t sample

subversion 재시작

$> /etc/init.d/svnserve stop
$> /etc/init.d/svnserve start

아파치 재시작

$> /etc/init.d/httpd restart

svn client를 이용해서 서버에 접근해본다.

https://weeppp.com/test/sample

checkout 하고 인증 받은 뒤에 svn을 이용하면 된다.