WebSocket을 프록시하도록 Apache2를 구성 하시겠습니까?


40

WebSocket 프로토콜은 HTTP 프로토콜의 확장입니다. 그러나 Apache2의 프록시 모듈은 알지 못하는 것으로 보이며 중요한 헤더를 버리고 호출을 표준 HTTP 호출로 변환합니다.

Apache2가 (1) WebSocket을 이해하거나 (2) 단순히 무엇이든지 맹목적으로 전달하는 방법이 있습니까?

답변:


23

이제 Apache 트렁크에 mod_proxy_wstunnel이라는 모듈이 있는데 mod_proxy (ProxyPass / ProxyPassReverse)가 WebSocket 트래픽을 통과 할 수 있습니다. 누군가 mod_proxy_wstunnel을 Apache 2.4 / 2.2로 백 포팅하는 것에 대한 블로그 게시물을 작성하고 패치를 제공했습니다.

우분투에서 mod_proxy_wstunnel (Ubuntu Server 11.10 및 Apache 2.2.20으로 테스트) 을 설정하는 구체적인 지침을 찾아 내 블로그에 게시했습니다. 아래에 복사했습니다.

# Check apache version (should be 2.2.20 as of writing, if not adjust the next step)
dpkg -s apache2

# Checkout apache source
svn checkout http://svn.apache.org/repos/asf/httpd/httpd/tags/2.2.20/ httpd-2.2.20

# Get patch and apply it
wget http://cafarelli.fr/gentoo/apache-2.2.24-wstunnel.patch
cd httpd-2.2.20
patch -p1 < ../apache-2.2.24-wstunnel.patch

# Build Apache 
svn co http://svn.apache.org/repos/asf/apr/apr/branches/1.4.x srclib/apr
svn co http://svn.apache.org/repos/asf/apr/apr-util/branches/1.3.x srclib/apr-util
./buildconf
./configure --enable-proxy=shared --enable-proxy_wstunnel=shared
make

# Copy the module and recompiled mod_proxy (for new symbols) to the ubuntu apache installation and update the permissions to match the other modules
sudo cp modules/proxy/.libs/mod_proxy{_wstunnel,}.so /usr/lib/apache2/modules/
sudo chmod 644 /usr/lib/apache2/modules/mod_proxy{_wstunnel,}.so
echo -e "# Depends: proxy\nLoadModule proxy_wstunnel_module /usr/lib/apache2/modules/mod_proxy_wstunnel.so" | sudo tee -a /etc/apache2/mods-available/proxy_wstunnel.load

# Enable the module (also make any configuration changes you need)
sudo a2enmod proxy_wstunnel
sudo service apache2 restart

2
내가 당신의 가이드를 따랐을 때, 당신이하지 않은 단계가있었습니다. apr 체크 아웃을 한 후에 ./buildconfig구성 파일을 만들기 위해 실행 해야했습니다. 그리고 설치하라는 몇 가지 종속성이있었습니다.
notbad.jpeg

수행이 후크 위로 글래스 피시 4 이상 WSS : (SSL)
아르키메데스 Trajano

1
@ notbad.jpeg : 아마도 ./buildconf (./buildconfig가 아님) :-)
Erik Forsberg

1
그냥 내 의견 ... 이것은 우분투 12.04에서 아파치 2.2.22-1ubuntu1.10에 설치되고로드되었지만 결국에는 효과가 없었습니다. 프록시가 "업그레이드"헤더 (소스 코드에 "RFC2616 13.5.1에 ​​이러한 헤더를 제거해야 함"이라고 표시되어 있음)를 제거하고있었습니다. 서버는 단지 하나의 홉이 아니라 서버가 기대하는 헤더이므로 작동하지 않습니다. 대신 iptables DNAT 규칙으로 대체했습니다.
Peter

11

아파치 httpd가 조만간 그것들을 지원할 것이라는 것을 나타내는 것은 없다 .

아파치를 통해 웹 소켓을 실행해야하는 경우 mod_pywebsocket을 시도 하십시오 . 나는 그것을 시도했고 작동합니다.

내가 선호하는 몇 가지 대안은 다음과 같습니다.




1

이것은 socket.io 1.0에서 작동 하도록 올바르게 구성하는 방법에 대한 @Andrew Moss 의 답변에 추가 되었습니다 VirtualHost! CentOS에 대한 부분을 건너 뛰십시오!


CentOS 6에 갇혀 있다면 다음과 같이하십시오.

  1. 여기서mod_proxy_wstunnel 모듈 의 백 포트 소스를 다운로드 하십시오 (Gist를 복제하거나 파일을 개별적으로 다운로드하십시오)
  2. 빌드에 필요한 모든 것을 설치하십시오 : yum install make gcc httpd-devel
  3. RPM 빌드 환경 설정 (기본적으로 권한이없는 사용자 및 일부 디렉토리)
  4. 복사 .c에 -file를 SOURCES환경의 하위 폴더와 .spec에 -file SPECS하위 폴더.
  5. 운영 rpmbuild -ba mod_proxy_wstunnel.spec
  6. 패키지는 이제 SRPMS하위 폴더에 있습니다
  7. 패키지를 설치하십시오 : rpm -i /path/to/package.rpm
  8. 이익

또한 Apache에서 자동으로 모듈을로드하므로으로 다시 시작하면됩니다 service httpd restart.


업 설정 VirtualHost실제로 봉사하는 Socket.io 서버 및 (기본적으로 사용할 수 아래입니다 클라이언트 스크립트 http://your.server/socket.io/socket.io.js) 좀 더 때문에의 아파치 2.2에 복잡 에서 버그 mod_proxy모듈 :

다음과 같은 다시 쓰기 규칙이 제공됩니다.

RewriteRule    ^/ws(.*)$  ws://localhost:9000/ws  [P]

mod_rewrite 이 파일을 파일 경로로 취급하여 액세스 로그에

[26/Sep/2013:09:46:07 -0400] "GET /ws://localhost:9000/ws HTTP/1.1" 400 317

따라서 rewrite-rule에서 -protocol을 사용할 수 없습니다.ws 내부적으로 HTTP GET 요청으로 변환되기 때문입니다.

그래도 해결 방법이 있습니다.

<VirtualHost *:80>
        ServerName your.server

        # Proxy socket.io Websocket
        RewriteEngine On

        # socket.io 1.0+ starts all connections with an HTTP polling request
        RewriteCond %{QUERY_STRING} transport=polling       [NC]
        RewriteRule /(.*)           http://localhost:8081/$1 [P]

        ProxyRequests Off

        # Explicitly send the request for the client-script to HTTP:
        ProxyPass /socket.io/socket.io.js http://localhost:8081/socket.io/socket.io.js
        ProxyPassReverse /socket.io/socket.io.js http://localhost:8081/socket.io/socket.io.js

        # Anything else goes to the WebSocket protocol:
        ProxyPass /socket.io/ ws://localhost:8081/socket.io/
        ProxyPassReverse /socket.io/ ws://localhost:8081/socket.io/

        # Any additional stuff (the actual site) comes here
        ProxyPass / http://localhost:8081/
        ProxyPassReverse / http://localhost:8081/
</VirtualHost>

이는 긴 폴링 요청 (WebSocket을 사용할 수없는 경우 폴백 메커니즘 임)과 클라이언트 라이브러리 요청을 제외하고 전송 된 모든 것이- 프로토콜 /socket.io로 전달되도록 ws://합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.