Use new lingua extractor API

This gives a saner way to call into lingua's Python extractor.
diff --git a/mako/ext/babelplugin.py b/mako/ext/babelplugin.py
index e761f5b..699d8e0 100644
--- a/mako/ext/babelplugin.py
+++ b/mako/ext/babelplugin.py
@@ -11,10 +11,10 @@
 
 class BabelMakoExtractor(MessageExtractor):
     def __init__(self, keywords, comment_tags, options):
-        self.comment_tags = comment_tags
         self.keywords = keywords
         self.options = options
         self.config = {
+                'comment-tags': u' '.join(comment_tags),
                 'encoding': options.get('input_encoding',
                     options.get('encoding', None)),
             }
@@ -24,9 +24,10 @@
         return self.process_file(fileobj)
 
     def process_python(self, code, code_lineno, translator_strings):
+        comment_tags = self.config['comment-tags']
         for lineno, funcname, messages, python_translator_comments \
                 in extract_python(code,
-                        self.keywords, self.comment_tags, self.options):
+                        self.keywords, comment_tags, self.options):
             yield (code_lineno + (lineno - 1), funcname, messages,
                    translator_strings + python_translator_comments)
 
diff --git a/mako/ext/extract.py b/mako/ext/extract.py
index 8165793..0d9c60c 100644
--- a/mako/ext/extract.py
+++ b/mako/ext/extract.py
@@ -1,3 +1,4 @@
+import re
 from mako import compat
 from mako import lexer
 from mako import parsetree
@@ -13,6 +14,7 @@
     def extract_nodes(self, nodes):
         translator_comments = []
         in_translator_comments = False
+        comment_tags = filter(None, re.split(r'\s+', self.config['comment-tags']))
 
         for node in nodes:
             child_nodes = None
@@ -26,7 +28,7 @@
                 if in_translator_comments:
                     translator_comments.extend(self._split_comment(node.lineno, value))
                     continue
-                for comment_tag in self.comment_tags:
+                for comment_tag in comment_tags:
                     if value.startswith(comment_tag):
                         in_translator_comments = True
                         translator_comments.extend(self._split_comment(node.lineno,
diff --git a/mako/ext/linguaplugin.py b/mako/ext/linguaplugin.py
index 3bbdb2f..2f970d9 100644
--- a/mako/ext/linguaplugin.py
+++ b/mako/ext/linguaplugin.py
@@ -1,5 +1,7 @@
+import io
 from lingua.extractors import Extractor
-from lingua.extractors.python import _extract_python
+from lingua.extractors import Message
+from lingua.extractors import get_extractor
 from mako.ext.extract import MessageExtractor
 
 
@@ -8,17 +10,23 @@
     extensions = ['.mako']
     default_config = {
             'encoding': 'utf-8',
+            'comment-tags': '',
             }
 
-    def __call__(self, filename, options):
+    def __call__(self, filename, options, fileobj=None):
         self.options = options
         self.filename = filename
-        with open(filename) as input:
-            return self.process_file(fileobj)
+        self.python_extractor = get_extractor('x.py')
+        if fileobj is None:
+            fileobj = open(filename, 'rb')
+        return self.process_file(fileobj)
 
     def process_python(self, code, code_lineno, translator_strings):
-        for msg in _extract_python(self.filename, code.getvalue(), self.options,
-                code_lineno):
+        source = code.getvalue().strip()
+        if source.endswith(':'):
+            source += ' pass'
+            code = io.BytesIO(source)
+        for msg in self.python_extractor(self.filename, self.options, code, code_lineno):
             if translator_strings:
                 msg = Message(msg.msgctxt, msg.msgid, msg.msgid_plural,
                               msg.flags,
diff --git a/setup.py b/setup.py
index 11dbb14..60ce08e 100644
--- a/setup.py
+++ b/setup.py
@@ -47,7 +47,7 @@
       url='http://www.makotemplates.org/',
       license='MIT',
       packages=find_packages('.', exclude=['examples*', 'test*']),
-      tests_require=['nose >= 0.11', 'mock', 'Babel', 'lingua'],
+      tests_require=['nose >= 0.11', 'mock', 'Babel', 'lingua >= 3.2'],
       test_suite="nose.collector",
       zip_safe=False,
       install_requires=install_requires,
diff --git a/test/ext/test_linguaplugin.py b/test/ext/test_linguaplugin.py
index 841f206..55b3ba1 100644
--- a/test/ext/test_linguaplugin.py
+++ b/test/ext/test_linguaplugin.py
@@ -1,7 +1,7 @@
-import io
-import mock
-import unittest
+import os
 from mako.ext.linguaplugin import LinguaMakoExtractor
+from lingua.extractors import register_extractors
+from .. import TemplateTest, template_base
 
 
 class MockOptions:
@@ -9,11 +9,35 @@
     domain = None
 
 
-class Test_LinguaMakoExtractor(unittest.TestCase):
-    def test_parse_python_expression(self):
-        plugin = LinguaMakoExtractor()
-        plugin.options = MockOptions()
-        plugin.filename = 'dummy.mako'
-        input = io.BytesIO(b'<p>${_("Message")}</p>')
-        messages = list(plugin.process_file(input))
-        self.assertEqual(len(messages), 1)
+class ExtractMakoTestCase(TemplateTest):
+    def test_extract(self):
+        register_extractors()
+        plugin = LinguaMakoExtractor({'comment-tags': 'TRANSLATOR'})
+        messages = list(plugin(os.path.join(template_base, 'gettext.mako'), MockOptions()))
+        msgids = [(m.msgid, m.msgid_plural) for m in messages]
+        self.assertEqual(
+                msgids,
+                [
+                    ('Page arg 1', None),
+                    ('Page arg 2', None),
+                    ('Begin', None),
+                    ('Hi there!', None),
+                    ('Hello', None),
+                    ('Welcome', None),
+                    ('Yo', None),
+                    ('The', None),
+                    ('bunny', 'bunnies'),
+                    ('Goodbye', None),
+                    ('Babel', None),
+                    ('hella', 'hellas'),
+                    ('The', None),
+                    ('bunny', 'bunnies'),
+                    ('Goodbye, really!', None),
+                    ('P.S. byebye', None),
+                    ('Top', None),
+                    (u'foo', None),
+                    ('hoho', None),
+                    (u'bar', None),
+                    ('Inside a p tag', None),
+                    ('Later in a p tag', None),
+                    ('No action at a distance.', None)])