주거용 인터넷 환경에서 Cloudflare Tunnel을 이용해 Discourse 설치하기

yo @Falco, nginx 로그에 real_ip(cf가 CF-Connecting-IP 헤더로 제공하는)가 제대로 들어오고 있나요? 제 경우에는 안 들어오네요. cloudflared의 IP만 보입니다.

아래 중 하나 또는 둘 다 처리가 필요할 것 같습니다(조사 후 후속 조치하겠습니다):

  • cloudflared의 IP에 대해 nginx 설정에 set_real_ip_from 설정 라인을 추가해야 합니다. 만약 이것이 문제라면, templates/cloudflare.template.yml에서 제공하는 다른 set_real_ip_from 라인들은 argotunnel 사용자에게 필요하지 않을 것으로 추측됩니다. 이 경우, 메인 app.yml에서 cloudflared IP를 환경 변수 등으로 가져오는 별도의 argotunnel 템플릿을 docker 저장소에 추가하는 것이 좋을 수 있습니다.
  • log_format 수정. 이 부분은 아마도 문제가 아닐 것 같습니다. 필요 없음 확인

수정:

제가 동작하게 만드는 방법입니다:

cloudflare 템플릿을 사용하지 마세요. 의미가 없습니다.
대신, 다음 내용을 app.yml에 병합하세요:

hooks:
  after_web_config:
    - file:
        path: /etc/nginx/conf.d/cloudflare_tunnel_real_ip.conf
        contents: |
          # restore original visitor IPs (ngx_http_realip_module)
          set_real_ip_from 10.100.20.200/32; # your cloudflared/argotunnel IP range
          real_ip_header CF-Connecting-IP;

참고로, 이 설정은 자동으로 nginx의 http 컨텍스트에 들어가는데, 이것이 적절한 위치입니다.

P.S. 제 생각에는 깔끔함을 위해 cloudflare 템플릿도 nginx 설정을 sed -i를 사용해 /etc/nginx/conf.d/discourse.conf에 추가하는 대신 별도의 파일로 생성해야 합니다.

1개의 좋아요

네 @shyguy, @Falco 님의 단계를 따르고 있습니다.
네, 터널을 사용하고 있습니다. Cloudflare에서 DDoS 보호를 받기 전에는 DDoS 공격으로 인해 서버 CPU 사용률이 매우 높았고, 액세스 로그가 20MB까지 차올랐으며, 로그에는 제 도커 IP만 확인되었습니다. 서버를 보호하기 위해 / URL 경로에 방문자를 대상으로 챌린지를 설정했는데, 만료된 캐시 때문에 Discourse에서 오류가 발생했습니다.



DDoS 공격을 받으면 Falco 웹사이트와 같은 증상이 나타나고, CPU 사용량이 높아집니다.

2개의 좋아요

@shyguy 이 IP 범위를 어디서 받을 수 있나요? 죄송하지만 질문드립니다.

이건 어떨까요..? 이 명령어는 컨테이너 내부에서 실행해야 하나, 외부에서 실행해야 하나요?

1개의 좋아요

명확하지 않았을 수 있으니, 저의 그 게시글은 nginx 로깅을 수정하는 것에만 관한 것이었습니다.

이를 수정하지 않으면 nginx 로그의 모든 요청이 실제 클라이언트 IP가 아니라 하나의 IP(여러분의 cloudflared)에서 온 것처럼 보일 것입니다.

그 IP(또는 IP 범위)는 cloudflared가 discourse로 연결되는 IP이므로, 여러분의 설정에 따라 달라집니다. 확실한 방법 중 하나는 nginx 로그 파일을 확인하고 거기서 IP를 가져오는 것입니다. 그리고 그 뒤에 /32를 추가하면 됩니다.

만약 그의 가이드를 정확히 따르고 있다면 127.0.0.1/32일 것이라고 추측합니다.

아니요, 그것은 cloudflare.template.yml 템플릿에 대한 제안이었을 뿐이며, 이 설정에서는 사용해서는 안 됩니다.

첫 번째 게시글의 그의 가이드를 따르되, 설정에 해당 템플릿을 추가하는 단계는 무시하세요. 대신, 제가 제공한 훅을 추가하세요.

1개의 좋아요

해당 설정을 따라 적용했는데 작동하지 않았습니다.

[27/May/2023:15:49:45 +0000] "sub.domain.ltd" 172.17.0.1 "POST /
[27/May/2023:15:49:45 +0000] "sub.domain.ltd" 172.17.0.1 "POST /
[27/May/2023:15:49:46 +0000] "sub.domain.ltd" 172.17.0.1 "GET /chat
[27/May/2023:15:49:46 +0000] "sub.domain.ltd" 172.17.0.1 "POST /message-bus
[27/May/2023:15:49:54 +0000] "sub.domain.ltd" 172.17.0.1 "POST /message-bus/

hooks:
  after_web_config:
    - file:
        path: /etc/nginx/conf.d/cloudflare_tunnel_real_ip.conf
        contents: |
          # 원본 방문자 IP 복원 (ngx_http_realip_module)
          set_real_ip_from 172.17.0.1/32; # cloudflared/argotunnel IP 범위
          real_ip_header CF-Connecting-IP;

어디가 잘못된 건가요? @shyguy님, 도와주세요.

아쉽군. 내 생각엔 설정이 맞는 것 같은데, 왜 문제가 발생하는지 모르겠어.

이렇게 동작해야 해:

  • Cloudflare 프록시는 클라이언트의 IP를 포함하는 CF-Connecting-IP 헤더를 추가해
  • Discourse의 nginx는 ngx_http_realip_module로 컴파일되어 있어 – 이 모듈은 해당 헤더를 읽고 실제 클라이언트 IP가 표시되도록 로그 등을 수정하는 소프트웨어야
  • set_real_ip_from은 전달된 IP 범위에서 오는 연결에 대해 이 기능을 활성화해. 보통은 Cloudflare의 IP 범위여야 하는데(cloudflare.template.yml 편의 템플릿이 공급), argotunnel을 사용하고 있으므로 argotunnel의 IP를 사용하면 돼.

내 훅(hook)을 비활성화해 보고. nginx 로그에서 이전/이후 IP가 같은지 확인해 봐.


우리 설정의 유일한 차이점은 내가 argotunnel(cloudflared)을 Docker에서 실행한다는 거야.

그걸 시도하고 싶다면…

cloudflared 전용 네트워크를 하나 만들었어:

docker network create --subnet 10.200.10.0/24 cf_tunnel

여기 compose 파일이야:

services:
  cloudflared:
    image: cloudflare/cloudflared:latest
    container_name: cloudflared
    command: tunnel run
    restart: unless-stopped
    networks:
      wan:
      cf_tunnel:
        # for ngx_http_realip_module
        # set to a high IP so that hopefully docker doesn't DHCP assign
        #   another container that IP if it starts before cloudflared
        ipv4_address: 10.200.10.200 # this is the ip for `set_real_ip_from` in nginx

    volumes:
      # should be owned by uid:gid 65532:65532
      - ./conf:/home/nonroot/.cloudflared

networks:
  cf_tunnel:
    external: true # just means a network not managed by compose

# for performance:
# https://github.com/quic-go/quic-go/wiki/UDP-Receive-Buffer-Size
# sudo nano /etc/sysctl.conf
  # add this line:
  # net.core.rmem_max=2500000
  # (my old value was 212992 – check it with: sudo sysctl net.core.rmem_max)

그 conf 디렉토리에 설정/인증서를 전달할 수 있어 (compose 파일의 주석처럼 chown을 기억해) 아니면 설정 절차를 다시 거치면 돼. 로그인 같은 cloudflared 명령은 이렇게 실행할 수 있어:

docker run -it --rm -v /path/to/conf:/home/nonroot/.cloudflared cloudflare/cloudflared:latest YOUR_CMD_HERE

그리고 discourse 컨테이너를 네트워크에 참여시켜야 해. 컨테이너 yml 파일 하단에 이렇게 해서 할 수 있어:

docker_args:
  - '--network=cf_tunnel' # optionally, you could set a static IP here too
1개의 좋아요

Cloudflare 터널을 통해 Discourse 수신 메일 서버 컨테이너를 성공적으로 구동하신 분이 계신가요?

과거에 Cloudflare 터널 뒤에 다른 메일 서버를 설정할 때 문제가 있었지만, Pi에서 80번 포트와 443번 포트를 사용하는 앱은 정상적으로 실행됩니다.

저는 여러 서버에서 Discourse를 설정해 본 경험이 있으며, 당분간은 메인 Discourse 컨테이너에 대해 크게 걱정하지 않습니다.

이 문제와 관련이 있을 것 같지만, 오프토픽이라고 생각하시면 제 답변에서 새 게시물을 작성해 주십시오.

감사합니다.

클라우드플레어 터널은 웹 트래픽에만 사용되며 다른 포트에는 적용되지 않는다고 생각합니다.

제가 맞다는 것을 시사하는 내용입니다: https://community.cloudflare.com/t/can-i-create-a-mail-server-with-cloudflare-tunnel/386089

2개의 좋아요

argo 서비스를 사용했습니다. 첫 달에 28유로를 지불하고 나서야 포기했죠. 실제로는 최소 200ms의 차이가 있었습니다. 하지만 매달 200ms를 위해 28유로를 지불할 수 없어서 해지했습니다. 더 큰 사이트라면 청구서가 더 많이 발생할 수 있다는 점을 염두에 두시기 바랍니다.

해당 사이트의 트래픽은 800~1,000명의 고유 사용자입니다. 이에 따라 계산해 보시면 됩니다.

1개의 좋아요

또한 터널을 사용하기 시작한 이후로 미디어 업로드는 번거롭거나 거의 불가능할 정도가 되었습니다.
처음에는 정상적으로 업로드가 되다가 이 오류가 발생합니다.

apt-get update를 실행하면 이 오류가 발생합니다

64비트 OS를 실행해야 합니다 :sweat_smile:

아, 그거 64비트였네 ㅋㅋ. 근데 결국 해결했어. apt get upgrade를 실행하고 cloudflare 서비스를 재시작했더니 업로드가 됐거든. 그리고 cloudflare 터널로 영상 업로드에 제한이 있는지 알아? 20MB짜리 영상 업로드하는데 문제가 생기는데, 이전에는 없었거든.

Cloudflare 터널을 설정했고, 현재 활성화 상태입니다:

그러나 설치 과정에서 'Discourse가 도메인에 도달할 수 없음’이라는 오류가 계속 표시됩니다.
App.yml 파일에 DISCOURSE_FORCE_HTTPS: true를 입력해 두었습니다.

하지만 설치 과정을 취소한 것이 아니라, App.yml을 수정하기도 전에 자동으로 취소되었습니다. 이것이 오류의 원인이 될 수 있을까요?

1개의 좋아요

나도 마찬가지야. @Tobiasp, 아직 고쳤어? 만약 고쳤다면 어떻게 고쳤어? 고마워

1개의 좋아요

공개 IP를 가지고 있었고, 설치를 위해 이를 사용했습니다. 그런 다음 Cloudflare Tunnel을 설치했습니다.

1개의 좋아요

설정 파일이나 관련 자료, 그리고 어떻게 진행했는지 알려주실 수 있나요? 감사합니다!

1개의 좋아요

그리고 모든 내용과 해결책을 한데 모으기 위해:

4개의 좋아요

가이드를 따라 하다 보니 네트워크를 연결할지, 아니면 애플리케이션을 연결할지 선택하라고 합니다. 무엇을 선택해야 하나요?

1개의 좋아요