Когда я начал писать простые колбные веб-приложения обратно в колледж, я на самом деле не предложил, что происходило в спину, когда я запускаю приложение для колба
Поэтому, когда я бегу Python App.py
это всплывает
* Serving Flask app "somename" * Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)
Теперь я могу взаимодействовать с приложениями, отправив запросы и получаете ответы, но как я могу этому … Я ничего не сделал, чтобы это случилось .. Я только что написал логику, а колба сделали это для меня, и я смог получить вещи действительно быстро
Это почти похоже, даже когда вы смотрите на другие рамки, такие как Django
Django предоставляет тонны вещей из коробки для вас как маршрутизацию, представления, шаблоны, аутентификация, промежуточное программное обеспечение и многое другое с очень богатой документацией, чтобы вы всегда находились в вашей зоне комфорта. И с огромным сообществом любых проблем, с которыми я столкнулся с Джанго, был один ответ стойки
Эти рамки обернуты все Таким образом, вы просто пишите в своей логике, и вы можете отправлять запросы и обрабатывать ответы
Запустив свое приложение и отправку HTTP-запросов, вы понимаете 3 вещи, происходящие в потоке HTTP
Вы открываете соединение TCP: (в моем случае это локальный хост) TCP-соединение используется для отправки запроса или нескольких и получения ответа. Клиент может открыть новое соединение, повторно использовать существующее соединение или открыть несколько подключений TCP с серверами.
Отправить сообщение HTTP-запроса с вашим приложением
GET / HTTP/1.1 Host: developer.mozilla.org Accept-Language: fr
- Вы получаете ответ с сервера, который вы обрабатываете с вашим приложением
HTTP/1.1 200 OK Date: Sat, 09 Oct 2010 14:28:02 GMT Server: Apache Last-Modified: Tue, 01 Dec 2009 20:18:22 GMT ETag: "51142bc1-7449-479b075b2891b" Accept-Ranges: bytes Content-Length: 29769 Content-Type: text/html
Теперь вы закрываете или повторно используете соединение
Но тогда, как, черт возьми, сделают эти Python Framework обрабатывать HTTP-запросы? Потому что это кажется волшебной … и я хотел бы узнать трюк или два, так что давайте сломаемся: D
Ну, может быть, ваш сайт статичен, и у вас есть все ваши файлы спасенный
Тогда для каждого запроса у вас уже есть соответствующий статический файл как ответ … потрясающий это действительно быстро, вы могли бы сделать тонны методов кэширования, и это все действительно легко и просто Но я имею в виду, что это статично, что означает, что вы должны вручную идти и редактировать файлы HTML каждый раз
Чтобы решить эту проблему, возникла общий интерфейс Gateway, который вызывает сценарий, который динамически генерирует веб-страницу
Интерфейс Common Gateway (CGI) предлагает стандартный протокол для веб-серверов для выполнения программ, которые выполняют как приложения для консоли (также называются программами интерфейса командной строки), работающие на сервере, который генерирует веб-страницы динамически
HTTP-запрос, который попадает в разрывы в переменные ENV, которые действуют в качестве ввода и вызывают сценарий, который действует как функция, и вы получаете свой вывод как STDOUT … Так что, если вы просто распечатаете Hello World, это был бы ваш ответ HTTP
Как прохладно и простое, как все это звуки, вы не можете позволить себе запустить сценарий каждый раз, когда вы получите запрос
Поэтому нам нужен отдельный веб-сервер и приложение Python
Введите WSGI.
Или как классные люди называют это интерфейсом Web Server
WSGI может быть реализован с простой функцией, и каждый раз, когда есть запрос, мы просто называем функцию InstaeAd выполнения целого сценария
Это спецификация, которая описывает, как веб-сервер связывается с веб-приложениями, и как веб-приложения могут быть церованы вместе, чтобы обработать один запрос
WSGI – это не сервер, модуль Python, каркас, API или любой вид программного обеспечения. Это просто спецификация интерфейса, по которому сервер и приложение обмениваются
Ну это означает свободу, потому что нам не нужно беспокоиться о веб-серверах, таких как Nginx или Apache, учитывая, что они поняли этот общий интерфейс, и мы могли бы легко переключиться в любое время к
Также есть действительно классная статья, сравнивающая эти два веб-сервера https://serverguy.com/comparison/apache-vs-nginx/
И если вы хотите создать свои собственные рамки, то вам не нужно знать много HTTP и вместо этого строить что-то, что реализует эту простую функцию (Тот, который ниже – боевика)
def app(environ, start_response): data = b"Hello, World!\n" start_response("200 OK", [ ("Content-Type", "text/plain"), ("Content-Length", str(len(data))) ]) return iter([data])
Эта функция принимает два аргумента
start_response: это вызывается с кодом состояния, заголовками и намерениями, которые вы хотите отправить обратно (здесь это общий Hello World)
окружающая среда: Ну, это словарь с некоторой информацией, такой как request_method, path_info, server_protocol etc
Серверы WSGI, такие как Gunicorn, предназначены для одновременной обработки многих запросов. Рамки не выполняются для обработки тысяч запросов и определить, как лучше по маршруту их с сервера. Они также могут взаимодействовать с несколькими веб-серверами и поддерживать несколько процессов бегущего веб-приложения. Они также могут Async (Bjoern, которая на самом деле быстрее, но не совместима с http/1.1)
Gunicorn описывает себя как веб-сервер перед вилком, что означает, что мастер создает вилки, которые обрабатывают каждый запрос. Вилка – это совершенно отдельный процесс, и часть «Pre» на самом деле означает, что рабочие процессы заранее создаются, так что время не потрачено впустую только когда требуется рабочий
Очень обычно используемая комбинация включает Nginx + Gunicorn + Django, где боевика действует как промежуточное программное обеспечение между Nginx и Django
Но теперь с огнестремом почему, черт возьми, нам нужен нгинкс … кажется ненужным для меня
Хорошо с помощью Gunicorn NGNIX действует как обратный прокси-сервер, который можно использовать для обеспечения балансировки нагрузки, предоставлять веб-ускорение через кэширование или сжимание входящих и исходящих данных, а также обеспечить дополнительный уровень безопасности, перехватывающие запросы, направляющиеся для внутренних серверов, а также оружием Предназначен, чтобы быть сервером приложений, который находится за обратным прокси-сервером, который обрабатывает балансировку нагрузки, кэширование и предотвращение прямого доступа к внутренним ресурсам.
Фактически Python поставляется с собственным встроенным веб-сервером, который предоставляет стандартные обработчики GET и HEAD. Вы можете использовать это, чтобы повернуть любой каталог в вашей системе в свой каталог веб-сервера. Я на самом деле использовал это, чтобы поделиться кодом и вещами со своими сверстниками, и это довольно удобно <3
Теперь, чтобы подтвердить тот факт, что я узнал что-то, давайте написать сумму свежий код с розетками … ughh … Теперь я рад, что мне не нужно делать каждый раз, когда я пишу WebApp
Теперь давайте запустим этот код, чтобы начать простой веб-сервер на порт 8000
import socket HOST = '' ## Symbolic name meaning all available interfaces PORT = 8000 ## Port 8000 ''' AF_INET is an address family that is used to designate the type of addresses that your socket can communicate with (in this case, Internet Protocol v4 addresses). SOCK_STREAM is a constant indicating the type of socket (TCP), ''' listen_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM) ''' Set the value of the given socket option When retrieving a socket option, or setting it, you specify the option name as well as the level. When level = SOL_SOCKET, the item will be searched for in the socket itself. For example, suppose we want to set the socket option to reuse the address to 1 (on/true), we pass in the "level" SOL_SOCKET and the value we want it set to. This will set the SO_REUSEADDR in my socket to 1. ''' listen_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) ## Bind to the host and port listen_socket.bind((HOST, PORT)) ## Listen to the host/port listen_socket.listen(1) print(f'Serving your very own HTTP on port {PORT} ...') while True: client_connection, client_address = listen_socket.accept() """ The recv() function receives data on a socket with descriptor socket and stores it in a buffer. """ request_data = client_connection.recv(1024) print(request_data.decode('utf-8')) ## Decode the data assuming UTF=8 Endoding http_response = b"""\ HTTP/1.1 200 OK Sample Response to be parsed! """ ## Send a response and close the connection client_connection.sendall(http_response) client_connection.close()
Запустите файл .. Я спас его как WebServer.py
$ python webserver.py Serving your very own HTTP on port 8888 ...
Теперь давайте Curl -V http://localhost: 8000/
* Trying 127.0.0.1... * TCP_NODELAY set * Connected to localhost (127.0.0.1) port 8000 (#0) > GET / HTTP/1.1 > Host: localhost:8000 > User-Agent: curl/7.58.0 > Accept: */* > < HTTP/1.1 200 OK * no chunk, no close, no size. Assume close to signal end < Sample Response to be parsed! * Closing connection 0
Может быть, также попробовать Telnet localhost 8000.
Trying 127.0.0.1... Connected to localhost. Escape character is '^]'. HTTP/1.1 200 OK Sample Response to be parsed! Connection closed by foreign host.
Там вы идете простой веб-сервер для отправки запросов и получить ответы
Теперь вы можете написать собственную веб-каркас для взаимодействия с помощью этого веб-сервера, и у вас будет существенно написание собственного приложения с нуля
По сути, вы получаете анализируемые ответы на обработку/хранение или что-то, что вы находитесь в
import requests r = requests.get('http://127.0.0.1:8000/') print(r.content)
Различные веб-каркасы связываются с веб-серверами по-разному
В пирамиде у вас есть объект приложения, который возвращается из Make
from pyramid.config import Configurator from pyramid.response import Response def hello_world(request): return Response( 'Hello world from Pyramid!\n', content_type='text/plain', ) config = Configurator() config.add_route('hello', '/hello') config.add_view(hello_world, route_name='hello') app = config.make_wsgi_app()
Флабка на самом деле строит вокруг Werkzeug, который является библиотекой Wekzeug Wekzeug и Werkzeug Werkzeug Werkzeug, используя его для обработки деталей WSGI при предоставлении большего количества структуры и шаблонов для определения мощных приложений. В колбе мы фактически определяем это как приложение, которое мы используем в качестве декоратора для наших взглядов, и он получил маршрутизацию и Другие функциональные возможности встроены в нее
from flask import Flask from flask import Response flask_app = Flask('flaskapp') @flask_app.route('/hello') def hello_world(): return Response( 'Hello world from Flask!\n', mimetype='text/plain' ) app = flask_app.wsgi_app
Содержит украденный контент от https://github.com/rspivak/lsbaws https://www.youtube.com/watch?v=wqrcnvaklio.
Вы прокручивались до конца:)
Оригинал: “https://dev.to/sangarshanan/behind-your-web-application-wsgi-web-server-2hai”