Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/apache/8.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用Apache和Daphne提供静态文件_Apache_Django Channels_Daphne - Fatal编程技术网

使用Apache和Daphne提供静态文件

使用Apache和Daphne提供静态文件,apache,django-channels,daphne,Apache,Django Channels,Daphne,我正在努力学习使用django频道,并且已经完成了教程和教程。我现在正尝试使用Apache和Daphne将其部署到数字海洋液滴上 我有两个问题: 我的静态文件未被使用(我已运行collectstatic) 我只有在键入Daphne时才能让Daphne工作 asgi:应用程序——端口8001——绑定0.0.0.0-v2 而不是使用下面的daphne.service文件 这是我的Apacheconf文件,我希望它能为静态文件服务: <VirtualHost *:80> S

我正在努力学习使用django频道,并且已经完成了教程和教程。我现在正尝试使用Apache和Daphne将其部署到数字海洋液滴上

我有两个问题:

  • 我的静态文件未被使用(我已运行collectstatic)

  • 我只有在键入Daphne时才能让Daphne工作 asgi:应用程序——端口8001——绑定0.0.0.0-v2 而不是使用下面的
    daphne.service
    文件

  • 这是我的
    Apache
    conf文件,我希望它能为静态文件服务:

    <VirtualHost *:80>
            ServerAdmin webmaster@hexiawebservices.co.uk
        ServerName multichat.hexiawebservices.co.uk
        ServerAlias www.multichat.hexiawebservices.co.uk
        DocumentRoot /var/www/multichat
    
            ProxyPreserveHost On
            ProxyPass / http://0.0.0.0:8001/
            ProxyPassReverse / http://0.0.0.0:8001/
    
        Alias /robots.txt /var/www/multichat/static/robots.txt
        Alias /favicon.ico /var/www/multichat/static/favicon.ico
    
        Alias /media/ /var/www/multichat/media/
        Alias /static/ /var/www/multichat/static/
    
        <Directory /var/www/multichat/static>
            Require all granted
        </Directory>
    
        <Directory /var/www/multichat/media>
            Require all granted
        </Directory>
    
        <Directory /var/www/multichat/multichat>
            <Files wsgi.py>
                Require all granted
            </Files>
        </Directory>
    
            ErrorLog ${APACHE_LOG_DIR}/error.log
            CustomLog ${APACHE_LOG_DIR}/access.log combined
    
    </VirtualHost>
    
    编辑1

    根据要求,这里是
    routing.py

    from django.urls import path
    
    from channels.http import AsgiHandler
    from channels.routing import ProtocolTypeRouter, URLRouter
    from channels.auth import AuthMiddlewareStack
    
    from chat.consumers import ChatConsumer
    
    application = ProtocolTypeRouter({
        "websocket": AuthMiddlewareStack(
            URLRouter([
                path("chat/stream/", ChatConsumer),
            ]),
        ),
    
    })
    
    from django.conf import settings
    
    from channels.generic.websocket import AsyncJsonWebsocketConsumer
    
    from .exceptions import ClientError
    from .utils import get_room_or_error
    
    
    class ChatConsumer(AsyncJsonWebsocketConsumer):
        """
        This chat consumer handles websocket connections for chat clients.
    
        It uses AsyncJsonWebsocketConsumer, which means all the handling functions
        must be async functions, and any sync work (like ORM access) has to be
        behind database_sync_to_async or sync_to_async. For more, read
        http://channels.readthedocs.io/en/latest/topics/consumers.html
        """
    
        ##### WebSocket event handlers
    
        async def connect(self):
            """
            Called when the websocket is handshaking as part of initial connection.
            """
            # Are they logged in?
            if self.scope["user"].is_anonymous:
                # Reject the connection
                await self.close()
            else:
                # Accept the connection
                await self.accept()
            # Store which rooms the user has joined on this connection
            self.rooms = set()
    
        async def receive_json(self, content):
            """
            Called when we get a text frame. Channels will JSON-decode the payload
            for us and pass it as the first argument.
            """
            # Messages will have a "command" key we can switch on
            command = content.get("command", None)
            try:
                if command == "join":
                    # Make them join the room
                    await self.join_room(content["room"])
                elif command == "leave":
                    # Leave the room
                    await self.leave_room(content["room"])
                elif command == "send":
                    await self.send_room(content["room"], content["message"])
            except ClientError as e:
                # Catch any errors and send it back
                await self.send_json({"error": e.code})
    
        async def disconnect(self, code):
            """
            Called when the WebSocket closes for any reason.
            """
            # Leave all the rooms we are still in
            for room_id in list(self.rooms):
                try:
                    await self.leave_room(room_id)
                except ClientError:
                    pass
    
        ##### Command helper methods called by receive_json
    
        async def join_room(self, room_id):
            """
            Called by receive_json when someone sent a join command.
            """
            # The logged-in user is in our scope thanks to the authentication ASGI middleware
            room = await get_room_or_error(room_id, self.scope["user"])
            # Send a join message if it's turned on
            if settings.NOTIFY_USERS_ON_ENTER_OR_LEAVE_ROOMS:
                await self.channel_layer.group_send(
                    room.group_name,
                    {
                        "type": "chat.join",
                        "room_id": room_id,
                        "username": self.scope["user"].username,
                    }
                )
            # Store that we're in the room
            self.rooms.add(room_id)
            # Add them to the group so they get room messages
            await self.channel_layer.group_add(
                room.group_name,
                self.channel_name,
            )
            # Instruct their client to finish opening the room
            await self.send_json({
                "join": str(room.id),
                "title": room.title,
            })
    
        async def leave_room(self, room_id):
            """
            Called by receive_json when someone sent a leave command.
            """
            # The logged-in user is in our scope thanks to the authentication ASGI middleware
            room = await get_room_or_error(room_id, self.scope["user"])
            # Send a leave message if it's turned on
            if settings.NOTIFY_USERS_ON_ENTER_OR_LEAVE_ROOMS:
                await self.channel_layer.group_send(
                    room.group_name,
                    {
                        "type": "chat.leave",
                        "room_id": room_id,
                        "username": self.scope["user"].username,
                    }
                )
            # Remove that we're in the room
            self.rooms.discard(room_id)
            # Remove them from the group so they no longer get room messages
            await self.channel_layer.group_discard(
                room.group_name,
                self.channel_name,
            )
            # Instruct their client to finish closing the room
            await self.send_json({
                "leave": str(room.id),
            })
    
        async def send_room(self, room_id, message):
            """
            Called by receive_json when someone sends a message to a room.
            """
            # Check they are in this room
            if room_id not in self.rooms:
                raise ClientError("ROOM_ACCESS_DENIED")
            # Get the room and send to the group about it
            room = await get_room_or_error(room_id, self.scope["user"])
            await self.channel_layer.group_send(
                room.group_name,
                {
                    "type": "chat.message",
                    "room_id": room_id,
                    "username": self.scope["user"].username,
                    "message": message,
                }
            )
    
        ##### Handlers for messages sent over the channel layer
    
        # These helper methods are named by the types we send - so chat.join becomes chat_join
        async def chat_join(self, event):
            """
            Called when someone has joined our chat.
            """
            # Send a message down to the client
            await self.send_json(
                {
                    "msg_type": settings.MSG_TYPE_ENTER,
                    "room": event["room_id"],
                    "username": event["username"],
                },
            )
    
        async def chat_leave(self, event):
            """
            Called when someone has left our chat.
            """
            # Send a message down to the client
            await self.send_json(
                {
                    "msg_type": settings.MSG_TYPE_LEAVE,
                    "room": event["room_id"],
                    "username": event["username"],
                },
            )
    
        async def chat_message(self, event):
            """
            Called when someone has messaged our chat.
            """
            # Send a message down to the client
            await self.send_json(
                {
                    "msg_type": settings.MSG_TYPE_MESSAGE,
                    "room": event["room_id"],
                    "username": event["username"],
                    "message": event["message"],
                },
            )
    
    a
    consumers.py

    from django.urls import path
    
    from channels.http import AsgiHandler
    from channels.routing import ProtocolTypeRouter, URLRouter
    from channels.auth import AuthMiddlewareStack
    
    from chat.consumers import ChatConsumer
    
    application = ProtocolTypeRouter({
        "websocket": AuthMiddlewareStack(
            URLRouter([
                path("chat/stream/", ChatConsumer),
            ]),
        ),
    
    })
    
    from django.conf import settings
    
    from channels.generic.websocket import AsyncJsonWebsocketConsumer
    
    from .exceptions import ClientError
    from .utils import get_room_or_error
    
    
    class ChatConsumer(AsyncJsonWebsocketConsumer):
        """
        This chat consumer handles websocket connections for chat clients.
    
        It uses AsyncJsonWebsocketConsumer, which means all the handling functions
        must be async functions, and any sync work (like ORM access) has to be
        behind database_sync_to_async or sync_to_async. For more, read
        http://channels.readthedocs.io/en/latest/topics/consumers.html
        """
    
        ##### WebSocket event handlers
    
        async def connect(self):
            """
            Called when the websocket is handshaking as part of initial connection.
            """
            # Are they logged in?
            if self.scope["user"].is_anonymous:
                # Reject the connection
                await self.close()
            else:
                # Accept the connection
                await self.accept()
            # Store which rooms the user has joined on this connection
            self.rooms = set()
    
        async def receive_json(self, content):
            """
            Called when we get a text frame. Channels will JSON-decode the payload
            for us and pass it as the first argument.
            """
            # Messages will have a "command" key we can switch on
            command = content.get("command", None)
            try:
                if command == "join":
                    # Make them join the room
                    await self.join_room(content["room"])
                elif command == "leave":
                    # Leave the room
                    await self.leave_room(content["room"])
                elif command == "send":
                    await self.send_room(content["room"], content["message"])
            except ClientError as e:
                # Catch any errors and send it back
                await self.send_json({"error": e.code})
    
        async def disconnect(self, code):
            """
            Called when the WebSocket closes for any reason.
            """
            # Leave all the rooms we are still in
            for room_id in list(self.rooms):
                try:
                    await self.leave_room(room_id)
                except ClientError:
                    pass
    
        ##### Command helper methods called by receive_json
    
        async def join_room(self, room_id):
            """
            Called by receive_json when someone sent a join command.
            """
            # The logged-in user is in our scope thanks to the authentication ASGI middleware
            room = await get_room_or_error(room_id, self.scope["user"])
            # Send a join message if it's turned on
            if settings.NOTIFY_USERS_ON_ENTER_OR_LEAVE_ROOMS:
                await self.channel_layer.group_send(
                    room.group_name,
                    {
                        "type": "chat.join",
                        "room_id": room_id,
                        "username": self.scope["user"].username,
                    }
                )
            # Store that we're in the room
            self.rooms.add(room_id)
            # Add them to the group so they get room messages
            await self.channel_layer.group_add(
                room.group_name,
                self.channel_name,
            )
            # Instruct their client to finish opening the room
            await self.send_json({
                "join": str(room.id),
                "title": room.title,
            })
    
        async def leave_room(self, room_id):
            """
            Called by receive_json when someone sent a leave command.
            """
            # The logged-in user is in our scope thanks to the authentication ASGI middleware
            room = await get_room_or_error(room_id, self.scope["user"])
            # Send a leave message if it's turned on
            if settings.NOTIFY_USERS_ON_ENTER_OR_LEAVE_ROOMS:
                await self.channel_layer.group_send(
                    room.group_name,
                    {
                        "type": "chat.leave",
                        "room_id": room_id,
                        "username": self.scope["user"].username,
                    }
                )
            # Remove that we're in the room
            self.rooms.discard(room_id)
            # Remove them from the group so they no longer get room messages
            await self.channel_layer.group_discard(
                room.group_name,
                self.channel_name,
            )
            # Instruct their client to finish closing the room
            await self.send_json({
                "leave": str(room.id),
            })
    
        async def send_room(self, room_id, message):
            """
            Called by receive_json when someone sends a message to a room.
            """
            # Check they are in this room
            if room_id not in self.rooms:
                raise ClientError("ROOM_ACCESS_DENIED")
            # Get the room and send to the group about it
            room = await get_room_or_error(room_id, self.scope["user"])
            await self.channel_layer.group_send(
                room.group_name,
                {
                    "type": "chat.message",
                    "room_id": room_id,
                    "username": self.scope["user"].username,
                    "message": message,
                }
            )
    
        ##### Handlers for messages sent over the channel layer
    
        # These helper methods are named by the types we send - so chat.join becomes chat_join
        async def chat_join(self, event):
            """
            Called when someone has joined our chat.
            """
            # Send a message down to the client
            await self.send_json(
                {
                    "msg_type": settings.MSG_TYPE_ENTER,
                    "room": event["room_id"],
                    "username": event["username"],
                },
            )
    
        async def chat_leave(self, event):
            """
            Called when someone has left our chat.
            """
            # Send a message down to the client
            await self.send_json(
                {
                    "msg_type": settings.MSG_TYPE_LEAVE,
                    "room": event["room_id"],
                    "username": event["username"],
                },
            )
    
        async def chat_message(self, event):
            """
            Called when someone has messaged our chat.
            """
            # Send a message down to the client
            await self.send_json(
                {
                    "msg_type": settings.MSG_TYPE_MESSAGE,
                    "room": event["room_id"],
                    "username": event["username"],
                    "message": event["message"],
                },
            )
    

    这是为我排序的conf文件:

    <VirtualHost *:80>
        ServerAdmin webmaster@hexiawebservices.co.uk
        ServerName multichat.hexiawebservices.co.uk
        ServerAlias www.multichat.hexiawebservices.co.uk
        DocumentRoot /var/www/multichat
    
        RewriteEngine on
        RewriteCond %{HTTP:UPGRADE} ^WebSocket$ [NC,OR]
        RewriteCond %{HTTP:CONNECTION} ^Upgrade$ [NC]
        RewriteRule .* ws://0.0.0.0:8001%{REQUEST_URI} [P,QSA,L]
    
        ProxyPreserveHost On
        ProxyRequests Off
        ProxyPassMatch ^/(ws(/.*)?)$ ws://0.0.0.0:8001/$1
        ProxyPass / http://0.0.0.0:8001/
        ProxyPassReverse / http://0.0.0.0:8001/
    
        Alias /robots.txt /var/www/multichat/static/robots.txt
        Alias /favicon.ico /var/www/multichat/static/favicon.ico
    
        Alias /media/ /var/www/multichat/media/
        Alias /static/ /var/www/multichat/static/
    
        <Directory /var/www/multichat/static>
            Require all granted
        </Directory>
    
        <Directory /var/www/multichat/media>
            Require all granted
        </Directory>
    
        <Directory /var/www/multichat/multichat>
            <Files wsgi.py>
                Require all granted
            </Files>
        </Directory>
    
        ErrorLog ${APACHE_LOG_DIR}/error.log
        CustomLog ${APACHE_LOG_DIR}/access.log combined
    
    </VirtualHost>
    
    
    服务器管理员webmaster@hexiawebservices.co.uk
    ServerName multichat.hexiawebservices.co.uk
    ServerAlias www.multichat.hexiawebservices.co.uk
    DocumentRoot/var/www/multichat
    重新启动发动机
    RewriteCond%{HTTP:UPGRADE}^WebSocket$[NC,或]
    RewriteCond%{HTTP:CONNECTION}^升级$[NC]
    重写规则。*ws://0.0.0.0:8001%{REQUEST_URI}[P,QSA,L]
    代理主机
    代理请求关闭
    ProxyPassMatch^/(ws(/.*)$ws://0.0.0.0:8001/$1
    ProxyPass/http://0.0.0.0:8001/
    ProxyPassReverse/http://0.0.0.0:8001/
    Alias/robots.txt/var/www/multichat/static/robots.txt
    别名/favicon.ico/var/www/multichat/static/favicon.ico
    别名/media//var/www/multichat/media/
    别名/static//var/www/multichat/static/
    要求所有授权
    要求所有授权
    要求所有授权
    ErrorLog${APACHE_LOG_DIR}/error.LOG
    CustomLog${APACHE\u LOG\u DIR}/access.LOG组合
    
    这是为我排序的conf文件:

    <VirtualHost *:80>
        ServerAdmin webmaster@hexiawebservices.co.uk
        ServerName multichat.hexiawebservices.co.uk
        ServerAlias www.multichat.hexiawebservices.co.uk
        DocumentRoot /var/www/multichat
    
        RewriteEngine on
        RewriteCond %{HTTP:UPGRADE} ^WebSocket$ [NC,OR]
        RewriteCond %{HTTP:CONNECTION} ^Upgrade$ [NC]
        RewriteRule .* ws://0.0.0.0:8001%{REQUEST_URI} [P,QSA,L]
    
        ProxyPreserveHost On
        ProxyRequests Off
        ProxyPassMatch ^/(ws(/.*)?)$ ws://0.0.0.0:8001/$1
        ProxyPass / http://0.0.0.0:8001/
        ProxyPassReverse / http://0.0.0.0:8001/
    
        Alias /robots.txt /var/www/multichat/static/robots.txt
        Alias /favicon.ico /var/www/multichat/static/favicon.ico
    
        Alias /media/ /var/www/multichat/media/
        Alias /static/ /var/www/multichat/static/
    
        <Directory /var/www/multichat/static>
            Require all granted
        </Directory>
    
        <Directory /var/www/multichat/media>
            Require all granted
        </Directory>
    
        <Directory /var/www/multichat/multichat>
            <Files wsgi.py>
                Require all granted
            </Files>
        </Directory>
    
        ErrorLog ${APACHE_LOG_DIR}/error.log
        CustomLog ${APACHE_LOG_DIR}/access.log combined
    
    </VirtualHost>
    
    
    服务器管理员webmaster@hexiawebservices.co.uk
    ServerName multichat.hexiawebservices.co.uk
    ServerAlias www.multichat.hexiawebservices.co.uk
    DocumentRoot/var/www/multichat
    重新启动发动机
    RewriteCond%{HTTP:UPGRADE}^WebSocket$[NC,或]
    RewriteCond%{HTTP:CONNECTION}^升级$[NC]
    重写规则。*ws://0.0.0.0:8001%{REQUEST_URI}[P,QSA,L]
    代理主机
    代理请求关闭
    ProxyPassMatch^/(ws(/.*)$ws://0.0.0.0:8001/$1
    ProxyPass/http://0.0.0.0:8001/
    ProxyPassReverse/http://0.0.0.0:8001/
    Alias/robots.txt/var/www/multichat/static/robots.txt
    别名/favicon.ico/var/www/multichat/static/favicon.ico
    别名/media//var/www/multichat/media/
    别名/static//var/www/multichat/static/
    要求所有授权
    要求所有授权
    要求所有授权
    ErrorLog${APACHE_LOG_DIR}/error.LOG
    CustomLog${APACHE\u LOG\u DIR}/access.LOG组合
    
    我已经解决了这项服务的问题。我需要使用
    sudo systemctl enable daphne.service启用它或重新启动。我将静态文件移动到AWS S3存储桶中,并从那里为它们提供服务,这些文件现在可以正常使用,但是我现在得到了这个错误:
    WebSocket连接到'ws://multichat.hexiawebservices.co.uk/chat/stream/'失败:WebSocket握手时出错:意外响应代码:404
    发布路由和消费者代码您安装了Apache模块
    mod_proxy\u wstunel
    ?是,
    mod\u proxy\u wstunnel
    已启用。我已经解决了该服务的问题。我需要使用
    sudo systemctl enable daphne.service启用它或重新启动。我将静态文件移动到AWS S3存储桶中,并从那里为它们提供服务,这些文件现在可以正常使用,但是我现在得到了这个错误:
    WebSocket连接到'ws://multichat.hexiawebservices.co.uk/chat/stream/'失败:在WebSocket握手期间出错:意外响应代码:404
    发布路由和消费者代码您是否安装了Apache模块
    mod_proxy_wstunel
    ?是的,
    mod proxy_wstunel
    已启用