您的位置:首页 > 编程语言 > Python开发

python代码refine实例

2013-12-03 11:56 351 查看
有段代码这么写的:

def http_request(request_url="", method="POST", data=""):
headers = {};
headers["Content-Type"] = "application/json;charset=utf-8";
headers["Accept"] = "application/json";

try:
# TODO: never use system default block request, use eventlet instead.
req = urllib2.Request(url=request_url, data=data, headers=headers);
req.get_method = lambda: method;
urllib2.socket.setdefaulttimeout(Constants.JOIN_TRANSCODER_TIMEOUT);
response = urllib2.urlopen(req);
except Exception, ex:
# TODO: always this error code?
code = Errors.join_transcoder_error;
msg = "url=%s connection error, code=%#x, detail=%s"%(request_url, code, ex);
Logger.error(tag, "http_request+error %s"%(msg));
return (code, msg, Errors.parse_msg(code, msg));

if not Constants.is_request_ok(response.code):
code = Errors.join_transcoder_error;
msg = "url=%s request error, code=%#x"%(request_url, code);
Logger.error(tag, "http_request+error %s"%(msg));
return (code, msg, Errors.parse_msg(code, msg));

response_str = response.read();
ret = json.loads(response_str);
return (ret["code"], "url=%s request success"%(request_url), response_str);


做的事情很少,但是看起来超级复杂,原因在于这个函数提供了:

1. http请求的功能,包括GET/POST。

2. 错误处理:错误和具体的逻辑相关(join_transcoder_error)。

3. 混乱的错误逻辑:几个地方都判断错误,返回不同的码。

4. 混乱的返回值:试图提供直接返回给client的错误信息,应该返回定义良好的错误码。

5. 实际上这个函数只是返回了http的结果,外面还得去解析json。

会导致使用起来很奇怪:

def join(self):
(code, msg, response_str) = http_request(self.worker_url, "GET", data=None);
self.error_code = code;
if not Errors.is_success(code):
self.reset(code);
return code;

ret = json.loads(response_str);
if Constants.is_offline(ret["data"]["heartbeat_time"]):
code = Errors.not_heartbeat_error;
Logger.debug(self.__tag, "transcoder+join transcoder worker_id=%s, url=%s "
"change status to offline. code=%#x"%(self.worker_id, self.worker_url, code));
self.reset(code);
return code;

self.status = ret["data"]["status"];
self.error_code = ret["code"];
self.remain_cpu = ret["data"]["remain_cpu"];
self.heartbeat_time = ret["data"]["heartbeat_time"];

if ret["data"]["remain_cpu"] == 0:
self.status = Constants.WORKER_STATUS_WORKING;

return Errors.success;


拿到http_request之后还需要解析json,很罗嗦。

建议refine如下:

'''
perform a http get request, parse the response to json.
@param url: a str indicates the url to request.
@return tuple(code, desc, data) where:
code: the error code, @see: Errors.
desc: the error description str.
data: parsed response object in json. None if error.
'''
def http_get(url):
(code, desc, data) = (Errors.success, "success", None);

try:
res = eventlet.green.urllib2.urlopen(url=str(url)).read();
except Exception, ex:
code = Errors.network_http_get;
desc = "http get error, url=%s, code=%#x, exception=%s"%(url, code, ex);
Logger.error(tag, "http_request+error %s"%(desc));
return (code, desc, data);

try:
data = json.loads(res);
except Exception, ex:
code = Errors.network_json_parse;
desc = "parse json error, url=%s, code=%#x, res=%s, exception=%s"%(url, code, res, ex);
Logger.error(tag, "http_request+error %s"%(desc));
return (code, desc, data);

return (code, desc, data);


这个函数分开了GET和POST,对结果解析为JSON。调用如下:

def join(self):
(code, desc, data) = bravo_utility.http_get(self.worker_url);
self.error_code = code;
if not Errors.is_success(code):
self.reset(code);
return code;

self.status = data["data"]["status"];
self.error_code = data["code"];
self.remain_cpu = data["data"]["remain_cpu"];
self.heartbeat_time = data["data"]["heartbeat_time"];

if data["data"]["remain_cpu"] == 0:
self.status = Constants.WORKER_STATUS_WORKING;

return Errors.success;


当然,还有更好的做法,但这样改已经有所进步了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: