>  기사  >  백엔드 개발  >  Python에서 웹 개발을 배포하는 방법 소개

Python에서 웹 개발을 배포하는 방법 소개

Y2J
Y2J원래의
2017-05-13 14:03:291504검색

이 글에서는 참고할만한 가치가 있는 Python으로 웹 개발 프로그램을 배포하는 여러 가지 방법을 주로 소개합니다. 아래 편집기로 살펴보겠습니다

1. fastcgi는 flup 모듈을 통해 지원됩니다. nginx의 해당 구성 명령은 fastcgi_pass

2입니다. nginx는 이를 전달하기 위해 Proxy_pass를 사용합니다. 백엔드 애플리케이션에는 높은 동시성을 처리할 수 있는 http 서버가 내장되어 있어야 합니다. Python의 웹프레임워크에서는 tornado만 선택할 수 있습니다.

3, 4개 부분을 포함하는 uwsgi 그룹화:

  • uwsgi 프로토콜

  • 웹 서버 내장 지원 프로토콜 모듈

  • 애플리케이션 서버 프로토콜 지원 모듈

  • 프로세스 제어 프로그램

nginx가 내장- uwsgi 프로토콜 및 0.8.4부터 시작하는 uwsgi 프로토콜 지원 매우 간단합니다. 4바이트 헤더 + 본문 본문은 http, cgi 등과 같은 많은 프로토콜의 패키지일 수 있습니다(헤더의 필드로 표시됨). ).

uwsgi의 특징은 자체 프로세스 제어 프로그램이며 C 언어로 작성되었으며 실제로spawn-fcgi/php-fpm과 유사합니다. 따라서 uwsgi는 (python, lua, ruby, erlang, go) 등을 포함한 다양한 애플리케이션 프레임워크를 지원할 수 있습니다.

4. mod_python, 이는 Apache의 내장 모듈이며 크게 의존합니다. mod_python으로 컴파일된 Python 버전, apache와 함께 사용, 권장하지 않음

5. cgi, 이는 너무 오래되어 권장되지 않으며 nginx는 cgi 모드를 지원하지 않으므로 lighttpd 또는 apache만 사용할 수 있습니다

6.spawn-fcgi, 이것은 lighttpd 설치 패키지와 함께 제공되는 fastcgi 다중 프로세스 관리 프로그램입니다. flup과 동일한 효과가 있습니다. Python 코드 수준이고 generate-fcgi는 외부 프로그램입니다. spawn-fcgi는 매우 다재다능하며 php, python, perl 등 모든 언어로 개발된 코드를 지원할 수 있습니다. 코드가 fastcgi 인터페이스를 구현하는 한 관리에 도움이 될 수 있습니다.

7. 전체 이름은 Simple Common Gateway Interface이며, scgi 프로토콜은 fastcgi와 매우 유사하다고 생각합니다. nginx의 해당 구성 명령은 scgi_pass입니다. 원하는 경우 사용할 수 있으며 flup도 이를 지원합니다.

8. uwsgi와 유사한 도구인 Gunicorn은 레일 배포 도구(Unicorn)에서 이식되었습니다. 그러나 그것이 사용하는 프로토콜은 WSGI이고, 전체 이름은 python2.5에 정의된 공식 표준(PEP 333)인 Python 웹 서버 게이트웨이 인터페이스입니다. 이는 뿌리가 좋고 배포가 비교적 간단합니다. .org/

9. Apache의 모듈인 mod_wsgi는 WSGI 프로토콜(code.google.com/p/modwsgi/

uwsgi

uwsgi 설치

pip install uwsgi

uwsgi 구성

uwsgi에는 여러 구성을 사용할 수 있습니다.


1,ini 
2,xml 
3,json
4,yaml

구성 예


$ cat etc/uwsgi.ini 
[uwsgi]
socket = 127.0.0.1:9005
chdir = /Users/suoning/python_project/trunk/
wsgi-file = main.py
processes = 4
stats = 127.0.0.1:9000
daemonize = /tmp/uwsgiServer.log
pidfile = /tmp/uwsgi.pid
vacuum = true
log-maxsize = 50000000
disable-logging = true
callable = app
$

구성 매개변수에 대한 자세한 설명:

공통 옵션 :

소켓: 주소 및 포트 번호, 예: 소켓 = 127.0.0.1:50000

프로세스: 시작된 프로세스 수

작업자: 시작된 프로세스 수는 프로세스와 동일합니다(공식 웹사이트). 지정된 수의 작업자/프로세스를 생성한다고 말합니다)

chdir: 실행 디렉터리를 지정합니다(앱을 로드하기 전에 지정된 디렉터리에 대한 chdir)

wsgi-file: Load wsgi-file(.wsgi 파일 로드)

stats: 지정된 주소에서, 상태서비스를 켭니다(지정된 주소에서 통계 서버를 활성화합니다)

스레드: 실행 중인 스레드. GIL의 존재로 인해 이것은 정말 쓸모가 없다고 생각합니다. (지정된 스레드 수를 사용하여 사전 스레드 모드에서 작업자 실행)

마스터: 마스터 프로세스 존재 허용(마스터 프로세스 활성화)

daemonize: 프로세스가 백그라운드에서 실행되고 지정된 로그 파일 또는 UDP 서버에 기록됩니다(uWSGI를 daemonize). 실제로 가장 일반적으로 사용되는 방법은 실행 중인 기록을 로컬 파일로 출력하는 것입니다.

log-maxsize :以固定的文件大小(单位KB),切割日志文件。 例如:log-maxsize = 50000000  就是50M一个日志文件。

pidfile : 指定pid文件的位置,记录主进程的pid号。

vacuum : 当服务器退出的时候自动清理环境,删除unix socket文件和pid文件(try to remove all of the generated file/sockets)

disable-logging : 不记录请求信息的日志。只记录错误以及uWSGI内部消息到日志中。如果不开启这项,那么你的日志中会大量出现这种记录:

[pid: 347|app: 0|req: 106/367] 117.116.122.172 () {52 vars in 961 bytes} [Thu Jul  7 19:20:56 2016] POST /post => generated 65 bytes in 6 msecs (HTTP/1.1 200) 2 headers in 88 bytes (1 switches on core 0)

配置nginx


$ cat etc/nginx/servers/tongbupan.conf

server {
 listen  80;
 server_name localhost;

 location / {
  include uwsgi_params;
  uwsgi_pass 127.0.0.1:9005;
 }

 location /webstatic/ {
  expires 7d;
  add_header Cache-Control public;
  alias /Users/suoning/probject/python_project/webstatic/trunk/;
 }

}

$ 
$ nginx -t
nginx: the configuration file /usr/local/etc/nginx/nginx.conf syntax is ok
nginx: configuration file /usr/local/etc/nginx/nginx.conf test is successful
$ 
$ nginx -s reload
$

配置application

flask 示例


...
app = Flask('pan')
...

if name == 'main':
 # app.run(host='0.0.0.0', port=5000)
 app.run()

# 注意:变量app对应uwsgi配置文件uwsgi.ini中 callable = app

启动uwsgi


$ 
$ uwsgi --ini /usr/local/etc/uwsgi.ini
[uWSGI] getting INI configuration from /usr/local/etc/uwsgi.ini
$ 
$ ps -ef|grep uwsgi
11428  1 0 11:40下午 ??   0:01.23 uwsgi --ini /usr/local/etc/uwsgi.ini
11432 11428 0 11:40下午 ??   0:00.00 uwsgi --ini /usr/local/etc/uwsgi.ini
11433 11428 0 11:40下午 ??   0:00.00 uwsgi --ini /usr/local/etc/uwsgi.ini
11434 11428 0 11:40下午 ??   0:00.00 uwsgi --ini /usr/local/etc/uwsgi.ini
11435 11428 0 11:40下午 ??   0:00.00 uwsgi --ini /usr/local/etc/uwsgi.ini
11440 69240 0 11:40下午 ttys000 0:00.00 grep uwsgi
$ 
$ lsof -i tcp:9000
COMMAND PID USER FD TYPE    DEVICE SIZE/OFF NODE NAME
uwsgi 11428 suoning 28u IPv4 0x5583e11534d24e73  0t0 TCP localhost:cslistener (LISTEN)
$
$ lsof -i tcp:9005
COMMAND PID USER FD TYPE    DEVICE SIZE/OFF NODE NAME
uwsgi 11428 suoning 6u IPv4 0x5583e11535699e73  0t0 TCP localhost:9005 (LISTEN)
uwsgi 11432 suoning 6u IPv4 0x5583e11535699e73  0t0 TCP localhost:9005 (LISTEN)
uwsgi 11433 suoning 6u IPv4 0x5583e11535699e73  0t0 TCP localhost:9005 (LISTEN)
uwsgi 11434 suoning 6u IPv4 0x5583e11535699e73  0t0 TCP localhost:9005 (LISTEN)
uwsgi 11435 suoning 6u IPv4 0x5583e11535699e73  0t0 TCP localhost:9005 (LISTEN)
$

FCGI

参考:webpy.org/cookbook/fastcgi-nginx

配置Nginx


$ cat etc/nginx/servers/pan.conf

server {
 listen  80;
 server_name localhost;

 error_page 500 502 503 504 /50x.html;
 location = /50x.html {
  root html;
 }

 location / {
  fastcgi_param REQUEST_METHOD $request_method;
  fastcgi_param QUERY_STRING $query_string;
  fastcgi_param CONTENT_TYPE $content_type;
  fastcgi_param CONTENT_LENGTH $content_length;
  fastcgi_param GATEWAY_INTERFACE CGI/1.1;
  fastcgi_param SERVER_SOFTWARE nginx/$nginx_version;
  fastcgi_param REMOTE_ADDR $remote_addr;
  fastcgi_param REMOTE_PORT $remote_port;
  fastcgi_param SERVER_ADDR $server_addr;
  fastcgi_param SERVER_PORT $server_port;
  fastcgi_param SERVER_NAME $server_name;
  fastcgi_param SERVER_PROTOCOL $server_protocol;
  fastcgi_param SCRIPT_FILENAME $fastcgi_script_name;
  fastcgi_param PATH_INFO $fastcgi_script_name;
  fastcgi_pass 127.0.0.1:9005;
 }

 location /webstatic/ {
  expires 7d;
  add_header Cache-Control public;
  alias /Users/suoning/probject/python_project/webstatic/trunk/;
 }

}

$

配置application

简单示例


from flup.server.fcgi import WSGIServer
from pan import app

WSGIServer(
 app,
 bindAddress=(host, port),
 maxThreads=threads
).run()

生产环境示例


#!/usr/bin/env python
# -*- coding: utf-8 -*-
author = 'suoning'


import sys
import argparse
from flup.server.fcgi import WSGIServer
from lib.daemon import Daemon
from pan import app

APP_NAME = 'pan_platform'
APP_INST_NAME = '20170501'

parser = argparse.ArgumentParser(description=u'Run an pan FastCGI server')
parser.add_argument('command', type=str,
     help=u'command [start|stop|restart]',
     choices=['start', 'stop', 'restart'])
parser.add_argument('-p', '--port', type=int,
     help=u'port of this server', required=True)
parser.add_argument('-t', '--threads', type=int, default=50,
     help=u'max number of threads')
parser.add_argument('-host', '--host', default='0.0.0.0',
     help=u'Listen to the main clause')


class panPlatformDaemon(Daemon):
 def run(self):
  # 运行服务
  try:
   WSGIServer(
    app,
    bindAddress=(args.host, args.port),
    maxThreads=args.threads,
    umask=0111
   ).run()
  except:
   sys.stderr.write('oops')


def gen_pidfile(port):
 return '/var/run/%s_%s_%d.pid' % (APP_NAME, APP_INST_NAME, port)


if name == 'main':
 args = parser.parse_args()
 daemon = panPlatformDaemon(gen_pidfile(args.port))
 if 'start' == args.command:
  daemon.start()
 elif 'stop' == args.command:
  daemon.stop()
 elif 'restart' == args.command:
  daemon.restart()
 else:
  print "Unknown command"
  sys.exit(2)
 sys.exit(0)

fastcgi协议和http协议在代码部署中的的优劣对比

  • fastcgi虽然是二进制协议,相对于http协议,并不节省资源。二进制协议,只能节省数字的表达,比如 1234567,用字符串表示需要7个Byte,用数字就是4个Byte,而字符串到哪里都一样

  • fastcgi在传输数据的时候,为了兼容cgi协议,还要带上一堆cgi的环境变量,所以和http协议相比,用fastcgi传输数据并不省,反而多一些

  • fastcgi 唯一的优点是,它是长连接的,用户并发1000个request,fastcgi可能就用10个 链接转发给后端的appplication,如果用http协议,那来多少给多少,会向后端appplication 发起1000个请求

  • http代理转发方式,在面对超高并发的情况下会出问题,因为,tcp协议栈当中,port是int16整型 你本地新建一个connect,需要消耗一个端口,最多能到65536。外部并发几十万个请求,port池耗干,你的服务器只能拒绝响应了

CGI, FCGI, SCGI, WSGI 区别

WIKI Links:

CGI - en.wikipedia.org/wiki/Common_Gateway_Interface
FCGI - en.wikipedia.org/wiki/Fcgi
SCGI - en.wikipedia.org/wiki/SCGI
WSGI - en.wikipedia.org/wiki/Wsgi 

Other reference:

helpful.knobs-dials.com/index.php/CGI%2C_FastCGI%2C_SCGI%2C_WSGI%2C_servlets_and_such#FastCGI_and_SCGI

CGI = Common Gateway Interface

顾名思义,它是一种接口规范。该规范详细定义了Web服务器中运行的服务器代理程序,怎样获取及返回网页生成过程中,服务器环境上下文和HTTP协议中的参数名称,如大家所熟知的:REQUEST_METHOD,QUERY_STRING,CONTENT_TYPE等等。绝大部分的Web服务器程序,是以脚本的形式代理接受并处理HTTP请求,返回HTTP页面或响应。这些脚本程序,就是大家所熟知的PHP、ASPJSP等等。

FCGI = Fast CGI

실제로 특정 구현에서는 CGI의 변형입니다. CGI 에이전트 프로그램과 웹 호스트 서비스 프로그램 간의 통신 오버헤드를 줄여 웹 서비스 성능 향상이라는 궁극적인 목표를 달성하는 것이 디자인 아이디어이다. FCGI는 사양 측면에서 CGI와 다르지 않지만 구체적인 구현 방법에는 개선이 있음을 알 수 있습니다. CGI의 접근 방식은 각 HTTP 요청에 대해 웹 호스트 서비스 프로그램이 서버 스크립트를 호출하기 위해 새로운 프로세스를 생성한다는 것입니다. 이에 따라 FCGI의 접근 방식은 웹 호스트 서비스 프로그램 프로세스와 통신하기 위해 독립적인 FCGI 서비스 프로그램 프로세스를 구축하는 것입니다. FCGI 서비스 프로세스가 시작되면 리소스를 할당하고 HTTP 요청에 응답하기 위한 스레드를 생성하며 자체 라이프 사이클 을 통해 프로세스를 생성하기 위해 시스템에서 발생하는 리소스 오버헤드를 크게 줄입니다. PHP 및 ASP.Net과 같은 최신 인기 웹 서버 프로그램은 기본적으로 FCGI를 구현한 것입니다.

SCGI = Simple CGI

데이터 프로토콜과 응답 프로세스를 간소화한 FCGI의 산물입니다. 설계 목적은 AJAX 또는 REST 기반으로 증가하는 HTTP 요청 수에 적응하고 더 빠르고 간결한 응답을 제공하는 것입니다. 그리고 SCGI는 서버가 HTTP 프로토콜 요청에 대한 응답을 반환하면 HTTP 연결이 즉시 종료된다는 데 동의합니다. 따라서 SCGI가 일반적인 의미에서 SOA가 주창하는 "요청-망각(request-forget)" 통신 모델에 더 적합하다고 보는 것은 어렵지 않습니다.

WSGI = 웹 서버 게이트웨이 인터페이스

이 프로토콜은 Python 언어로 특허를 받았습니다. 이는 웹 서비스 호스트 프로그램과 HTTP 응답 브로커 간의 통신을 위해 보편적으로 적용 가능한 인터페이스 집합을 정의합니다. 이는 Python 프로그래머가 웹 프레임워크와 웹 호스팅 서버 프로그램 사이에 심각한 결합이 있음을 발견했기 때문에 발생했습니다. 예를 들어 일부 프레임워크는 Apache의 mod_python용으로 설계되었습니다. 따라서 WSGI는 매우 낮은 수준의 인터페이스 세트를 정의합니다. 일반적인 Python 웹 프레임워크에서는 CherryPy, Django, web.py, web2py, TurboGears, Tornado, Pylons, BlueBream, Google App Engine [모호함 – 논의], Trac, Flask, Pyramid 등 이 프로토콜을 구현했습니다. 등등

위 내용은 Python에서 웹 개발을 배포하는 방법 소개의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.