Browse Source

[enh] add result_templates/code.html

Thomas Pointhuber 10 years ago
parent
commit
7adb17452d

+ 1 - 0
requirements.txt

@@ -3,4 +3,5 @@ flask-babel
 requests
 requests
 lxml
 lxml
 pyyaml
 pyyaml
+pygments
 python-dateutil
 python-dateutil

+ 20 - 12
searx/engines/searchcode_code.py

@@ -21,6 +21,18 @@ paging = True
 url = 'https://searchcode.com/'
 url = 'https://searchcode.com/'
 search_url = url+'api/codesearch_I/?{query}&p={pageno}'
 search_url = url+'api/codesearch_I/?{query}&p={pageno}'
 
 
+code_endings = {'c': 'c',
+                'css': 'css',
+                'cpp': 'cpp',
+                'c++': 'cpp',
+                'h': 'c',
+                'html': 'html',
+                'hpp': 'cpp',
+                'js': 'js',
+                'lua': 'lua',
+                'php': 'php',
+                'py': 'python'}
+
 
 
 # do search-request
 # do search-request
 def request(query, params):
 def request(query, params):
@@ -40,26 +52,22 @@ def response(resp):
     for result in search_results['results']:
     for result in search_results['results']:
         href = result['url']
         href = result['url']
         title = "" + result['name'] + " - " + result['filename']
         title = "" + result['name'] + " - " + result['filename']
-        content = result['repo'] + "<br />"
+        repo = result['repo']
         
         
         lines = dict()
         lines = dict()
         for line, code in result['lines'].items():
         for line, code in result['lines'].items():
             lines[int(line)] = code
             lines[int(line)] = code
 
 
-        content = content + '<pre class="code-formatter"><table class="code">'
-        for line, code in sorted(lines.items()):
-            content = content + '<tr><td class="line-number" style="padding-right:5px;">' 
-            content = content + str(line) + '</td><td class="code-snippet">' 
-            # Replace every two spaces with ' &nbps;' to keep formatting while allowing the browser to break the line if necessary
-            content = content + cgi.escape(code).replace('\t', '    ').replace('  ', '&nbsp; ').replace('  ', ' &nbsp;') 
-            content = content + "</td></tr>"
-            
-        content = content + "</table></pre>"
-        
+        code_language = code_endings.get(result['filename'].split('.')[-1].lower(), None)
+
         # append result
         # append result
         results.append({'url': href,
         results.append({'url': href,
                         'title': title,
                         'title': title,
-                        'content': content})
+                        'content': '',
+                        'repository': repo,
+                        'codelines': sorted(lines.items()),
+                        'code_language': code_language,
+                        'template': 'code.html'})
 
 
     # return results
     # return results
     return results
     return results

+ 79 - 1
searx/static/courgette/css/style.css

@@ -579,4 +579,82 @@ select {
   border: 1px solid #DDD;
   border: 1px solid #DDD;
   padding: 0.5em 0.8em;
   padding: 0.5em 0.8em;
   font-size: 1em;
   font-size: 1em;
-}
+}
+
+.highlight .hll { background-color: #ffffcc }
+.highlight  { background: #f8f8f8; }
+.highlight .c { color: #408080; font-style: italic } /* Comment */
+.highlight .err { border: 1px solid #FF0000 } /* Error */
+.highlight .k { color: #008000; font-weight: bold } /* Keyword */
+.highlight .o { color: #666666 } /* Operator */
+.highlight .cm { color: #408080; font-style: italic } /* Comment.Multiline */
+.highlight .cp { color: #BC7A00 } /* Comment.Preproc */
+.highlight .c1 { color: #408080; font-style: italic } /* Comment.Single */
+.highlight .cs { color: #408080; font-style: italic } /* Comment.Special */
+.highlight .gd { color: #A00000 } /* Generic.Deleted */
+.highlight .ge { font-style: italic } /* Generic.Emph */
+.highlight .gr { color: #FF0000 } /* Generic.Error */
+.highlight .gh { color: #000080; font-weight: bold } /* Generic.Heading */
+.highlight .gi { color: #00A000 } /* Generic.Inserted */
+.highlight .go { color: #888888 } /* Generic.Output */
+.highlight .gp { color: #000080; font-weight: bold } /* Generic.Prompt */
+.highlight .gs { font-weight: bold } /* Generic.Strong */
+.highlight .gu { color: #800080; font-weight: bold } /* Generic.Subheading */
+.highlight .gt { color: #0044DD } /* Generic.Traceback */
+.highlight .kc { color: #008000; font-weight: bold } /* Keyword.Constant */
+.highlight .kd { color: #008000; font-weight: bold } /* Keyword.Declaration */
+.highlight .kn { color: #008000; font-weight: bold } /* Keyword.Namespace */
+.highlight .kp { color: #008000 } /* Keyword.Pseudo */
+.highlight .kr { color: #008000; font-weight: bold } /* Keyword.Reserved */
+.highlight .kt { color: #B00040 } /* Keyword.Type */
+.highlight .m { color: #666666 } /* Literal.Number */
+.highlight .s { color: #BA2121 } /* Literal.String */
+.highlight .na { color: #7D9029 } /* Name.Attribute */
+.highlight .nb { color: #008000 } /* Name.Builtin */
+.highlight .nc { color: #0000FF; font-weight: bold } /* Name.Class */
+.highlight .no { color: #880000 } /* Name.Constant */
+.highlight .nd { color: #AA22FF } /* Name.Decorator */
+.highlight .ni { color: #999999; font-weight: bold } /* Name.Entity */
+.highlight .ne { color: #D2413A; font-weight: bold } /* Name.Exception */
+.highlight .nf { color: #0000FF } /* Name.Function */
+.highlight .nl { color: #A0A000 } /* Name.Label */
+.highlight .nn { color: #0000FF; font-weight: bold } /* Name.Namespace */
+.highlight .nt { color: #008000; font-weight: bold } /* Name.Tag */
+.highlight .nv { color: #19177C } /* Name.Variable */
+.highlight .ow { color: #AA22FF; font-weight: bold } /* Operator.Word */
+.highlight .w { color: #bbbbbb } /* Text.Whitespace */
+.highlight .mf { color: #666666 } /* Literal.Number.Float */
+.highlight .mh { color: #666666 } /* Literal.Number.Hex */
+.highlight .mi { color: #666666 } /* Literal.Number.Integer */
+.highlight .mo { color: #666666 } /* Literal.Number.Oct */
+.highlight .sb { color: #BA2121 } /* Literal.String.Backtick */
+.highlight .sc { color: #BA2121 } /* Literal.String.Char */
+.highlight .sd { color: #BA2121; font-style: italic } /* Literal.String.Doc */
+.highlight .s2 { color: #BA2121 } /* Literal.String.Double */
+.highlight .se { color: #BB6622; font-weight: bold } /* Literal.String.Escape */
+.highlight .sh { color: #BA2121 } /* Literal.String.Heredoc */
+.highlight .si { color: #BB6688; font-weight: bold } /* Literal.String.Interpol */
+.highlight .sx { color: #008000 } /* Literal.String.Other */
+.highlight .sr { color: #BB6688 } /* Literal.String.Regex */
+.highlight .s1 { color: #BA2121 } /* Literal.String.Single */
+.highlight .ss { color: #19177C } /* Literal.String.Symbol */
+.highlight .bp { color: #008000 } /* Name.Builtin.Pseudo */
+.highlight .vc { color: #19177C } /* Name.Variable.Class */
+.highlight .vg { color: #19177C } /* Name.Variable.Global */
+.highlight .vi { color: #19177C } /* Name.Variable.Instance */
+.highlight .il { color: #666666 } /* Literal.Number.Integer.Long */
+
+.highlight pre { overflow: auto; }
+
+.highlight .lineno {
+    -webkit-touch-callout: none;
+    -webkit-user-select: none;
+    -khtml-user-select: none;
+    -moz-user-select: none;
+    -ms-user-select: none;
+    user-select: none;
+    cursor: default;
+}
+    
+.highlight .lineno::selection { background: transparent; } /* WebKit/Blink Browsers */
+.highlight .lineno::-moz-selection { background: transparent; } /* Gecko Browsers */

File diff suppressed because it is too large
+ 0 - 86
searx/static/default/css/style.css


+ 83 - 0
searx/static/default/less/code.less

@@ -0,0 +1,83 @@
+.highlight .hll { background-color: #ffffcc }
+.highlight  { background: #f8f8f8; }
+.highlight .c { color: #408080; font-style: italic } /* Comment */
+.highlight .err { border: 1px solid #FF0000 } /* Error */
+.highlight .k { color: #008000; font-weight: bold } /* Keyword */
+.highlight .o { color: #666666 } /* Operator */
+.highlight .cm { color: #408080; font-style: italic } /* Comment.Multiline */
+.highlight .cp { color: #BC7A00 } /* Comment.Preproc */
+.highlight .c1 { color: #408080; font-style: italic } /* Comment.Single */
+.highlight .cs { color: #408080; font-style: italic } /* Comment.Special */
+.highlight .gd { color: #A00000 } /* Generic.Deleted */
+.highlight .ge { font-style: italic } /* Generic.Emph */
+.highlight .gr { color: #FF0000 } /* Generic.Error */
+.highlight .gh { color: #000080; font-weight: bold } /* Generic.Heading */
+.highlight .gi { color: #00A000 } /* Generic.Inserted */
+.highlight .go { color: #888888 } /* Generic.Output */
+.highlight .gp { color: #000080; font-weight: bold } /* Generic.Prompt */
+.highlight .gs { font-weight: bold } /* Generic.Strong */
+.highlight .gu { color: #800080; font-weight: bold } /* Generic.Subheading */
+.highlight .gt { color: #0044DD } /* Generic.Traceback */
+.highlight .kc { color: #008000; font-weight: bold } /* Keyword.Constant */
+.highlight .kd { color: #008000; font-weight: bold } /* Keyword.Declaration */
+.highlight .kn { color: #008000; font-weight: bold } /* Keyword.Namespace */
+.highlight .kp { color: #008000 } /* Keyword.Pseudo */
+.highlight .kr { color: #008000; font-weight: bold } /* Keyword.Reserved */
+.highlight .kt { color: #B00040 } /* Keyword.Type */
+.highlight .m { color: #666666 } /* Literal.Number */
+.highlight .s { color: #BA2121 } /* Literal.String */
+.highlight .na { color: #7D9029 } /* Name.Attribute */
+.highlight .nb { color: #008000 } /* Name.Builtin */
+.highlight .nc { color: #0000FF; font-weight: bold } /* Name.Class */
+.highlight .no { color: #880000 } /* Name.Constant */
+.highlight .nd { color: #AA22FF } /* Name.Decorator */
+.highlight .ni { color: #999999; font-weight: bold } /* Name.Entity */
+.highlight .ne { color: #D2413A; font-weight: bold } /* Name.Exception */
+.highlight .nf { color: #0000FF } /* Name.Function */
+.highlight .nl { color: #A0A000 } /* Name.Label */
+.highlight .nn { color: #0000FF; font-weight: bold } /* Name.Namespace */
+.highlight .nt { color: #008000; font-weight: bold } /* Name.Tag */
+.highlight .nv { color: #19177C } /* Name.Variable */
+.highlight .ow { color: #AA22FF; font-weight: bold } /* Operator.Word */
+.highlight .w { color: #bbbbbb } /* Text.Whitespace */
+.highlight .mf { color: #666666 } /* Literal.Number.Float */
+.highlight .mh { color: #666666 } /* Literal.Number.Hex */
+.highlight .mi { color: #666666 } /* Literal.Number.Integer */
+.highlight .mo { color: #666666 } /* Literal.Number.Oct */
+.highlight .sb { color: #BA2121 } /* Literal.String.Backtick */
+.highlight .sc { color: #BA2121 } /* Literal.String.Char */
+.highlight .sd { color: #BA2121; font-style: italic } /* Literal.String.Doc */
+.highlight .s2 { color: #BA2121 } /* Literal.String.Double */
+.highlight .se { color: #BB6622; font-weight: bold } /* Literal.String.Escape */
+.highlight .sh { color: #BA2121 } /* Literal.String.Heredoc */
+.highlight .si { color: #BB6688; font-weight: bold } /* Literal.String.Interpol */
+.highlight .sx { color: #008000 } /* Literal.String.Other */
+.highlight .sr { color: #BB6688 } /* Literal.String.Regex */
+.highlight .s1 { color: #BA2121 } /* Literal.String.Single */
+.highlight .ss { color: #19177C } /* Literal.String.Symbol */
+.highlight .bp { color: #008000 } /* Name.Builtin.Pseudo */
+.highlight .vc { color: #19177C } /* Name.Variable.Class */
+.highlight .vg { color: #19177C } /* Name.Variable.Global */
+.highlight .vi { color: #19177C } /* Name.Variable.Instance */
+.highlight .il { color: #666666 } /* Literal.Number.Integer.Long */
+
+.highlight pre {
+    overflow: auto;
+}
+
+.highlight .lineno {
+    -webkit-touch-callout: none;
+    -webkit-user-select: none;
+    -khtml-user-select: none;
+    -moz-user-select: none;
+    -ms-user-select: none;
+    user-select: none;
+    cursor: default;
+    
+    &::selection {
+        background: transparent; /* WebKit/Blink Browsers */
+    }
+    &::-moz-selection {
+        background: transparent; /* Gecko Browsers */
+    }
+}

+ 2 - 0
searx/static/default/less/style.less

@@ -8,6 +8,8 @@
 
 
 @import "mixins.less";
 @import "mixins.less";
 
 
+@import "code.less";
+
 // Main LESS-Code
 // Main LESS-Code
 
 
 html {
 html {

File diff suppressed because it is too large
+ 0 - 369
searx/static/oscar/css/bootstrap.min.css


File diff suppressed because it is too large
+ 0 - 22
searx/static/oscar/css/oscar.min.css


+ 79 - 0
searx/static/oscar/less/oscar/code.less

@@ -0,0 +1,79 @@
+.highlight .hll { background-color: #ffffcc }
+.highlight  { background: #f8f8f8; }
+.highlight .c { color: #408080; font-style: italic } /* Comment */
+.highlight .err { border: 1px solid #FF0000 } /* Error */
+.highlight .k { color: #008000; font-weight: bold } /* Keyword */
+.highlight .o { color: #666666 } /* Operator */
+.highlight .cm { color: #408080; font-style: italic } /* Comment.Multiline */
+.highlight .cp { color: #BC7A00 } /* Comment.Preproc */
+.highlight .c1 { color: #408080; font-style: italic } /* Comment.Single */
+.highlight .cs { color: #408080; font-style: italic } /* Comment.Special */
+.highlight .gd { color: #A00000 } /* Generic.Deleted */
+.highlight .ge { font-style: italic } /* Generic.Emph */
+.highlight .gr { color: #FF0000 } /* Generic.Error */
+.highlight .gh { color: #000080; font-weight: bold } /* Generic.Heading */
+.highlight .gi { color: #00A000 } /* Generic.Inserted */
+.highlight .go { color: #888888 } /* Generic.Output */
+.highlight .gp { color: #000080; font-weight: bold } /* Generic.Prompt */
+.highlight .gs { font-weight: bold } /* Generic.Strong */
+.highlight .gu { color: #800080; font-weight: bold } /* Generic.Subheading */
+.highlight .gt { color: #0044DD } /* Generic.Traceback */
+.highlight .kc { color: #008000; font-weight: bold } /* Keyword.Constant */
+.highlight .kd { color: #008000; font-weight: bold } /* Keyword.Declaration */
+.highlight .kn { color: #008000; font-weight: bold } /* Keyword.Namespace */
+.highlight .kp { color: #008000 } /* Keyword.Pseudo */
+.highlight .kr { color: #008000; font-weight: bold } /* Keyword.Reserved */
+.highlight .kt { color: #B00040 } /* Keyword.Type */
+.highlight .m { color: #666666 } /* Literal.Number */
+.highlight .s { color: #BA2121 } /* Literal.String */
+.highlight .na { color: #7D9029 } /* Name.Attribute */
+.highlight .nb { color: #008000 } /* Name.Builtin */
+.highlight .nc { color: #0000FF; font-weight: bold } /* Name.Class */
+.highlight .no { color: #880000 } /* Name.Constant */
+.highlight .nd { color: #AA22FF } /* Name.Decorator */
+.highlight .ni { color: #999999; font-weight: bold } /* Name.Entity */
+.highlight .ne { color: #D2413A; font-weight: bold } /* Name.Exception */
+.highlight .nf { color: #0000FF } /* Name.Function */
+.highlight .nl { color: #A0A000 } /* Name.Label */
+.highlight .nn { color: #0000FF; font-weight: bold } /* Name.Namespace */
+.highlight .nt { color: #008000; font-weight: bold } /* Name.Tag */
+.highlight .nv { color: #19177C } /* Name.Variable */
+.highlight .ow { color: #AA22FF; font-weight: bold } /* Operator.Word */
+.highlight .w { color: #bbbbbb } /* Text.Whitespace */
+.highlight .mf { color: #666666 } /* Literal.Number.Float */
+.highlight .mh { color: #666666 } /* Literal.Number.Hex */
+.highlight .mi { color: #666666 } /* Literal.Number.Integer */
+.highlight .mo { color: #666666 } /* Literal.Number.Oct */
+.highlight .sb { color: #BA2121 } /* Literal.String.Backtick */
+.highlight .sc { color: #BA2121 } /* Literal.String.Char */
+.highlight .sd { color: #BA2121; font-style: italic } /* Literal.String.Doc */
+.highlight .s2 { color: #BA2121 } /* Literal.String.Double */
+.highlight .se { color: #BB6622; font-weight: bold } /* Literal.String.Escape */
+.highlight .sh { color: #BA2121 } /* Literal.String.Heredoc */
+.highlight .si { color: #BB6688; font-weight: bold } /* Literal.String.Interpol */
+.highlight .sx { color: #008000 } /* Literal.String.Other */
+.highlight .sr { color: #BB6688 } /* Literal.String.Regex */
+.highlight .s1 { color: #BA2121 } /* Literal.String.Single */
+.highlight .ss { color: #19177C } /* Literal.String.Symbol */
+.highlight .bp { color: #008000 } /* Name.Builtin.Pseudo */
+.highlight .vc { color: #19177C } /* Name.Variable.Class */
+.highlight .vg { color: #19177C } /* Name.Variable.Global */
+.highlight .vi { color: #19177C } /* Name.Variable.Instance */
+.highlight .il { color: #666666 } /* Literal.Number.Integer.Long */
+
+.highlight .lineno {
+    -webkit-touch-callout: none;
+    -webkit-user-select: none;
+    -khtml-user-select: none;
+    -moz-user-select: none;
+    -ms-user-select: none;
+    user-select: none;
+    cursor: default;
+    
+    &::selection {
+        background: transparent; /* WebKit/Blink Browsers */
+    }
+    &::-moz-selection {
+        background: transparent; /* Gecko Browsers */
+    }
+}

+ 2 - 0
searx/static/oscar/less/oscar/oscar.less

@@ -9,3 +9,5 @@
 @import "search.less";
 @import "search.less";
 
 
 @import "cursor.less";
 @import "cursor.less";
+
+@import "code.less";

+ 9 - 0
searx/templates/courgette/result_templates/code.html

@@ -0,0 +1,9 @@
+<div class="result {{ result.class }}">
+    <h3 class="result_title"> {% if result['favicon'] %}<img width="14" height="14" class="favicon" src="static/{{theme}}/img/icon_{{result['favicon']}}.ico" alt="{{result['favicon']}}" />{% endif %}<a href="{{ result.url }}">{{ result.title|safe }}</a></h3>
+    <p class="url">{{ result.pretty_url }} <a class="cache_link" href="https://web.archive.org/web/{{ result.url }}">cached</a></p>
+    {% if result.publishedDate %}<p class="published_date">{{ result.publishedDate }}</p>{% endif %}
+    <p class="content">{% if result.img_src %}<img src="{{ result.img_src }}" class="image" />{% endif %}{% if result.content %}{{ result.content|safe }}<br class="last"/>{% endif %}</p>
+    {% if result.repository %}<p class="result-content"><a href="{{ result.repository|safe }}">{{ result.repository }}</a></p>{% endif %}
+
+    {{ result.codelines|code_highlighter(result.code_language)|safe }}
+</div>

+ 9 - 0
searx/templates/default/result_templates/code.html

@@ -0,0 +1,9 @@
+<div class="result {{ result.class }}">
+    <h3 class="result_title"> {% if result['favicon'] %}<img width="14" height="14" class="favicon" src="static/{{theme}}/img/icon_{{result['favicon']}}.ico" alt="{{result['favicon']}}" />{% endif %}<a href="{{ result.url }}">{{ result.title|safe }}</a></h3>
+    <p class="url">{{ result.pretty_url }} <a class="cache_link" href="https://web.archive.org/web/{{ result.url }}">cached</a></p>
+    {% if result.publishedDate %}<p class="published_date">{{ result.publishedDate }}</p>{% endif %}
+    <p class="content">{% if result.img_src %}<img src="{{ result.img_src }}" class="image" />{% endif %}{% if result.content %}{{ result.content|safe }}<br class="last"/>{% endif %}</p>
+    {% if result.repository %}<p class="result-content"><a href="{{ result.repository|safe }}">{{ result.repository }}</a></p>{% endif %}
+
+    {{ result.codelines|code_highlighter(result.code_language)|safe }}
+</div>

+ 17 - 0
searx/templates/oscar/result_templates/code.html

@@ -0,0 +1,17 @@
+{% from 'oscar/macros.html' import icon %}
+
+<h4 class="result_header">{% if result['favicon'] %}<img width="32" height="32" class="favicon" src="static/{{ theme }}/img/icons/{{ result['favicon'] }}.png" alt="{{ result['favicon'] }}" /> {% endif %}<a href="{{ result.url }}">{{ result.title|safe }}</a></h4>
+
+{% if result.publishedDate %}<time class="text-muted" datetime="{{ result.pubdate }}" >{{ result.publishedDate }}</time>{% endif %}
+<small><a class="text-info" href="https://web.archive.org/web/{{ result.url }}">{{ icon('link') }} {{ _('cached') }}</a></small>
+
+{% if result.content %}<p class="result-content">{{ result.content|safe }}</p>{% endif %}
+
+{% if result.repository %}<p class="result-content">{{ icon('file') }} <a href="{{ result.repository|safe }}">{{ result.repository }}</a></p>{% endif %}
+
+{{ result.codelines|code_highlighter(result.code_language)|safe }}
+
+<div class="clearfix"></div>
+
+<span class="label label-default pull-right">{{ result.engine }}</span>
+<p class="text-muted">{{ result.pretty_url }}</p>

+ 46 - 0
searx/webapp.py

@@ -33,6 +33,9 @@ from flask import (
     redirect, send_from_directory
     redirect, send_from_directory
 )
 )
 from flask.ext.babel import Babel, gettext, format_date
 from flask.ext.babel import Babel, gettext, format_date
+from pygments import highlight
+from pygments.lexers import get_lexer_by_name
+from pygments.formatters import HtmlFormatter
 from searx import settings, searx_dir
 from searx import settings, searx_dir
 from searx.engines import (
 from searx.engines import (
     categories, engines, get_engines_stats, engine_shortcuts
     categories, engines, get_engines_stats, engine_shortcuts
@@ -90,6 +93,49 @@ def get_locale():
     return locale
     return locale
 
 
 
 
+# code-highlighter
+@app.template_filter('code_highlighter')
+def code_highlighter(codelines, language=None):
+    if not language:
+        language = 'text'
+
+    # find lexer by programing language
+    lexer = get_lexer_by_name(language, stripall=True)
+    
+    html_code = ''
+    tmp_code = ''
+    last_line = None
+
+    # parse lines
+    for line, code in codelines:
+        if not last_line:
+            line_code_start = line
+
+        # new codeblock is detected
+        if last_line != None and\
+           last_line +1 != line:
+
+            # highlight last codepart
+            formatter = HtmlFormatter(linenos='inline', linenostart=line_code_start)
+            html_code = html_code + highlight(tmp_code, lexer, formatter)
+            
+            # reset conditions for next codepart
+            tmp_code = ''
+            line_code_start = line
+
+        # add codepart
+        tmp_code += code + '\n'
+        
+        # update line
+        last_line = line
+
+    # highlight last codepart
+    formatter = HtmlFormatter(linenos='inline', linenostart=line_code_start)
+    html_code = html_code + highlight(tmp_code, lexer, formatter)
+
+    return html_code
+
+
 def get_base_url():
 def get_base_url():
     if settings['server']['base_url']:
     if settings['server']['base_url']:
         hostname = settings['server']['base_url']
         hostname = settings['server']['base_url']

+ 1 - 0
setup.py

@@ -44,6 +44,7 @@ setup(
         'requests',
         'requests',
         'lxml',
         'lxml',
         'pyyaml',
         'pyyaml',
+        'pygments',
         'setuptools',
         'setuptools',
         'python-dateutil',
         'python-dateutil',
     ],
     ],

+ 1 - 0
versions.cfg

@@ -4,6 +4,7 @@ Flask = 0.10.1
 Flask-Babel = 0.9
 Flask-Babel = 0.9
 Jinja2 = 2.7.2
 Jinja2 = 2.7.2
 MarkupSafe = 0.18
 MarkupSafe = 0.18
+Pygments = 2.0.1
 WebOb = 1.3.1
 WebOb = 1.3.1
 WebTest = 2.0.11
 WebTest = 2.0.11
 Werkzeug = 0.9.4
 Werkzeug = 0.9.4

Some files were not shown because too many files changed in this diff