def __init__(self): super(UniventionPackageCheck, self).__init__() self.tester = uub.UPCFileTester() self.tester.addTest(re.compile( r'eval\s+(`|[$][(])\s*(/usr/sbin/)?(ucr|univention-baseconfig|univention-config-registry)\s+shell\s*[^`)]*[`)]\s*' ), '0017-1', 'unquoted call of eval "$(ucr shell)"', cntmax=0) self.tester.addTest(re.compile(r'\btr\s+(-[a-zA-Z]+\s+)*\['), '0017-2', 'unquoted argument for tr (e.g. "tr -d [a-z]")', cntmax=0) self.tester.addTest(re.compile( r'''\btr\s+(-[a-zA-Z]+\s+)*["']\[+[^\]]+\]+["']\s+\['''), '0017-2', 'unquoted argument for tr (e.g. "tr -d [a-z]")', cntmax=0) self.tester.addTest(re.compile( r'\bunivention-ldapsearch\b.*\s-[a-wyzA-Z]*x[a-wyzA-Z]*\b'), '0017-3', 'use of univention-ldapsearch -x', cntmax=0) self.tester.addTest( re.compile(r'\b(?:/sbin/)?ip6?tables\b +(?!--wait\b)'), '0017-4', 'iptables without --wait', cntmax=0)
def check(self, path: str) -> None: """ the real check """ super(UniventionPackageCheck, self).check(path) tester = uub.UPCFileTester() tester.addTest( re.compile(r'''(?:(?<=['" \t])|^)(?:/usr/sbin/)?univention-admin(?=['" \t]|$)'''), '0016-2', 'Use of deprecated "univention-admin"', cntmax=0) tester.addTest( re.compile(r'''(?:(?<=['" \t])|^)(?:/usr/sbin/)?univention-baseconfig(?=["' \t]|$)'''), '0016-3', 'Use of deprecated "univention-baseconfig"', cntmax=0) tester.addTest( re.compile(r'''\bfrom\b.+\bunivention_baseconfig\b.+\bimport\b|\bimport\b.+\bunivention_baseconfig\b'''), '0016-4', 'Use of deprecated "univention_baseconfig"', cntmax=0) tester.addTest( re.compile(r'''@%@BCWARNING=.+?@%@'''), '0016-5', 'Use of deprecated "@%@BCWARNING=@%@"', cntmax=0) ignore_suffixes = ('.1', '.2', '.3', '.4', '.5', '.6', '.7', '.8', '.txt') ignore_files = ('changelog', 'README') for fn in uub.FilteredDirWalkGenerator(path, ignore_suffixes=ignore_suffixes, ignore_files=ignore_files): tester.open(fn) msglist = tester.runTests() self.msg.extend(msglist) for fn in uub.FilteredDirWalkGenerator(os.path.join(path, 'debian'), suffixes=('.univention-baseconfig',)): self.addmsg('0016-6', 'Use of deprecated "debian/*.univention-baseconfig"', fn)
def __init__(self): super(UniventionPackageCheck, self).__init__() self.name = '0017-Shell' self.tester = uub.UPCFileTester() self.tester.addTest(re.compile( r'eval\s+(`|[$][(])\s*(/usr/sbin/)?(ucr|univention-baseconfig|univention-config-registry)\s+shell\s*[^`)]*[`)]\s*' ), '0017-1', 'unquoted call of eval "$(ucr shell)"', cntmax=0)
def check(self, path): """ the real check """ super(UniventionPackageCheck, self).check(path) py_files = [] for fn in uub.FilteredDirWalkGenerator(path): if fn.endswith('.py'): # add all files to list that end with ".py" py_files.append(fn) continue try: content = open(fn, 'r').read(100) # add all files that contain a hashbang in first line except (IOError, OSError): self.debug('Failed to read 100 bytes from %r' % (fn,)) else: if content.startswith('#!'): py_files.append(fn) tester = uub.UPCFileTester() tester.addTest(re.compile('.has_key\s*\('), '0009-5', 'dict.has_key is deprecated in python3 - please use "if key in dict:"', cntmax=0) tester.addTest(re.compile(r'''\braise\s*(?:'[^']+'|"[^"]+")'''), '0009-6', 'raise "text" is deprecated in python3', cntmax=0) tester.addTest(re.compile(r"""\b(?:if|while)\b.*(?:(?:!=|<>|==)\s*None\b|\bNone\s*(?:!=|<>|==)).*:"""), '0009-7', 'fragile comparison with None', cntmax=0) tester.addTest(re.compile( r'''(?:baseConfig|configRegistry|ucr)(?:\[.+\]|\.get\(.+\)).*\bin\s* [[(] (?:\s*(['"])(?:yes|no|1|0|true|false|on|off|enabled?|disabled?)\1\s*,?\s*){3,} [])]''', re.VERBOSE | re.IGNORECASE), '0009-8', 'use ucr.is_true() or .is_false()', cntmax=0) for fn in py_files: try: content = open(fn, 'r').read(100) except (IOError, OSError): self.addmsg('0009-1', 'failed to open and read file', filename=fn) continue self.debug('testing %s' % fn) if not content: continue tester.open(fn) msglist = tester.runTests() self.msg.extend(msglist) firstline = content.splitlines()[0] match = UniventionPackageCheck.RE_HASHBANG.match(firstline) if match: version, space, option, tail = match.groups() if not version: self.addmsg('0009-2', 'file does not specify python version in hashbang', filename=fn) elif version != '2.7': self.addmsg('0009-3', 'file specifies wrong python version in hashbang', filename=fn) if space and not option: self.addmsg('0009-4', 'file contains whitespace after python command', filename=fn) if tail: self.addmsg('0009-9', 'hashbang contains more than one option', filename=fn)
def check(self, path: str) -> None: """ the real check """ super(UniventionPackageCheck, self).check(path) tester = uub.UPCFileTester() tester.addTest(re.compile(r'dc=univention,dc=(?:local|qa|test)'), '0002-2', 'contains invalid basedn', cntmax=0) tester.addTest(re.compile(r'univention\.(?:local|qa|test)'), '0002-3', 'contains invalid domainname', cntmax=0) for fn in chain( uub.FilteredDirWalkGenerator(join(path, 'conffiles')), uub.FilteredDirWalkGenerator(join(path, 'debian')), ): try: tester.open(fn) except EnvironmentError: self.addmsg('0002-1', 'failed to open and read file', fn) else: self.msg += tester.runTests()
def check_names(self, files: Iterable[str]) -> None: tester = uub.UPCFileTester() tester.addTest( re.compile( r''' (?<!custom_groupname[( ]) (?<!custom_username[( ]) (['"]) \b (?:Domain\ Users|Domain\ Admins|Administrator|Windows\ Hosts) \b \1 ''', re.VERBOSE), '0008-7', 'found well-known LDAP object but no custom_*name()', cntmax=0) for fn in files: try: tester.open(fn) except EnvironmentError: self.addmsg('0002-1', 'failed to open and read file', fn) continue else: self.msg += tester.runTests()
def __init__(self) -> None: super(UniventionPackageCheck, self).__init__() self.tester = uub.UPCFileTester() self.tester.addTest(re.compile( r'eval\s+(`|[$][(])\s*(/usr/sbin/)?(ucr|univention-baseconfig|univention-config-registry)\s+shell\s*[^`)]*[`)]\s*' ), '0017-1', 'unquoted call of eval "$(ucr shell)"', cntmax=0) self.tester.addTest(re.compile(r'\b tr \s+ (-[a-zA-Z]+\s+)* \[', re.VERBOSE), '0017-2', 'unquoted argument for tr (e.g. "tr -d [a-z]")', cntmax=0) self.tester.addTest(re.compile( r'''\b tr \s+ (-[a-zA-Z]+\s+)* ["']\[+[^\]]+\]+["']\s+\[''', re.VERBOSE), '0017-2', 'unquoted argument for tr (e.g. "tr -d [a-z]")', cntmax=0) self.tester.addTest(re.compile( r'\b univention-ldapsearch \b .* \s-[a-wyzA-Z]*x[a-wyzA-Z]* \b', re.VERBOSE), '0017-3', 'use of univention-ldapsearch -x', cntmax=0) self.tester.addTest(re.compile( r'\b (?:/sbin/)? ip6?tables \b \s+ (?!--wait \b)', re.VERBOSE), '0017-4', 'iptables without --wait', cntmax=0) self.tester.addTest(re.compile( r'\b sed \s+ .* s (.) .* \\\(\.\*\\\) \$? \1 \\1 \1', re.VERBOSE), '0017-5', 'Use `sed -n "s/^prefix: //p"`', cntmax=0) self.tester.addTest(re.compile( r'\b sed (?: \s+ -[bnsuz]*[Er][bnsuze]* \b )+ .* s (.) .* \(\.\*\) \$? \1 \\1 \1', re.VERBOSE), '0017-5', 'Use `sed -n "s/^prefix: //p"`', cntmax=0) self.tester.addTest(re.compile( r'\b ldapsearch \b .+ \b ldapsearch-wrapper \b', re.VERBOSE), '0017-6', 'Use `ldapsearch -o ldif-wrap=no`', cntmax=0) self.tester.addTest(re.compile(r'\b (\w+) \[ \${\#\1\[[@*]\]} \]=', re.VERBOSE), '0017-7', 'Use `array+=(val)`', cntmax=0) self.tester.addTest(re.compile( r'''\b (?:cat|more) \s+ (?:'[^']*'|"[^"]*"|[^"'*? |])+ \s* \|(?!\|)''', re.VERBOSE), '0017-8', "Useless use of `cat`; redirect STDIN instead", cntmax=0) self.tester.addTest(re.compile( r'\b grep \b .* \|(?!\|) .* \b (?:awk|perl|sed) \b', re.VERBOSE), '0017-9', "Useless use of `grep`; use /PATTERN/s instead", cntmax=0) self.tester.addTest(re.compile( r'\b echo \s+ (?:-[ne]+ \s+)* (")? \$\( [^<][^)]* \) \1 \s* (?:$|[|&]|\d*[<>])', re.VERBOSE), '0017-10', "Useless use of `echo $(...)` for single argument", cntmax=0)
def check(self, path: str) -> None: """ the real check """ super(UniventionPackageCheck, self).check(path) tester = uub.UPCFileTester() tester.addTest( re.compile(r'\.has_key\s*\('), '0009-5', 'dict.has_key is deprecated in python3 - please use "if key in dict:"', cntmax=0) tester.addTest(re.compile(r'''\braise\s*(?:'[^']+'|"[^"]+")'''), '0009-6', 'raise "text" is deprecated in python3', cntmax=0) tester.addTest(re.compile( r"""\b(?:if|while)\b.*(?:(?:!=|<>|==)\s*None\b|\bNone\s*(?:!=|<>|==)).*:""" ), '0009-7', 'fragile comparison with None', cntmax=0) tester.addTest(re.compile( r'''(?:baseConfig|configRegistry|ucr)(?:\[.+\]|\.get\(.+\)).*\bin\s* [\[\(] (?:\s*(['"])(?:yes|no|1|0|true|false|on|off|enabled?|disabled?)\1\s*,?\s*){3,} [\]\)]''', re.VERBOSE | re.IGNORECASE), '0009-8', 'use ucr.is_true() or .is_false()', cntmax=0) tester.addTest( re.compile( r'''\.search\s*\( .*?\b attr \s*=\s* (?:(?P<list>\[)|(?P<tuple>\()) \s* (?P<str>["']) dn (?P=str) \s* (?(list)\])(?(tuple)\)) ''', re.VERBOSE), '0009-11', 'Use uldap.searchDn() instead of uldap.search(attr=["dn"])', cntmax=0) for fn in python_files(path): tester.open(fn) if not tester.raw: continue msglist = tester.runTests() self.msg.extend(msglist) match = self.RE_HASHBANG.match(tester.lines[0]) if match: version, space, option, tail = match.groups() if not version: self.addmsg( '0009-2', 'file does not specify python version in hashbang', fn, 1) elif version not in {'2.7', '3'}: self.addmsg( '0009-3', 'file specifies wrong python version in hashbang', fn, 1) if space and not option: self.addmsg( '0009-4', 'file contains whitespace after python command', fn, 1) if tail: self.addmsg('0009-9', 'hashbang contains more than one option', fn, 1) for row, col, m in uub.line_regexp(tester.raw, RE_LENIENT): txt = m.group("str") if not txt: continue if self.RE_STRING.match(txt): continue self.addmsg('0009-10', 'invalid Python string literal: %s' % (txt, ), fn, row, col) try: tree = ast.parse(tester.raw, fn) visitor = FindAssign(self, fn) visitor.visit(tree) except Exception as ex: self.addmsg('0009-1', 'Parsing failed: %s' % ex, fn)