# Fly.io + Backblaze로 Wagtail 배포하기 이 튜토리얼에서는 두 가지 플랫폼을 사용하여 사이트를 배포합니다. [fly.io](https://fly.io)에서 사이트를 호스팅하고 [Backblaze](https://www.backblaze.com)에서 사이트 이미지를 제공합니다. fly.io를 사용하여 사이트를 호스팅하고 이미지를 제공할 수 있습니다. 그러나 사이트를 호스팅하는 플랫폼이 아닌 다른 플랫폼에 이미지를 저장하면 성능, 보안 및 안정성이 향상됩니다. ```{note} 이 튜토리얼에서는 "yourname"을 여러 번 보게 될 것입니다. 원하는 이름으로 바꾸세요. ``` ## Backblaze B2 클라우드 스토리지 설정하기 이미지를 제공하려면 다음 단계에 따라 Backblaze B2 스토리지를 설정하세요. 1. 브라우저에서 Backblaze [웹사이트](https://www.backblaze.com)를 방문하세요. 2. 상단 탐색 메뉴에서 **Products**를 클릭한 다음 드롭다운에서 **B2 Cloud Storage**를 선택하세요. 3. 다음 단계에 따라 Backblaze B2 클라우드 스토리지에 가입하세요. a. 이메일 주소와 비밀번호를 입력하세요. b. 적절한 지역을 선택하세요. c. **Sign Up Now**를 클릭하세요. 4. 다음 단계에 따라 이메일을 확인하세요. a. 측면 탐색 메뉴에서 **Account > My Settings**로 이동하세요. b. **Security section**에서 **Verify Email**을 클릭하세요. c. 가입 이메일 주소를 입력한 다음 **Send Code**를 클릭하세요. d. 이메일 받은 편지함이나 스팸 폴더에서 인증 이메일을 확인하세요. e. 인증 링크를 클릭하거나 인증 코드를 사용하세요. 5. **B2 Cloud Storage > Bucket**으로 이동하여 **Create a Bucket**을 클릭하여 버킷을 만드세요. 6. **B2 Cloud Storage > Bucket**으로 이동한 다음 **Create a Bucket**을 클릭하세요. 7. 버킷 정보를 다음과 같이 추가하세요. | 버킷 정보 | 지침 | | ------------------- | ------------------------------------------------------------------ | | Bucket Unique Name | 고유한 버킷 이름을 사용하세요. 예: _yourname-wagtail-portfolio_ | | Files in Bucket are | **Public** 선택 | | Default Encryption | **Disable** 선택 | | Object Lock | **Disable** 선택 | 8. **Create a Bucket**을 클릭하세요. ## 사이트를 Backblaze B2 클라우드 스토리지에 연결하기 Backblaze B2 클라우드 스토리지를 설정한 후 포트폴리오 사이트에 연결해야 합니다. 프로젝트 디렉터리 루트에 `.env.production` 파일을 만드는 것으로 시작하세요. 이 단계에서 프로젝트 디렉터리는 다음과 같아야 합니다. ```text mysite/ ├── base ├── blog ├── home ├── media ├── mysite ├── portfolio ├── search ├── .dockerignore ├── .gitignore ├── .env.production ├── Dockerfile ├── manage.py ├── mysite/ └── requirements.txt ``` 이제 `.env.production` 파일에 다음 환경 변수를 추가하세요. ```text AWS_STORAGE_BUCKET_NAME= AWS_S3_ENDPOINT_URL=https:// AWS_S3_REGION_NAME= AWS_S3_ACCESS_KEY_ID= AWS_S3_SECRET_ACCESS_KEY= DJANGO_ALLOWED_HOSTS= DJANGO_CSRF_TRUSTED_ORIGINS=https:// DJANGO_SETTINGS_MODULE=mysite.settings.production ``` ### Backblaze B2 버킷 정보 채우기 다음 단계는 환경 변수에 대한 값을 제공하는 것입니다. `.env.production` 파일에서 Backblaze B2 버킷 정보를 환경 변수 값으로 다음과 같이 사용하세요. | 환경 변수 | 지침 | | --------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | AWS_STORAGE_BUCKET_NAME | Backblaze B2 버킷 이름 사용 | | AWS_S3_ENDPOINT_URL | Backblaze B2 엔드포인트 URL을 사용하세요. 예: _https://s3.us-east-005.backblazeb2.com_ | | AWS_S3_REGION_NAME | 엔드포인트 URL에서 버킷의 지역을 확인하세요. 예: 엔드포인트 URL이 _s3.us-east-005.backblazeb2.com_인 경우 버킷 지역은 _us-east-005_입니다. | | AWS_S3_ACCESS_KEY_ID | 지금은 비워두세요. | | AWS_S3_SECRET_ACCESS_KEY | 지금은 비워두세요. | | DJANGO_ALLOWED_HOSTS | 지금은 비워두세요. | | DJANGO_CSRF_TRUSTED_ORIGINS | _https://_ 사용 | | DJANGO_SETTINGS_MODULE | _mysite.settings.production_ 사용 | 앞의 표에서 `AWS_S3_ACCESS_KEY_ID`, `AWS_S3_SECRET_ACCESS_KEY`, `DJANGO_ALLOWED_HOSTS` 에 대한 값을 제공하지 않았습니다. `AWS_S3_ACCESS_KEY_ID` 및 `AWS_S3_SECRET_ACCESS_KEY` 에 대한 값을 얻으려면 다음 단계를 따르세요. 1. Backblaze B2 계정에 로그인하세요. 2. **Account > Application Keys**로 이동하세요. 3. **Add a New Application Key**를 클릭하세요. 4. 애플리케이션 키 설정을 다음과 같이 구성하세요. | 설정 | 지침 | | --------------------------- | -------------------------------------------------- | | Name of Key | 고유한 이름 제공 | | Allow access to Buckets | 이전에 만든 Backblaze B2 버킷 선택 | | Type of Access | **Read and Write** 선택 | | Allow List All Bucket Names | 선택 해제 상태로 두기 | | File name prefix | 필드를 비워두기 | | Duration (seconds) | 필드를 비워두기 | 5. **Create New Key**를 클릭하세요. 이제 `.env.production` 파일에서 `keyID` 를 `AWS_S3_ACCESS_KEY_ID` 값으로, `applicationKey` 를 `AWS_S3_SECRET_ACCESS_KEY` 값으로 사용하세요. | 환경 변수 | 지침 | | ------------------------ | --------------------------- | | AWS_S3_ACCESS_KEY_ID | **keyID** 사용 | | AWS_S3_SECRET_ACCESS_KEY | **applicationKey** 사용 | 이 단계에서 `.env.production` 파일의 내용은 다음과 같습니다. ```text AWS_STORAGE_BUCKET_NAME=yourname-wagtail-portfolio AWS_S3_ENDPOINT_URL=https://s3.us-east-005.backblazeb2.com AWS_S3_REGION_NAME=us-east-005 AWS_S3_ACCESS_KEY_ID=your Backblaze keyID AWS_S3_SECRET_ACCESS_KEY=your Backblaze applicationKey DJANGO_ALLOWED_HOSTS= DJANGO_CSRF_TRUSTED_ORIGINS=https:// DJANGO_SETTINGS_MODULE=mysite.settings.production ``` ```{note} Backblaze B2 스토리지는 Amazon Web Services의 S3처럼 작동하기 때문에 _AWS_와 _S3_를 사용합니다. `.env.production` 파일을 커밋하거나 공유하지 마세요. 변수가 있는 사람은 누구나 사이트에 액세스할 수 있습니다. 비밀 애플리케이션 키를 분실한 경우 앞의 지침에 따라 새 키를 만드세요. ``` Backblaze B2 클라우드 스토리지 설정 방법에 대한 자세한 내용은 [Backblaze B2 클라우드 스토리지 설명서](https://www.backblaze.com/docs/cloud-storage/)를 참조하세요. ## Fly.io 설정하기 이제 사이트를 Backblaze 스토리지에 연결했으니, 사이트를 호스팅하기 위해 Fly.io를 설정할 차례입니다. Fly.io 계정을 설정하려면 다음 단계를 따르세요. 1. 브라우저에서 [Fly.io](https://fly.io/)를 방문하세요. 2. **Sign Up**을 클릭하세요. 3. GitHub 계정, Google 계정 또는 이메일 옵션을 사용하여 가입하세요. 4. 이메일 받은 편지함에서 확인 링크를 확인하여 이메일을 인증하세요. ```{note} 이메일 인증에 실패하면 Fly.io [대시보드](https://fly.io/dashboard)로 이동하여 다시 시도하세요. ``` 5. **Dashboard > Billing**으로 이동하여 **Add credit card**를 클릭하여 신용카드를 추가하세요. ```{note} 신용카드를 추가하면 Fly.io에서 프로젝트를 만들 수 있습니다. Fly.io는 신용카드를 추가한 후 비용을 청구하지 않습니다. ``` 6. 프로젝트 디렉터리로 이동한 다음 터미널에서 다음 명령을 실행하여 [flyctl을 설치](https://fly.io/docs/hands-on/install-flyctl/)하세요. macOS에서: ```sh # Homebrew 패키지 관리자가 설치되어 있으면 다음 명령을 실행하세요: brew install flyctl # Homebrew 패키지 관리자가 설치되어 있지 않으면 다음 명령을 실행하세요: curl -L https://fly.io/install.sh | sh ``` 리눅스에서: ```sh curl -L https://fly.io/install.sh | sh ``` Windows에서는 **PowerShell**에서 프로젝트 디렉터리로 이동하여 환경을 활성화하고 다음 명령을 실행하세요. ```doscon pwsh -Command "iwr https://fly.io/install.ps1 -useb | iex" ``` ```{note} Windows에서 `pwsh` 라는 용어를 인식할 수 없다는 오류가 발생하면 [PowerShell MSI](https://learn.microsoft.com/en-us/powershell/scripting/install/installing-powershell-on-windows?view=powershell-7.3#installing-the-msi-package)를 설치한 다음 앞의 Windows 명령을 다시 실행하세요. ``` 7. 다음 명령을 실행하여 Fly.io에 [로그인](https://fly.io/docs/hands-on/sign-in/)하세요. ```sh fly auth login ``` Microsoft WSL을 사용하는 경우 다음을 실행하세요. ```doscon ln -s /usr/bin/wslview /usr/local/bin/xdg-open ``` ```{note} flyctl을 성공적으로 설치했지만 "`fly` 를 인식할 수 없습니다" 또는 "flyctl: 명령을 찾을 수 없음 오류"라는 오류가 발생하면 PATH에 flyctl을 추가해야 합니다. 자세한 내용은 [설치 후 flyctl: 명령을 찾을 수 없음 오류 발생](https://community.fly.io/t/getting-flyctl-command-not-found-error-post-install/4954/1)을 읽어보세요. ``` 8. `fly launch` 를 실행하여 Fly.io 프로젝트를 만드세요. 그런 다음 `y` 를 눌러 설정을 구성하세요. 9. fly.io의 관리자 화면으로 이동합니다. 필드를 다음과 같이 채우세요. | 필드 | 지침 | | ------------------------------ | ------------------------------------------------------------------------------------ | | Choose a region for deployment | _env.production_ 파일의 _AWS_S3_REGION_NAME_과 가장 가까운 지역을 선택하세요. | | CPU & Memory | VM Size - shared-cpu-1x VM Memory - 512 MB | | Database | Fly Postgres - 가장 작은 옵션 선택 | **Confirm settings**을 클릭하여 확인하세요. ```{note} 데이터베이스를 애플리케이션과 직접 만들지 않으면 앱과 데이터베이스가 연결되지 않습니다. 앱이 fly launch를 사용하여 다시 시작될 경우, 웹 UI를 통해 앱을 시작할 때 새 데이터베이스를 만드는 것이 좋습니다. ``` 10. 터미널로 돌아가서 결과 프롬프트 질문에 다음과 같이 답하세요. | 질문 | 지침 | | ------------------------------ | ----------- | | Overwrite ".../.dockerignore"? | _y_ 입력 | | Overwrite ".../Dockerfile"? | _y_ 입력 | `fly launch` 명령은 프로젝트 디렉터리에 `Dockerfile` 과 `fly.toml` 이라는 두 개의 새 파일을 만듭니다. Visual Studio Code 터미널과 같은 타사 앱 터미널을 사용하는 경우 Postgres 데이터베이스를 만들 때 오류가 발생할 수 있습니다. 이 오류를 해결하려면 다음 단계를 따르세요. 1. 프로젝트 디렉터리에서 `fly.toml` 파일을 삭제하세요. 2. 브라우저에서 Fly.io 계정으로 이동하여 **Dashboard**를 클릭하세요. 3. **Apps** 목록에서 생성된 앱을 클릭하세요. 4. 측면 탐색 메뉴에서 **Settings**를 클릭하세요. 5. **Delete app**을 클릭하세요. 6. 앱 이름을 입력하세요. 7. **Yes delete it**을 클릭하세요. 8. **Apps** 목록의 모든 앱에 대해 3, 4, 5, 6, 7단계를 반복하세요. 9. 내장 터미널 또는 Windows의 PowerShell MSI에서 `fly launch` 명령을 실행하세요. ## Fly.io를 사용하도록 사이트 사용자 정의하기 이제 최종 배포를 위해 포트폴리오 사이트를 구성해야 합니다. `fly launch` 명령은 프로젝트 디렉터리에 `Dockerfile` 과 `fly.toml` 이라는 두 개의 새 파일을 만듭니다. Git이 환경 파일을 무시하도록 `.gitignore` 파일에 다음을 추가하세요. ``` .env* ``` 또한 Docker가 환경 및 미디어 파일을 무시하도록 `.dockerignore` 파일에 다음을 추가하세요. ``` .env* media ``` Fly.io가 `1` 개의 워커를 사용하도록 구성하세요. 이렇게 하면 사이트가 Fly.io의 낮은 메모리 허용량으로 더 잘 작동할 수 있습니다. 이렇게 하려면 `Dockerfile` 의 마지막 줄을 다음과 같이 수정하세요. ``` CMD ["gunicorn", "--bind", ":8000", "--workers", "1", "mysite.wsgi"] ``` 또한 `fly.toml` 파일에 다음이 있는지 확인하세요. ```toml [deploy] release_command = "python manage.py migrate --noinput" ``` `fly.toml` 파일은 다음과 같아야 합니다. ```toml app = "yourname-wagtail-portfolio" primary_region = "lhr" console_command = "/code/manage.py shell" [build] # 배포 명령 추가: [deploy] release_command = "python manage.py migrate --noinput" [env] PORT = "8000" [http_service] internal_port = 8000 force_https = true auto_stop_machines = true auto_start_machines = true min_machines_running = 0 processes = ["app"] [[statics]] guest_path = "/code/static" url_prefix = "/static/" ``` 이제 `requirements.txt` 파일의 내용을 다음으로 교체하여 프로덕션 종속성을 추가하세요. ```text Django>=4.2,<4.3 wagtail==5.1.1 gunicorn>=21.2.0,<22.0.0 psycopg[binary]>=3.1.10,<3.2.0 dj-database-url>=2.1.0,<3.0.0 whitenoise>=5.0,<5.1 django-storages[s3]>=1.14.0,<2.0.0 ``` 앞의 종속성은 프로덕션 서버에서 사이트를 성공적으로 실행하는 데 필요한 도구와 라이브러리가 있는지 확인합니다. 인지하지 못할 수 있는 종속성에 대한 설명은 다음과 같습니다. 1. `gunicorn` 은 Docker에서 사이트를 실행하는 웹 서버입니다. 2. `psycopg` 는 사이트를 PostgreSQL 데이터베이스에 연결하는 PostgreSQL 어댑터입니다. 3. `dj-database-url` 은 데이터베이스 구성을 단순화하고 사이트를 PostgreSQL 데이터베이스에 연결하는 패키지입니다. 4. `whitenoise` 는 정적 파일을 제공하는 Django 패키지입니다. 5. `django-storages` 는 파일 저장을 처리하고 Backblaze B2 스토리지에 연결하는 Django 라이브러리입니다. `mysite/settings/production.py` 파일의 내용을 다음으로 바꾸세요. ```python import os import random import string import dj_database_url from .base import * DEBUG = False DATABASES = { "default": dj_database_url.config( conn_max_age=600, conn_health_checks=True ) } SECRET_KEY = os.environ["SECRET_KEY"] SECURE_PROXY_SSL_HEADER = ("HTTP_X_FORWARDED_PROTO", "https") SECURE_SSL_REDIRECT = True ALLOWED_HOSTS = os.getenv("DJANGO_ALLOWED_HOSTS", "*").split(",") CSRF_TRUSTED_ORIGINS = os.getenv("DJANGO_CSRF_TRUSTED_ORIGINS", "").split(",") EMAIL_BACKEND = "django.core.mail.backends.console.EmailBackend" MIDDLEWARE.append("whitenoise.middleware.WhiteNoiseMiddleware") STORAGES["staticfiles"]["BACKEND"] = "whitenoise.storage.CompressedManifestStaticFilesStorage" if "AWS_STORAGE_BUCKET_NAME" in os.environ: AWS_STORAGE_BUCKET_NAME = os.getenv("AWS_STORAGE_BUCKET_NAME") AWS_S3_REGION_NAME = os.getenv("AWS_S3_REGION_NAME") AWS_S3_ENDPOINT_URL = os.getenv("AWS_S3_ENDPOINT_URL") AWS_S3_ACCESS_KEY_ID = os.getenv("AWS_S3_ACCESS_KEY_ID") AWS_S3_SECRET_ACCESS_KEY = os.getenv("AWS_S3_SECRET_ACCESS_KEY") INSTALLED_APPS.append("storages") STORAGES["default"]["BACKEND"] = "storages.backends.s3boto3.S3Boto3Storage" AWS_S3_OBJECT_PARAMETERS = { 'CacheControl': 'max-age=86400', } LOGGING = { "version": 1, "disable_existing_loggers": False, "handlers": { "console": { "class": "logging.StreamHandler", }, }, "loggers": { "django": { "handlers": ["console"], "level": os.getenv("DJANGO_LOG_LEVEL", "INFO"), }, }, } WAGTAIL_REDIRECTS_FILE_STORAGE = "cache" try: from .local import * except ImportError: pass ``` `mysite/settings/production.py` 파일의 일부 코드에 대한 설명은 다음과 같습니다. 1. `DEBUG = False` 는 프로덕션 환경에 대한 디버깅을 끕니다. 보안 및 성능에 중요합니다. 2. `SECRET_KEY = os.environ["SECRET_KEY"]` 는 환경 변수에서 프로젝트의 비밀 키를 검색합니다. 3. `SECURE_PROXY_SSL_HEADER = ("HTTP_X_FORWARDED_PROTO", "https")` 는 Heroku와 같은 리버스 프록시 뒤에 사이트를 배포하는 경우 Django가 보안 HTTPS 연결을 감지할 수 있도록 합니다. 4. `SECURE_SSL_REDIRECT = True` 는 HTTPS 리디렉션을 강제합니다. 이렇게 하면 사이트에 대한 모든 연결이 안전합니다. 5. `ALLOWED_HOSTS = os.getenv("DJANGO_ALLOWED_HOSTS", "*").split(",")` 는 사이트에 액세스할 수 있는 호스트 이름을 정의합니다. `DJANGO_ALLOWED_HOSTS` 환경 변수에서 값을 검색합니다. 특정 호스트가 정의되지 않은 경우 기본적으로 모든 호스트를 허용합니다. 6. `EMAIL_BACKEND = "django.core.mail.backends.console.EmailBackend"` 는 콘솔 이메일 백엔드를 사용하도록 사이트를 구성합니다. 이메일을 보내기 위해 적절한 이메일 백엔드를 사용하도록 구성할 수 있습니다. 7. `WAGTAIL_REDIRECTS_FILE_STORAGE = "cache"` 는 Wagtail의 리디렉션에 대한 파일 스토리지를 구성합니다. 여기서는 캐시를 사용하도록 설정합니다. 이제 `.env.production` 파일을 다음과 같이 수정하여 환경 변수 구성을 완료하세요. | 환경 변수 | 지침 | | --------------------------- | ----------------------------------------------------------------------------------------------------- | | DJANGO_ALLOWED_HOSTS | fly.io 프로젝트 이름과 일치해야 합니다. 예: _yourname-wagtail-portfolio.fly.dev_ | | DJANGO_CSRF_TRUSTED_ORIGINS | 프로젝트의 도메인 이름과 일치해야 합니다. 예: _https://yourname-wagtail-portfolio.fly.dev_ | `.env.production` 파일의 내용은 이제 다음과 같아야 합니다. ```text AWS_STORAGE_BUCKET_NAME=yourname-wagtail-portfolio AWS_S3_ENDPOINT_URL=https://s3.us-east-005.backblazeb2.com AWS_S3_REGION_NAME=us-east-005 AWS_S3_ACCESS_KEY_ID=your Backblaze keyID AWS_S3_SECRET_ACCESS_KEY=your Backblaze applicationKey DJANGO_ALLOWED_HOSTS=yourname-wagtail-portfolio.fly.dev DJANGO_CSRF_TRUSTED_ORIGINS=https://yourname-wagtail-portfolio.fly.dev DJANGO_SETTINGS_MODULE=mysite.settings.production ``` Fly.io가 사용할 비밀을 설정하려면 다음을 실행하세요. ```sh flyctl secrets import < .env.production ``` Windows에서는 PowerShell MSI에서 다음 명령을 실행하세요. ```doscon Get-Content .env.production | flyctl secrets import ``` 마지막으로 다음 명령을 실행하여 사이트를 Fly.io에 배포하세요. ```sh fly deploy --ha=false ``` ```{note} "fly deploy"를 실행하면 앱에 대해 두 개의 머신이 생성됩니다. "--ha=false" 플래그를 사용하면 앱에 대해 하나의 머신이 생성됩니다. ``` 축하합니다! 이제 사이트가 라이브 상태입니다. 그러나 콘텐츠를 추가해야 합니다. 라이브 사이트에 대한 관리자 사용자를 만드는 것으로 시작하세요. 다음 명령을 실행하세요. ```sh flyctl ssh console ``` 그런 다음 실행하세요. ```sh DJANGO_SUPERUSER_USERNAME=username DJANGO_SUPERUSER_EMAIL=mail@example.com DJANGO_SUPERUSER_PASSWORD=password python manage.py createsuperuser --noinput ``` ```{note} _username_, _mail@example.com_, _password_를 원하는 사용자 이름, 이메일 주소 및 비밀번호로 바꾸십시오. ``` Fly.io에서 Django 프로젝트를 설정하는 방법에 대한 자세한 내용은 [Fly.io의 Django](https://fly.io/docs/django/)를 참조하세요. ## 라이브 사이트에 콘텐츠 추가하기 지금까지 로컬 환경에서 사이트에 콘텐츠를 추가해 왔습니다. 이제 사이트가 서버에서 라이브 상태이므로 라이브 사이트에 콘텐츠를 추가해야 합니다. 라이브 사이트에 콘텐츠를 추가하려면 브라우저에서 ` https://yourname-wagtail-portfolio.fly.dev/admin/` 으로 이동하여 튜토리얼의 다음 하위 섹션에 있는 단계를 따르세요. - [홈페이지에 콘텐츠 추가하기](add_content_to_your_homepage) - [소셜 미디어 링크 추가하기](add_your_social_media_links) - [바닥글 텍스트 추가하기](add_footer_text) - [사이트 메뉴에 페이지 추가하기](add_pages_to_your_site_menu) - [연락처 정보 추가하기](add_your_contact_information) - [이력서 추가하기](add_your_resume) ```{note} 브라우저에서 라이브 사이트에 액세스하려고 할 때 오류가 발생하면 Fly.io 대시보드에서 애플리케이션 로그를 확인하세요. 애플리케이션 로그를 확인하려면 **Dashboard > Apps > yourname-wagtail-portfolio > Monitoring**을 클릭하세요. ```