From 8ad37f6036436e040ebf4217d5fab897030bbbdc Mon Sep 17 00:00:00 2001 From: Dave Halter Date: Sun, 9 Jul 2017 00:49:23 +0200 Subject: [PATCH] Move parsing the version around. --- parso/grammar.py | 36 ++++-------------------------------- parso/utils.py | 34 ++++++++++++++++++++++++++++++++++ test/test_load_grammar.py | 4 ++-- 3 files changed, 40 insertions(+), 34 deletions(-) diff --git a/parso/grammar.py b/parso/grammar.py index 3094850..2bf8b10 100644 --- a/parso/grammar.py +++ b/parso/grammar.py @@ -1,11 +1,9 @@ import hashlib import os -import sys -import re -from parso._compatibility import FileNotFoundError, unicode +from parso._compatibility import FileNotFoundError from parso.pgen2.pgen import generate_grammar -from parso.utils import splitlines, source_to_unicode +from parso.utils import splitlines, source_to_unicode, version_string_to_int from parso.python.diff import DiffParser from parso.python.tokenize import tokenize_lines from parso.cache import parser_cache, load_module, save_module @@ -21,8 +19,7 @@ class Grammar(object): :param text: A BNF representation of your grammar. """ - def __init__(self, text, tokenizer, parser=BaseParser, - diff_parser=None): + def __init__(self, text, tokenizer, parser=BaseParser, diff_parser=None): self._pgen_grammar = generate_grammar(text) self._parser = parser self._tokenizer = tokenizer @@ -123,26 +120,6 @@ class Grammar(object): return '<%s:%s>' % (self.__class__.__name__, txt) -def _parse_version(version): - match = re.match(r'(\d+)(?:\.(\d)(?:\.\d+)?)?$', version) - if match is None: - raise ValueError('The given version is not in the right format. ' - 'Use something like "3.2" or "3".') - - major = match.group(1) - minor = match.group(2) - if minor is None: - # Use the latest Python in case it's not exactly defined, because the - # grammars are typically backwards compatible? - if major == "2": - minor = "7" - elif major == "3": - minor = "6" - else: - raise NotImplementedError("Sorry, no support yet for those fancy new/old versions.") - return int(major + minor) - - def load_grammar(version=None): """ Loads a Python grammar. The default version is the current Python version. @@ -150,12 +127,7 @@ def load_grammar(version=None): If you need support for a specific version, please use e.g. `version='3.3'`. """ - if version is None: - version = '%s.%s' % sys.version_info[:2] - if not isinstance(version, (unicode, str)): - raise TypeError("version must be a string like 3.2.") - - version_int = _parse_version(version) + version_int = version_string_to_int(version) # For these versions we use the same grammar files, because nothing # changed. diff --git a/parso/utils.py b/parso/utils.py index 6ca3b2c..047643a 100644 --- a/parso/utils.py +++ b/parso/utils.py @@ -1,5 +1,6 @@ from collections import namedtuple import re +import sys from ast import literal_eval from parso._compatibility import unicode @@ -85,3 +86,36 @@ def version_info(): from parso import __version__ tupl = re.findall(r'[a-z]+|\d+', __version__) return Version(*[x if i == 3 else int(x) for i, x in enumerate(tupl)]) + + +def _parse_version(version): + match = re.match(r'(\d+)(?:\.(\d)(?:\.\d+)?)?$', version) + if match is None: + raise ValueError('The given version is not in the right format. ' + 'Use something like "3.2" or "3".') + + major = match.group(1) + minor = match.group(2) + if minor is None: + # Use the latest Python in case it's not exactly defined, because the + # grammars are typically backwards compatible? + if major == "2": + minor = "7" + elif major == "3": + minor = "6" + else: + raise NotImplementedError("Sorry, no support yet for those fancy new/old versions.") + return int(major + minor) + + +def version_string_to_int(version): + """ + Checks for a valid version number (e.g. `3.2` or `2.7.1` or `3`) and + returns a corresponding int that is always two characters long in decimal. + """ + if version is None: + version = '%s.%s' % sys.version_info[:2] + if not isinstance(version, (unicode, str)): + raise TypeError("version must be a string like 3.2.") + + return _parse_version(version) diff --git a/test/test_load_grammar.py b/test/test_load_grammar.py index 8ba083d..147a19e 100644 --- a/test/test_load_grammar.py +++ b/test/test_load_grammar.py @@ -1,6 +1,6 @@ import pytest from parso.grammar import load_grammar -from parso import grammar +from parso import utils def test_load_inexisting_grammar(): @@ -17,7 +17,7 @@ def test_load_inexisting_grammar(): ('2', 27), ('3', 36), ('1.1', 11), ('1.1.1', 11), ('300.1.31', 3001) ]) def test_parse_version(string, result): - assert grammar._parse_version(string) == result + assert utils._parse_version(string) == result @pytest.mark.parametrize('string', ['1.', 'a', '#', '1.3.4.5', '1.12'])