diff --git a/.pylintrc b/.pylintrc index 9b1489b..049ea91 100644 --- a/.pylintrc +++ b/.pylintrc @@ -61,17 +61,7 @@ confidence= # --enable=similarities". If you want to run only the classes checker, but have # no Warning level messages displayed, use "--disable=all --enable=classes # --disable=W". -disable=print-statement, - parameter-unpacking, - unpacking-in-except, - old-raise-syntax, - backtick, - long-suffix, - old-ne-operator, - old-octal-literal, - import-star-module-level, - non-ascii-bytes-literal, - raw-checker-failed, +disable=raw-checker-failed, bad-inline-option, locally-disabled, file-ignored, @@ -79,67 +69,6 @@ disable=print-statement, useless-suppression, deprecated-pragma, use-symbolic-message-instead, - apply-builtin, - basestring-builtin, - buffer-builtin, - cmp-builtin, - coerce-builtin, - execfile-builtin, - file-builtin, - long-builtin, - raw_input-builtin, - reduce-builtin, - standarderror-builtin, - unicode-builtin, - xrange-builtin, - coerce-method, - delslice-method, - getslice-method, - setslice-method, - no-absolute-import, - old-division, - dict-iter-method, - dict-view-method, - next-method-called, - metaclass-assignment, - indexing-exception, - raising-string, - reload-builtin, - oct-method, - hex-method, - nonzero-method, - cmp-method, - input-builtin, - round-builtin, - intern-builtin, - unichr-builtin, - map-builtin-not-iterating, - zip-builtin-not-iterating, - range-builtin-not-iterating, - filter-builtin-not-iterating, - using-cmp-argument, - eq-without-hash, - div-method, - idiv-method, - rdiv-method, - exception-message-attribute, - invalid-str-codec, - sys-max-int, - bad-python3-import, - deprecated-string-function, - deprecated-str-translate-call, - deprecated-itertools-function, - deprecated-types-field, - next-method-defined, - dict-items-not-iterating, - dict-keys-not-iterating, - dict-values-not-iterating, - deprecated-operator-function, - deprecated-urllib-function, - xreadlines-attribute, - deprecated-sys-function, - exception-escape, - comprehension-escape, # custom changes follow import-outside-toplevel, global-statement, diff --git a/Dockerfile b/Dockerfile index cd1a593..0a451db 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,11 +1,11 @@ # NOTE: Use the run-container.sh script to build and launch this container. # NOTE: Multi-stage builds require Docker >= 17.05. -FROM rockylinux:8 AS base +FROM rockylinux:8.5 AS base # update packages and install requirements RUN dnf -y upgrade-minimal && \ - dnf install -y python38 && \ + dnf install -y python39 && \ dnf install -y ghostscript && \ dnf clean all diff --git a/asl_rulebook2/extract/content.py b/asl_rulebook2/extract/content.py index 228fd93..6deb71c 100755 --- a/asl_rulebook2/extract/content.py +++ b/asl_rulebook2/extract/content.py @@ -166,7 +166,8 @@ class ExtractContent( ExtractBase ): # process each element on the page curr_caption = None self._top_left_elem = self._prev_elem = None - elem_filter = lambda e: isinstance( e, LTChar ) + def elem_filter( elem ): + return isinstance( elem, LTChar ) sort_elems = self._curr_pageid not in disable_sort_items and str(page_no) not in disable_sort_items for _, elem in PageElemIterator( lt_page, elem_filter=elem_filter, sort_elems=sort_elems ): diff --git a/asl_rulebook2/extract/index.py b/asl_rulebook2/extract/index.py index 81dab12..58bce5a 100755 --- a/asl_rulebook2/extract/index.py +++ b/asl_rulebook2/extract/index.py @@ -53,7 +53,8 @@ class ExtractIndex( ExtractBase ): # process each element on the page self._prev_y0 = 99999 - elem_filter = lambda e: isinstance( e, LTChar ) + def elem_filter( elem ): + return isinstance( elem, LTChar ) for _, elem in PageElemIterator( lt_page, elem_filter=elem_filter ): # check if we should ignore this element diff --git a/asl_rulebook2/utils.py b/asl_rulebook2/utils.py index 3e82b08..c0e1d62 100644 --- a/asl_rulebook2/utils.py +++ b/asl_rulebook2/utils.py @@ -73,7 +73,7 @@ def strip_html( val ): self.strict = False def handle_data( self, data ): buf.write( data ) - def error( self, message ): + def error( self, message ): #pylint: disable=missing-function-docstring pass # strip HTML diff --git a/asl_rulebook2/webapp/asop.py b/asl_rulebook2/webapp/asop.py index 71c7e98..d82b909 100644 --- a/asl_rulebook2/webapp/asop.py +++ b/asl_rulebook2/webapp/asop.py @@ -2,7 +2,8 @@ import os -from flask import jsonify, render_template_string, send_from_directory, safe_join, url_for, abort +from flask import jsonify, render_template_string, send_from_directory, url_for, abort +from werkzeug.utils import safe_join from asl_rulebook2.webapp import app from asl_rulebook2.webapp.content import tag_ruleids diff --git a/asl_rulebook2/webapp/doc.py b/asl_rulebook2/webapp/doc.py index 73ac3ba..696ca79 100644 --- a/asl_rulebook2/webapp/doc.py +++ b/asl_rulebook2/webapp/doc.py @@ -5,7 +5,8 @@ import io import re import markdown -from flask import make_response, send_file, abort, safe_join +from flask import make_response, send_file, abort +from werkzeug.utils import safe_join from asl_rulebook2.webapp import app @@ -18,7 +19,7 @@ def get_doc( path ): # locate the documentation file dname = os.path.join( os.path.dirname( __file__ ), "../../doc/" ) fname = safe_join( dname, path ) - if not os.path.isfile( fname ): + if fname is None or not os.path.isfile( fname ): # FUDGE! If this package has been installed in non-editable mode (i.e. into site-packages, while it's possible # to get the root doc/ directory included in the installation (by adding a __init__.py file :-/, then including # it in MANIFEST.in), it ends up in asl-rulebook2's parent directory (i.e. the main site-packages directory), @@ -27,7 +28,7 @@ def get_doc( path ): # is installed. This won't work on Windows, but we'll do the necessary penance, and just live with it... :-/ dname = os.path.join( os.path.dirname( __file__ ), "data/doc/" ) fname = safe_join( dname, path ) - if not os.path.isfile( fname ): + if fname is None or not os.path.isfile( fname ): abort( 404 ) # check if the file is Markdown diff --git a/asl_rulebook2/webapp/tests/control_tests.py b/asl_rulebook2/webapp/tests/control_tests.py index 2c087b2..167d74b 100644 --- a/asl_rulebook2/webapp/tests/control_tests.py +++ b/asl_rulebook2/webapp/tests/control_tests.py @@ -1,7 +1,7 @@ """ Allow the test suite to control a remote webapp server. """ import grpc -from google.protobuf.empty_pb2 import Empty +from google.protobuf.empty_pb2 import Empty #pylint: disable=no-name-in-module from asl_rulebook2.webapp.tests.proto.generated.control_tests_pb2_grpc import ControlTestsStub diff --git a/asl_rulebook2/webapp/tests/control_tests_servicer.py b/asl_rulebook2/webapp/tests/control_tests_servicer.py index cccd8af..cf160cd 100644 --- a/asl_rulebook2/webapp/tests/control_tests_servicer.py +++ b/asl_rulebook2/webapp/tests/control_tests_servicer.py @@ -4,7 +4,7 @@ import os import inspect import logging -from google.protobuf.empty_pb2 import Empty +from google.protobuf.empty_pb2 import Empty #pylint: disable=no-name-in-module from asl_rulebook2.webapp.tests.proto.generated.control_tests_pb2_grpc \ import ControlTestsServicer as BaseControlTestsServicer diff --git a/asl_rulebook2/webapp/tests/proto/generated/control_tests_pb2.py b/asl_rulebook2/webapp/tests/proto/generated/control_tests_pb2.py index c582d10..6b7b2ce 100644 --- a/asl_rulebook2/webapp/tests/proto/generated/control_tests_pb2.py +++ b/asl_rulebook2/webapp/tests/proto/generated/control_tests_pb2.py @@ -3,6 +3,7 @@ # source: control_tests.proto """Generated protocol buffer code.""" from google.protobuf import descriptor as _descriptor +from google.protobuf import descriptor_pool as _descriptor_pool from google.protobuf import message as _message from google.protobuf import reflection as _reflection from google.protobuf import symbol_database as _symbol_database @@ -14,121 +15,12 @@ _sym_db = _symbol_database.Default() from google.protobuf import empty_pb2 as google_dot_protobuf_dot_empty__pb2 -DESCRIPTOR = _descriptor.FileDescriptor( - name='control_tests.proto', - package='', - syntax='proto3', - serialized_options=None, - create_key=_descriptor._internal_create_key, - serialized_pb=b'\n\x13\x63ontrol_tests.proto\x1a\x1bgoogle/protobuf/empty.proto\",\n\x11SetDataDirRequest\x12\x17\n\x0f\x66ixturesDirName\x18\x01 \x01(\t\"h\n\x16SetAppConfigValRequest\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\x10\n\x06strVal\x18\x02 \x01(\tH\x00\x12\x10\n\x06intVal\x18\x03 \x01(\x05H\x00\x12\x11\n\x07\x62oolVal\x18\x04 \x01(\x08H\x00\x42\n\n\x08\x61\x63_oneof2\x86\x02\n\x0c\x43ontrolTests\x12<\n\nstartTests\x12\x16.google.protobuf.Empty\x1a\x16.google.protobuf.Empty\x12:\n\x08\x65ndTests\x12\x16.google.protobuf.Empty\x1a\x16.google.protobuf.Empty\x12\x38\n\nsetDataDir\x12\x12.SetDataDirRequest\x1a\x16.google.protobuf.Empty\x12\x42\n\x0fsetAppConfigVal\x12\x17.SetAppConfigValRequest\x1a\x16.google.protobuf.Emptyb\x06proto3' - , - dependencies=[google_dot_protobuf_dot_empty__pb2.DESCRIPTOR,]) +DESCRIPTOR = _descriptor_pool.Default().AddSerializedFile(b'\n\x13\x63ontrol_tests.proto\x1a\x1bgoogle/protobuf/empty.proto\",\n\x11SetDataDirRequest\x12\x17\n\x0f\x66ixturesDirName\x18\x01 \x01(\t\"h\n\x16SetAppConfigValRequest\x12\x0b\n\x03key\x18\x01 \x01(\t\x12\x10\n\x06strVal\x18\x02 \x01(\tH\x00\x12\x10\n\x06intVal\x18\x03 \x01(\x05H\x00\x12\x11\n\x07\x62oolVal\x18\x04 \x01(\x08H\x00\x42\n\n\x08\x61\x63_oneof2\x86\x02\n\x0c\x43ontrolTests\x12<\n\nstartTests\x12\x16.google.protobuf.Empty\x1a\x16.google.protobuf.Empty\x12:\n\x08\x65ndTests\x12\x16.google.protobuf.Empty\x1a\x16.google.protobuf.Empty\x12\x38\n\nsetDataDir\x12\x12.SetDataDirRequest\x1a\x16.google.protobuf.Empty\x12\x42\n\x0fsetAppConfigVal\x12\x17.SetAppConfigValRequest\x1a\x16.google.protobuf.Emptyb\x06proto3') - -_SETDATADIRREQUEST = _descriptor.Descriptor( - name='SetDataDirRequest', - full_name='SetDataDirRequest', - filename=None, - file=DESCRIPTOR, - containing_type=None, - create_key=_descriptor._internal_create_key, - fields=[ - _descriptor.FieldDescriptor( - name='fixturesDirName', full_name='SetDataDirRequest.fixturesDirName', index=0, - number=1, type=9, cpp_type=9, label=1, - has_default_value=False, default_value=b"".decode('utf-8'), - message_type=None, enum_type=None, containing_type=None, - is_extension=False, extension_scope=None, - serialized_options=None, file=DESCRIPTOR, create_key=_descriptor._internal_create_key), - ], - extensions=[ - ], - nested_types=[], - enum_types=[ - ], - serialized_options=None, - is_extendable=False, - syntax='proto3', - extension_ranges=[], - oneofs=[ - ], - serialized_start=52, - serialized_end=96, -) - - -_SETAPPCONFIGVALREQUEST = _descriptor.Descriptor( - name='SetAppConfigValRequest', - full_name='SetAppConfigValRequest', - filename=None, - file=DESCRIPTOR, - containing_type=None, - create_key=_descriptor._internal_create_key, - fields=[ - _descriptor.FieldDescriptor( - name='key', full_name='SetAppConfigValRequest.key', index=0, - number=1, type=9, cpp_type=9, label=1, - has_default_value=False, default_value=b"".decode('utf-8'), - message_type=None, enum_type=None, containing_type=None, - is_extension=False, extension_scope=None, - serialized_options=None, file=DESCRIPTOR, create_key=_descriptor._internal_create_key), - _descriptor.FieldDescriptor( - name='strVal', full_name='SetAppConfigValRequest.strVal', index=1, - number=2, type=9, cpp_type=9, label=1, - has_default_value=False, default_value=b"".decode('utf-8'), - message_type=None, enum_type=None, containing_type=None, - is_extension=False, extension_scope=None, - serialized_options=None, file=DESCRIPTOR, create_key=_descriptor._internal_create_key), - _descriptor.FieldDescriptor( - name='intVal', full_name='SetAppConfigValRequest.intVal', index=2, - number=3, type=5, cpp_type=1, label=1, - has_default_value=False, default_value=0, - message_type=None, enum_type=None, containing_type=None, - is_extension=False, extension_scope=None, - serialized_options=None, file=DESCRIPTOR, create_key=_descriptor._internal_create_key), - _descriptor.FieldDescriptor( - name='boolVal', full_name='SetAppConfigValRequest.boolVal', index=3, - number=4, type=8, cpp_type=7, label=1, - has_default_value=False, default_value=False, - message_type=None, enum_type=None, containing_type=None, - is_extension=False, extension_scope=None, - serialized_options=None, file=DESCRIPTOR, create_key=_descriptor._internal_create_key), - ], - extensions=[ - ], - nested_types=[], - enum_types=[ - ], - serialized_options=None, - is_extendable=False, - syntax='proto3', - extension_ranges=[], - oneofs=[ - _descriptor.OneofDescriptor( - name='ac_oneof', full_name='SetAppConfigValRequest.ac_oneof', - index=0, containing_type=None, - create_key=_descriptor._internal_create_key, - fields=[]), - ], - serialized_start=98, - serialized_end=202, -) - -_SETAPPCONFIGVALREQUEST.oneofs_by_name['ac_oneof'].fields.append( - _SETAPPCONFIGVALREQUEST.fields_by_name['strVal']) -_SETAPPCONFIGVALREQUEST.fields_by_name['strVal'].containing_oneof = _SETAPPCONFIGVALREQUEST.oneofs_by_name['ac_oneof'] -_SETAPPCONFIGVALREQUEST.oneofs_by_name['ac_oneof'].fields.append( - _SETAPPCONFIGVALREQUEST.fields_by_name['intVal']) -_SETAPPCONFIGVALREQUEST.fields_by_name['intVal'].containing_oneof = _SETAPPCONFIGVALREQUEST.oneofs_by_name['ac_oneof'] -_SETAPPCONFIGVALREQUEST.oneofs_by_name['ac_oneof'].fields.append( - _SETAPPCONFIGVALREQUEST.fields_by_name['boolVal']) -_SETAPPCONFIGVALREQUEST.fields_by_name['boolVal'].containing_oneof = _SETAPPCONFIGVALREQUEST.oneofs_by_name['ac_oneof'] -DESCRIPTOR.message_types_by_name['SetDataDirRequest'] = _SETDATADIRREQUEST -DESCRIPTOR.message_types_by_name['SetAppConfigValRequest'] = _SETAPPCONFIGVALREQUEST -_sym_db.RegisterFileDescriptor(DESCRIPTOR) - +_SETDATADIRREQUEST = DESCRIPTOR.message_types_by_name['SetDataDirRequest'] +_SETAPPCONFIGVALREQUEST = DESCRIPTOR.message_types_by_name['SetAppConfigValRequest'] SetDataDirRequest = _reflection.GeneratedProtocolMessageType('SetDataDirRequest', (_message.Message,), { 'DESCRIPTOR' : _SETDATADIRREQUEST, '__module__' : 'control_tests_pb2' @@ -143,61 +35,14 @@ SetAppConfigValRequest = _reflection.GeneratedProtocolMessageType('SetAppConfigV }) _sym_db.RegisterMessage(SetAppConfigValRequest) +_CONTROLTESTS = DESCRIPTOR.services_by_name['ControlTests'] +if _descriptor._USE_C_DESCRIPTORS == False: - -_CONTROLTESTS = _descriptor.ServiceDescriptor( - name='ControlTests', - full_name='ControlTests', - file=DESCRIPTOR, - index=0, - serialized_options=None, - create_key=_descriptor._internal_create_key, - serialized_start=205, - serialized_end=467, - methods=[ - _descriptor.MethodDescriptor( - name='startTests', - full_name='ControlTests.startTests', - index=0, - containing_service=None, - input_type=google_dot_protobuf_dot_empty__pb2._EMPTY, - output_type=google_dot_protobuf_dot_empty__pb2._EMPTY, - serialized_options=None, - create_key=_descriptor._internal_create_key, - ), - _descriptor.MethodDescriptor( - name='endTests', - full_name='ControlTests.endTests', - index=1, - containing_service=None, - input_type=google_dot_protobuf_dot_empty__pb2._EMPTY, - output_type=google_dot_protobuf_dot_empty__pb2._EMPTY, - serialized_options=None, - create_key=_descriptor._internal_create_key, - ), - _descriptor.MethodDescriptor( - name='setDataDir', - full_name='ControlTests.setDataDir', - index=2, - containing_service=None, - input_type=_SETDATADIRREQUEST, - output_type=google_dot_protobuf_dot_empty__pb2._EMPTY, - serialized_options=None, - create_key=_descriptor._internal_create_key, - ), - _descriptor.MethodDescriptor( - name='setAppConfigVal', - full_name='ControlTests.setAppConfigVal', - index=3, - containing_service=None, - input_type=_SETAPPCONFIGVALREQUEST, - output_type=google_dot_protobuf_dot_empty__pb2._EMPTY, - serialized_options=None, - create_key=_descriptor._internal_create_key, - ), -]) -_sym_db.RegisterServiceDescriptor(_CONTROLTESTS) - -DESCRIPTOR.services_by_name['ControlTests'] = _CONTROLTESTS - + DESCRIPTOR._options = None + _SETDATADIRREQUEST._serialized_start=52 + _SETDATADIRREQUEST._serialized_end=96 + _SETAPPCONFIGVALREQUEST._serialized_start=98 + _SETAPPCONFIGVALREQUEST._serialized_end=202 + _CONTROLTESTS._serialized_start=205 + _CONTROLTESTS._serialized_end=467 # @@protoc_insertion_point(module_scope) diff --git a/asl_rulebook2/webapp/tests/test_footnotes.py b/asl_rulebook2/webapp/tests/test_footnotes.py index 39e0a61..8557ade 100644 --- a/asl_rulebook2/webapp/tests/test_footnotes.py +++ b/asl_rulebook2/webapp/tests/test_footnotes.py @@ -36,11 +36,13 @@ def test_footnotes( webdriver, webapp ): if root.attrib["class"] == "footnote": # this is a single footnote footnote_elems = [ root ] - get_content = lambda fnote: fnote.find( "div[@class='content']" ).text + def get_content( fnote ): + return fnote.find( "div[@class='content']" ).text else: # there are multiple footnotes footnote_elems = root.findall( "div[@class='footnote']" ) - get_content = lambda fnote: "".join( fnote.xpath( "text()" ) ) + def get_content( fnote ): + return "".join( fnote.xpath( "text()" ) ) # extract content from each footnote for footnote in footnote_elems: header = footnote.find( "div[@class='header']" ) diff --git a/requirements-dev.txt b/requirements-dev.txt index 25e1749..6053f71 100644 --- a/requirements-dev.txt +++ b/requirements-dev.txt @@ -1,6 +1,6 @@ -pytest==7.0.1 -selenium==4.1.0 -grpcio==1.44.0 -protobuf==3.19.4 -pylint==2.12.2 +pytest==7.1.2 +selenium==4.2.0 +grpcio==1.46.3 +grpcio-tools==1.46.3 +pylint==2.14.1 pytest-pylint==0.18.0 diff --git a/requirements.txt b/requirements.txt index ca2fb00..cdc7007 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,12 +1,12 @@ -# python 3.8.7 +# python 3.10.4 -flask==2.0.3 -flask-socketio==5.1.1 -eventlet==0.33.0 +flask==2.1.2 +flask-socketio==5.2.0 +eventlet==0.33.1 pyyaml==6.0 -lxml==4.8.0 -markdown==3.3.6 -click==8.0.4 +lxml==4.9.0 +markdown==3.3.7 +click==8.1.3 -pdfminer.six==20211012 -pikepdf==5.0.1 +pdfminer.six==20220524 +pikepdf==5.1.3