From 794676f241a284a2df95b57224aa7f9165f058e0 Mon Sep 17 00:00:00 2001
From: Aslak Knutsen
Date: Fri, 1 Mar 2013 18:46:45 +0100
Subject: Update REST API to new KittyStore backend
* Move to use APIView as Resource base
* Add List Resource to show all lists
* Custom serialize Thread, Email and List objects
---
hyperkitty/api.py | 105 +++++++++++++++++++++++++++++-------------
hyperkitty/templates/api.html | 19 ++++++--
hyperkitty/urls.py | 6 ++-
3 files changed, 93 insertions(+), 37 deletions(-)
(limited to 'hyperkitty')
diff --git a/hyperkitty/api.py b/hyperkitty/api.py
index f7c7431..1160c3d 100644
--- a/hyperkitty/api.py
+++ b/hyperkitty/api.py
@@ -20,68 +20,111 @@
import json
import re
-from rest_framework.views import View
+from rest_framework.views import APIView
+from rest_framework.response import Response
+from rest_framework import serializers
+from rest_framework.exceptions import ParseError
from django.conf.urls import url
from django.conf import settings
-from django.http import HttpResponseNotModified, HttpResponse
from hyperkitty.lib import get_store
+from kittystore.storm.model import Email, Thread
-class EmailResource(View):
+class ListSerializer(serializers.Serializer):
+ name = serializers.CharField()
+ display_name = serializers.CharField()
+ description = serializers.CharField()
+
+class EmailSerializer(serializers.Serializer):
+ list_name = serializers.EmailField()
+ message_id = serializers.CharField()
+ thread_id = serializers.CharField()
+ sender_name = serializers.CharField()
+ sender_email = serializers.EmailField()
+ subject = serializers.CharField()
+ in_reply_to = serializers.CharField()
+ date = serializers.DateTimeField()
+
+class EmailLinkSerializer(serializers.Serializer):
+ list_name = serializers.EmailField()
+ message_id = serializers.CharField()
+ sender_name = serializers.CharField()
+ sender_email = serializers.EmailField()
+ date = serializers.DateTimeField()
+
+class ThreadSerializer(serializers.Serializer):
+ thread_id = serializers.CharField()
+ list_name = serializers.EmailField()
+ date_active = serializers.DateTimeField()
+ subject = serializers.CharField()
+ starting_email = EmailLinkSerializer()
+ email_ids = serializers.CharField()
+ participants = serializers.CharField()
+
+
+class ListResource(APIView):
+ """ Resource used to retrieve lists from the archives using the
+ REST API.
+ """
+
+ def get(self, request):
+ store = get_store(request)
+ lists = store.get_lists()
+ if not lists:
+ return Response(status=404)
+ else:
+ return Response(ListSerializer(lists, many=True).data)
+
+class EmailResource(APIView):
""" Resource used to retrieve emails from the archives using the
REST API.
"""
def get(self, request, mlist_fqdn, messageid):
- list_name = mlist_fqdn.split('@')[0]
store = get_store(request)
- email = store.get_message_by_hash_from_list(list_name, messageid)
+ email = store.get_message_by_id_from_list(mlist_fqdn, messageid)
if not email:
- return HttpResponse(status=404)
+ return Response(status=404)
else:
- return email
+ return Response(EmailSerializer(email).data)
-class ThreadResource(View):
+class ThreadResource(APIView):
""" Resource used to retrieve threads from the archives using the
REST API.
"""
def get(self, request, mlist_fqdn, threadid):
- list_name = mlist_fqdn.split('@')[0]
store = get_store(request)
- thread = store.get_thread(list_name, threadid)
+ thread = store.get_thread(mlist_fqdn, threadid)
if not thread:
- return HttpResponse(status=404)
+ return Response(status=404)
else:
- return thread
+ return Response(ThreadSerializer(thread).data)
-class SearchResource(View):
+class SearchResource(APIView):
""" Resource used to search the archives using the REST API.
"""
def get(self, request, mlist_fqdn, field, keyword):
- list_name = mlist_fqdn.split('@')[0]
-
- if field not in ['Subject', 'Content', 'SubjectContent', 'From']:
- return HttpResponse(status=404)
+ fields = ['Subject', 'Content', 'SubjectContent', 'From']
+ if field not in fields:
+ raise ParseError(detail="Unknown field: " + field + ". Supported fields are " + ", ".join(fields))
- regex = '.*%s.*' % keyword
- if field == 'SubjectContent':
- query_string = {'$or' : [
- {'Subject': re.compile(regex, re.IGNORECASE)},
- {'Content': re.compile(regex, re.IGNORECASE)}
- ]}
- else:
- query_string = {field.capitalize():
- re.compile(regex, re.IGNORECASE)}
-
- #print query_string, field, keyword
store = get_store(request)
- threads = store.search_archives(list_name, query_string)
+ threads = None
+ if field == 'Subject':
+ threads = store.search_list_for_subject(mlist_fqdn, keyword)
+ elif field == 'Content':
+ threads = store.search_list_for_content(mlist_fqdn, keyword)
+ elif field == 'SubjectContent':
+ threads = store.search_list_for_content_subject(mlist_fqdn, keyword)
+ elif field == 'From':
+ threads = store.search_list_for_sender(mlist_fqdn, keyword)
+
if not threads:
- return HttpResponse(status=404)
+ return Response(status=404)
else:
- return threads
+ return Response(EmailSerializer(threads, many=True).data)
diff --git a/hyperkitty/templates/api.html b/hyperkitty/templates/api.html
index 4c4af27..422d6a2 100644
--- a/hyperkitty/templates/api.html
+++ b/hyperkitty/templates/api.html
@@ -26,14 +26,25 @@
+
+
+
+Using the address /api/list/ you will be able to
+retrieve the information known about all the mailing-lists.
+
+
For example:
+ {% url 'api_list' %}
+
+
+
@@ -43,7 +54,7 @@ retrieve the information known about a specific email on the specified mailing-l
Using the address /api/thread/<list name>/<Message-ID> you will be able to
retrieve the all the email for a specific thread on the specified mailing-list.
- For example:
+ For example:
{% url 'api_thread' mlist_fqdn='devel@fp.o' threadid='13129854572893334' %}
@@ -61,7 +72,7 @@ search for all emails of the specified mailing-list containing the provided keyw
Content
SubjectContent
- For example:
+ For example:
{% url 'api_search' mlist_fqdn='devel@fp.o' field='From' keyword='pingoured' %}
diff --git a/hyperkitty/urls.py b/hyperkitty/urls.py
index 887c54f..1a2e945 100644
--- a/hyperkitty/urls.py
+++ b/hyperkitty/urls.py
@@ -23,7 +23,7 @@
from django.conf.urls import patterns, include, url
from django.conf import settings
from django.views.generic.base import TemplateView
-from api import EmailResource, ThreadResource, SearchResource
+from api import ListResource, EmailResource, ThreadResource, SearchResource
from django.contrib.staticfiles.urls import staticfiles_urlpatterns
from django.contrib.auth.views import login as login_view
@@ -93,7 +93,9 @@ urlpatterns = patterns('hyperkitty.views',
# REST API
url(r'^api/$', TemplateView.as_view(template_name="api.html")),
- url(r'^api/email\/(?P[^/@]+@[^/@]+)\/(?P.*)/',
+ url(r'^api/list\/',
+ ListResource.as_view(), name="api_list"),
+ url(r'^api/email\/(?P[^/@]+@[^/@]+)\/(?P.*)/',
EmailResource.as_view(), name="api_email"),
url(r'^api/thread\/(?P[^/@]+@[^/@]+)\/(?P.*)/',
ThreadResource.as_view(), name="api_thread"),
--
cgit