web-dev-qa-db-ja.com

pythonのSimpleHTTPServerでヘッダーを設定できますか?

SimpleHTTPServerを使用して、作業中のいくつかのWebページをテストしています。うまくいきますが、いくつかのクロスドメインリクエストを行う必要があります。そのためには、ページがアクセスを許可されているドメインにAccess-Control-Allow-Originヘッダーを設定する必要があります。

SimpleHTTPServerでヘッダーを設定し、元のコンテンツを提供する簡単な方法はありますか?ヘッダーは各リクエストで同じです。

47
nynexman4464

これはend_headers()の振る舞いを変更するため、ちょっとしたハックですが、_SimpleHTTPServer.py_ファイル全体をコピーして貼り付けるよりも少し良いと思います。

私のアプローチは、サブクラスのend_headers()をオーバーライドし、その中でsend_my_headers()を呼び出し、続いてスーパークラスのend_headers()を呼び出します。

20行未満でも1〜2行ではありません。主に定型。

_#!/usr/bin/env python
import SimpleHTTPServer

class MyHTTPRequestHandler(SimpleHTTPServer.SimpleHTTPRequestHandler):
    def end_headers(self):
        self.send_my_headers()

        SimpleHTTPServer.SimpleHTTPRequestHandler.end_headers(self)

    def send_my_headers(self):
        self.send_header("Access-Control-Allow-Origin", "*")


if __== '__main__':
    SimpleHTTPServer.test(HandlerClass=MyHTTPRequestHandler)
_
49
berto

簡単な方法「追加ヘッダーを書き込み、既存の機能を保持する1-2行を追加する」という単純な方法はありません。。したがって、最良の解決策は、SimpleHTTPRequestHandlerクラスをサブクラス化し、新しいヘッダーを追加して機能を再実装することです。

これを行う簡単な方法がない理由の背後にある問題は、Pythonライブラリ: http:/のSimpleHTTPRequestHandlerクラスの実装を見ることで観察できます。 /hg.python.org/cpython/file/19c74cadea95/Lib/http/server.py#l654

send_head()メソッド、特に応答ヘッダーを送信するメソッドの最後の行に注意してください。 end_headers()メソッドの呼び出しに注意してください。このメソッドは、すべてのヘッダーの終わりと応答本文の始まりを示す空白行とともに、ヘッダーを出力に書き込みます。 http://docs.python.org/py3k/library/http.server .html#http.server.BaseHTTPRequestHandler.end_headers

したがって、SimpleHTTPRequestHandlerハンドラーをサブクラス化し、スーパークラスdo_GET()メソッドを呼び出してから、別のヘッダーを追加することはできません。ヘッダーの送信は既に終了しているためです。スーパークラスdo_GET()メソッドの呼び出しが返されます。 do_GET()メソッドは本文(要求されたファイル)を送信し、本文を送信する必要があるため、このように動作する必要があります-ヘッダーの送信を確定する必要があります。

したがって、再び、あなたはSimpleHTTPRequestHandlerクラスのサブクラス化に固執し、それをライブラリのコードとして正確に実装し(コピーして貼り付けますか?)、 end_headers()send_head()メソッド:

...
self.send_header("Last-Modified", self.date_time_string(fs.st_mtime))
# this below is the new header
self.send_header('Access-Control-Allow-Origin', '*')
self.end_headers()
return f
...
9
Ivan Zuzak
# coding: utf-8
import SimpleHTTPServer
import SocketServer
PORT = 9999

def do_GET(self):
    self.send_response(200)
    self.send_header('Access-Control-Allow-Origin', 'http://example.com')           
    self.end_headers()

Handler = SimpleHTTPServer.SimpleHTTPRequestHandler
Handler.do_GET = do_GET
httpd = SocketServer.TCPServer(("", PORT), Handler)
httpd.serve_forever()
4
iMom0

これは古い答えですが、グーグルでの最初の結果...

基本的に@ iMon0が提案したもの..正しいと思われる?..doPOSTの例

def do_POST(self):
    self.send_response()
    self.send_header('Content-type','application/json')
    self.send_header('Access-Control-Allow-Origin','*')
    self.end_headers()
    sTest = {}
    sTest['dummyitem'] = "Just an example of JSON"
    self.wfile.write(json.dumps(sTest))

これを行うことにより、フローは正しいと感じます。

1:リクエストを受け取ります

2:必要なヘッダーと応答タイプを適用します

3:必要なデータをポストバックします。これが何であり、どのようになりますか。

上記の例は私にとってはうまく機能しており、さらに拡張することができます。これは単なるベアのJSONポストサーバーです。だから私は誰かがそれを必要とするか、私自身がそれのために数ヶ月後に戻ってくるので、SOFにこれを残します。

これは有効なJSONファイルを生成します sTestオブジェクトのみで、PHP生成されたページ/ファイルと同じです。

0
Angry 84