2015-07-12 9 views
27

Я пытаюсь создать простой сервер REST с python SimpleHTTPServer. У меня возникают проблемы с чтением данных из сообщения. Пожалуйста, дайте мне знать, правильно ли я делаю это.Чтение JSON от SimpleHTTPServer Почтовые данные

from SimpleHTTPServer import SimpleHTTPRequestHandler 
import SocketServer 
import simplejson 

class S(SimpleHTTPRequestHandler): 
    def _set_headers(self): 
     self.send_response(200) 
     self.send_header('Content-type', 'text/html') 
     self.end_headers() 

    def do_GET(self): 
     print "got get request %s" % (self.path) 
     if self.path == '/': 
      self.path = '/index.html' 
      return SimpleHTTPRequestHandler.do_GET(self) 

    def do_POST(self): 
     print "got post!!" 
     content_len = int(self.headers.getheader('content-length', 0)) 
     post_body = self.rfile.read(content_len) 
     test_data = simplejson.loads(post_body) 
     print "post_body(%s)" % (test_data) 
     return SimpleHTTPRequestHandler.do_POST(self) 

def run(handler_class=S, port=80): 
    httpd = SocketServer.TCPServer(("", port), handler_class) 
    print 'Starting httpd...' 
    httpd.serve_forever() 

Файл index.html

<html> 
<title>JSON TEST PAGE</title> 
<head> 
<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> 
<script type="text/javascript"> 

JSONTest = function() { 

var resultDiv = $("#resultDivContainer"); 

$.ajax({ 
    url: "http://128.107.138.51:8080", 
    type: "POST", 
    data: {txt1: $("#json_text").val()}, 
    dataType: "json", 
    success: function (result) { 
     switch (result) { 
      case true: 
       processResponse(result); 
       break; 
      default: 
       resultDiv.html(result); 
     } 
    }, 
    error: function (xhr, ajaxOptions, thrownError) { 
    alert(xhr.status); 
    alert(thrownError); 
    } 
}); 
}; 

</script> 
</head> 
<body> 

<h1>My Web Page</h1> 
<div id="resultDivContainer"></div> 
<form> 
<textarea name="json_text" id="json_text" rows="50" cols="80"> 
[{"resources": {"dut": "any_ts", "endpoint1": "endpoint", "endpoint2": "endpoint"}}, 
{"action": "create_conference", "serverName": "dut", "confName": "GURU_TEST"}] 
</textarea> 
<button type="button" onclick="JSONTest()">Generate Test</button> 
</form> 
</body> 
</html> 

SimpleJson не удается загрузить JSON из сообщения POST. Я не знаком с веб-кодированием, и я даже не уверен, что то, что я делаю, подходит для создания простого сервера API REST. Я ценю вашу помощь.

+1

Кроме того, пожалуйста, дайте мне знать, если это не путь, и если имея Джанго это единственный путь. –

ответ

32

Спасибо matthewatabet за идею Клейна. Я решил реализовать его с помощью BaseHTTPHandler. Код ниже.

from BaseHTTPServer import BaseHTTPRequestHandler, HTTPServer 
import SocketServer 
import simplejson 
import random 

class S(BaseHTTPRequestHandler): 
    def _set_headers(self): 
     self.send_response(200) 
     self.send_header('Content-type', 'text/html') 
     self.end_headers() 

    def do_GET(self): 
     self._set_headers() 
     f = open("index.html", "r") 
     self.wfile.write(f.read()) 

    def do_HEAD(self): 
     self._set_headers() 

    def do_POST(self): 
     self._set_headers() 
     print "in post method" 
     self.data_string = self.rfile.read(int(self.headers['Content-Length'])) 

     self.send_response(200) 
     self.end_headers() 

     data = simplejson.loads(self.data_string) 
     with open("test123456.json", "w") as outfile: 
      simplejson.dump(data, outfile) 
     print "{}".format(data) 
     f = open("for_presen.py") 
     self.wfile.write(f.read()) 
     return 


def run(server_class=HTTPServer, handler_class=S, port=80): 
    server_address = ('', port) 
    httpd = server_class(server_address, handler_class) 
    print 'Starting httpd...' 
    httpd.serve_forever() 

if __name__ == "__main__": 
    from sys import argv 

if len(argv) == 2: 
    run(port=int(argv[1])) 
else: 
    run() 

И соответствующая страница HTML

<form action="/profile/index/sendmessage" method="post" enctype="application/x-www-form-urlencoded"> 
<div class="upload_form"> 
    <dt id="message-label"><label class="optional" for="message">Enter Message</label></dt> 
    <dd id="message-element"> 
    <textarea cols="80" rows="50" id="message" name="message"> 
[{"resources": {"dut": "any_ts", "endpoint1": "multistream_endpoint", "endpoint2": "multistream_endpoint"}}, 

{"action": "create_conference", "serverName": "dut", "conferenceName": "GURU_SLAVE_TS"}, 

{"action": "dial_out_ep", "serverName": "dut", "confName": "GURU_SLAVE_TS", "epName": "endpoint1"} 
] 
     </textarea></dd> 
    <dt id="id-label">&nbsp;</dt> 
    <dd id="id-element"> 
    <input type="hidden" id="id" value="145198" name="id"></dd> 
    <dt id="send_message-label">&nbsp;</dt> 
    <dd id="send_message-element"> 
    <input type="submit" class="sendamessage" value="Send" id="send_message" name="send_message"></dd> 
</div> 
</form> 

<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> 
<script type="text/javascript"> 
$("input.sendamessage").click(function(event) { 
event.preventDefault(); 

var message = $('textarea#message').val(); 
var id  = $('input#id').val(); 
url = "http://128.107.138.51:8080" 

var posting = $.post(url, message) 

posting.done(function(data) { 
    alert(message); 
}); 
}); 


</script> 
8

SimpleHTTPRequestHandler не поддерживает POST. Это очень просто. Проверьте Кляйн, чей сервер немного более полнофункциональный.

Там в пример JSon PUT (довольно близко к POST) здесь: https://pypi.python.org/pypi/klein/0.2.3

import json 

from klein import Klein 


class ItemStore(object): 
    app = Klein() 

    def __init__(self): 
     self._items = {} 

    @app.route('/') 
    def items(self, request): 
     request.setHeader('Content-Type', 'application/json') 
     return json.dumps(self._items) 

    @app.route('/<string:name>', methods=['PUT']) 
    def save_item(self, request, name): 
     request.setHeader('Content-Type', 'application/json') 
     body = json.loads(request.content.read()) 
     self._items[name] = body 
     return json.dumps({'success': True}) 

    @app.route('/<string:name>', methods=['GET']) 
    def get_item(self, request, name): 
     request.setHeader('Content-Type', 'application/json') 
     return json.dumps(self._items.get(name)) 


if __name__ == '__main__': 
    store = ItemStore() 
    store.app.run('localhost', 8080) 
+0

Спасибо за ссылку. Я также подумал, что это можно сделать с помощью BaseHTTPHandler. –