convert to unicode_literals
[htsworkflow.git] / bcmagic / views.py
1 from __future__ import unicode_literals
2
3 from django.http import HttpResponse
4 from django.template import RequestContext, Template, Context
5 from django.shortcuts import render_to_response
6 from django.core.exceptions import ObjectDoesNotExist
7
8 from . import models
9 from .utils import report_error, redirect_to_url
10 from .plugin import bcm_plugin_processor
11 from . import plugin
12 #from htsworkflow.util.jsonutil import encode_json
13
14 try:
15     import json
16 except ImportError as e:
17     import simplejson as json
18
19 import re
20
21 from htsworkflow.frontend.bcmagic import forms
22
23
24 def index(request):
25     """
26     Display a barcode magic input box
27     """
28     form = forms.BarcodeMagicForm()
29
30     return render_to_response('bcmagic/magic.html', {'bcmagic': form},
31                               context_instance=RequestContext(request))
32
33
34 def __plugin_search(text):
35     """
36     Runs registered plugins to search for results
37     """
38
39     hits = []
40     for label, search_func in plugin._SEARCH_FUNCTIONS.items():
41         result = search_func(text)
42         if result is not None:
43             hits.extend(result)
44
45     n = len(hits)
46     if n == 0:
47         msg = 'No hits found for: %s' % (text)
48         return report_error(msg)
49     elif n == 1:
50         return redirect_to_url(hits[0][1])
51     else:
52         msg = "%d hits found for (%s); multi-hit not implemented yet." % \
53               (n, text)
54         return report_error(msg)
55
56
57     #return json.dumps(hits)
58
59
60 def __magic_process(text):
61     """
62     Based on scanned text, check to see if there is map object to use
63     for a useful redirect.
64     """
65     # Split text on |
66     split_text = text.split('|')
67
68     # There should always be at least one | in a valid scan.
69     if len(split_text) <= 1:
70         #return report_error('Invalid text: %s' % (text))
71         return __plugin_search(text)
72
73     # Keyword is the first element in the list
74     keyword = split_text[0]
75
76     # Attempt to find a KeywordMap based on keyword
77     try:
78         keymap = models.KeywordMap.objects.get(keyword=keyword)
79     except ObjectDoesNotExist(e):
80         return report_error('Keyword (%s) is not defined' % (keyword))
81
82     # Remove keyword and only scan the content
83     content = '|'.join(split_text[1:])
84
85     #FIXME: would be faster to cache compiled regex
86     search = re.compile(keymap.regex)
87
88     mo = search.search(content)
89
90     # if the search was invalid
91     if not mo:
92         return report_error(
93             '(%s) failed to match (%s)' % (keymap.regex, content)
94         )
95
96     t = Template(keymap.url_template)
97     c = Context(mo.groupdict())
98
99     return redirect_to_url(str(t.render(c)))
100
101
102 def magic(request):
103     """
104     Let the magic begin
105     """
106     d = {}
107
108     #Retrieve posted text from processing
109     if 'text' in request.POST:
110         text = request.POST['text']
111     else:
112         text = None
113
114     #Retrieve bmc_mode for processing
115     if 'bcm_mode' in request.POST:
116         bcm_mode = request.POST['bcm_mode']
117     else:
118         bcm_mode = None
119
120     ################################
121     # Handle some errors
122     ################################
123
124     # Did not receive text error
125     if text is None or text.strip() == '':
126         d['mode'] = 'Error'
127         d['status'] = 'Did not recieve text'
128
129         return HttpResponse(json.dumps(d), 'text/plain')
130
131     # Did not receive bcm_mode error
132     if bcm_mode is None or bcm_mode.strip() == '':
133         d['mode'] = 'Error'
134         d['status'] = 'Missing bcm_mode information'
135
136     ################################
137     # Figure out which mode to use
138     ################################
139     keyword = text.split('|')[0]
140
141     # Handle URL mode by default
142     if keyword == 'url':
143         d['mode'] = 'redirect'
144         d['url'] = text.split('|')[1]
145
146     # Pass off processing to plugins
147     elif bcm_mode != 'default':
148         d = bcm_plugin_processor(keyword, text, bcm_mode)
149
150     # Try keyword mapper
151     else:
152         d = __magic_process(text)
153
154     return HttpResponse(json.dumps(d), 'text/plain')
155
156
157 def json_test(request):
158     d = {}
159
160     if 'text' in request.POST:
161         text = request.POST['text']
162     else:
163         text = None
164
165     #return HttpResponse(json.dumps(request.POST.items()), 'text/plain')
166     if text is None or text.strip() == '':
167         d['mode'] = 'Error'
168         d['status'] = 'Did not recieve text'
169         return HttpResponse(json.dumps(d), 'text/plain')
170
171     if text.split('|')[0] == 'url':
172         d['mode'] = 'redirect'
173         d['url'] = text.split('|')[1]
174     else:
175         d['msg'] = 'Recieved text: %s' % (text)
176         d['mode'] = 'clear'
177
178     return HttpResponse(json.dumps(d), 'text/plain')