Hello community,

here is the log from the commit of package python-certbot-nginx for 
openSUSE:Factory checked in at 2020-05-14 23:27:09
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-certbot-nginx (Old)
 and      /work/SRC/openSUSE:Factory/.python-certbot-nginx.new.2738 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "python-certbot-nginx"

Thu May 14 23:27:09 2020 rev:19 rq:805545 version:1.4.0

Changes:
--------
--- 
/work/SRC/openSUSE:Factory/python-certbot-nginx/python-certbot-nginx.changes    
    2020-03-11 18:56:42.159711268 +0100
+++ 
/work/SRC/openSUSE:Factory/.python-certbot-nginx.new.2738/python-certbot-nginx.changes
      2020-05-14 23:27:11.701295301 +0200
@@ -1,0 +2,7 @@
+Thu May 14 08:51:38 UTC 2020 - Marketa Calabkova <mcalabk...@suse.com>
+
+- update to version 1.4.0
+  * Fix nginx plugin crash when non-ASCII configuration file is being read 
(instead,
+    the user will be warned that UTF-8 must be used).
+
+-------------------------------------------------------------------

Old:
----
  certbot-nginx-1.3.0.tar.gz

New:
----
  certbot-nginx-1.4.0.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ python-certbot-nginx.spec ++++++
--- /var/tmp/diff_new_pack.u4X5he/_old  2020-05-14 23:27:12.373296767 +0200
+++ /var/tmp/diff_new_pack.u4X5he/_new  2020-05-14 23:27:12.373296767 +0200
@@ -18,14 +18,13 @@
 
 %{?!python_module:%define python_module() python-%{**} python3-%{**}}
 Name:           python-certbot-nginx
-Version:        1.3.0
+Version:        1.4.0
 Release:        0
 Summary:        Nginx plugin for Certbot
 License:        Apache-2.0
 URL:            https://github.com/letsencrypt/letsencrypt
 Source:         
https://files.pythonhosted.org/packages/source/c/certbot-nginx/certbot-nginx-%{version}.tar.gz
-BuildRequires:  %{python_module certbot >= 1.1.0}
-BuildRequires:  %{python_module mock}
+BuildRequires:  %{python_module certbot >= 1.4.0}
 BuildRequires:  %{python_module pyOpenSSL}
 BuildRequires:  %{python_module pyparsing >= 1.5.5}
 BuildRequires:  %{python_module pytest}
@@ -34,8 +33,8 @@
 BuildRequires:  nginx
 BuildRequires:  python-rpm-macros
 Requires:       nginx
-Requires:       python-acme >= 1.0.0
-Requires:       python-certbot >= 1.1.0
+Requires:       python-acme >= 1.4.0
+Requires:       python-certbot >= 1.4.0
 Requires:       python-pyOpenSSL
 Requires:       python-pyparsing >= 1.5.5
 Requires:       python-zope.interface

++++++ certbot-nginx-1.3.0.tar.gz -> certbot-nginx-1.4.0.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/PKG-INFO 
new/certbot-nginx-1.4.0/PKG-INFO
--- old/certbot-nginx-1.3.0/PKG-INFO    2020-03-03 21:36:47.000000000 +0100
+++ new/certbot-nginx-1.4.0/PKG-INFO    2020-05-05 21:37:47.727920800 +0200
@@ -1,6 +1,6 @@
 Metadata-Version: 1.2
 Name: certbot-nginx
-Version: 1.3.0
+Version: 1.4.0
 Summary: Nginx plugin for Certbot
 Home-page: https://github.com/letsencrypt/letsencrypt
 Author: Certbot Project
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/certbot_nginx/_internal/configurator.py 
new/certbot-nginx-1.4.0/certbot_nginx/_internal/configurator.py
--- old/certbot-nginx-1.3.0/certbot_nginx/_internal/configurator.py     
2020-03-03 21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/certbot_nginx/_internal/configurator.py     
2020-05-05 21:37:33.000000000 +0200
@@ -1,5 +1,4 @@
 """Nginx Configuration"""
-# https://github.com/PyCQA/pylint/issues/73
 from distutils.version import LooseVersion
 import logging
 import re
@@ -749,7 +748,7 @@
 
             # if there is no separate SSL block, break the block into two and
             # choose the SSL block.
-            if vhost.ssl and any([not addr.ssl for addr in vhost.addrs]):
+            if vhost.ssl and any(not addr.ssl for addr in vhost.addrs):
                 _, vhost = self._split_block(vhost)
 
             header_directives = [
@@ -984,7 +983,7 @@
             logger.warning("NGINX derivative %s is not officially supported by"
                            " certbot", product_name)
 
-        nginx_version = tuple([int(i) for i in product_version.split(".")])
+        nginx_version = tuple(int(i) for i in product_version.split("."))
 
         # nginx < 0.8.48 uses machine hostname as default server_name instead 
of
         # the empty string
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/certbot_nginx/_internal/display_ops.py 
new/certbot-nginx-1.4.0/certbot_nginx/_internal/display_ops.py
--- old/certbot-nginx-1.3.0/certbot_nginx/_internal/display_ops.py      
2020-03-03 21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/certbot_nginx/_internal/display_ops.py      
2020-05-05 21:37:33.000000000 +0200
@@ -17,7 +17,7 @@
     :rtype: :class:`list`of type `~obj.Vhost`
     """
     if not vhosts:
-        return list()
+        return []
     tags_list = [vhost.display_repr()+"\n" for vhost in vhosts]
     # Remove the extra newline from the last entry
     if tags_list:
@@ -33,7 +33,7 @@
 def _reversemap_vhosts(names, vhosts):
     """Helper function for select_vhost_multiple for mapping string
     representations back to actual vhost objects"""
-    return_vhosts = list()
+    return_vhosts = []
 
     for selection in names:
         for vhost in vhosts:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/certbot_nginx/_internal/parser.py 
new/certbot-nginx-1.4.0/certbot_nginx/_internal/parser.py
--- old/certbot-nginx-1.3.0/certbot_nginx/_internal/parser.py   2020-03-03 
21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/certbot_nginx/_internal/parser.py   2020-05-05 
21:37:33.000000000 +0200
@@ -2,6 +2,7 @@
 import copy
 import functools
 import glob
+import io
 import logging
 import re
 
@@ -205,12 +206,16 @@
             if item in self.parsed and not override:
                 continue
             try:
-                with open(item) as _file:
+                with io.open(item, "r", encoding="utf-8") as _file:
                     parsed = nginxparser.load(_file)
                     self.parsed[item] = parsed
                     trees.append(parsed)
             except IOError:
                 logger.warning("Could not open file: %s", item)
+            except UnicodeDecodeError:
+                logger.warning("Could not read file: %s due to invalid "
+                               "character. Only UTF-8 encoding is "
+                               "supported.", item)
             except pyparsing.ParseException as err:
                 logger.debug("Could not parse file: %s due to %s", item, err)
         return trees
@@ -399,9 +404,9 @@
                 if directive and directive[0] == 'listen':
                     # Exclude one-time use parameters which will cause an 
error if repeated.
                     # 
https://nginx.org/en/docs/http/ngx_http_core_module.html#listen
-                    exclude = set(('default_server', 'default', 'setfib', 
'fastopen', 'backlog',
+                    exclude = {'default_server', 'default', 'setfib', 
'fastopen', 'backlog',
                                    'rcvbuf', 'sndbuf', 'accept_filter', 
'deferred', 'bind',
-                                   'ipv6only', 'reuseport', 'so_keepalive'))
+                                   'ipv6only', 'reuseport', 'so_keepalive'}
 
                     for param in exclude:
                         # See: 
github.com/certbot/certbot/pull/6223#pullrequestreview-143019225
@@ -414,10 +419,13 @@
 def _parse_ssl_options(ssl_options):
     if ssl_options is not None:
         try:
-            with open(ssl_options) as _file:
+            with io.open(ssl_options, "r", encoding="utf-8") as _file:
                 return nginxparser.load(_file)
         except IOError:
             logger.warning("Missing NGINX TLS options file: %s", ssl_options)
+        except UnicodeDecodeError:
+            logger.warning("Could not read file: %s due to invalid character. "
+                           "Only UTF-8 encoding is supported.", ssl_options)
         except pyparsing.ParseBaseException as err:
             logger.debug("Could not parse file: %s due to %s", ssl_options, 
err)
     return []
@@ -570,7 +578,7 @@
 
 
 INCLUDE = 'include'
-REPEATABLE_DIRECTIVES = set(['server_name', 'listen', INCLUDE, 'rewrite', 
'add_header'])
+REPEATABLE_DIRECTIVES = {'server_name', 'listen', INCLUDE, 'rewrite', 
'add_header'}
 COMMENT = ' managed by Certbot'
 COMMENT_BLOCK = [' ', '#', COMMENT]
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/certbot_nginx/_internal/parser_obj.py 
new/certbot-nginx-1.4.0/certbot_nginx/_internal/parser_obj.py
--- old/certbot-nginx-1.3.0/certbot_nginx/_internal/parser_obj.py       
2020-03-03 21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/certbot_nginx/_internal/parser_obj.py       
2020-05-05 21:37:33.000000000 +0200
@@ -206,7 +206,7 @@
         :returns: whether this lists is parseable by `Sentence`.
         """
         return isinstance(lists, list) and len(lists) > 0 and \
-            all([isinstance(elem, six.string_types) for elem in lists])
+            all(isinstance(elem, six.string_types) for elem in lists)
 
     def parse(self, raw_list, add_spaces=False):
         """ Parses a list of string types into this object.
@@ -214,7 +214,7 @@
         if add_spaces:
             raw_list = _space_list(raw_list)
         if not isinstance(raw_list, list) or \
-                any([not isinstance(elem, six.string_types) for elem in 
raw_list]):
+                any(not isinstance(elem, six.string_types) for elem in 
raw_list):
             raise errors.MisconfigurationError("Sentence parsing expects a 
list of string types.")
         self._data = raw_list
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/certbot_nginx.egg-info/PKG-INFO 
new/certbot-nginx-1.4.0/certbot_nginx.egg-info/PKG-INFO
--- old/certbot-nginx-1.3.0/certbot_nginx.egg-info/PKG-INFO     2020-03-03 
21:36:47.000000000 +0100
+++ new/certbot-nginx-1.4.0/certbot_nginx.egg-info/PKG-INFO     2020-05-05 
21:37:47.000000000 +0200
@@ -1,6 +1,6 @@
 Metadata-Version: 1.2
 Name: certbot-nginx
-Version: 1.3.0
+Version: 1.4.0
 Summary: Nginx plugin for Certbot
 Home-page: https://github.com/letsencrypt/letsencrypt
 Author: Certbot Project
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/certbot_nginx.egg-info/SOURCES.txt 
new/certbot-nginx-1.4.0/certbot_nginx.egg-info/SOURCES.txt
--- old/certbot-nginx-1.3.0/certbot_nginx.egg-info/SOURCES.txt  2020-03-03 
21:36:47.000000000 +0100
+++ new/certbot-nginx-1.4.0/certbot_nginx.egg-info/SOURCES.txt  2020-05-05 
21:37:47.000000000 +0200
@@ -31,16 +31,19 @@
 tests/obj_test.py
 tests/parser_obj_test.py
 tests/parser_test.py
+tests/test_log_util.py
 tests/test_util.py
 tests/testdata/etc_nginx/broken.conf
 tests/testdata/etc_nginx/comment_in_file.conf
 tests/testdata/etc_nginx/edge_cases.conf
 tests/testdata/etc_nginx/foo.conf
+tests/testdata/etc_nginx/invalid_unicode_comments.conf
 tests/testdata/etc_nginx/mime.types
 tests/testdata/etc_nginx/minimalistic_comments.conf
 tests/testdata/etc_nginx/multiline_quotes.conf
 tests/testdata/etc_nginx/nginx.conf
 tests/testdata/etc_nginx/server.conf
+tests/testdata/etc_nginx/valid_unicode_comments.conf
 tests/testdata/etc_nginx/sites-enabled/default
 tests/testdata/etc_nginx/sites-enabled/example.com
 tests/testdata/etc_nginx/sites-enabled/example.net
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/certbot_nginx.egg-info/requires.txt 
new/certbot-nginx-1.4.0/certbot_nginx.egg-info/requires.txt
--- old/certbot-nginx-1.3.0/certbot_nginx.egg-info/requires.txt 2020-03-03 
21:36:47.000000000 +0100
+++ new/certbot-nginx-1.4.0/certbot_nginx.egg-info/requires.txt 2020-05-05 
21:37:47.000000000 +0200
@@ -1,7 +1,9 @@
-acme>=1.0.0
-certbot>=1.1.0
-mock
+acme>=1.4.0
+certbot>=1.4.0
 PyOpenSSL
 pyparsing>=1.5.5
 setuptools
 zope.interface
+
+[:python_version < "3.3"]
+mock
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/setup.py 
new/certbot-nginx-1.4.0/setup.py
--- old/certbot-nginx-1.3.0/setup.py    2020-03-03 21:36:38.000000000 +0100
+++ new/certbot-nginx-1.4.0/setup.py    2020-05-05 21:37:34.000000000 +0200
@@ -1,23 +1,33 @@
+from distutils.version import StrictVersion
 import sys
 
+from setuptools import __version__ as setuptools_version
 from setuptools import find_packages
 from setuptools import setup
 from setuptools.command.test import test as TestCommand
 
-version = '1.3.0'
+version = '1.4.0'
 
 # Remember to update local-oldest-requirements.txt when changing the minimum
 # acme/certbot version.
 install_requires = [
-    'acme>=1.0.0',
-    'certbot>=1.1.0',
-    'mock',
+    'acme>=1.4.0',
+    'certbot>=1.4.0',
     'PyOpenSSL',
     'pyparsing>=1.5.5',  # Python3 support
     'setuptools',
     'zope.interface',
 ]
 
+setuptools_known_environment_markers = (StrictVersion(setuptools_version) >= 
StrictVersion('36.2'))
+if setuptools_known_environment_markers:
+    install_requires.append('mock ; python_version < "3.3"')
+elif 'bdist_wheel' in sys.argv[1:]:
+    raise RuntimeError('Error, you are trying to build certbot wheels using an 
old version '
+                       'of setuptools. Version 36.2+ of setuptools is 
required.')
+elif sys.version_info < (3,3):
+    install_requires.append('mock')
+
 
 class PyTest(TestCommand):
     user_options = []
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/tests/configurator_test.py 
new/certbot-nginx-1.4.0/tests/configurator_test.py
--- old/certbot-nginx-1.3.0/tests/configurator_test.py  2020-03-03 
21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/tests/configurator_test.py  2020-05-05 
21:37:33.000000000 +0200
@@ -1,7 +1,10 @@
 """Test for certbot_nginx._internal.configurator."""
 import unittest
 
-import mock
+try:
+    import mock
+except ImportError: # pragma: no cover
+    from unittest import mock # type: ignore
 import OpenSSL
 
 from acme import challenges
@@ -104,7 +107,7 @@
         filep = self.config.parser.abs_path('sites-enabled/example.com')
         mock_vhost = obj.VirtualHost(filep,
                                      None, None, None,
-                                     set(['.example.com', 'example.*']),
+                                     {'.example.com', 'example.*'},
                                      None, [0])
         self.config.parser.add_server_directives(
             mock_vhost,
@@ -150,11 +153,11 @@
         self._test_choose_vhosts_common('ipv6.com', 'ipv6_conf')
 
     def _test_choose_vhosts_common(self, name, conf):
-        conf_names = {'localhost_conf': set(['localhost', 
r'~^(www\.)?(example|bar)\.']),
-                 'server_conf': set(['somename', 'another.alias', 'alias']),
-                 'example_conf': set(['.example.com', 'example.*']),
-                 'foo_conf': set(['*.www.foo.com', '*.www.example.com']),
-                 'ipv6_conf': set(['ipv6.com'])}
+        conf_names = {'localhost_conf': {'localhost', 
r'~^(www\.)?(example|bar)\.'},
+                 'server_conf': {'somename', 'another.alias', 'alias'},
+                 'example_conf': {'.example.com', 'example.*'},
+                 'foo_conf': {'*.www.foo.com', '*.www.example.com'},
+                 'ipv6_conf': {'ipv6.com'}}
 
         conf_path = {'localhost': "etc_nginx/nginx.conf",
                    'alias': "etc_nginx/nginx.conf",
@@ -177,7 +180,7 @@
             self.assertTrue(vhost.ipv6_enabled())
             # Make sure that we have SSL enabled also for IPv6 addr
             self.assertTrue(
-                any([True for x in vhost.addrs if x.ssl and x.ipv6]))
+                any(True for x in vhost.addrs if x.ssl and x.ipv6))
 
     def test_choose_vhosts_bad(self):
         bad_results = ['www.foo.com', 'example', 't.www.bar.co',
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/tests/http_01_test.py 
new/certbot-nginx-1.4.0/tests/http_01_test.py
--- old/certbot-nginx-1.3.0/tests/http_01_test.py       2020-03-03 
21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/tests/http_01_test.py       2020-05-05 
21:37:33.000000000 +0200
@@ -2,7 +2,10 @@
 import unittest
 
 import josepy as jose
-import mock
+try:
+    import mock
+except ImportError: # pragma: no cover
+    from unittest import mock # type: ignore
 import six
 
 from acme import challenges
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/tests/obj_test.py 
new/certbot-nginx-1.4.0/tests/obj_test.py
--- old/certbot-nginx-1.3.0/tests/obj_test.py   2020-03-03 21:36:36.000000000 
+0100
+++ new/certbot-nginx-1.4.0/tests/obj_test.py   2020-05-05 21:37:33.000000000 
+0200
@@ -98,10 +98,10 @@
 
     def test_set_inclusion(self):
         from certbot_nginx._internal.obj import Addr
-        set_a = set([self.addr1, self.addr2])
+        set_a = {self.addr1, self.addr2}
         addr1b = Addr.fromstring("192.168.1.1")
         addr2b = Addr.fromstring("192.168.1.1:* ssl")
-        set_b = set([addr1b, addr2b])
+        set_b = {addr1b, addr2b}
 
         self.assertEqual(set_a, set_b)
 
@@ -120,8 +120,8 @@
         ]
         self.vhost1 = VirtualHost(
             "filep",
-            set([Addr.fromstring("localhost")]), False, False,
-            set(['localhost']), raw1, [])
+            {Addr.fromstring("localhost")}, False, False,
+            {'localhost'}, raw1, [])
         raw2 = [
             ['listen', '69.50.225.155:9000'],
             [['if', '($scheme', '!=', '"https") '],
@@ -130,24 +130,24 @@
         ]
         self.vhost2 = VirtualHost(
             "filep",
-            set([Addr.fromstring("localhost")]), False, False,
-            set(['localhost']), raw2, [])
+            {Addr.fromstring("localhost")}, False, False,
+            {'localhost'}, raw2, [])
         raw3 = [
             ['listen', '69.50.225.155:9000'],
             ['rewrite', '^(.*)$', '$scheme://www.domain.com$1', 'permanent']
         ]
         self.vhost3 = VirtualHost(
             "filep",
-            set([Addr.fromstring("localhost")]), False, False,
-            set(['localhost']), raw3, [])
+            {Addr.fromstring("localhost")}, False, False,
+            {'localhost'}, raw3, [])
         raw4 = [
             ['listen', '69.50.225.155:9000'],
             ['server_name', 'return.com']
         ]
         self.vhost4 = VirtualHost(
             "filp",
-            set([Addr.fromstring("localhost")]), False, False,
-            set(['localhost']), raw4, [])
+            {Addr.fromstring("localhost")}, False, False,
+            {'localhost'}, raw4, [])
         raw_has_hsts = [
             ['listen', '69.50.225.155:9000'],
             ['server_name', 'return.com'],
@@ -155,16 +155,16 @@
         ]
         self.vhost_has_hsts = VirtualHost(
             "filep",
-            set([Addr.fromstring("localhost")]), False, False,
-            set(['localhost']), raw_has_hsts, [])
+            {Addr.fromstring("localhost")}, False, False,
+            {'localhost'}, raw_has_hsts, [])
 
     def test_eq(self):
         from certbot_nginx._internal.obj import Addr
         from certbot_nginx._internal.obj import VirtualHost
         vhost1b = VirtualHost(
             "filep",
-            set([Addr.fromstring("localhost blah")]), False, False,
-            set(['localhost']), [], [])
+            {Addr.fromstring("localhost blah")}, False, False,
+            {'localhost'}, [], [])
 
         self.assertEqual(vhost1b, self.vhost1)
         self.assertEqual(str(vhost1b), str(self.vhost1))
@@ -203,8 +203,8 @@
             ['#', ' managed by Certbot'], []]
         vhost_haystack = VirtualHost(
             "filp",
-            set([Addr.fromstring("localhost")]), False, False,
-            set(['localhost']), test_haystack, [])
+            {Addr.fromstring("localhost")}, False, False,
+            {'localhost'}, test_haystack, [])
         test_bad_haystack = [['listen', '80'], ['root', '/var/www/html'],
             ['index', 'index.html index.htm index.nginx-debian.html'],
             ['server_name', 'two.functorkitten.xyz'], ['listen', '443 ssl'],
@@ -219,8 +219,8 @@
             ['#', ' managed by Certbot'], []]
         vhost_bad_haystack = VirtualHost(
             "filp",
-            set([Addr.fromstring("localhost")]), False, False,
-            set(['localhost']), test_bad_haystack, [])
+            {Addr.fromstring("localhost")}, False, False,
+            {'localhost'}, test_bad_haystack, [])
         self.assertTrue(vhost_haystack.contains_list(test_needle))
         self.assertFalse(vhost_bad_haystack.contains_list(test_needle))
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/tests/parser_obj_test.py 
new/certbot-nginx-1.4.0/tests/parser_obj_test.py
--- old/certbot-nginx-1.3.0/tests/parser_obj_test.py    2020-03-03 
21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/tests/parser_obj_test.py    2020-05-05 
21:37:33.000000000 +0200
@@ -2,7 +2,10 @@
 
 import unittest
 
-import mock
+try:
+    import mock
+except ImportError: # pragma: no cover
+    from unittest import mock # type: ignore
 
 from certbot_nginx._internal.parser_obj import COMMENT_BLOCK
 from certbot_nginx._internal.parser_obj import parse_raw
@@ -80,7 +83,7 @@
         fake_parser1.should_parse = lambda x: False
         parsing_hooks.return_value = (fake_parser1,)
         self.assertRaises(errors.MisconfigurationError, parse_raw, [])
-        parsing_hooks.return_value = tuple()
+        parsing_hooks.return_value = ()
         self.assertRaises(errors.MisconfigurationError, parse_raw, [])
 
     def test_parse_raw_passes_add_spaces(self):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/tests/parser_test.py 
new/certbot-nginx-1.4.0/tests/parser_test.py
--- old/certbot-nginx-1.3.0/tests/parser_test.py        2020-03-03 
21:36:36.000000000 +0100
+++ new/certbot-nginx-1.4.0/tests/parser_test.py        2020-05-05 
21:37:33.000000000 +0200
@@ -4,7 +4,6 @@
 import shutil
 import unittest
 
-from acme.magic_typing import List  # pylint: disable=unused-import, 
no-name-in-module
 from certbot import errors
 from certbot.compat import os
 from certbot_nginx._internal import nginxparser
@@ -127,7 +126,7 @@
         vhost = 
obj.VirtualHost(nparser.abs_path('sites-enabled/globalssl.com'),
                                 [obj.Addr('4.8.2.6', '57', True, False,
                                           False, False)],
-                                True, True, set(['globalssl.com']), [], [0])
+                                True, True, {'globalssl.com'}, [], [0])
 
         globalssl_com = [x for x in vhosts if 'globalssl.com' in x.filep][0]
         self.assertEqual(vhost, globalssl_com)
@@ -140,8 +139,8 @@
                                  [obj.Addr('', '8080', False, False,
                                            False, False)],
                                  False, True,
-                                 set(['localhost',
-                                      r'~^(www\.)?(example|bar)\.']),
+                                 {'localhost',
+                                      r'~^(www\.)?(example|bar)\.'},
                                  [], [10, 1, 9])
         vhost2 = obj.VirtualHost(nparser.abs_path('nginx.conf'),
                                  [obj.Addr('somename', '8080', False, False,
@@ -149,7 +148,7 @@
                                   obj.Addr('', '8000', False, False,
                                            False, False)],
                                  False, True,
-                                 set(['somename', 'another.alias', 'alias']),
+                                 {'somename', 'another.alias', 'alias'},
                                  [], [10, 1, 12])
         vhost3 = obj.VirtualHost(nparser.abs_path('sites-enabled/example.com'),
                                  [obj.Addr('69.50.225.155', '9000',
@@ -157,19 +156,19 @@
                                   obj.Addr('127.0.0.1', '', False, False,
                                            False, False)],
                                  False, True,
-                                 set(['.example.com', 'example.*']), [], [0])
+                                 {'.example.com', 'example.*'}, [], [0])
         vhost4 = obj.VirtualHost(nparser.abs_path('sites-enabled/default'),
                                  [obj.Addr('myhost', '', False, True,
                                            False, False),
                                   obj.Addr('otherhost', '', False, True,
                                            False, False)],
-                                 False, True, set(['www.example.org']),
+                                 False, True, {'www.example.org'},
                                  [], [0])
         vhost5 = obj.VirtualHost(nparser.abs_path('foo.conf'),
                                  [obj.Addr('*', '80', True, True,
                                            False, False)],
-                                 True, True, set(['*.www.foo.com',
-                                                  '*.www.example.com']),
+                                 True, True, {'*.www.foo.com',
+                                                  '*.www.example.com'},
                                  [], [2, 1, 0])
 
         self.assertEqual(14, len(vhosts))
@@ -209,11 +208,11 @@
         nparser = parser.NginxParser(self.config_path)
         mock_vhost = obj.VirtualHost(nparser.abs_path('nginx.conf'),
                                      None, None, None,
-                                     set(['localhost',
-                                           r'~^(www\.)?(example|bar)\.']),
+                                     {'localhost',
+                                           r'~^(www\.)?(example|bar)\.'},
                                      None, [10, 1, 9])
         example_com = nparser.abs_path('sites-enabled/example.com')
-        names = set(['.example.com', 'example.*'])
+        names = {'.example.com', 'example.*'}
         mock_vhost.filep = example_com
         mock_vhost.names = names
         mock_vhost.path = [0]
@@ -233,8 +232,8 @@
         nparser = parser.NginxParser(self.config_path)
         mock_vhost = obj.VirtualHost(nparser.abs_path('nginx.conf'),
                                      None, None, None,
-                                     set(['localhost',
-                                           r'~^(www\.)?(example|bar)\.']),
+                                     {'localhost',
+                                           r'~^(www\.)?(example|bar)\.'},
                                      None, [10, 1, 9])
         nparser.add_server_directives(mock_vhost,
                                       [['foo', 'bar'], ['\n ', 
'ssl_certificate', ' ',
@@ -244,7 +243,7 @@
         self.assertEqual(1, len(re.findall(ssl_re, dump)))
 
         example_com = nparser.abs_path('sites-enabled/example.com')
-        names = set(['.example.com', 'example.*'])
+        names = {'.example.com', 'example.*'}
         mock_vhost.filep = example_com
         mock_vhost.names = names
         mock_vhost.path = [0]
@@ -265,7 +264,7 @@
                            ]]])
 
         server_conf = nparser.abs_path('server.conf')
-        names = set(['alias', 'another.alias', 'somename'])
+        names = {'alias', 'another.alias', 'somename'}
         mock_vhost.filep = server_conf
         mock_vhost.names = names
         mock_vhost.path = []
@@ -280,7 +279,7 @@
         example_com = nparser.abs_path('sites-enabled/example.com')
         mock_vhost = obj.VirtualHost(example_com,
                                      None, None, None,
-                                     set(['.example.com', 'example.*']),
+                                     {'.example.com', 'example.*'},
                                      None, [0])
         nparser.add_server_directives(mock_vhost,
                                       [['\n  ', '#', ' ', 'what a nice 
comment']])
@@ -302,7 +301,7 @@
 
     def test_replace_server_directives(self):
         nparser = parser.NginxParser(self.config_path)
-        target = set(['.example.com', 'example.*'])
+        target = {'.example.com', 'example.*'}
         filep = nparser.abs_path('sites-enabled/example.com')
         mock_vhost = obj.VirtualHost(filep, None, None, None, target, None, 
[0])
         nparser.update_or_add_server_directives(
@@ -315,7 +314,7 @@
                            ['server_name', 'foobar.com'], ['#', COMMENT],
                            ['server_name', 'example.*'], []
                            ]]])
-        mock_vhost.names = set(['foobar.com', 'example.*'])
+        mock_vhost.names = {'foobar.com', 'example.*'}
         nparser.update_or_add_server_directives(
             mock_vhost, [['ssl_certificate', 'cert.pem']])
         self.assertEqual(
@@ -329,19 +328,19 @@
 
     def test_get_best_match(self):
         target_name = 'www.eff.org'
-        names = [set(['www.eff.org', 'irrelevant.long.name.eff.org', '*.org']),
-                 set(['eff.org', 'ww2.eff.org', 'test.www.eff.org']),
-                 set(['*.eff.org', '.www.eff.org']),
-                 set(['.eff.org', '*.org']),
-                 set(['www.eff.', 'www.eff.*', '*.www.eff.org']),
-                 set(['example.com', r'~^(www\.)?(eff.+)', '*.eff.*']),
-                 set(['*', r'~^(www\.)?(eff.+)']),
-                 set(['www.*', r'~^(www\.)?(eff.+)', '.test.eff.org']),
-                 set(['*.org', r'*.eff.org', 'www.eff.*']),
-                 set(['*.www.eff.org', 'www.*']),
-                 set(['*.org']),
-                 set([]),
-                 set(['example.com'])]
+        names = [{'www.eff.org', 'irrelevant.long.name.eff.org', '*.org'},
+                 {'eff.org', 'ww2.eff.org', 'test.www.eff.org'},
+                 {'*.eff.org', '.www.eff.org'},
+                 {'.eff.org', '*.org'},
+                 {'www.eff.', 'www.eff.*', '*.www.eff.org'},
+                 {'example.com', r'~^(www\.)?(eff.+)', '*.eff.*'},
+                 {'*', r'~^(www\.)?(eff.+)'},
+                 {'www.*', r'~^(www\.)?(eff.+)', '.test.eff.org'},
+                 {'*.org', r'*.eff.org', 'www.eff.*'},
+                 {'*.www.eff.org', 'www.*'},
+                 {'*.org'},
+                 set(),
+                 {'example.com'}]
         winners = [('exact', 'www.eff.org'),
                    (None, None),
                    ('exact', '.www.eff.org'),
@@ -482,7 +481,43 @@
                 called = True
         self.assertTrue(called)
 
-
+    def test_valid_unicode_characters(self):
+        nparser = parser.NginxParser(self.config_path)
+        path = nparser.abs_path('valid_unicode_comments.conf')
+        parsed = nparser._parse_files(path)  # pylint: disable=protected-access
+        self.assertEqual(['server'], parsed[0][2][0])
+        self.assertEqual(['listen', '80'], parsed[0][2][1][3])
+
+    def test_invalid_unicode_characters(self):
+        with self.assertLogs() as log:
+            nparser = parser.NginxParser(self.config_path)
+            path = nparser.abs_path('invalid_unicode_comments.conf')
+            parsed = nparser._parse_files(path)  # pylint: 
disable=protected-access
+
+        self.assertEqual([], parsed)
+        self.assertTrue(any(
+            ('invalid character' in output) and ('UTF-8' in output)
+            for output in log.output
+        ))
+
+    def test_valid_unicode_characters_in_ssl_options(self):
+        nparser = parser.NginxParser(self.config_path)
+        path = nparser.abs_path('valid_unicode_comments.conf')
+        parsed = parser._parse_ssl_options(path)  # pylint: 
disable=protected-access
+        self.assertEqual(['server'], parsed[2][0])
+        self.assertEqual(['listen', '80'], parsed[2][1][3])
+
+    def test_invalid_unicode_characters_in_ssl_options(self):
+        with self.assertLogs() as log:
+            nparser = parser.NginxParser(self.config_path)
+            path = nparser.abs_path('invalid_unicode_comments.conf')
+            parsed = parser._parse_ssl_options(path)  # pylint: 
disable=protected-access
+
+        self.assertEqual([], parsed)
+        self.assertTrue(any(
+            ('invalid character' in output) and ('UTF-8' in output)
+            for output in log.output
+        ))
 
 if __name__ == "__main__":
     unittest.main()  # pragma: no cover
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/tests/test_log_util.py 
new/certbot-nginx-1.4.0/tests/test_log_util.py
--- old/certbot-nginx-1.3.0/tests/test_log_util.py      1970-01-01 
01:00:00.000000000 +0100
+++ new/certbot-nginx-1.4.0/tests/test_log_util.py      2020-05-05 
21:37:33.000000000 +0200
@@ -0,0 +1,125 @@
+"""Backport for `TestCase.assertLogs()`.
+
+Most of the idea and code are from CPython implementation.
+https://github.com/python/cpython/blob/b76518d43fb82ed9e5d27025d18c90a23d525c90/Lib/unittest/case.py
+"""
+import logging
+import collections
+
+__all__ = ['AssertLogsMixin']
+
+LoggingWatcher = collections.namedtuple('LoggingWatcher', ['records', 
'output'])
+
+
+class CapturingHandler(logging.Handler):
+    """
+    A logging handler capturing all (raw and formatted) logging output.
+    """
+
+    def __init__(self):
+        super(CapturingHandler, self).__init__()
+        self.watcher = LoggingWatcher([], [])
+
+    def flush(self):
+        pass
+
+    def emit(self, record):
+        self.watcher.records.append(record)
+        self.watcher.output.append(self.format(record))
+
+
+
+class AssertLogsContext(object):
+    """
+    A context manager used to implement `TestCase.assertLogs()`.
+    """
+
+    LOGGING_FORMAT = '%(levelname)s:%(name)s:%(message)s'
+
+    def __init__(self, test_case, logger_name, level):
+        self.test_case = test_case
+
+        self.logger_name = logger_name
+        self.logger_states = None
+        self.logger = None
+
+        if level:
+            # pylint: disable=protected-access,no-member
+            try:
+                # In Python 3.x
+                name_to_level = logging._nameToLevel  # type: ignore
+            except AttributeError:
+                # In Python 2.7
+                name_to_level = logging._levelNames  # type: ignore
+
+            self.level = name_to_level.get(level, level)
+        else:
+            self.level = logging.INFO
+
+        self.watcher = None
+
+    def _save_logger_states(self):
+        self.logger_states = (self.logger.handlers[:], self.logger.level, 
self.logger.propagate)
+
+    def _restore_logger_states(self):
+        self.logger.handlers, self.logger.level, self.logger.propagate = 
self.logger_states
+
+    def __enter__(self):
+        if isinstance(self.logger_name, logging.Logger):
+            self.logger = self.logger_name
+        else:
+            self.logger = logging.getLogger(self.logger_name)
+
+        formatter = logging.Formatter(self.LOGGING_FORMAT)
+
+        handler = CapturingHandler()
+        handler.setFormatter(formatter)
+
+        self._save_logger_states()
+        self.logger.handlers = [handler]
+        self.logger.setLevel(self.level)
+        self.logger.propagate = False
+
+        self.watcher = handler.watcher
+        return handler.watcher
+
+    def __exit__(self, exc_type, exc_value, tb):
+        self._restore_logger_states()
+
+        if exc_type is not None:
+            # let unexpected exceptions pass through
+            return
+
+        if not self.watcher.records:
+            self._raiseFailure(
+                "no logs of level {} or higher triggered on {}"
+                .format(logging.getLevelName(self.level), self.logger.name))
+
+    def _raiseFailure(self, message):
+        message = self.test_case._formatMessage(None, message)  # pylint: 
disable=protected-access
+        raise self.test_case.failureException(message)
+
+
+class AssertLogsMixin(object):
+    """
+    A mixin that implements `TestCase.assertLogs()`.
+    """
+
+    def assertLogs(self, logger=None, level=None):
+        """Fail unless a log message of level *level* or higher is emitted
+        on *logger_name* or its children.  If omitted, *level* defaults to
+        INFO and *logger* defaults to the root logger.
+        This method must be used as a context manager, and will yield
+        a recording object with two attributes: `output` and `records`.
+        At the end of the context manager, the `output` attribute will
+        be a list of the matching formatted log messages and the
+        `records` attribute will be a list of the corresponding LogRecord
+        objects.
+        Example::
+            with self.assertLogs('foo', level='INFO') as cm:
+                logging.getLogger('foo').info('first message')
+                logging.getLogger('foo.bar').error('second message')
+            self.assertEqual(cm.output, ['INFO:foo:first message',
+                                         'ERROR:foo.bar:second message'])
+        """
+        return AssertLogsContext(self, logger, level)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/certbot-nginx-1.3.0/tests/test_util.py 
new/certbot-nginx-1.4.0/tests/test_util.py
--- old/certbot-nginx-1.3.0/tests/test_util.py  2020-03-03 21:36:36.000000000 
+0100
+++ new/certbot-nginx-1.4.0/tests/test_util.py  2020-05-05 21:37:33.000000000 
+0200
@@ -4,7 +4,10 @@
 import tempfile
 
 import josepy as jose
-import mock
+try:
+    import mock
+except ImportError: # pragma: no cover
+    from unittest import mock # type: ignore
 import pkg_resources
 import zope.component
 
@@ -14,9 +17,10 @@
 from certbot.tests import util as test_util
 from certbot_nginx._internal import configurator
 from certbot_nginx._internal import nginxparser
+import test_log_util
 
 
-class NginxTest(test_util.ConfigTestCase):
+class NginxTest(test_log_util.AssertLogsMixin, test_util.ConfigTestCase):
 
     def setUp(self):
         super(NginxTest, self).setUp()
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/tests/testdata/etc_nginx/invalid_unicode_comments.conf 
new/certbot-nginx-1.4.0/tests/testdata/etc_nginx/invalid_unicode_comments.conf
--- 
old/certbot-nginx-1.3.0/tests/testdata/etc_nginx/invalid_unicode_comments.conf  
    1970-01-01 01:00:00.000000000 +0100
+++ 
new/certbot-nginx-1.4.0/tests/testdata/etc_nginx/invalid_unicode_comments.conf  
    2020-05-05 21:37:33.000000000 +0200
@@ -0,0 +1,7 @@
+# This configuration file is saved with EUC-KR (a.k.a. cp949) encoding,
+# including some Korean letters.
+
+server {
+    # �ȳ��ϼ���. 80�� ��Ʈ���� ��û�� ��ٸ���.
+    listen     80;
+}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/certbot-nginx-1.3.0/tests/testdata/etc_nginx/valid_unicode_comments.conf 
new/certbot-nginx-1.4.0/tests/testdata/etc_nginx/valid_unicode_comments.conf
--- 
old/certbot-nginx-1.3.0/tests/testdata/etc_nginx/valid_unicode_comments.conf    
    1970-01-01 01:00:00.000000000 +0100
+++ 
new/certbot-nginx-1.4.0/tests/testdata/etc_nginx/valid_unicode_comments.conf    
    2020-05-05 21:37:33.000000000 +0200
@@ -0,0 +1,9 @@
+# This configuration file is saved with valid UTF-8 encoding,
+# including some CJK alphabets.
+
+server {
+    # 안녕하세요. 80번 포트에서 요청을 기다린다.
+    # こんにちは。80番ポートからリクエストを待つ。
+    # 你好。等待端口80上的请求。
+    listen     80;
+}


Reply via email to