Skip to content

Commit

Permalink
Rest of the linters
Browse files Browse the repository at this point in the history
  • Loading branch information
fizyk committed May 5, 2021
1 parent 5ded3c9 commit b4597b9
Show file tree
Hide file tree
Showing 7 changed files with 54 additions and 39 deletions.
24 changes: 12 additions & 12 deletions port_for/_download_ranges.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,22 +3,24 @@
This module/script is for updating port_for._ranges with recent information
from IANA and Wikipedia.
"""
from __future__ import absolute_import
import sys
import os
import re
import datetime
import urllib2
from urllib.request import Request, urlopen
from xml.etree import ElementTree

from port_for.utils import to_ranges, ranges_to_set

name = os.path.abspath(
os.path.normpath(os.path.join(os.path.dirname(__file__), ".."))
)
sys.path.insert(0, name)

from port_for.utils import to_ranges, ranges_to_set

IANA_DOWNLOAD_URL = "https://www.iana.org/assignments/service-names-port-numbers/service-names-port-numbers.xml"
IANA_DOWNLOAD_URL = (
"https://www.iana.org/assignments"
"/service-names-port-numbers/service-names-port-numbers.xml"
)
IANA_NS = "http://www.iana.org/assignments"
WIKIPEDIA_PAGE = "http://en.wikipedia.org/wiki/List_of_TCP_and_UDP_port_numbers"

Expand All @@ -40,7 +42,7 @@ def _write_unassigned_ranges(out_filename):


def _unassigned_ports():
"""Returns a set of all unassigned ports (according to IANA and Wikipedia)"""
"""Return a set of all unassigned ports (according to IANA and Wikipedia)"""
free_ports = ranges_to_set(_parse_ranges(_iana_unassigned_port_ranges()))
known_ports = ranges_to_set(_wikipedia_known_port_ranges())
return free_ports.difference(known_ports)
Expand All @@ -51,21 +53,19 @@ def _wikipedia_known_port_ranges():
Returns used port ranges according to Wikipedia page.
This page contains unofficial well-known ports.
"""
req = urllib2.Request(
WIKIPEDIA_PAGE, headers={"User-Agent": "Magic Browser"}
)
page = urllib2.urlopen(req).read().decode("utf8")
req = Request(WIKIPEDIA_PAGE, headers={"User-Agent": "Magic Browser"})
page = urlopen(req).read().decode("utf8")

# just find all numbers in table cells
ports = re.findall("<td>((\d+)(\W(\d+))?)</td>", page, re.U)
ports = re.findall(r"<td>((\d+)(\W(\d+))?)</td>", page, re.U)
return ((int(p[1]), int(p[3] if p[3] else p[1])) for p in ports)


def _iana_unassigned_port_ranges():
"""
Returns unassigned port ranges according to IANA.
"""
page = urllib2.urlopen(IANA_DOWNLOAD_URL).read()
page = urlopen(IANA_DOWNLOAD_URL).read()
xml = ElementTree.fromstring(page)
records = xml.findall("{%s}record" % IANA_NS)
for record in records:
Expand Down
4 changes: 3 additions & 1 deletion port_for/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,9 @@ def good_port_ranges(ports=None, min_range_len=20, border=3):
ports = available_ports()
ranges = utils.to_ranges(list(ports))
lenghts = sorted([(r[1] - r[0], r) for r in ranges], reverse=True)
long_ranges = [l[1] for l in lenghts if l[0] >= min_range_len]
long_ranges = [
length[1] for length in lenghts if length[0] >= min_range_len
]
without_borders = [
(low + border, high - border) for low, high in long_ranges
]
Expand Down
39 changes: 20 additions & 19 deletions port_for/docopt.py
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ def fix_identities(self, uniq=None):
"""Make pattern-tree tips point to same object if they are equal."""
if not hasattr(self, "children"):
return self
uniq = list(set(self.flat)) if uniq == None else uniq
uniq = list(set(self.flat)) if uniq is None else uniq
for i, c in enumerate(self.children):
if not hasattr(c, "children"):
assert c in uniq
Expand Down Expand Up @@ -108,7 +108,7 @@ def __init__(self, name, value=None):

def match(self, left, collected=None):
collected = [] if collected is None else collected
args = [l for l in left if type(l) is Argument]
args = [arg_left for arg_left in left if type(arg_left) is Argument]
if not len(args):
return False, left, collected
left.remove(args[0])
Expand Down Expand Up @@ -138,7 +138,7 @@ def __init__(self, name, value=False):

def match(self, left, collected=None):
collected = [] if collected is None else collected
args = [l for l in left if type(l) is Argument]
args = [arg_left for arg_left in left if type(arg_left) is Argument]
if not len(args) or args[0].value != self.name:
return False, left, collected
left.remove(args[0])
Expand All @@ -153,7 +153,7 @@ def __init__(self, short=None, long=None, argcount=0, value=False):
assert argcount in (0, 1)
self.short, self.long = short, long
self.argcount, self.value = argcount, value
self.value = None if value == False and argcount else value # HACK
self.value = None if not value and argcount else value # HACK

@classmethod
def parse(class_, option_description):
Expand All @@ -168,20 +168,20 @@ def parse(class_, option_description):
else:
argcount = 1
if argcount:
matched = re.findall("\[default: (.*)\]", description, flags=re.I)
matched = re.findall(r"\[default: (.*)\]", description, flags=re.I)
value = matched[0] if matched else None
return class_(short, long, argcount, value)

def match(self, left, collected=None):
collected = [] if collected is None else collected
left_ = []
for l in left:
for arg_left in left:
# if this is so greedy, how to handle OneOrMore then?
if not (
type(l) is Option
and (self.short, self.long) == (l.short, l.long)
type(arg_left) is Option
and (self.short, self.long) == (arg_left.short, arg_left.long)
):
left_.append(l)
left_.append(arg_left)
return (left != left_), left_, collected

@property
Expand All @@ -200,20 +200,20 @@ def __repr__(self):
class AnyOptions(Pattern):
def match(self, left, collected=None):
collected = [] if collected is None else collected
left_ = [l for l in left if not type(l) == Option]
left_ = [opt_left for opt_left in left if not type(opt_left) == Option]
return (left != left_), left_, collected


class Required(Pattern):
def match(self, left, collected=None):
collected = [] if collected is None else collected
l = copy(left)
copied_left = copy(left)
c = copy(collected)
for p in self.children:
matched, l, c = p.match(l, c)
matched, copied_left, c = p.match(copied_left, c)
if not matched:
return False, left, collected
return True, l, c
return True, copied_left, c


class Optional(Pattern):
Expand All @@ -229,20 +229,21 @@ class OneOrMore(Pattern):
def match(self, left, collected=None):
assert len(self.children) == 1
collected = [] if collected is None else collected
l = copy(left)
pattern_left = copy(left)
c = copy(collected)
l_ = None
matched = True
times = 0
while matched:
# could it be that something didn't match but changed l or c?
matched, l, c = self.children[0].match(l, c)
# could it be that something didn't match but
# changed pattern_left or c?
matched, pattern_left, c = self.children[0].match(pattern_left, c)
times += 1 if matched else 0
if l_ == l:
if l_ == pattern_left:
break
l_ = copy(l)
l_ = copy(pattern_left)
if times >= 1:
return True, l, c
return True, pattern_left, c
return False, left, collected


Expand Down
6 changes: 5 additions & 1 deletion port_for/ephemeral.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,11 @@ def _bsd_ranges():
stdout, stderr = pp.communicate()
lines = stdout.decode("ascii").split("\n")
out = dict(
[[x.strip().rsplit(".")[-1] for x in l.split(":")] for l in lines if l]
[
[x.strip().rsplit(".")[-1] for x in line.split(":")]
for line in lines
if line
]
)

ranges = [
Expand Down
7 changes: 7 additions & 0 deletions setup.cfg
Original file line number Diff line number Diff line change
@@ -1,6 +1,13 @@
[bdist_wheel]
universal=1

[pycodestyle]
max-line-length = 80
exclude = docs/*,build/*,venv/*

[pydocstyle]
ignore = D203,D212
match = '(?!docs|build|venv).*\.py'

[tool:pytest]
addopts = -vvv --capture=no --showlocals --cov port_for --cov tests --ignore port_for/_download_ranges.py
Expand Down
3 changes: 2 additions & 1 deletion setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,8 @@
scripts=["scripts/port-for"],
url="https://github.com/kmike/port-for/",
license="MIT license",
description="""Utility that helps with local TCP ports managment. It can find an unused TCP localhost port and remember the association.""",
description="""Utility that helps with local TCP ports managment.
It can find an unused TCP localhost port and remember the association.""",
long_description=open("README.rst").read(),
classifiers=[
"Development Status :: 4 - Beta",
Expand Down
10 changes: 5 additions & 5 deletions tests/test_cases.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@


def test_common_ports():
assert port_for.is_available(80) == False
assert port_for.is_available(11211) == False
assert not port_for.is_available(80)
assert not port_for.is_available(11211)


def test_good_port_ranges():
Expand All @@ -35,16 +35,16 @@ def test_something_works():

def test_binding():
# low ports are not available
assert port_for.port_is_used(10) == True
assert port_for.port_is_used(10)


def test_binding_high():
s = socket.socket()
s.bind(("", 0))
port = s.getsockname()[1]
assert port_for.port_is_used(port) == True
assert port_for.port_is_used(port)
s.close()
assert port_for.port_is_used(port) == False
assert not port_for.port_is_used(port)


class SelectPortTest(unittest.TestCase):
Expand Down

0 comments on commit b4597b9

Please sign in to comment.