def expire_requests(): reqs = db.request_take_expired() headers = dict() headers['Content-Type'] = 'text/html' body = 'Service Unavailable\n' for r in reqs: publish(grip_prefix + 'wait-%s-%s' % (r[0], r[1]), HttpResponseFormat(code=503, headers=headers, body=body), id='1', prev_id='0') return len(reqs)
def item(request, headline_id): h = get_object_or_404(Headline, pk=headline_id) if request.wscontext: ws = request.wscontext if ws.is_opening(): ws.accept() ws.subscribe(headline_id) while ws.can_recv(): message = ws.recv() if message is None: ws.close() break return HttpResponse() elif request.method == 'GET': if request.META.get('HTTP_ACCEPT') == 'text/event-stream': resp = HttpResponse(content_type='text/event-stream') set_hold_stream(request, headline_id) return resp else: wait = request.META.get('HTTP_WAIT') if wait: wait = int(wait) if wait < 1: wait = None if wait > 300: wait = 300 inm = request.META.get('HTTP_IF_NONE_MATCH') etag = '"%s"' % calendar.timegm(h.date.utctimetuple()) if inm == etag: resp = HttpResponseNotModified() if wait: set_hold_longpoll(request, headline_id, timeout=wait) else: resp = _json_response(h.to_data()) resp['ETag'] = etag return resp elif request.method == 'PUT': hdata = json.loads(request.read()) h.type = hdata['type'] h.title = hdata.get('title', '') h.text = hdata.get('text', '') h.save() hdata = h.to_data() hjson = json.dumps(hdata) etag = '"%s"' % calendar.timegm(h.date.utctimetuple()) rheaders = {'Content-Type': 'application/json', 'ETag': etag} hpretty = json.dumps(hdata, indent=4) + '\n' formats = list() formats.append(HttpResponseFormat(body=hpretty, headers=rheaders)) formats.append(HttpStreamFormat('event: update\ndata: %s\n\n' % hjson)) formats.append(WebSocketMessageFormat(hjson)) publish(headline_id, formats) resp = _json_response(hdata) resp['ETag'] = etag return resp else: return HttpResponseNotAllowed(['GET', 'PUT'])
def _publish_item(list_id, item, cursor): data = item.to_data() _add_totals(list_id, data) body = _json_data([data]) + '\n' stream_data = deepcopy(data) stream_data['change-id'] = str(cursor.cur) stream_content = _json_data(stream_data, False) + '\n' headers = {'Link': _changes_link(list_id, cursor.cur)} formats = [] formats.append(HttpResponseFormat(headers=headers, body=body)) formats.append(HttpStreamFormat(stream_content)) publish('todos-%s' % list_id, formats, id=cursor.cur, prev_id=cursor.prev)
def respond(req, inbox_id, item_id): if req.method == 'POST': try: content = json.loads(req.body) except: return HttpResponseBadRequest( 'Bad Request: Body must be valid JSON\n') try: code = content.get('code') if code is not None: code = int(code) else: code = 200 reason = content.get('reason') headers = content.get('headers') if 'body-bin' in content: body = b64decode(content['body-bin']) elif 'body' in content: body = content['body'] else: body = '' except: return HttpResponseBadRequest( 'Bad Request: Bad format of response\n') try: db.request_remove_pending(inbox_id, item_id) except redis_ops.InvalidId: return HttpResponseBadRequest('Bad Request: Invalid id\n') except redis_ops.ObjectDoesNotExist: return HttpResponseNotFound('Not Found\n') except: return HttpResponse('Service Unavailable\n', status=503) publish( grip_prefix + 'wait-%s-%s' % (inbox_id, item_id), HttpResponseFormat(code=code, reason=reason, headers=headers, body=body)) return HttpResponse('Ok\n') else: return HttpResponseNotAllowed(['POST'])
def inbox(req, inbox_id): if req.method == 'GET': host = req.META.get('HTTP_HOST') if not host: return HttpResponseBadRequest('Bad Request: No \'Host\' header\n') try: inbox = db.inbox_get(inbox_id) except redis_ops.InvalidId: return HttpResponseBadRequest('Bad Request: Invalid id\n') except redis_ops.ObjectDoesNotExist: return HttpResponseNotFound('Not Found\n') except: return HttpResponse('Service Unavailable\n', status=503) out = dict() out['id'] = inbox_id out['base_url'] = 'http://' + host + '/i/' + inbox_id + '/' out['ttl'] = inbox['ttl'] response_mode = inbox.get('response_mode') if not response_mode: response_mode = 'auto' out['response_mode'] = response_mode return HttpResponse(json.dumps(out) + '\n', content_type='application/json') elif req.method == 'DELETE': try: db.inbox_delete(inbox_id) except redis_ops.InvalidId: return HttpResponseBadRequest('Bad Request: Invalid id\n') except redis_ops.ObjectDoesNotExist: return HttpResponseNotFound('Not Found\n') except: return HttpResponse('Service Unavailable\n', status=503) # we'll push a 404 to any long polls because we're that cool publish( grip_prefix + 'inbox-%s' % inbox_id, HttpResponseFormat(code=404, headers={'Content-Type': 'text/html'}, body='Not Found\n')) return HttpResponse('Deleted\n') else: return HttpResponseNotAllowed(['GET', 'DELETE'])
def hit(req, inbox_id): try: inbox = db.inbox_get(inbox_id) except redis_ops.InvalidId: return HttpResponseBadRequest('Bad Request: Invalid id\n') except redis_ops.ObjectDoesNotExist: return HttpResponseNotFound('Not Found\n') except: return HttpResponse('Service Unavailable\n', status=503) response_mode = inbox.get('response_mode') if not response_mode: response_mode = 'auto' # pubsubhubbub verify request? hub_challenge = req.GET.get('hub.challenge') if response_mode == 'wait' or (response_mode == 'wait-verify' and hub_challenge): respond_now = False else: respond_now = True item = _req_to_item(req) if hub_challenge: item['type'] = 'hub-verify' else: item['type'] = 'normal' try: item_id, prev_id, item_created = db.inbox_append_item(inbox_id, item) db.inbox_clear_expired_items(inbox_id) except redis_ops.InvalidId: return HttpResponseBadRequest('Bad Request: Invalid id\n') except redis_ops.ObjectDoesNotExist: return HttpResponseNotFound('Not Found\n') except: return HttpResponse('Service Unavailable\n', status=503) item['id'] = item_id item['created'] = item_created item = _convert_item(item, respond_now) hr_headers = dict() hr_headers['Content-Type'] = 'application/json' hr = dict() hr['last_cursor'] = item_id hr['items'] = [item] hr_body = json.dumps(hr) + '\n' hs_body = json.dumps(item) + '\n' formats = list() formats.append(HttpResponseFormat(headers=hr_headers, body=hr_body)) formats.append(HttpStreamFormat(hs_body)) publish(grip_prefix + 'inbox-%s' % inbox_id, formats, id=item_id, prev_id=prev_id) if respond_now: if hub_challenge: return HttpResponse(hub_challenge) else: return HttpResponse('Ok\n') else: # wait for the user to respond db.request_add_pending(inbox_id, item_id) set_hold_longpoll(req, grip_prefix + 'wait-%s-%s' % (inbox_id, item_id)) return HttpResponse('Service Unavailable\n', status=503, content_type='text/html')