diff --git a/.circleci/config.yml b/.circleci/config.yml index b8d9bb466c21..f29c69235e68 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -15,7 +15,7 @@ variables: jobs: get_code: docker: - - image: cimg/python:3.7 + - image: cimg/python:3.8 <<: *set_workdir steps: # Replace standard code checkout with shallow clone to speed things up. @@ -73,7 +73,7 @@ jobs: - ~/repo validate_test_tools: docker: - - image: cimg/python:3.7 + - image: cimg/python:3.8 <<: *set_workdir steps: - *restore_repo_cache diff --git a/.github/workflows/api.yaml b/.github/workflows/api.yaml index 90038e328865..753f669f148f 100644 --- a/.github/workflows/api.yaml +++ b/.github/workflows/api.yaml @@ -28,7 +28,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.8'] chunk: [0, 1] services: postgres: diff --git a/.github/workflows/check_test_class_names.yaml b/.github/workflows/check_test_class_names.yaml index 92db607c7bdb..217995df93e4 100644 --- a/.github/workflows/check_test_class_names.yaml +++ b/.github/workflows/check_test_class_names.yaml @@ -11,7 +11,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] steps: - uses: actions/checkout@v3 - uses: actions/setup-python@v4 diff --git a/.github/workflows/converter_tests.yaml b/.github/workflows/converter_tests.yaml index 359edf8b0d9e..1d8c0ee963b8 100644 --- a/.github/workflows/converter_tests.yaml +++ b/.github/workflows/converter_tests.yaml @@ -22,7 +22,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] steps: - if: github.event_name == 'schedule' run: | diff --git a/.github/workflows/cwl_conformance.yaml b/.github/workflows/cwl_conformance.yaml index 716a8ca2bbbd..206bd33798a1 100644 --- a/.github/workflows/cwl_conformance.yaml +++ b/.github/workflows/cwl_conformance.yaml @@ -22,7 +22,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.8'] marker: ['green', 'red and required', 'red and not required'] conformance-version: ['cwl_conformance_v1_0'] #, 'cwl_conformance_v1_1', 'cwl_conformance_v1_2'] services: diff --git a/.github/workflows/db_indexes.yaml b/.github/workflows/db_indexes.yaml index af8455edd887..88f1d02297af 100644 --- a/.github/workflows/db_indexes.yaml +++ b/.github/workflows/db_indexes.yaml @@ -24,11 +24,11 @@ jobs: matrix: db: ['postgresql', 'sqlite'] postgresql-version: ['13'] - python-version: ['3.7'] + python-version: ['3.8'] include: - db: postgresql postgresql-version: '9.6' - python-version: '3.7' + python-version: '3.8' services: postgres: image: postgres:${{ matrix.postgresql-version }} diff --git a/.github/workflows/dependencies.yaml b/.github/workflows/dependencies.yaml index 0d02ae2f1234..31405cc13498 100644 --- a/.github/workflows/dependencies.yaml +++ b/.github/workflows/dependencies.yaml @@ -9,17 +9,12 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] steps: - uses: actions/checkout@v3 - uses: actions/setup-python@v4 with: - # poetry requires Python >=3.8, but lint requirements currently need - # to be generated with `pip freeze`` on the oldest Python version - # supported by Galaxy. - python-version: | - ${{ matrix.python-version }} - 3.8 + python-version: ${{ matrix.python-version }} - name: Update dependencies run: | python -m venv .venv diff --git a/.github/workflows/deployment.yaml b/.github/workflows/deployment.yaml index 441f35e71673..082e93d9328d 100644 --- a/.github/workflows/deployment.yaml +++ b/.github/workflows/deployment.yaml @@ -33,7 +33,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] steps: - uses: actions/checkout@v3 with: diff --git a/.github/workflows/docs.yaml b/.github/workflows/docs.yaml index 6de9bf997964..9f67f3322488 100644 --- a/.github/workflows/docs.yaml +++ b/.github/workflows/docs.yaml @@ -16,7 +16,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] steps: - name: Get target branch name (push) if: github.event_name == 'push' diff --git a/.github/workflows/first_startup.yaml b/.github/workflows/first_startup.yaml index 34093cae9605..10f506dbbedf 100644 --- a/.github/workflows/first_startup.yaml +++ b/.github/workflows/first_startup.yaml @@ -21,7 +21,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] defaults: run: shell: bash -l {0} diff --git a/.github/workflows/framework.yaml b/.github/workflows/framework.yaml index 5de51cca7cad..53a287c5d7c0 100644 --- a/.github/workflows/framework.yaml +++ b/.github/workflows/framework.yaml @@ -25,7 +25,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] services: postgres: image: postgres:13 diff --git a/.github/workflows/integration.yaml b/.github/workflows/integration.yaml index d3660517fb72..58aa81dd63c3 100644 --- a/.github/workflows/integration.yaml +++ b/.github/workflows/integration.yaml @@ -29,7 +29,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.8'] chunk: ['0', '1', '2', '3'] services: postgres: diff --git a/.github/workflows/integration_selenium.yaml b/.github/workflows/integration_selenium.yaml index e8cf74fb5639..427a41ec1559 100644 --- a/.github/workflows/integration_selenium.yaml +++ b/.github/workflows/integration_selenium.yaml @@ -29,7 +29,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] services: postgres: image: postgres:13 diff --git a/.github/workflows/lint.yaml b/.github/workflows/lint.yaml index 590f93cd5e2c..037f343d9ee9 100644 --- a/.github/workflows/lint.yaml +++ b/.github/workflows/lint.yaml @@ -22,7 +22,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] env: LINT_PATH: 'lib/galaxy/dependencies/pinned-lint-requirements.txt' TYPE_PATH: 'lib/galaxy/dependencies/pinned-typecheck-requirements.txt' diff --git a/.github/workflows/lint_openapi_schema.yml b/.github/workflows/lint_openapi_schema.yml index 32ddedf5cd7d..c327fabe72e8 100644 --- a/.github/workflows/lint_openapi_schema.yml +++ b/.github/workflows/lint_openapi_schema.yml @@ -20,7 +20,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] steps: - uses: actions/checkout@v3 with: diff --git a/.github/workflows/mulled.yaml b/.github/workflows/mulled.yaml index a9e84ef28a5e..1b140eb1f6c3 100644 --- a/.github/workflows/mulled.yaml +++ b/.github/workflows/mulled.yaml @@ -20,7 +20,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.8'] steps: - uses: actions/checkout@v3 with: diff --git a/.github/workflows/osx_startup.yaml b/.github/workflows/osx_startup.yaml index 0015076712b6..d550c6741678 100644 --- a/.github/workflows/osx_startup.yaml +++ b/.github/workflows/osx_startup.yaml @@ -18,7 +18,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] defaults: run: shell: bash -l {0} diff --git a/.github/workflows/performance.yaml b/.github/workflows/performance.yaml index 4eda60399585..48287a739f8c 100644 --- a/.github/workflows/performance.yaml +++ b/.github/workflows/performance.yaml @@ -24,7 +24,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] services: postgres: image: postgres:13 diff --git a/.github/workflows/publish_artifacts.yaml b/.github/workflows/publish_artifacts.yaml index fd4d736f1b34..3703d932c0cc 100644 --- a/.github/workflows/publish_artifacts.yaml +++ b/.github/workflows/publish_artifacts.yaml @@ -9,7 +9,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ['3.7'] + python-version: ['3.8'] steps: - uses: actions/setup-python@v4 with: diff --git a/.github/workflows/reports_startup.yaml b/.github/workflows/reports_startup.yaml index 805686e3d388..5597489d3726 100644 --- a/.github/workflows/reports_startup.yaml +++ b/.github/workflows/reports_startup.yaml @@ -18,7 +18,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] defaults: run: shell: bash -l {0} diff --git a/.github/workflows/selenium.yaml b/.github/workflows/selenium.yaml index 11cf1886fc2b..b8235cb7869f 100644 --- a/.github/workflows/selenium.yaml +++ b/.github/workflows/selenium.yaml @@ -30,7 +30,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.8'] chunk: [0, 1, 2] services: postgres: diff --git a/.github/workflows/test_galaxy_packages.yaml b/.github/workflows/test_galaxy_packages.yaml index 089d4f45f19e..f2e5d88b52a7 100644 --- a/.github/workflows/test_galaxy_packages.yaml +++ b/.github/workflows/test_galaxy_packages.yaml @@ -18,7 +18,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] steps: - uses: actions/checkout@v3 with: diff --git a/.github/workflows/test_galaxy_packages_for_pulsar.yaml b/.github/workflows/test_galaxy_packages_for_pulsar.yaml index 7f5f5499bc4c..2a8e39cadbce 100644 --- a/.github/workflows/test_galaxy_packages_for_pulsar.yaml +++ b/.github/workflows/test_galaxy_packages_for_pulsar.yaml @@ -20,7 +20,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.7'] # don't upgrade, see https://github.com/galaxyproject/galaxy/pull/16649 steps: - uses: actions/checkout@v3 with: diff --git a/.github/workflows/toolshed.yaml b/.github/workflows/toolshed.yaml index 4e3a2b2cac8c..95db16b404ac 100644 --- a/.github/workflows/toolshed.yaml +++ b/.github/workflows/toolshed.yaml @@ -21,7 +21,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] shed-api: ['v1', 'v2'] test-install-client: ['galaxy_api', 'standalone'] services: diff --git a/.github/workflows/unit-postgres.yaml b/.github/workflows/unit-postgres.yaml index 6e695fd64082..f2c57b6228d4 100644 --- a/.github/workflows/unit-postgres.yaml +++ b/.github/workflows/unit-postgres.yaml @@ -22,7 +22,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.8'] services: postgres: image: postgres:13 diff --git a/.github/workflows/unit.yaml b/.github/workflows/unit.yaml index 8ade16541a1f..9c32eae057d6 100644 --- a/.github/workflows/unit.yaml +++ b/.github/workflows/unit.yaml @@ -20,7 +20,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: ['3.7', '3.11'] + python-version: ['3.8', '3.11'] steps: - uses: actions/checkout@v3 with: diff --git a/Makefile b/Makefile index c1caf63227a9..570e7b346d83 100644 --- a/Makefile +++ b/Makefile @@ -52,6 +52,11 @@ format: ## Format Python code base remove-unused-imports: ## Remove unused imports in Python code base $(IN_VENV) autoflake --in-place --remove-all-unused-imports --recursive --verbose lib/ test/ +pyupgrade: ## Convert older code patterns to Python3.7/3.8 idiomatic ones + ack --type=python -f | grep -v '^lib/galaxy/schema/bco/\|^lib/galaxy/schema/drs/\|^lib/tool_shed_client/schema/trs\|^tools/\|^.venv/\|^.tox/\|^lib/galaxy/files/sources/\|^lib/galaxy/job_metrics/\|^lib/galaxy/objectstore/\|^lib/galaxy/tool_util/\|^lib/galaxy/util/\|^test/functional/tools/cwl_tools/' | xargs pyupgrade --py38-plus + ack --type=python -f | grep -v '^lib/galaxy/schema/bco/\|^lib/galaxy/schema/drs/\|^lib/tool_shed_client/schema/trs\|^tools/\|^.venv/\|^.tox/\|^lib/galaxy/files/sources/\|^lib/galaxy/job_metrics/\|^lib/galaxy/objectstore/\|^lib/galaxy/tool_util/\|^lib/galaxy/util/\|^test/functional/tools/cwl_tools/' | xargs auto-walrus + ack --type=python -f lib/galaxy/files/sources/ lib/galaxy/job_metrics/ lib/galaxy/objectstore/ lib/galaxy/tool_util/ lib/galaxy/util/ | xargs pyupgrade --py37-plus + docs-slides-ready: test -f plantuml.jar || wget http://jaist.dl.sourceforge.net/project/plantuml/plantuml.jar java -jar plantuml.jar -c $(DOC_SOURCE_DIR)/slideshow/architecture/images/plantuml_options.txt -tsvg $(SLIDESHOW_DIR)/architecture/images/ *.plantuml.txt diff --git a/README.rst b/README.rst index 34d382dc68bb..17e11d9ff098 100644 --- a/README.rst +++ b/README.rst @@ -24,12 +24,12 @@ Community support is available at `Galaxy Help Galaxy Quickstart ================= -Galaxy requires Python 3.7 . To check your Python version, run: +Galaxy requires Python 3.8 . To check your Python version, run: .. code:: console $ python -V - Python 3.7.6 + Python 3.8.18 Start Galaxy: diff --git a/client/src/api/schema/schema.ts b/client/src/api/schema/schema.ts index 4b6887c7444f..7e4f142a7a05 100644 --- a/client/src/api/schema/schema.ts +++ b/client/src/api/schema/schema.ts @@ -2422,8 +2422,8 @@ export interface components { /** * Type * @description The digest method used to create the checksum. - * The value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://www.iana.org/assignments/named-information/named-information.xhtml#hash-alg[IANA Named Information Hash Algorithm Registry]. Other values MAY be used, as long as implementors are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920]. - * GA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future. Until then, if implementors do choose such an algorithm (e.g. because it's implemented by their storage provider), they SHOULD use an existing standard `type` value such as `md5`, `etag`, `crc32c`, `trunc512`, or `sha1`. + * The value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://www.iana.org/assignments/named-information/named-information.xhtml#hash-alg[IANA Named Information Hash Algorithm Registry]. Other values MAY be used, as long as implementers are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920]. + * GA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future. Until then, if implementers do choose such an algorithm (e.g. because it's implemented by their storage provider), they SHOULD use an existing standard `type` value such as `md5`, `etag`, `crc32c`, `trunc512`, or `sha1`. * @example sha-256 */ type: string; diff --git a/doc/parse_gx_xsd.py b/doc/parse_gx_xsd.py index 450f8e4d15c6..d7f3b631712d 100644 --- a/doc/parse_gx_xsd.py +++ b/doc/parse_gx_xsd.py @@ -107,8 +107,7 @@ def _build_tag(tag, hide_attributes): assertions_buffer.write(f"#### ``{element.attrib['name']}``:\n\n{doc}\n\n") text = text.replace(line, assertions_buffer.getvalue()) tag_help.write(text) - best_practices = _get_bp_link(annotation_el) - if best_practices: + if best_practices := _get_bp_link(annotation_el): tag_help.write("\n\n### Best Practices\n") tag_help.write( """ diff --git a/doc/source/admin/python.md b/doc/source/admin/python.md index 23870548c8e3..015f85e08a10 100644 --- a/doc/source/admin/python.md +++ b/doc/source/admin/python.md @@ -1,6 +1,6 @@ # Supported Python versions -Galaxy's core functionality is currently supported on Python **>=3.7** . +Galaxy's core functionality is currently supported on Python **>=3.8** . If Galaxy complains about the version of Python you are using: diff --git a/doc/source/dev/debugging_tests.md b/doc/source/dev/debugging_tests.md index 231747572be7..6bda2d5c92f8 100644 --- a/doc/source/dev/debugging_tests.md +++ b/doc/source/dev/debugging_tests.md @@ -52,7 +52,7 @@ index 6647588dfb..c8d82957a1 100644 @@ -14,7 +14,7 @@ jobs: fail-fast: false matrix: - python-version: ['3.7'] + python-version: ['3.8'] - subset: ['upload_datatype', 'extended_metadata', 'kubernetes', 'not (upload_datatype or extended_metadata or kubernetes)'] + subset: ['not (upload_datatype or extended_metadata or kubernetes)'] services: diff --git a/lib/galaxy/actions/library.py b/lib/galaxy/actions/library.py index b1f3a8bbfae8..32d555700166 100644 --- a/lib/galaxy/actions/library.py +++ b/lib/galaxy/actions/library.py @@ -224,8 +224,7 @@ def _get_path_paste_uploaded_datasets(self, trans, params, library_bunch, respon return uploaded_datasets, 200, None def _get_path_files_and_folders(self, params, preserve_dirs): - problem_response = self._check_path_paste_params(params) - if problem_response: + if problem_response := self._check_path_paste_params(params): return problem_response files_and_folders = [] for line, path in self._paths_list(params): diff --git a/lib/galaxy/app.py b/lib/galaxy/app.py index 1c8d04847c09..2048dc1ea18c 100644 --- a/lib/galaxy/app.py +++ b/lib/galaxy/app.py @@ -846,8 +846,7 @@ def to_str(self, **kwd): class ExecutionTimerFactory: def __init__(self, config): - statsd_host = getattr(config, "statsd_host", None) - if statsd_host: + if statsd_host := getattr(config, "statsd_host", None): from galaxy.web.statsd_client import GalaxyStatsdClient self.galaxy_statsd_client: Optional[GalaxyStatsdClient] = GalaxyStatsdClient( diff --git a/lib/galaxy/app_unittest_utils/tools_support.py b/lib/galaxy/app_unittest_utils/tools_support.py index 77c759499d75..6c94d5eb59da 100644 --- a/lib/galaxy/app_unittest_utils/tools_support.py +++ b/lib/galaxy/app_unittest_utils/tools_support.py @@ -123,7 +123,7 @@ class MockContext: def __init__(self, model_objects=None): self.expunged_all = False self.flushed = False - self.model_objects = model_objects or defaultdict(lambda: {}) + self.model_objects = model_objects or defaultdict(dict) self.created_objects = [] self.current = self diff --git a/lib/galaxy/auth/__init__.py b/lib/galaxy/auth/__init__.py index 932639e75a3a..388e4ac2beb1 100644 --- a/lib/galaxy/auth/__init__.py +++ b/lib/galaxy/auth/__init__.py @@ -123,8 +123,7 @@ def active_authenticators(self, email, username, password): def _get_allow_register(d): s = d.get("allow-register", True) - lower_s = str(s).lower() - if lower_s == "challenge": + if (lower_s := str(s).lower()) == "challenge": return lower_s else: return string_as_bool(s) diff --git a/lib/galaxy/celery/__init__.py b/lib/galaxy/celery/__init__.py index 84afb8ee18b2..8459893402f0 100644 --- a/lib/galaxy/celery/__init__.py +++ b/lib/galaxy/celery/__init__.py @@ -101,8 +101,7 @@ def get_galaxy_app(): @lru_cache(maxsize=1) def build_app(): - kwargs = get_app_properties() - if kwargs: + if kwargs := get_app_properties(): kwargs["check_migrate_databases"] = False kwargs["use_display_applications"] = False kwargs["use_converters"] = False diff --git a/lib/galaxy/celery/tasks.py b/lib/galaxy/celery/tasks.py index b94cc8f832b4..828e692ba0a2 100644 --- a/lib/galaxy/celery/tasks.py +++ b/lib/galaxy/celery/tasks.py @@ -68,12 +68,12 @@ log = get_logger(__name__) -@lru_cache() +@lru_cache def setup_data_table_manager(app): app._configure_tool_data_tables(from_shed_config=False) -@lru_cache() +@lru_cache def cached_create_tool_from_representation(app, raw_tool_source): return create_tool_from_representation( app=app, raw_tool_source=raw_tool_source, tool_dir="", tool_source_class="XmlToolSource" diff --git a/lib/galaxy/config/__init__.py b/lib/galaxy/config/__init__.py index 70f43efd9225..836b69a5f7f0 100644 --- a/lib/galaxy/config/__init__.py +++ b/lib/galaxy/config/__init__.py @@ -59,11 +59,10 @@ if TYPE_CHECKING: from galaxy.model import User -try: - from importlib.resources import files # type: ignore[attr-defined] -except ImportError: - # Python < 3.9 - from importlib_resources import files # type: ignore[no-redef] +if sys.version_info >= (3, 9): + from importlib.resources import files +else: + from importlib_resources import files log = logging.getLogger(__name__) @@ -1173,7 +1172,6 @@ def _process_config(self, kwargs: Dict[str, Any]) -> None: log_destination = kwargs.get("log_destination") log_rotate_size = size_to_bytes(unicodify(kwargs.get("log_rotate_size", 0))) log_rotate_count = int(kwargs.get("log_rotate_count", 0)) - galaxy_daemon_log_destination = os.environ.get("GALAXY_DAEMON_LOG") if log_destination == "stdout": LOGGING_CONFIG_DEFAULT["handlers"]["console"] = { "class": "logging.StreamHandler", @@ -1192,7 +1190,7 @@ def _process_config(self, kwargs: Dict[str, Any]) -> None: "maxBytes": log_rotate_size, "backupCount": log_rotate_count, } - if galaxy_daemon_log_destination: + if galaxy_daemon_log_destination := os.environ.get("GALAXY_DAEMON_LOG"): LOGGING_CONFIG_DEFAULT["handlers"]["files"] = { "class": "logging.handlers.RotatingFileHandler", "formatter": "stack", diff --git a/lib/galaxy/config/config_manage.py b/lib/galaxy/config/config_manage.py index 5f91bc0d386c..4f0da4d9ddf6 100644 --- a/lib/galaxy/config/config_manage.py +++ b/lib/galaxy/config/config_manage.py @@ -428,8 +428,7 @@ def _replace_file(args: Namespace, f: StringIO, app_desc: App, from_path: str, t def _build_sample_yaml(args: Namespace, app_desc: App) -> None: schema = app_desc.schema f = StringIO() - description = getattr(schema, "description", None) - if description: + if description := getattr(schema, "description", None): description = description.lstrip() as_comment = "\n".join(f"# {line}" for line in description.split("\n")) + "\n" f.write(as_comment) @@ -519,8 +518,7 @@ def _warn(message: str) -> None: def _get_option_desc(option: Dict[str, Any]) -> str: desc = option["desc"] - parent_dir = option.get("path_resolves_to") - if parent_dir: + if parent_dir := option.get("path_resolves_to"): path_resolves = f"The value of this option will be resolved with respect to <{parent_dir}>." return f"{desc}\n{path_resolves}" if desc else path_resolves return desc diff --git a/lib/galaxy/config/templates.py b/lib/galaxy/config/templates.py index e3d438b846a3..fc4b473ce7cc 100644 --- a/lib/galaxy/config/templates.py +++ b/lib/galaxy/config/templates.py @@ -10,14 +10,17 @@ from jinja2 import Environment -from galaxy.util.resources import resource_path +from galaxy.util.resources import ( + resource_path, + Traversable, +) TEMPLATE_SEP = ">>>>>>" # Used to split templates into doc/body sections def render(template_path: str, context: dict, custom_templates_dir: str) -> str: """Read and return templated content as string.""" - with open(_get_template_path(template_path, custom_templates_dir)) as f: + with _get_template_path(template_path, custom_templates_dir).open() as f: template_str = _get_template_body(f.read()) tmpl = Environment().from_string(template_str) return tmpl.render(**context) @@ -28,7 +31,7 @@ def _get_template_body(template: str) -> str: return template.split(TEMPLATE_SEP, 1)[-1].split("\n", 1)[1] -def _get_template_path(relpath: str, custom_templates_dir: str) -> Path: +def _get_template_path(relpath: str, custom_templates_dir: str) -> Traversable: """Return template file path.""" default_path = resource_path("galaxy.config", "templates") / relpath custom_path = Path(custom_templates_dir) / relpath diff --git a/lib/galaxy/datatypes/binary.py b/lib/galaxy/datatypes/binary.py index fa5352918990..a2343074f542 100644 --- a/lib/galaxy/datatypes/binary.py +++ b/lib/galaxy/datatypes/binary.py @@ -1491,11 +1491,9 @@ def get_index_value(tmp: Union[h5py.Dataset, h5py.Datatype, h5py.Group]): return tmp["_index"] return None else: - index_var = tmp.attrs.get("index") - if index_var is not None: + if (index_var := tmp.attrs.get("index")) is not None: return tmp[index_var] - index_var = tmp.attrs.get("_index") - if index_var is not None: + if (index_var := tmp.attrs.get("_index")) is not None: return tmp[index_var] return None diff --git a/lib/galaxy/datatypes/dataproviders/base.py b/lib/galaxy/datatypes/dataproviders/base.py index 22dbb6abcb10..6b4949111f31 100644 --- a/lib/galaxy/datatypes/dataproviders/base.py +++ b/lib/galaxy/datatypes/dataproviders/base.py @@ -56,8 +56,7 @@ def __new__(cls, name, base_classes, attributes): if base_settings: settings.update(base_settings) # get settings defined in this class - new_settings = attributes.pop("settings", None) - if new_settings: + if new_settings := attributes.pop("settings", None): settings.update(new_settings) attributes["settings"] = settings return type.__new__(cls, name, base_classes, attributes) diff --git a/lib/galaxy/datatypes/dataproviders/line.py b/lib/galaxy/datatypes/dataproviders/line.py index dcbdfc440123..560be0e9e0c8 100644 --- a/lib/galaxy/datatypes/dataproviders/line.py +++ b/lib/galaxy/datatypes/dataproviders/line.py @@ -184,8 +184,7 @@ def __iter__(self): parent_gen = super().__iter__() yield from parent_gen - last_block = self.handle_last_block() - if last_block is not None: + if (last_block := self.handle_last_block()) is not None: self.num_data_returned += 1 yield last_block diff --git a/lib/galaxy/datatypes/display_applications/parameters.py b/lib/galaxy/datatypes/display_applications/parameters.py index ede98fc73f6e..2462ac4a8875 100644 --- a/lib/galaxy/datatypes/display_applications/parameters.py +++ b/lib/galaxy/datatypes/display_applications/parameters.py @@ -118,8 +118,7 @@ def _get_dataset_like_object(self, other_values): return data def get_value(self, other_values, dataset_hash, user_hash, trans): - data = self._get_dataset_like_object(other_values) - if data: + if data := self._get_dataset_like_object(other_values): return DisplayDataValueWrapper(data, self, other_values, dataset_hash, user_hash, trans) return None @@ -165,8 +164,7 @@ def is_preparing(self, other_values): return False def ready(self, other_values): - value = self._get_dataset_like_object(other_values) - if value: + if value := self._get_dataset_like_object(other_values): if value.state == value.states.OK: return True elif value.state == value.states.ERROR: diff --git a/lib/galaxy/datatypes/isa.py b/lib/galaxy/datatypes/isa.py index 74ebb2ec59bf..68cc2c38752f 100644 --- a/lib/galaxy/datatypes/isa.py +++ b/lib/galaxy/datatypes/isa.py @@ -129,8 +129,7 @@ def _get_investigation(self, dataset: HasExtraFilesPath) -> Optional["Investigat We will use it to parse and access information from the archive.""" investigation = None - main_file = self._get_main_file(dataset) - if main_file is not None: + if (main_file := self._get_main_file(dataset)) is not None: investigation = self._make_investigation_instance(main_file) return investigation diff --git a/lib/galaxy/datatypes/registry.py b/lib/galaxy/datatypes/registry.py index d454810834b0..d6c4ac4fc174 100644 --- a/lib/galaxy/datatypes/registry.py +++ b/lib/galaxy/datatypes/registry.py @@ -483,8 +483,7 @@ def load_datatype_sniffers(self, root, override=False, compressed_sniffers=None) distributed config) or contained within an installed Tool Shed repository. """ sniffer_elem_classes = [e.attrib["type"] for e in self.sniffer_elems] - sniffers = root.find("sniffers") - if sniffers is not None: + if (sniffers := root.find("sniffers")) is not None: for elem in sniffers.findall("sniffer"): # Keep a status of the process steps to enable stopping the process of handling the sniffer if necessary. ok = True diff --git a/lib/galaxy/datatypes/text.py b/lib/galaxy/datatypes/text.py index 91ea44cd3b3a..e7670856665b 100644 --- a/lib/galaxy/datatypes/text.py +++ b/lib/galaxy/datatypes/text.py @@ -6,6 +6,7 @@ import logging import os import re +import shlex import subprocess import tempfile from typing import ( @@ -38,7 +39,6 @@ ) from galaxy.util import ( nice_size, - shlex_join, string_as_bool, unicodify, ) @@ -242,7 +242,7 @@ def _display_data_trusted( ofilename = dataset.get_file_name() log.exception( 'Command "%s" failed. Could not convert the Jupyter Notebook to HTML, defaulting to plain text.', - shlex_join(cmd), + shlex.join(cmd), ) return open(ofilename, mode="rb"), headers diff --git a/lib/galaxy/datatypes/util/maf_utilities.py b/lib/galaxy/datatypes/util/maf_utilities.py index bbfdf7967f51..52c18931c3c9 100644 --- a/lib/galaxy/datatypes/util/maf_utilities.py +++ b/lib/galaxy/datatypes/util/maf_utilities.py @@ -658,9 +658,6 @@ def get_starts_ends_fields_from_gene_bed(line): if len(fields) < 12: raise Exception(f"Not a proper 12 column BED line ({line}).") tx_start = int(fields[1]) - strand = fields[5] - if strand != "-": - strand = "+" # Default strand is + cds_start = int(fields[6]) cds_end = int(fields[7]) diff --git a/lib/galaxy/dependencies/dev-requirements.txt b/lib/galaxy/dependencies/dev-requirements.txt index 52ed8a5e480e..8c4bb177cba5 100644 --- a/lib/galaxy/dependencies/dev-requirements.txt +++ b/lib/galaxy/dependencies/dev-requirements.txt @@ -1,176 +1,172 @@ -aiohttp==3.8.6 ; python_version >= "3.7" and python_version < "3.12" -aiosignal==1.3.1 ; python_version >= "3.7" and python_version < "3.12" -alabaster==0.7.13 ; python_version >= "3.7" and python_version < "3.12" -amqp==5.2.0 ; python_version >= "3.7" and python_version < "3.12" -anyio==3.7.1 ; python_version >= "3.7" and python_version < "3.12" -ase==3.22.1 ; python_version >= "3.7" and python_version < "3.12" -async-timeout==4.0.3 ; python_version >= "3.7" and python_version < "3.12" -asynctest==0.13.0 ; python_version >= "3.7" and python_version < "3.8" -attrs==23.1.0 ; python_version >= "3.7" and python_version < "3.12" -axe-selenium-python==2.1.6 ; python_version >= "3.7" and python_version < "3.12" -babel==2.13.1 ; python_version >= "3.7" and python_version < "3.12" -billiard==3.6.4.0 ; python_version >= "3.7" and python_version < "3.12" -black==23.3.0 ; python_version >= "3.7" and python_version < "3.12" -bleach==6.0.0 ; python_version >= "3.7" and python_version < "3.12" -build==1.0.3 ; python_version >= "3.7" and python_version < "3.12" -cachecontrol[filecache]==0.13.1 ; python_version >= "3.7" and python_version < "3.12" -cached-property==1.5.2 ; python_version >= "3.7" and python_version < "3.8" -celery==5.2.7 ; python_version >= "3.7" and python_version < "3.12" -certifi==2023.11.17 ; python_version >= "3.7" and python_version < "3.12" -cffi==1.15.1 ; python_version >= "3.7" and python_version < "3.12" -charset-normalizer==3.3.2 ; python_version >= "3.7" and python_version < "3.12" -click-didyoumean==0.3.0 ; python_version >= "3.7" and python_version < "3.12" -click-plugins==1.1.1 ; python_version >= "3.7" and python_version < "3.12" -click-repl==0.3.0 ; python_version >= "3.7" and python_version < "3.12" -click==8.1.7 ; python_version >= "3.7" and python_version < "3.12" -codespell==2.2.5 ; python_version >= "3.7" and python_version < "3.12" -colorama==0.4.6 ; python_version >= "3.7" and python_version < "3.12" and (sys_platform == "win32" or platform_system == "Windows" or os_name == "nt") -coverage[toml]==7.2.7 ; python_version >= "3.7" and python_version < "3.12" -cryptography==41.0.5 ; python_version >= "3.7" and python_version < "3.12" -cwltest==2.3.20230825125225 ; python_version >= "3.7" and python_version < "3.12" -cycler==0.11.0 ; python_version >= "3.7" and python_version < "3.12" -darker==1.7.2 ; python_version >= "3.7" and python_version < "3.12" -defusedxml==0.7.1 ; python_version >= "3.7" and python_version < "3.12" -deprecated==1.2.14 ; python_version >= "3.7" and python_version < "3.12" -docutils==0.18.1 ; python_version >= "3.7" and python_version < "3.12" -exceptiongroup==1.2.0 ; python_version >= "3.7" and python_version < "3.11" -filelock==3.12.2 ; python_version >= "3.7" and python_version < "3.12" -fluent-logger==0.10.0 ; python_version >= "3.7" and python_version < "3.12" -fonttools==4.38.0 ; python_version >= "3.7" and python_version < "3.12" -frozenlist==1.3.3 ; python_version >= "3.7" and python_version < "3.12" -future==0.18.3 ; python_version >= "3.7" and python_version < "3.12" -galaxy-release-util==0.1.5 ; python_version >= "3.7" and python_version < "3.12" -greenlet==2.0.2 ; python_version >= "3.7" and python_version < "3.12" -h11==0.14.0 ; python_version >= "3.7" and python_version < "3.12" -httpcore==0.17.3 ; python_version >= "3.7" and python_version < "3.12" -httpx==0.24.1 ; python_version >= "3.7" and python_version < "3.12" -idna==3.5 ; python_version >= "3.7" and python_version < "3.12" -imagesize==1.4.1 ; python_version >= "3.7" and python_version < "3.12" -importlib-metadata==4.13.0 ; python_version >= "3.7" and python_version < "3.12" -importlib-resources==5.12.0 ; python_version >= "3.7" and python_version < "3.12" -iniconfig==2.0.0 ; python_version >= "3.7" and python_version < "3.12" -isodate==0.6.1 ; python_version >= "3.7" and python_version < "3.12" -isort==5.11.5 ; python_version >= "3.7" and python_version < "3.12" -jaraco-classes==3.2.3 ; python_version >= "3.7" and python_version < "3.12" -jeepney==0.8.0 ; python_version >= "3.7" and python_version < "3.12" and sys_platform == "linux" -jinja2==3.1.2 ; python_version >= "3.7" and python_version < "3.12" -junit-xml==1.9 ; python_version >= "3.7" and python_version < "3.12" -keyring==24.1.1 ; python_version >= "3.7" and python_version < "3.12" -kiwisolver==1.4.5 ; python_version >= "3.7" and python_version < "3.12" -kombu==5.2.4 ; python_version >= "3.7" and python_version < "3.12" -lxml==4.9.3 ; python_version >= "3.7" and python_version < "3.12" -markdown-it-py==2.2.0 ; python_version >= "3.7" and python_version < "3.12" -markdown-it-reporter==0.0.2 ; python_version >= "3.7" and python_version < "3.12" -markupsafe==2.1.3 ; python_version >= "3.7" and python_version < "3.12" -matplotlib==3.5.3 ; python_version >= "3.7" and python_version < "3.8" +aiohttp==3.9.1 ; python_version >= "3.8" and python_version < "3.12" +aiosignal==1.3.1 ; python_version >= "3.8" and python_version < "3.12" +alabaster==0.7.13 ; python_version >= "3.8" and python_version < "3.12" +amqp==5.2.0 ; python_version >= "3.8" and python_version < "3.12" +anyio==4.1.0 ; python_version >= "3.8" and python_version < "3.12" +ase==3.22.1 ; python_version >= "3.8" and python_version < "3.12" +async-timeout==4.0.3 ; python_version >= "3.8" and python_version < "3.11" +attrs==23.1.0 ; python_version >= "3.8" and python_version < "3.12" +axe-selenium-python==2.1.6 ; python_version >= "3.8" and python_version < "3.12" +babel==2.13.1 ; python_version >= "3.8" and python_version < "3.12" +backports-zoneinfo==0.2.1 ; python_version >= "3.8" and python_version < "3.9" +backports-zoneinfo[tzdata]==0.2.1 ; python_version >= "3.8" and python_version < "3.9" +billiard==4.2.0 ; python_version >= "3.8" and python_version < "3.12" +black==23.11.0 ; python_version >= "3.8" and python_version < "3.12" +build==1.0.3 ; python_version >= "3.8" and python_version < "3.12" +cachecontrol[filecache]==0.13.1 ; python_version >= "3.8" and python_version < "3.12" +celery==5.3.6 ; python_version >= "3.8" and python_version < "3.12" +certifi==2023.11.17 ; python_version >= "3.8" and python_version < "3.12" +cffi==1.16.0 ; python_version >= "3.8" and python_version < "3.12" +charset-normalizer==3.3.2 ; python_version >= "3.8" and python_version < "3.12" +click-didyoumean==0.3.0 ; python_version >= "3.8" and python_version < "3.12" +click-plugins==1.1.1 ; python_version >= "3.8" and python_version < "3.12" +click-repl==0.3.0 ; python_version >= "3.8" and python_version < "3.12" +click==8.1.7 ; python_version >= "3.8" and python_version < "3.12" +codespell==2.2.6 ; python_version >= "3.8" and python_version < "3.12" +colorama==0.4.6 ; python_version >= "3.8" and python_version < "3.12" and (sys_platform == "win32" or platform_system == "Windows" or os_name == "nt") +contourpy==1.1.1 ; python_version >= "3.8" and python_version < "3.12" +coverage[toml]==7.3.2 ; python_version >= "3.8" and python_version < "3.12" +cryptography==41.0.5 ; python_version >= "3.8" and python_version < "3.12" +cwltest==2.4.20231031143732 ; python_version >= "3.8" and python_version < "3.12" +cycler==0.12.1 ; python_version >= "3.8" and python_version < "3.12" +darker==1.7.2 ; python_version >= "3.8" and python_version < "3.12" +defusedxml==0.7.1 ; python_version >= "3.8" and python_version < "3.12" +deprecated==1.2.14 ; python_version >= "3.8" and python_version < "3.12" +docutils==0.18.1 ; python_version >= "3.8" and python_version < "3.12" +exceptiongroup==1.2.0 ; python_version >= "3.8" and python_version < "3.11" +filelock==3.13.1 ; python_version >= "3.8" and python_version < "3.12" +fluent-logger==0.10.0 ; python_version >= "3.8" and python_version < "3.12" +fonttools==4.45.1 ; python_version >= "3.8" and python_version < "3.12" +frozenlist==1.4.0 ; python_version >= "3.8" and python_version < "3.12" +future==0.18.3 ; python_version >= "3.8" and python_version < "3.12" +galaxy-release-util==0.1.5 ; python_version >= "3.8" and python_version < "3.12" +greenlet==3.0.1 ; python_version >= "3.8" and python_version < "3.12" +h11==0.14.0 ; python_version >= "3.8" and python_version < "3.12" +httpcore==1.0.2 ; python_version >= "3.8" and python_version < "3.12" +httpx==0.25.2 ; python_version >= "3.8" and python_version < "3.12" +idna==3.6 ; python_version >= "3.8" and python_version < "3.12" +imagesize==1.4.1 ; python_version >= "3.8" and python_version < "3.12" +importlib-metadata==6.8.0 ; python_version >= "3.8" and python_version < "3.12" +importlib-resources==6.1.1 ; python_version >= "3.8" and python_version < "3.12" +iniconfig==2.0.0 ; python_version >= "3.8" and python_version < "3.12" +isodate==0.6.1 ; python_version >= "3.8" and python_version < "3.12" +isort==5.12.0 ; python_version >= "3.8" and python_version < "3.12" +jaraco-classes==3.3.0 ; python_version >= "3.8" and python_version < "3.12" +jeepney==0.8.0 ; python_version >= "3.8" and python_version < "3.12" and sys_platform == "linux" +jinja2==3.1.2 ; python_version >= "3.8" and python_version < "3.12" +junit-xml==1.9 ; python_version >= "3.8" and python_version < "3.12" +keyring==24.3.0 ; python_version >= "3.8" and python_version < "3.12" +kiwisolver==1.4.5 ; python_version >= "3.8" and python_version < "3.12" +kombu==5.3.4 ; python_version >= "3.8" and python_version < "3.12" +lxml==4.9.3 ; python_version >= "3.8" and python_version < "3.12" +markdown-it-py==3.0.0 ; python_version >= "3.8" and python_version < "3.12" +markdown-it-reporter==0.0.2 ; python_version >= "3.8" and python_version < "3.12" +markupsafe==2.1.3 ; python_version >= "3.8" and python_version < "3.12" matplotlib==3.7.4 ; python_version >= "3.8" and python_version < "3.9" matplotlib==3.8.2 ; python_version >= "3.9" and python_version < "3.12" -mdit-py-plugins==0.3.5 ; python_version >= "3.7" and python_version < "3.12" -mdurl==0.1.2 ; python_version >= "3.7" and python_version < "3.12" -mirakuru==2.5.1 ; python_version >= "3.7" and python_version < "3.12" -mistune==2.0.5 ; python_version >= "3.7" and python_version < "3.12" -more-itertools==9.1.0 ; python_version >= "3.7" and python_version < "3.12" -msgpack==1.0.5 ; python_version >= "3.7" and python_version < "3.12" -multidict==6.0.4 ; python_version >= "3.7" and python_version < "3.12" -mypy-extensions==1.0.0 ; python_version >= "3.7" and python_version < "3.12" -myst-parser==1.0.0 ; python_version >= "3.7" and python_version < "3.12" -numpy==1.21.6 ; python_version >= "3.7" and python_version < "3.8" +mdit-py-plugins==0.4.0 ; python_version >= "3.8" and python_version < "3.12" +mdurl==0.1.2 ; python_version >= "3.8" and python_version < "3.12" +mirakuru==2.5.2 ; python_version >= "3.8" and python_version < "3.12" +mistune==2.0.5 ; python_version >= "3.8" and python_version < "3.12" +more-itertools==10.1.0 ; python_version >= "3.8" and python_version < "3.12" +msgpack==1.0.7 ; python_version >= "3.8" and python_version < "3.12" +multidict==6.0.4 ; python_version >= "3.8" and python_version < "3.12" +mypy-extensions==1.0.0 ; python_version >= "3.8" and python_version < "3.12" +myst-parser==2.0.0 ; python_version >= "3.8" and python_version < "3.12" +nh3==0.2.14 ; python_version >= "3.8" and python_version < "3.12" numpy==1.24.4 ; python_version >= "3.8" and python_version < "3.9" numpy==1.26.2 ; python_version >= "3.9" and python_version < "3.12" -outcome==1.3.0.post0 ; python_version >= "3.7" and python_version < "3.12" -packaging==23.2 ; python_version >= "3.7" and python_version < "3.12" -pathspec==0.11.2 ; python_version >= "3.7" and python_version < "3.12" -pillow==9.5.0 ; python_version >= "3.7" and python_version < "3.12" -pkce==1.0.3 ; python_version >= "3.7" and python_version < "3.12" -pkginfo==1.9.6 ; python_version >= "3.7" and python_version < "3.12" -platformdirs==4.0.0 ; python_version >= "3.7" and python_version < "3.12" -playwright==1.35.0 ; python_version >= "3.7" and python_version < "3.12" -pluggy==1.2.0 ; python_version >= "3.7" and python_version < "3.12" -port-for==0.7.1 ; python_version >= "3.7" and python_version < "3.12" -prettytable==3.7.0 ; python_version >= "3.7" and python_version < "3.12" -prompt-toolkit==3.0.41 ; python_version >= "3.7" and python_version < "3.12" -psutil==5.9.6 ; python_version >= "3.7" and python_version < "3.12" and sys_platform != "cygwin" -py==1.11.0 ; python_version >= "3.7" and python_version < "3.12" -pycparser==2.21 ; python_version >= "3.7" and python_version < "3.12" -pyee==9.0.4 ; python_version >= "3.7" and python_version < "3.12" -pygithub==2.1.1 ; python_version >= "3.7" and python_version < "3.12" -pygments==2.17.2 ; python_version >= "3.7" and python_version < "3.12" -pyjwt[crypto]==2.8.0 ; python_version >= "3.7" and python_version < "3.12" -pynacl==1.5.0 ; python_version >= "3.7" and python_version < "3.12" -pyparsing==3.0.9 ; python_version >= "3.7" and python_version < "3.12" -pyproject-hooks==1.0.0 ; python_version >= "3.7" and python_version < "3.12" -pysocks==1.7.1 ; python_version >= "3.7" and python_version < "3.12" -pytest-asyncio==0.21.1 ; python_version >= "3.7" and python_version < "3.12" -pytest-base-url==2.0.0 ; python_version >= "3.7" and python_version < "3.12" -pytest-celery==0.0.0 ; python_version >= "3.7" and python_version < "3.12" -pytest-cov==4.1.0 ; python_version >= "3.7" and python_version < "3.12" -pytest-html==3.2.0 ; python_version >= "3.7" and python_version < "3.12" -pytest-httpserver==1.0.6 ; python_version >= "3.7" and python_version < "3.12" -pytest-json-report==1.5.0 ; python_version >= "3.7" and python_version < "3.12" -pytest-metadata==3.0.0 ; python_version >= "3.7" and python_version < "3.12" -pytest-mock==3.11.1 ; python_version >= "3.7" and python_version < "3.12" -pytest-playwright==0.3.3 ; python_version >= "3.7" and python_version < "3.12" -pytest-postgresql==4.1.1 ; python_version >= "3.7" and python_version < "3.12" -pytest-shard==0.1.2 ; python_version >= "3.7" and python_version < "3.12" -pytest==7.4.3 ; python_version >= "3.7" and python_version < "3.12" -python-dateutil==2.8.2 ; python_version >= "3.7" and python_version < "3.12" -python-irodsclient==1.1.9 ; python_version >= "3.7" and python_version < "3.12" -python-slugify==8.0.1 ; python_version >= "3.7" and python_version < "3.12" -pytz==2023.3.post1 ; python_version >= "3.7" and python_version < "3.12" -pywin32-ctypes==0.2.2 ; python_version >= "3.7" and python_version < "3.12" and sys_platform == "win32" -pyyaml==6.0.1 ; python_version >= "3.7" and python_version < "3.12" -rdflib==6.2.0 ; python_version >= "3.7" and python_version < "3.12" -readme-renderer==37.3 ; python_version >= "3.7" and python_version < "3.12" -requests-toolbelt==1.0.0 ; python_version >= "3.7" and python_version < "3.12" -requests==2.31.0 ; python_version >= "3.7" and python_version < "3.12" -responses==0.23.3 ; python_version >= "3.7" and python_version < "3.12" -rfc3986==2.0.0 ; python_version >= "3.7" and python_version < "3.12" -rich==13.7.0 ; python_version >= "3.7" and python_version < "3.12" -ruamel-yaml-clib==0.2.8 ; platform_python_implementation == "CPython" and python_version < "3.11" and python_version >= "3.7" -ruamel-yaml==0.17.21 ; python_version >= "3.7" and python_version < "3.12" -schema-salad==8.4.20230808163024 ; python_version >= "3.7" and python_version < "3.12" -scipy==1.7.3 ; python_version >= "3.7" and python_version < "3.8" +outcome==1.3.0.post0 ; python_version >= "3.8" and python_version < "3.12" +packaging==23.2 ; python_version >= "3.8" and python_version < "3.12" +pathspec==0.11.2 ; python_version >= "3.8" and python_version < "3.12" +pillow==10.1.0 ; python_version >= "3.8" and python_version < "3.12" +pkce==1.0.3 ; python_version >= "3.8" and python_version < "3.12" +pkginfo==1.9.6 ; python_version >= "3.8" and python_version < "3.12" +platformdirs==4.0.0 ; python_version >= "3.8" and python_version < "3.12" +playwright==1.40.0 ; python_version >= "3.8" and python_version < "3.12" +pluggy==1.3.0 ; python_version >= "3.8" and python_version < "3.12" +port-for==0.7.2 ; python_version >= "3.8" and python_version < "3.12" +prettytable==3.9.0 ; python_version >= "3.8" and python_version < "3.12" +prompt-toolkit==3.0.41 ; python_version >= "3.8" and python_version < "3.12" +psutil==5.9.6 ; python_version >= "3.8" and python_version < "3.12" and sys_platform != "cygwin" +psycopg==3.1.13 ; python_version >= "3.8" and python_version < "3.12" +pycparser==2.21 ; python_version >= "3.8" and python_version < "3.12" +pyee==11.0.1 ; python_version >= "3.8" and python_version < "3.12" +pygithub==2.1.1 ; python_version >= "3.8" and python_version < "3.12" +pygments==2.17.2 ; python_version >= "3.8" and python_version < "3.12" +pyjwt[crypto]==2.8.0 ; python_version >= "3.8" and python_version < "3.12" +pynacl==1.5.0 ; python_version >= "3.8" and python_version < "3.12" +pyparsing==3.1.1 ; python_version >= "3.8" and python_version < "3.12" +pyproject-hooks==1.0.0 ; python_version >= "3.8" and python_version < "3.12" +pysocks==1.7.1 ; python_version >= "3.8" and python_version < "3.12" +pytest-asyncio==0.21.1 ; python_version >= "3.8" and python_version < "3.12" +pytest-base-url==2.0.0 ; python_version >= "3.8" and python_version < "3.12" +pytest-celery==0.0.0 ; python_version >= "3.8" and python_version < "3.12" +pytest-cov==4.1.0 ; python_version >= "3.8" and python_version < "3.12" +pytest-html==4.1.1 ; python_version >= "3.8" and python_version < "3.12" +pytest-httpserver==1.0.8 ; python_version >= "3.8" and python_version < "3.12" +pytest-json-report==1.5.0 ; python_version >= "3.8" and python_version < "3.12" +pytest-metadata==3.0.0 ; python_version >= "3.8" and python_version < "3.12" +pytest-mock==3.12.0 ; python_version >= "3.8" and python_version < "3.12" +pytest-playwright==0.4.3 ; python_version >= "3.8" and python_version < "3.12" +pytest-postgresql==5.0.0 ; python_version >= "3.8" and python_version < "3.12" +pytest-shard==0.1.2 ; python_version >= "3.8" and python_version < "3.12" +pytest==7.4.3 ; python_version >= "3.8" and python_version < "3.12" +python-dateutil==2.8.2 ; python_version >= "3.8" and python_version < "3.12" +python-irodsclient==1.1.9 ; python_version >= "3.8" and python_version < "3.12" +python-slugify==8.0.1 ; python_version >= "3.8" and python_version < "3.12" +pytz==2023.3.post1 ; python_version >= "3.8" and python_version < "3.9" +pywin32-ctypes==0.2.2 ; python_version >= "3.8" and python_version < "3.12" and sys_platform == "win32" +pyyaml==6.0.1 ; python_version >= "3.8" and python_version < "3.12" +rdflib==6.3.2 ; python_version >= "3.8" and python_version < "3.12" +readme-renderer==42.0 ; python_version >= "3.8" and python_version < "3.12" +requests-toolbelt==1.0.0 ; python_version >= "3.8" and python_version < "3.12" +requests==2.31.0 ; python_version >= "3.8" and python_version < "3.12" +responses==0.24.1 ; python_version >= "3.8" and python_version < "3.12" +rfc3986==2.0.0 ; python_version >= "3.8" and python_version < "3.12" +rich==13.7.0 ; python_version >= "3.8" and python_version < "3.12" +ruamel-yaml-clib==0.2.8 ; platform_python_implementation == "CPython" and python_version < "3.12" and python_version >= "3.8" +ruamel-yaml==0.18.5 ; python_version >= "3.8" and python_version < "3.12" +schema-salad==8.4.20231117150958 ; python_version >= "3.8" and python_version < "3.12" scipy==1.10.1 ; python_version >= "3.8" and python_version < "3.9" scipy==1.11.4 ; python_version >= "3.9" and python_version < "3.12" -secretstorage==3.3.3 ; python_version >= "3.7" and python_version < "3.12" and sys_platform == "linux" -selenium==4.11.2 ; python_version >= "3.7" and python_version < "3.12" -seletools==1.4.0 ; python_version >= "3.7" and python_version < "3.12" -setuptools==68.0.0 ; python_version >= "3.7" and python_version < "3.12" -six==1.16.0 ; python_version >= "3.7" and python_version < "3.12" -sniffio==1.3.0 ; python_version >= "3.7" and python_version < "3.12" -snowballstemmer==2.2.0 ; python_version >= "3.7" and python_version < "3.12" -sortedcontainers==2.4.0 ; python_version >= "3.7" and python_version < "3.12" -sphinx-rtd-theme==1.3.0 ; python_version >= "3.7" and python_version < "3.12" -sphinx==5.3.0 ; python_version >= "3.7" and python_version < "3.12" -sphinxcontrib-applehelp==1.0.2 ; python_version >= "3.7" and python_version < "3.12" -sphinxcontrib-devhelp==1.0.2 ; python_version >= "3.7" and python_version < "3.12" -sphinxcontrib-htmlhelp==2.0.0 ; python_version >= "3.7" and python_version < "3.12" -sphinxcontrib-jquery==4.1 ; python_version >= "3.7" and python_version < "3.12" -sphinxcontrib-jsmath==1.0.1 ; python_version >= "3.7" and python_version < "3.12" -sphinxcontrib-qthelp==1.0.3 ; python_version >= "3.7" and python_version < "3.12" -sphinxcontrib-serializinghtml==1.1.5 ; python_version >= "3.7" and python_version < "3.12" -statsd==4.0.1 ; python_version >= "3.7" and python_version < "3.12" -testfixtures==7.2.2 ; python_version >= "3.7" and python_version < "3.12" -text-unidecode==1.3 ; python_version >= "3.7" and python_version < "3.12" -tinydb==4.8.0 ; python_version >= "3.7" and python_version < "3.12" -toml==0.10.2 ; python_version >= "3.7" and python_version < "3.12" -tomli==2.0.1 ; python_version >= "3.7" and python_full_version <= "3.11.0a6" -trio-websocket==0.11.1 ; python_version >= "3.7" and python_version < "3.12" -trio==0.22.2 ; python_version >= "3.7" and python_version < "3.12" -tuspy==1.0.1 ; python_version >= "3.7" and python_version < "3.12" -twill==3.1 ; python_version >= "3.7" and python_version < "3.12" -twine==4.0.2 ; python_version >= "3.7" and python_version < "3.12" -typed-ast==1.5.5 ; python_version < "3.8" and implementation_name == "cpython" and python_version >= "3.7" -types-pyyaml==6.0.12.12 ; python_version >= "3.7" and python_version < "3.12" -typing-extensions==4.7.1 ; python_version >= "3.7" and python_version < "3.12" -urllib3==1.26.18 ; python_version >= "3.7" and python_version < "3.12" -urllib3[socks]==1.26.18 ; python_version >= "3.7" and python_version < "3.12" -vine==5.1.0 ; python_version >= "3.7" and python_version < "3.12" -watchdog==3.0.0 ; python_version >= "3.7" and python_version < "3.12" -wcwidth==0.2.12 ; python_version >= "3.7" and python_version < "3.12" -webencodings==0.5.1 ; python_version >= "3.7" and python_version < "3.12" -werkzeug==2.2.3 ; python_version >= "3.7" and python_version < "3.12" -wrapt==1.16.0 ; python_version >= "3.7" and python_version < "3.12" -wsproto==1.2.0 ; python_version >= "3.7" and python_version < "3.12" -yarl==1.9.3 ; python_version >= "3.7" and python_version < "3.12" -zipp==3.15.0 ; python_version >= "3.7" and python_version < "3.12" +secretstorage==3.3.3 ; python_version >= "3.8" and python_version < "3.12" and sys_platform == "linux" +selenium==4.15.2 ; python_version >= "3.8" and python_version < "3.12" +seletools==1.4.0 ; python_version >= "3.8" and python_version < "3.12" +setuptools==69.0.2 ; python_version >= "3.8" and python_version < "3.12" +six==1.16.0 ; python_version >= "3.8" and python_version < "3.12" +sniffio==1.3.0 ; python_version >= "3.8" and python_version < "3.12" +snowballstemmer==2.2.0 ; python_version >= "3.8" and python_version < "3.12" +sortedcontainers==2.4.0 ; python_version >= "3.8" and python_version < "3.12" +sphinx-rtd-theme==1.3.0 ; python_version >= "3.8" and python_version < "3.12" +sphinx==7.1.2 ; python_version >= "3.8" and python_version < "3.12" +sphinxcontrib-applehelp==1.0.4 ; python_version >= "3.8" and python_version < "3.12" +sphinxcontrib-devhelp==1.0.2 ; python_version >= "3.8" and python_version < "3.12" +sphinxcontrib-htmlhelp==2.0.1 ; python_version >= "3.8" and python_version < "3.12" +sphinxcontrib-jquery==4.1 ; python_version >= "3.8" and python_version < "3.12" +sphinxcontrib-jsmath==1.0.1 ; python_version >= "3.8" and python_version < "3.12" +sphinxcontrib-qthelp==1.0.3 ; python_version >= "3.8" and python_version < "3.12" +sphinxcontrib-serializinghtml==1.1.5 ; python_version >= "3.8" and python_version < "3.12" +statsd==4.0.1 ; python_version >= "3.8" and python_version < "3.12" +testfixtures==7.2.2 ; python_version >= "3.8" and python_version < "3.12" +text-unidecode==1.3 ; python_version >= "3.8" and python_version < "3.12" +tinydb==4.8.0 ; python_version >= "3.8" and python_version < "3.12" +toml==0.10.2 ; python_version >= "3.8" and python_version < "3.12" +tomli==2.0.1 ; python_version >= "3.8" and python_full_version <= "3.11.0a6" +trio-websocket==0.11.1 ; python_version >= "3.8" and python_version < "3.12" +trio==0.23.1 ; python_version >= "3.8" and python_version < "3.12" +tuspy==1.0.1 ; python_version >= "3.8" and python_version < "3.12" +twill==3.2.1 ; python_version >= "3.8" and python_version < "3.12" +twine==4.0.2 ; python_version >= "3.8" and python_version < "3.12" +typing-extensions==4.8.0 ; python_version >= "3.8" and python_version < "3.12" +tzdata==2023.3 ; python_version >= "3.8" and python_version < "3.12" +urllib3==1.26.18 ; python_version >= "3.8" and python_version < "3.12" +urllib3[socks]==1.26.18 ; python_version >= "3.8" and python_version < "3.12" +vine==5.1.0 ; python_version >= "3.8" and python_version < "3.12" +watchdog==3.0.0 ; python_version >= "3.8" and python_version < "3.12" +wcwidth==0.2.12 ; python_version >= "3.8" and python_version < "3.12" +werkzeug==3.0.1 ; python_version >= "3.8" and python_version < "3.12" +wrapt==1.16.0 ; python_version >= "3.8" and python_version < "3.12" +wsproto==1.2.0 ; python_version >= "3.8" and python_version < "3.12" +yarl==1.9.3 ; python_version >= "3.8" and python_version < "3.12" +zipp==3.17.0 ; python_version >= "3.8" and python_version < "3.12" diff --git a/lib/galaxy/dependencies/pinned-lint-requirements.txt b/lib/galaxy/dependencies/pinned-lint-requirements.txt index 6958b57997aa..6663da463581 100644 --- a/lib/galaxy/dependencies/pinned-lint-requirements.txt +++ b/lib/galaxy/dependencies/pinned-lint-requirements.txt @@ -1,10 +1,7 @@ attrs==23.1.0 -flake8==5.0.4 -flake8-bugbear==23.3.12 -importlib-metadata==4.2.0 +flake8==6.1.0 +flake8-bugbear==23.9.16 mccabe==0.7.0 -pycodestyle==2.9.1 -pyflakes==2.5.0 +pycodestyle==2.11.1 +pyflakes==3.1.0 ruff==0.1.6 -typing_extensions==4.7.1 -zipp==3.15.0 diff --git a/lib/galaxy/dependencies/pinned-requirements.txt b/lib/galaxy/dependencies/pinned-requirements.txt index d0c127d7b1b4..35c59dfd9e7f 100644 --- a/lib/galaxy/dependencies/pinned-requirements.txt +++ b/lib/galaxy/dependencies/pinned-requirements.txt @@ -1,217 +1,216 @@ -a2wsgi==1.7.0 ; python_version >= "3.7" and python_version < "3.12" -adal==1.2.7 ; python_version >= "3.7" and python_version < "3.12" -aiobotocore==2.4.2 ; python_version >= "3.7" and python_version < "3.12" -aiodataloader==0.4.0 ; python_version >= "3.7" and python_version < "3.12" -aiofiles==23.2.1 ; python_version >= "3.7" and python_version < "3.12" -aiohttp==3.8.6 ; python_version >= "3.7" and python_version < "3.12" -aioitertools==0.11.0 ; python_version >= "3.7" and python_version < "3.12" -aiosignal==1.3.1 ; python_version >= "3.7" and python_version < "3.12" -alembic==1.12.1 ; python_version >= "3.7" and python_version < "3.12" -amqp==5.2.0 ; python_version >= "3.7" and python_version < "3.12" -aniso8601==9.0.1 ; python_version >= "3.7" and python_version < "3.12" -anyio==3.7.1 ; python_version >= "3.7" and python_version < "3.12" -apispec==6.3.0 ; python_version >= "3.7" and python_version < "3.12" -appdirs==1.4.4 ; python_version >= "3.7" and python_version < "3.12" -arcp==0.2.1 ; python_version >= "3.7" and python_version < "3.12" -argcomplete==3.1.2 ; python_version >= "3.7" and python_version < "3.12" -async-timeout==4.0.3 ; python_version >= "3.7" and python_version < "3.12" -asynctest==0.13.0 ; python_version >= "3.7" and python_version < "3.8" -attmap==0.13.2 ; python_version >= "3.7" and python_version < "3.12" -attrs==23.1.0 ; python_version >= "3.7" and python_version < "3.12" -babel==2.13.1 ; python_version >= "3.7" and python_version < "3.12" -backports-zoneinfo==0.2.1 ; python_version >= "3.7" and python_version < "3.9" -bagit-profile==1.3.1 ; python_version >= "3.7" and python_version < "3.12" -bagit==1.8.1 ; python_version >= "3.7" and python_version < "3.12" -bcrypt==4.0.1 ; python_version >= "3.7" and python_version < "3.12" -bdbag==1.7.1 ; python_version >= "3.7" and python_version < "3.12" -beaker==1.12.1 ; python_version >= "3.7" and python_version < "3.12" -billiard==3.6.4.0 ; python_version >= "3.7" and python_version < "3.12" -bioblend==1.2.0 ; python_version >= "3.7" and python_version < "3.12" -bleach==6.0.0 ; python_version >= "3.7" and python_version < "3.12" -boltons==23.1.1 ; python_version >= "3.7" and python_version < "3.12" -boto==2.49.0 ; python_version >= "3.7" and python_version < "3.12" -botocore==1.27.59 ; python_version >= "3.7" and python_version < "3.12" -bx-python==0.10.0 ; python_version >= "3.7" and python_version < "3.12" -cachecontrol[filecache]==0.13.1 ; python_version >= "3.7" and python_version < "3.12" -cached-property==1.5.2 ; python_version >= "3.7" and python_version < "3.8" -celery==5.2.7 ; python_version >= "3.7" and python_version < "3.12" -certifi==2023.11.17 ; python_version >= "3.7" and python_version < "3.12" -cffi==1.15.1 ; python_version >= "3.7" and python_version < "3.12" -charset-normalizer==3.3.2 ; python_version >= "3.7" and python_version < "3.12" -cheetah3==3.2.6.post1 ; python_version >= "3.7" and python_version < "3.12" -circus==0.18.0 ; python_version >= "3.7" and python_version < "3.12" -click-didyoumean==0.3.0 ; python_version >= "3.7" and python_version < "3.12" -click-plugins==1.1.1 ; python_version >= "3.7" and python_version < "3.12" -click-repl==0.3.0 ; python_version >= "3.7" and python_version < "3.12" -click==8.1.7 ; python_version >= "3.7" and python_version < "3.12" -cloudauthz==0.6.0 ; python_version >= "3.7" and python_version < "3.12" -cloudbridge==3.2.0 ; python_version >= "3.7" and python_version < "3.12" -colorama==0.4.6 ; python_version >= "3.7" and python_version < "3.12" and platform_system == "Windows" -coloredlogs==15.0.1 ; python_version >= "3.7" and python_version < "3.12" -conda-package-streaming==0.9.0 ; python_version >= "3.7" and python_version < "3.12" -cryptography==41.0.5 ; python_version >= "3.7" and python_version < "3.12" -cwl-upgrader==1.2.8 ; python_version >= "3.7" and python_version < "3.12" -cwl-utils==0.28 ; python_version >= "3.7" and python_version < "3.12" -cwltool==3.1.20221109155812 ; python_version >= "3.7" and python_version < "3.12" -decorator==5.1.1 ; python_version >= "3.7" and python_version < "3.12" -defusedxml==0.7.1 ; python_version >= "3.7" and python_version < "3.12" -deprecation==2.1.0 ; python_version >= "3.7" and python_version < "3.12" -dictobj==0.4 ; python_version >= "3.7" and python_version < "3.12" -dnspython==2.3.0 ; python_version >= "3.7" and python_version < "3.12" -docopt==0.6.2 ; python_version >= "3.7" and python_version < "3.12" -docutils==0.18.1 ; python_version >= "3.7" and python_version < "3.12" -dparse==0.6.3 ; python_version >= "3.7" and python_version < "3.12" -ecdsa==0.18.0 ; python_version >= "3.7" and python_version < "3.12" -edam-ontology==1.25.2 ; python_version >= "3.7" and python_version < "3.12" -email-validator==2.0.0.post2 ; python_version >= "3.7" and python_version < "3.12" -exceptiongroup==1.2.0 ; python_version >= "3.7" and python_version < "3.11" -fastapi-utils==0.2.1 ; python_version >= "3.7" and python_version < "3.12" -fastapi==0.98.0 ; python_version >= "3.7" and python_version < "3.12" -filelock==3.12.2 ; python_version >= "3.7" and python_version < "3.12" -frozenlist==1.3.3 ; python_version >= "3.7" and python_version < "3.12" -fs==2.4.16 ; python_version >= "3.7" and python_version < "3.12" -fsspec==2023.1.0 ; python_version >= "3.7" and python_version < "3.12" -future==0.18.3 ; python_version >= "3.7" and python_version < "3.12" -galaxy-sequence-utils==1.1.5 ; python_version >= "3.7" and python_version < "3.12" -galaxy2cwl==0.1.4 ; python_version >= "3.7" and python_version < "3.12" -graphene-sqlalchemy==3.0.0b3 ; python_version >= "3.7" and python_version < "3.12" -graphene==3.3 ; python_version >= "3.7" and python_version < "3.12" -graphql-core==3.2.3 ; python_version >= "3.7" and python_version < "3.12" -graphql-relay==3.2.0 ; python_version >= "3.7" and python_version < "3.12" -gravity==1.0.4 ; python_version >= "3.7" and python_version < "3.12" -greenlet==2.0.2 ; python_version >= "3.7" and (platform_machine == "aarch64" or platform_machine == "ppc64le" or platform_machine == "x86_64" or platform_machine == "amd64" or platform_machine == "AMD64" or platform_machine == "win32" or platform_machine == "WIN32") and python_version < "3.12" -gunicorn==21.2.0 ; python_version >= "3.7" and python_version < "3.12" -gxformat2==0.18.0 ; python_version >= "3.7" and python_version < "3.12" -h11==0.14.0 ; python_version >= "3.7" and python_version < "3.12" -h5grove==1.3.0 ; python_version >= "3.7" and python_version < "3.12" -h5py==3.8.0 ; python_version >= "3.7" and python_version < "3.12" -humanfriendly==10.0 ; python_version >= "3.7" and python_version < "3.12" -idna==3.5 ; python_version >= "3.7" and python_version < "3.12" -importlib-metadata==4.13.0 ; python_version >= "3.7" and python_version < "3.12" -importlib-resources==5.12.0 ; python_version >= "3.7" and python_version < "3.12" -isa-rwval==0.10.10 ; python_version >= "3.7" and python_version < "3.12" -isodate==0.6.1 ; python_version >= "3.7" and python_version < "3.12" -jinja2==3.1.2 ; python_version >= "3.7" and python_version < "3.12" -jmespath==1.0.1 ; python_version >= "3.7" and python_version < "3.12" -jsonref==1.1.0 ; python_version >= "3.7" and python_version < "3.12" -jsonschema==4.17.3 ; python_version >= "3.7" and python_version < "3.12" -kombu==5.2.4 ; python_version >= "3.7" and python_version < "3.12" -lagom==2.6.0 ; python_version >= "3.7" and python_version < "3.12" -lxml==4.9.3 ; python_version >= "3.7" and python_version < "3.12" -mako==1.2.4 ; python_version >= "3.7" and python_version < "3.12" -markdown-it-py==2.2.0 ; python_version >= "3.7" and python_version < "3.12" -markdown==3.4.4 ; python_version >= "3.7" and python_version < "3.12" -markupsafe==2.1.3 ; python_version >= "3.7" and python_version < "3.12" -mdurl==0.1.2 ; python_version >= "3.7" and python_version < "3.12" -mercurial==6.6 ; python_version >= "3.7" and python_version < "3.12" -mistune==2.0.5 ; python_version >= "3.7" and python_version < "3.12" -mrcfile==1.4.3 ; python_version >= "3.7" and python_version < "3.12" -msal==1.25.0 ; python_version >= "3.7" and python_version < "3.12" -msgpack==1.0.5 ; python_version >= "3.7" and python_version < "3.12" -multidict==6.0.4 ; python_version >= "3.7" and python_version < "3.12" -mypy-extensions==1.0.0 ; python_version >= "3.7" and python_version < "3.12" -networkx==2.5 ; python_version >= "3.7" and python_version < "3.12" -nodeenv==1.8.0 ; python_version >= "3.7" and python_version < "3.12" -numpy==1.21.6 ; python_version >= "3.7" and python_version < "3.8" +a2wsgi==1.8.0 ; python_version >= "3.8" and python_version < "3.12" +adal==1.2.7 ; python_version >= "3.8" and python_version < "3.12" +aiobotocore==2.7.0 ; python_version >= "3.8" and python_version < "3.12" +aiodataloader==0.4.0 ; python_version >= "3.8" and python_version < "3.12" +aiofiles==23.2.1 ; python_version >= "3.8" and python_version < "3.12" +aiohttp==3.9.1 ; python_version >= "3.8" and python_version < "3.12" +aioitertools==0.11.0 ; python_version >= "3.8" and python_version < "3.12" +aiosignal==1.3.1 ; python_version >= "3.8" and python_version < "3.12" +alembic==1.12.1 ; python_version >= "3.8" and python_version < "3.12" +amqp==5.2.0 ; python_version >= "3.8" and python_version < "3.12" +aniso8601==9.0.1 ; python_version >= "3.8" and python_version < "3.12" +anyio==4.1.0 ; python_version >= "3.8" and python_version < "3.12" +apispec==6.3.0 ; python_version >= "3.8" and python_version < "3.12" +appdirs==1.4.4 ; python_version >= "3.8" and python_version < "3.12" +arcp==0.2.1 ; python_version >= "3.8" and python_version < "3.12" +argcomplete==3.1.6 ; python_version >= "3.8" and python_version < "3.12" +async-timeout==4.0.3 ; python_version >= "3.8" and python_version < "3.11" +attmap==0.13.2 ; python_version >= "3.8" and python_version < "3.12" +attrs==23.1.0 ; python_version >= "3.8" and python_version < "3.12" +babel==2.13.1 ; python_version >= "3.8" and python_version < "3.12" +backports-zoneinfo==0.2.1 ; python_version >= "3.8" and python_version < "3.9" +backports-zoneinfo[tzdata]==0.2.1 ; python_version >= "3.8" and python_version < "3.9" +bagit-profile==1.3.1 ; python_version >= "3.8" and python_version < "3.12" +bagit==1.8.1 ; python_version >= "3.8" and python_version < "3.12" +bcrypt==4.0.1 ; python_version >= "3.8" and python_version < "3.12" +bdbag==1.7.1 ; python_version >= "3.8" and python_version < "3.12" +beaker==1.12.1 ; python_version >= "3.8" and python_version < "3.12" +billiard==4.2.0 ; python_version >= "3.8" and python_version < "3.12" +bioblend==1.2.0 ; python_version >= "3.8" and python_version < "3.12" +bleach==6.1.0 ; python_version >= "3.8" and python_version < "3.12" +boltons==23.1.1 ; python_version >= "3.8" and python_version < "3.12" +boto==2.49.0 ; python_version >= "3.8" and python_version < "3.12" +botocore==1.31.64 ; python_version >= "3.8" and python_version < "3.12" +bx-python==0.10.0 ; python_version >= "3.8" and python_version < "3.12" +cachecontrol[filecache]==0.13.1 ; python_version >= "3.8" and python_version < "3.12" +celery==5.3.6 ; python_version >= "3.8" and python_version < "3.12" +certifi==2023.11.17 ; python_version >= "3.8" and python_version < "3.12" +cffi==1.16.0 ; python_version >= "3.8" and python_version < "3.12" +charset-normalizer==3.3.2 ; python_version >= "3.8" and python_version < "3.12" +cheetah3==3.2.6.post1 ; python_version >= "3.8" and python_version < "3.12" +circus==0.18.0 ; python_version >= "3.8" and python_version < "3.12" +click-didyoumean==0.3.0 ; python_version >= "3.8" and python_version < "3.12" +click-plugins==1.1.1 ; python_version >= "3.8" and python_version < "3.12" +click-repl==0.3.0 ; python_version >= "3.8" and python_version < "3.12" +click==8.1.7 ; python_version >= "3.8" and python_version < "3.12" +cloudauthz==0.6.0 ; python_version >= "3.8" and python_version < "3.12" +cloudbridge==3.2.0 ; python_version >= "3.8" and python_version < "3.12" +colorama==0.4.6 ; python_version >= "3.8" and python_version < "3.12" and platform_system == "Windows" +coloredlogs==15.0.1 ; python_version >= "3.8" and python_version < "3.12" +conda-package-streaming==0.9.0 ; python_version >= "3.8" and python_version < "3.12" +cryptography==41.0.5 ; python_version >= "3.8" and python_version < "3.12" +cwl-upgrader==1.2.10 ; python_version >= "3.8" and python_version < "3.12" +cwl-utils==0.31 ; python_version >= "3.8" and python_version < "3.12" +cwltool==3.1.20231114134824 ; python_version >= "3.8" and python_version < "3.12" +decorator==5.1.1 ; python_version >= "3.8" and python_version < "3.12" +defusedxml==0.7.1 ; python_version >= "3.8" and python_version < "3.12" +deprecation==2.1.0 ; python_version >= "3.8" and python_version < "3.12" +dictobj==0.4 ; python_version >= "3.8" and python_version < "3.12" +dnspython==2.4.2 ; python_version >= "3.8" and python_version < "3.12" +docopt==0.6.2 ; python_version >= "3.8" and python_version < "3.12" +docutils==0.18.1 ; python_version >= "3.8" and python_version < "3.12" +dparse==0.6.3 ; python_version >= "3.8" and python_version < "3.12" +ecdsa==0.18.0 ; python_version >= "3.8" and python_version < "3.12" +edam-ontology==1.25.2 ; python_version >= "3.8" and python_version < "3.12" +email-validator==2.1.0.post1 ; python_version >= "3.8" and python_version < "3.12" +exceptiongroup==1.2.0 ; python_version >= "3.8" and python_version < "3.11" +fastapi-utils==0.2.1 ; python_version >= "3.8" and python_version < "3.12" +fastapi==0.98.0 ; python_version >= "3.8" and python_version < "3.12" +filelock==3.13.1 ; python_version >= "3.8" and python_version < "3.12" +frozenlist==1.4.0 ; python_version >= "3.8" and python_version < "3.12" +fs==2.4.16 ; python_version >= "3.8" and python_version < "3.12" +fsspec==2023.10.0 ; python_version >= "3.8" and python_version < "3.12" +future==0.18.3 ; python_version >= "3.8" and python_version < "3.12" +galaxy-sequence-utils==1.1.5 ; python_version >= "3.8" and python_version < "3.12" +galaxy2cwl==0.1.4 ; python_version >= "3.8" and python_version < "3.12" +graphene-sqlalchemy==3.0.0b3 ; python_version >= "3.8" and python_version < "3.12" +graphene==3.3 ; python_version >= "3.8" and python_version < "3.12" +graphql-core==3.2.3 ; python_version >= "3.8" and python_version < "3.12" +graphql-relay==3.2.0 ; python_version >= "3.8" and python_version < "3.12" +gravity==1.0.4 ; python_version >= "3.8" and python_version < "3.12" +greenlet==3.0.1 ; python_version >= "3.8" and (platform_machine == "aarch64" or platform_machine == "ppc64le" or platform_machine == "x86_64" or platform_machine == "amd64" or platform_machine == "AMD64" or platform_machine == "win32" or platform_machine == "WIN32") and python_version < "3.12" +gunicorn==21.2.0 ; python_version >= "3.8" and python_version < "3.12" +gxformat2==0.18.0 ; python_version >= "3.8" and python_version < "3.12" +h11==0.14.0 ; python_version >= "3.8" and python_version < "3.12" +h5grove==1.3.0 ; python_version >= "3.8" and python_version < "3.12" +h5py==3.10.0 ; python_version >= "3.8" and python_version < "3.12" +humanfriendly==10.0 ; python_version >= "3.8" and python_version < "3.12" +idna==3.6 ; python_version >= "3.8" and python_version < "3.12" +importlib-metadata==6.8.0 ; python_version >= "3.8" and python_version < "3.12" +importlib-resources==6.1.1 ; python_version >= "3.8" and python_version < "3.12" +isa-rwval==0.10.10 ; python_version >= "3.8" and python_version < "3.12" +isodate==0.6.1 ; python_version >= "3.8" and python_version < "3.12" +jinja2==3.1.2 ; python_version >= "3.8" and python_version < "3.12" +jmespath==1.0.1 ; python_version >= "3.8" and python_version < "3.12" +jsonref==1.1.0 ; python_version >= "3.8" and python_version < "3.12" +jsonschema-specifications==2023.11.1 ; python_version >= "3.8" and python_version < "3.12" +jsonschema==4.20.0 ; python_version >= "3.8" and python_version < "3.12" +kombu==5.3.4 ; python_version >= "3.8" and python_version < "3.12" +lagom==2.6.0 ; python_version >= "3.8" and python_version < "3.12" +lxml==4.9.3 ; python_version >= "3.8" and python_version < "3.12" +mako==1.3.0 ; python_version >= "3.8" and python_version < "3.12" +markdown-it-py==3.0.0 ; python_version >= "3.8" and python_version < "3.12" +markdown==3.5.1 ; python_version >= "3.8" and python_version < "3.12" +markupsafe==2.1.3 ; python_version >= "3.8" and python_version < "3.12" +mdurl==0.1.2 ; python_version >= "3.8" and python_version < "3.12" +mercurial==6.6 ; python_version >= "3.8" and python_version < "3.12" +mistune==2.0.5 ; python_version >= "3.8" and python_version < "3.12" +mrcfile==1.4.3 ; python_version >= "3.8" and python_version < "3.12" +msal==1.25.0 ; python_version >= "3.8" and python_version < "3.12" +msgpack==1.0.7 ; python_version >= "3.8" and python_version < "3.12" +multidict==6.0.4 ; python_version >= "3.8" and python_version < "3.12" +mypy-extensions==1.0.0 ; python_version >= "3.8" and python_version < "3.12" +networkx==2.5 ; python_version >= "3.8" and python_version < "3.12" +nodeenv==1.8.0 ; python_version >= "3.8" and python_version < "3.12" numpy==1.24.4 ; python_version >= "3.8" and python_version < "3.9" numpy==1.26.2 ; python_version >= "3.9" and python_version < "3.12" -oauthlib==3.2.2 ; python_version >= "3.7" and python_version < "3.12" -orjson==3.9.7 ; python_version >= "3.7" and python_version < "3.12" -oyaml==1.0 ; python_version >= "3.7" and python_version < "3.12" -packaging==23.2 ; python_version >= "3.7" and python_version < "3.12" -paramiko==3.3.1 ; python_version >= "3.7" and python_version < "3.12" -parsley==1.3 ; python_version >= "3.7" and python_version < "3.12" -paste==3.7.1 ; python_version >= "3.7" and python_version < "3.12" -pastedeploy==3.1.0 ; python_version >= "3.7" and python_version < "3.12" -pebble==5.0.4 ; python_version >= "3.7" and python_version < "3.12" -pkgutil-resolve-name==1.3.10 ; python_version >= "3.7" and python_version < "3.9" -promise==2.3 ; python_version >= "3.7" and python_version < "3.12" -prompt-toolkit==3.0.41 ; python_version >= "3.7" and python_version < "3.12" -prov==1.5.1 ; python_version >= "3.7" and python_version < "3.12" -psutil==5.9.6 ; python_version >= "3.7" and python_version < "3.12" -pulsar-galaxy-lib==0.15.5 ; python_version >= "3.7" and python_version < "3.12" -pyasn1==0.5.1 ; python_version >= "3.7" and python_version < "3.12" -pycparser==2.21 ; python_version >= "3.7" and python_version < "3.12" -pycryptodome==3.19.0 ; python_version >= "3.7" and python_version < "3.12" -pydantic-tes==0.1.5 ; python_version >= "3.7" and python_version < "3.12" -pydantic==1.10.13 ; python_version >= "3.7" and python_version < "3.12" -pydantic[email]==1.10.13 ; python_version >= "3.7" and python_version < "3.12" -pydot==1.4.2 ; python_version >= "3.7" and python_version < "3.12" -pyeventsystem==0.1.0 ; python_version >= "3.7" and python_version < "3.12" -pyfaidx==0.7.2.2 ; python_version >= "3.7" and python_version < "3.12" -pygments==2.17.2 ; python_version >= "3.7" and python_version < "3.12" -pyjwt==2.8.0 ; python_version >= "3.7" and python_version < "3.12" -pyjwt[crypto]==2.8.0 ; python_version >= "3.7" and python_version < "3.12" -pykwalify==1.8.0 ; python_version >= "3.7" and python_version < "3.12" -pylibmagic==0.5.0 ; python_version >= "3.7" and python_version < "3.12" -pynacl==1.5.0 ; python_version >= "3.7" and python_version < "3.12" -pyparsing==3.0.9 ; python_version >= "3.7" and python_version < "3.12" +oauthlib==3.2.2 ; python_version >= "3.8" and python_version < "3.12" +orjson==3.9.10 ; python_version >= "3.8" and python_version < "3.12" +oyaml==1.0 ; python_version >= "3.8" and python_version < "3.12" +packaging==23.2 ; python_version >= "3.8" and python_version < "3.12" +paramiko==3.3.1 ; python_version >= "3.8" and python_version < "3.12" +parsley==1.3 ; python_version >= "3.8" and python_version < "3.12" +paste==3.7.1 ; python_version >= "3.8" and python_version < "3.12" +pastedeploy==3.1.0 ; python_version >= "3.8" and python_version < "3.12" +pebble==5.0.4 ; python_version >= "3.8" and python_version < "3.12" +pkgutil-resolve-name==1.3.10 ; python_version >= "3.8" and python_version < "3.9" +promise==2.3 ; python_version >= "3.8" and python_version < "3.12" +prompt-toolkit==3.0.41 ; python_version >= "3.8" and python_version < "3.12" +prov==1.5.1 ; python_version >= "3.8" and python_version < "3.12" +psutil==5.9.6 ; python_version >= "3.8" and python_version < "3.12" +pulsar-galaxy-lib==0.15.5 ; python_version >= "3.8" and python_version < "3.12" +pyasn1==0.5.1 ; python_version >= "3.8" and python_version < "3.12" +pycparser==2.21 ; python_version >= "3.8" and python_version < "3.12" +pycryptodome==3.19.0 ; python_version >= "3.8" and python_version < "3.12" +pydantic-tes==0.1.5 ; python_version >= "3.8" and python_version < "3.12" +pydantic==1.10.13 ; python_version >= "3.8" and python_version < "3.12" +pydantic[email]==1.10.13 ; python_version >= "3.8" and python_version < "3.12" +pydot==1.4.2 ; python_version >= "3.8" and python_version < "3.12" +pyeventsystem==0.1.0 ; python_version >= "3.8" and python_version < "3.12" +pyfaidx==0.7.2.2 ; python_version >= "3.8" and python_version < "3.12" +pygments==2.17.2 ; python_version >= "3.8" and python_version < "3.12" +pyjwt==2.8.0 ; python_version >= "3.8" and python_version < "3.12" +pyjwt[crypto]==2.8.0 ; python_version >= "3.8" and python_version < "3.12" +pykwalify==1.8.0 ; python_version >= "3.8" and python_version < "3.12" +pylibmagic==0.5.0 ; python_version >= "3.8" and python_version < "3.12" +pynacl==1.5.0 ; python_version >= "3.8" and python_version < "3.12" +pyparsing==3.1.1 ; python_version >= "3.8" and python_version < "3.12" pyreadline3==3.4.1 ; sys_platform == "win32" and python_version >= "3.8" and python_version < "3.12" -pyreadline==2.1 ; sys_platform == "win32" and python_version < "3.8" and python_version >= "3.7" -pyrsistent==0.19.3 ; python_version >= "3.7" and python_version < "3.12" -pysam==0.22.0 ; python_version >= "3.7" and python_version < "3.12" -python-dateutil==2.8.2 ; python_version >= "3.7" and python_version < "3.12" -python-jose==3.3.0 ; python_version >= "3.7" and python_version < "3.12" -python-magic==0.4.27 ; python_version >= "3.7" and python_version < "3.12" -python-multipart==0.0.6 ; python_version >= "3.7" and python_version < "3.12" -python3-openid==3.2.0 ; python_version >= "3.7" and python_version < "3.12" -pytz==2023.3.post1 ; python_version >= "3.7" and python_version < "3.12" -pyyaml==6.0.1 ; python_version >= "3.7" and python_version < "3.12" -pyzmq==25.1.1 ; python_version >= "3.7" and python_version < "3.12" -rdflib==6.2.0 ; python_version >= "3.7" and python_version < "3.12" -refgenconf==0.12.2 ; python_version >= "3.7" and python_version < "3.12" -regex==2023.10.3 ; python_version >= "3.7" and python_version < "3.12" -repoze-lru==0.7 ; python_version >= "3.7" and python_version < "3.12" -requests-oauthlib==1.3.1 ; python_version >= "3.7" and python_version < "3.12" -requests-toolbelt==1.0.0 ; python_version >= "3.7" and python_version < "3.12" -requests-unixsocket==0.3.0 ; python_version >= "3.7" and python_version < "3.12" -requests==2.31.0 ; python_version >= "3.7" and python_version < "3.12" -rich==13.7.0 ; python_version >= "3.7" and python_version < "3.12" -rocrate==0.9.0 ; python_version >= "3.7" and python_version < "3.12" -routes==2.5.1 ; python_version >= "3.7" and python_version < "3.12" -rsa==4.9 ; python_version >= "3.7" and python_version < "3.12" -ruamel-yaml-clib==0.2.8 ; platform_python_implementation == "CPython" and python_version < "3.11" and python_version >= "3.7" -ruamel-yaml==0.17.21 ; python_version >= "3.7" and python_version < "3.12" -s3fs==2023.1.0 ; python_version >= "3.7" and python_version < "3.12" -schema-salad==8.4.20230808163024 ; python_version >= "3.7" and python_version < "3.12" -setuptools-scm==5.0.2 ; python_version >= "3.7" and python_version < "3.12" -setuptools==68.0.0 ; python_version >= "3.7" and python_version < "3.12" -shellescape==3.8.1 ; python_version >= "3.7" and python_version < "3.12" -six==1.16.0 ; python_version >= "3.7" and python_version < "3.12" -sniffio==1.3.0 ; python_version >= "3.7" and python_version < "3.12" -social-auth-core[openidconnect]==4.0.3 ; python_version >= "3.7" and python_version < "3.12" -sortedcontainers==2.4.0 ; python_version >= "3.7" and python_version < "3.12" -sqlalchemy==1.4.50 ; python_version >= "3.7" and python_version < "3.12" -sqlitedict==2.1.0 ; python_version >= "3.7" and python_version < "3.12" -sqlparse==0.4.4 ; python_version >= "3.7" and python_version < "3.12" -starlette-context==0.3.5 ; python_version >= "3.7" and python_version < "3.12" -starlette-graphene3==0.6.0 ; python_version >= "3.7" and python_version < "3.12" -starlette==0.27.0 ; python_version >= "3.7" and python_version < "3.12" -supervisor==4.2.5 ; python_version >= "3.7" and python_version < "3.12" -svgwrite==1.4.3 ; python_version >= "3.7" and python_version < "3.12" -tenacity==8.2.3 ; python_version >= "3.7" and python_version < "3.12" -tifffile==2021.11.2 ; python_version >= "3.7" and python_version < "3.12" -tinydb==4.8.0 ; python_version >= "3.7" and python_version < "3.12" -tomli==2.0.1 ; python_version >= "3.7" and python_version < "3.11" -tornado==6.2 ; python_version >= "3.7" and python_version < "3.12" -tqdm==4.66.1 ; python_version >= "3.7" and python_version < "3.12" -tuspy==1.0.1 ; python_version >= "3.7" and python_version < "3.12" -tuswsgi==0.5.5 ; python_version >= "3.7" and python_version < "3.12" -typing-extensions==4.7.1 ; python_version >= "3.7" and python_version < "3.12" -tzdata==2023.3 ; python_version >= "3.7" and python_version < "3.12" and platform_system == "Windows" -tzlocal==5.1 ; python_version >= "3.7" and python_version < "3.12" -ubiquerg==0.6.3 ; python_version >= "3.7" and python_version < "3.12" -urllib3==1.26.18 ; python_version >= "3.7" and python_version < "3.12" -uvicorn==0.22.0 ; python_version >= "3.7" and python_version < "3.12" -uvloop==0.18.0 ; python_version >= "3.7" and python_version < "3.12" -vine==5.1.0 ; python_version >= "3.7" and python_version < "3.12" -wcwidth==0.2.12 ; python_version >= "3.7" and python_version < "3.12" -webencodings==0.5.1 ; python_version >= "3.7" and python_version < "3.12" -webob==1.8.7 ; python_version >= "3.7" and python_version < "3.12" -whoosh==2.7.4 ; python_version >= "3.7" and python_version < "3.12" -wrapt==1.16.0 ; python_version >= "3.7" and python_version < "3.12" -yacman==0.9.2 ; python_version >= "3.7" and python_version < "3.12" -yarl==1.9.3 ; python_version >= "3.7" and python_version < "3.12" -zipp==3.15.0 ; python_version >= "3.7" and python_version < "3.12" -zipstream-new==1.1.8 ; python_version >= "3.7" and python_version < "3.12" -zstandard==0.21.0 ; python_version >= "3.7" and python_version < "3.12" +pysam==0.22.0 ; python_version >= "3.8" and python_version < "3.12" +python-dateutil==2.8.2 ; python_version >= "3.8" and python_version < "3.12" +python-jose==3.3.0 ; python_version >= "3.8" and python_version < "3.12" +python-magic==0.4.27 ; python_version >= "3.8" and python_version < "3.12" +python-multipart==0.0.6 ; python_version >= "3.8" and python_version < "3.12" +python3-openid==3.2.0 ; python_version >= "3.8" and python_version < "3.12" +pytz==2023.3.post1 ; python_version >= "3.8" and python_version < "3.12" +pyyaml==6.0.1 ; python_version >= "3.8" and python_version < "3.12" +pyzmq==25.1.1 ; python_version >= "3.8" and python_version < "3.12" +rdflib==6.3.2 ; python_version >= "3.8" and python_version < "3.12" +referencing==0.31.0 ; python_version >= "3.8" and python_version < "3.12" +refgenconf==0.12.2 ; python_version >= "3.8" and python_version < "3.12" +regex==2023.10.3 ; python_version >= "3.8" and python_version < "3.12" +repoze-lru==0.7 ; python_version >= "3.8" and python_version < "3.12" +requests-oauthlib==1.3.1 ; python_version >= "3.8" and python_version < "3.12" +requests-toolbelt==1.0.0 ; python_version >= "3.8" and python_version < "3.12" +requests-unixsocket==0.3.0 ; python_version >= "3.8" and python_version < "3.12" +requests==2.31.0 ; python_version >= "3.8" and python_version < "3.12" +rich==13.7.0 ; python_version >= "3.8" and python_version < "3.12" +rocrate==0.9.0 ; python_version >= "3.8" and python_version < "3.12" +routes==2.5.1 ; python_version >= "3.8" and python_version < "3.12" +rpds-py==0.13.1 ; python_version >= "3.8" and python_version < "3.12" +rsa==4.9 ; python_version >= "3.8" and python_version < "3.12" +ruamel-yaml-clib==0.2.8 ; platform_python_implementation == "CPython" and python_version < "3.12" and python_version >= "3.8" +ruamel-yaml==0.18.5 ; python_version >= "3.8" and python_version < "3.12" +s3fs==2023.10.0 ; python_version >= "3.8" and python_version < "3.12" +schema-salad==8.4.20231117150958 ; python_version >= "3.8" and python_version < "3.12" +setuptools-scm==5.0.2 ; python_version >= "3.8" and python_version < "3.12" +setuptools==69.0.2 ; python_version >= "3.8" and python_version < "3.12" +shellescape==3.8.1 ; python_version >= "3.8" and python_version < "3.12" +six==1.16.0 ; python_version >= "3.8" and python_version < "3.12" +sniffio==1.3.0 ; python_version >= "3.8" and python_version < "3.12" +social-auth-core[openidconnect]==4.0.3 ; python_version >= "3.8" and python_version < "3.12" +sortedcontainers==2.4.0 ; python_version >= "3.8" and python_version < "3.12" +sqlalchemy==1.4.50 ; python_version >= "3.8" and python_version < "3.12" +sqlitedict==2.1.0 ; python_version >= "3.8" and python_version < "3.12" +sqlparse==0.4.4 ; python_version >= "3.8" and python_version < "3.12" +starlette-context==0.3.6 ; python_version >= "3.8" and python_version < "3.12" +starlette-graphene3==0.6.0 ; python_version >= "3.8" and python_version < "3.12" +starlette==0.27.0 ; python_version >= "3.8" and python_version < "3.12" +supervisor==4.2.5 ; python_version >= "3.8" and python_version < "3.12" +svgwrite==1.4.3 ; python_version >= "3.8" and python_version < "3.12" +tenacity==8.2.3 ; python_version >= "3.8" and python_version < "3.12" +tifffile==2023.7.10 ; python_version >= "3.8" and python_version < "3.12" +tinydb==4.8.0 ; python_version >= "3.8" and python_version < "3.12" +tomli==2.0.1 ; python_version >= "3.8" and python_version < "3.11" +tornado==6.3.3 ; python_version >= "3.8" and python_version < "3.12" +tqdm==4.66.1 ; python_version >= "3.8" and python_version < "3.12" +tuspy==1.0.1 ; python_version >= "3.8" and python_version < "3.12" +tuswsgi==0.5.5 ; python_version >= "3.8" and python_version < "3.12" +typing-extensions==4.8.0 ; python_version >= "3.8" and python_version < "3.12" +tzdata==2023.3 ; python_version >= "3.8" and python_version < "3.12" +tzlocal==5.2 ; python_version >= "3.8" and python_version < "3.12" +ubiquerg==0.6.3 ; python_version >= "3.8" and python_version < "3.12" +urllib3==1.26.18 ; python_version >= "3.8" and python_version < "3.12" +uvicorn==0.24.0.post1 ; python_version >= "3.8" and python_version < "3.12" +uvloop==0.19.0 ; python_version >= "3.8" and python_version < "3.12" +vine==5.1.0 ; python_version >= "3.8" and python_version < "3.12" +wcwidth==0.2.12 ; python_version >= "3.8" and python_version < "3.12" +webencodings==0.5.1 ; python_version >= "3.8" and python_version < "3.12" +webob==1.8.7 ; python_version >= "3.8" and python_version < "3.12" +whoosh==2.7.4 ; python_version >= "3.8" and python_version < "3.12" +wrapt==1.16.0 ; python_version >= "3.8" and python_version < "3.12" +yacman==0.9.2 ; python_version >= "3.8" and python_version < "3.12" +yarl==1.9.3 ; python_version >= "3.8" and python_version < "3.12" +zipp==3.17.0 ; python_version >= "3.8" and python_version < "3.12" +zipstream-new==1.1.8 ; python_version >= "3.8" and python_version < "3.12" +zstandard==0.22.0 ; python_version >= "3.8" and python_version < "3.12" diff --git a/lib/galaxy/dependencies/pinned-typecheck-requirements.txt b/lib/galaxy/dependencies/pinned-typecheck-requirements.txt index a898a0a2c2a1..f25703f5524c 100644 --- a/lib/galaxy/dependencies/pinned-typecheck-requirements.txt +++ b/lib/galaxy/dependencies/pinned-typecheck-requirements.txt @@ -1,22 +1,21 @@ -cffi==1.15.1 ; python_version >= "3.7" and python_version < "3.12" -cryptography==41.0.5 ; python_version >= "3.7" and python_version < "3.12" -mypy-extensions==1.0.0 ; python_version >= "3.7" and python_version < "3.12" -mypy==1.4.1 ; python_version >= "3.7" and python_version < "3.12" -pycparser==2.21 ; python_version >= "3.7" and python_version < "3.12" -pydantic==1.10.13 ; python_version >= "3.7" and python_version < "3.12" -tomli==2.0.1 ; python_version >= "3.7" and python_version < "3.11" -typed-ast==1.5.5 ; python_version >= "3.7" and python_version < "3.8" -types-bleach==6.1.0.1 ; python_version >= "3.7" and python_version < "3.12" -types-boto==2.49.18.9 ; python_version >= "3.7" and python_version < "3.12" -types-contextvars==2.4.7.3 ; python_version >= "3.7" and python_version < "3.12" -types-dataclasses==0.6.6 ; python_version >= "3.7" and python_version < "3.12" -types-docutils==0.20.0.3 ; python_version >= "3.7" and python_version < "3.12" -types-markdown==3.5.0.3 ; python_version >= "3.7" and python_version < "3.12" -types-paramiko==3.3.0.2 ; python_version >= "3.7" and python_version < "3.12" -types-pkg-resources==0.1.3 ; python_version >= "3.7" and python_version < "3.12" -types-python-dateutil==2.8.19.14 ; python_version >= "3.7" and python_version < "3.12" -types-pyyaml==6.0.12.12 ; python_version >= "3.7" and python_version < "3.12" -types-requests==2.31.0.6 ; python_version >= "3.7" and python_version < "3.12" -types-six==1.16.21.9 ; python_version >= "3.7" and python_version < "3.12" -types-urllib3==1.26.25.14 ; python_version >= "3.7" and python_version < "3.12" -typing-extensions==4.7.1 ; python_version >= "3.7" and python_version < "3.12" +cffi==1.16.0 ; python_version >= "3.8" and python_version < "3.12" +cryptography==41.0.5 ; python_version >= "3.8" and python_version < "3.12" +mypy-extensions==1.0.0 ; python_version >= "3.8" and python_version < "3.12" +mypy==1.7.1 ; python_version >= "3.8" and python_version < "3.12" +pycparser==2.21 ; python_version >= "3.8" and python_version < "3.12" +pydantic==1.10.13 ; python_version >= "3.8" and python_version < "3.12" +tomli==2.0.1 ; python_version >= "3.8" and python_version < "3.11" +types-bleach==6.1.0.1 ; python_version >= "3.8" and python_version < "3.12" +types-boto==2.49.18.9 ; python_version >= "3.8" and python_version < "3.12" +types-contextvars==2.4.7.3 ; python_version >= "3.8" and python_version < "3.12" +types-dataclasses==0.6.6 ; python_version >= "3.8" and python_version < "3.12" +types-docutils==0.20.0.3 ; python_version >= "3.8" and python_version < "3.12" +types-markdown==3.5.0.3 ; python_version >= "3.8" and python_version < "3.12" +types-paramiko==3.3.0.2 ; python_version >= "3.8" and python_version < "3.12" +types-pkg-resources==0.1.3 ; python_version >= "3.8" and python_version < "3.12" +types-python-dateutil==2.8.19.14 ; python_version >= "3.8" and python_version < "3.12" +types-pyyaml==6.0.12.12 ; python_version >= "3.8" and python_version < "3.12" +types-requests==2.31.0.6 ; python_version >= "3.8" and python_version < "3.12" +types-six==1.16.21.9 ; python_version >= "3.8" and python_version < "3.12" +types-urllib3==1.26.25.14 ; python_version >= "3.8" and python_version < "3.12" +typing-extensions==4.8.0 ; python_version >= "3.8" and python_version < "3.12" diff --git a/lib/galaxy/dependencies/update.sh b/lib/galaxy/dependencies/update.sh index 7771ea30791e..01708a54cfe4 100755 --- a/lib/galaxy/dependencies/update.sh +++ b/lib/galaxy/dependencies/update.sh @@ -6,7 +6,7 @@ set -e -SUPPORTED_PYTHON_VERSIONS="3.7 3.8 3.9 3.10 3.11" +SUPPORTED_PYTHON_VERSIONS="3.8 3.9 3.10 3.11" NOT_SUPPORTED_NEXT_PYTHON_VERSION="3.12" this_directory="$(cd "$(dirname "$0")" > /dev/null && pwd)" diff --git a/lib/galaxy/dependencies/update_lint_requirements.sh b/lib/galaxy/dependencies/update_lint_requirements.sh index 6f06089aabf8..0225d931d11d 100755 --- a/lib/galaxy/dependencies/update_lint_requirements.sh +++ b/lib/galaxy/dependencies/update_lint_requirements.sh @@ -11,7 +11,7 @@ THIS_DIRECTORY="$(cd "$(dirname "$0")" > /dev/null && pwd)" update_pinned_reqs() { VENV=$(mktemp -d "${TMPDIR:-/tmp}/$1_venv.XXXXXXXXXX") - python3.7 -m venv "${VENV}" + python3.8 -m venv "${VENV}" . "${VENV}/bin/activate" pip install --upgrade pip setuptools pip install -r "${THIS_DIRECTORY}/$1-requirements.txt" diff --git a/lib/galaxy/files/sources/drs.py b/lib/galaxy/files/sources/drs.py index a2b8ec6869b1..3e05ca4bd56e 100644 --- a/lib/galaxy/files/sources/drs.py +++ b/lib/galaxy/files/sources/drs.py @@ -64,8 +64,7 @@ def _write_from(self, target_path, native_path, user_context=None, opts: Optiona raise NotImplementedError() def score_url_match(self, url: str): - match = self._url_regex.match(url) - if match: + if match := self._url_regex.match(url): return match.span()[1] else: return 0 diff --git a/lib/galaxy/forms/forms.py b/lib/galaxy/forms/forms.py index 80e6c9067f10..ce8a1c2580fa 100644 --- a/lib/galaxy/forms/forms.py +++ b/lib/galaxy/forms/forms.py @@ -54,16 +54,14 @@ def from_elem(self, elem, form_definition_current=None): form_type = elem.get("type", None) # load layout layout = [] - layouts_elem = elem.find("layout") - if layouts_elem: + if layouts_elem := elem.find("layout"): for layout_elem in layouts_elem.findall("grid"): layout_name = layout_elem.get("name", None) assert layout_name and layout_name not in layout, "Layout grid element requires a unique name." layout.append(layout_name) # load fields fields = [] - fields_elem = elem.find("fields") - if fields_elem is not None: + if (fields_elem := elem.find("fields")) is not None: for field_elem in fields_elem.findall("field"): field_type = field_elem.get("type") assert field_type in self.field_type_factories, f"Invalid form field type ( {field_type} )." diff --git a/lib/galaxy/job_execution/actions/post.py b/lib/galaxy/job_execution/actions/post.py index 39aa70b8ae52..0ce006d35492 100644 --- a/lib/galaxy/job_execution/actions/post.py +++ b/lib/galaxy/job_execution/actions/post.py @@ -140,8 +140,7 @@ def execute_on_mapped_over( if step_input and hasattr(step_input, "name"): input_names[input_key] = step_input.name - new_name = cls._gen_new_name(action, input_names, replacement_dict) - if new_name: + if new_name := cls._gen_new_name(action, input_names, replacement_dict): for name, step_output in step_outputs.items(): if action.output_name == "" or name == action.output_name: step_output.name = new_name @@ -248,8 +247,7 @@ def execute(cls, app, sa_session, action, job, replacement_dict, final_job_state if has_collection and hasattr(has_collection, "name"): input_names[input_assoc.name] = has_collection.name - new_name = cls._gen_new_name(action, input_names, replacement_dict) - if new_name: + if new_name := cls._gen_new_name(action, input_names, replacement_dict): for dataset_assoc in job.output_datasets: if action.output_name == "" or dataset_assoc.name == action.output_name: dataset_assoc.dataset.name = new_name diff --git a/lib/galaxy/job_execution/output_collect.py b/lib/galaxy/job_execution/output_collect.py index e251c8655e8c..4b96a03a89c3 100644 --- a/lib/galaxy/job_execution/output_collect.py +++ b/lib/galaxy/job_execution/output_collect.py @@ -90,8 +90,7 @@ def permissions(self): return self._permissions def set_default_hda_permissions(self, primary_data): - permissions = self.permissions - if permissions is not UNSET: + if (permissions := self.permissions) is not UNSET: self._security_agent.set_all_dataset_permissions(primary_data.dataset, permissions, new=True, flush=False) def copy_dataset_permissions(self, init_from, primary_data): @@ -676,9 +675,8 @@ def match(self, dataset_instance, filename, path=None, parent_paths=None): pattern = self._pattern_for_dataset(dataset_instance) if self.match_relative_path and parent_paths: filename = os.path.join(*parent_paths, filename) - re_match = re.match(pattern, filename) match_object = None - if re_match: + if re_match := re.match(pattern, filename): match_object = RegexCollectedDatasetMatch(re_match, self, filename, path=path) return match_object diff --git a/lib/galaxy/job_execution/ports/view.py b/lib/galaxy/job_execution/ports/view.py index 807c2d5d4b77..86598d0d26b3 100644 --- a/lib/galaxy/job_execution/ports/view.py +++ b/lib/galaxy/job_execution/ports/view.py @@ -25,8 +25,7 @@ def register_container_information(self, job_id, **kwd): # Copy/paste from JobFilesView - TODO: de-duplicate. def __authorize_job_access(self, encoded_job_id, **kwargs): - key = "job_key" - if key not in kwargs: + if (key := "job_key") not in kwargs: error_message = f"Job files action requires a valid '{key}'." raise ObjectAttributeMissingException(error_message) diff --git a/lib/galaxy/jobs/__init__.py b/lib/galaxy/jobs/__init__.py index 91a0ed792be1..48a22bae5d10 100644 --- a/lib/galaxy/jobs/__init__.py +++ b/lib/galaxy/jobs/__init__.py @@ -165,8 +165,7 @@ def job_config_xml_to_dict(config, root): config_dict["runners"] = runners # Parser plugins section populate 'runners' and 'dynamic' in config_dict. - plugins = root.find("plugins") - if plugins is not None: + if (plugins := root.find("plugins")) is not None: for plugin in ConfiguresHandlers._findall_with_required(plugins, "plugin", ("id", "type", "load")): if plugin.get("type") == "runner": workers = plugin.get("workers", plugins.get("workers", JobConfiguration.DEFAULT_NWORKERS)) @@ -243,8 +242,7 @@ def job_config_xml_to_dict(config, root): resource_groups = {} # Parse resources... - resources = root.find("resources") - if resources is not None: + if (resources := root.find("resources")) is not None: default_resource_group = resources.get("default", None) if default_resource_group: resources_config_dict["default"] = default_resource_group @@ -259,9 +257,8 @@ def job_config_xml_to_dict(config, root): config_dict["resources"] = resources_config_dict # Parse tool mappings - tools = root.find("tools") config_dict["tools"] = [] - if tools is not None: + if (tools := root.find("tools")) is not None: for tool in tools.findall("tool"): # There can be multiple definitions with identical ids, but different params tool_mapping_conf = {} @@ -275,8 +272,7 @@ def job_config_xml_to_dict(config, root): config_dict["tools"].append(tool_mapping_conf) limits_config = [] - limits = root.find("limits") - if limits is not None: + if (limits := root.find("limits")) is not None: for limit in JobConfiguration._findall_with_required(limits, "limit", ("type",)): limit_dict = {} for key in ["type", "tag", "id", "window"]: @@ -1237,8 +1233,7 @@ def prepare(self, compute_environment=None): def get_special(): stmt = select(model.JobExportHistoryArchive).filter_by(job=job).limit(1) - jeha = self.sa_session.scalars(stmt).first() - if jeha: + if jeha := self.sa_session.scalars(stmt).first(): return jeha.fda stmt = select(model.GenomeIndexToolData).filter_by(job=job).limit(1) return self.sa_session.scalars(stmt).first() @@ -1510,8 +1505,7 @@ def is_ready_for_resubmission(self, job=None): if job is None: job = self.get_job() - destination_params = job.destination_params - if "__resubmit_delay_seconds" in destination_params: + if "__resubmit_delay_seconds" in (destination_params := job.destination_params): delay = float(destination_params["__resubmit_delay_seconds"]) if job.seconds_since_updated < delay: return False @@ -2410,8 +2404,7 @@ def container_monitor_command(self, container, **kwds): @property def user(self): job = self.get_job() - user_email = job.get_user_email() - if user_email: + if user_email := job.get_user_email(): return user_email elif job.galaxy_session is not None: return f"anonymous@{job.galaxy_session.remote_addr.split()[-1]}" diff --git a/lib/galaxy/jobs/command_factory.py b/lib/galaxy/jobs/command_factory.py index 10b9c137347a..1c2a67da86ad 100644 --- a/lib/galaxy/jobs/command_factory.py +++ b/lib/galaxy/jobs/command_factory.py @@ -123,8 +123,7 @@ def build_command( __handle_remote_command_line_building(commands_builder, job_wrapper, for_pulsar=for_pulsar) - container_monitor_command = job_wrapper.container_monitor_command(container) - if container_monitor_command: + if container_monitor_command := job_wrapper.container_monitor_command(container): commands_builder.prepend_command(container_monitor_command) working_directory = remote_job_directory or job_wrapper.working_directory diff --git a/lib/galaxy/jobs/handler.py b/lib/galaxy/jobs/handler.py index 2472f874be37..279b853a9198 100644 --- a/lib/galaxy/jobs/handler.py +++ b/lib/galaxy/jobs/handler.py @@ -1250,8 +1250,7 @@ def stop(self, job, job_wrapper): from galaxy.celery import celery_app celery_app.control.revoke(job.job_runner_external_id) - job_runner_name = job.get_job_runner_name() - if job_runner_name is not None: + if (job_runner_name := job.get_job_runner_name()) is not None: runner_name = job_runner_name.split(":", 1)[0] log.debug(f"Stopping job {job_wrapper.get_id_tag()} in {runner_name} runner") try: diff --git a/lib/galaxy/jobs/mapper.py b/lib/galaxy/jobs/mapper.py index 963a01bb724d..f5bac4e68407 100644 --- a/lib/galaxy/jobs/mapper.py +++ b/lib/galaxy/jobs/mapper.py @@ -160,8 +160,7 @@ def __get_expand_function(self, destination): rules_module_name = destination.params.get("rules_module") rule_modules = self.__get_rule_modules_or_defaults(rules_module_name) expand_function = None - expand_function_name = destination.params.get("function") - if expand_function_name: + if expand_function_name := destination.params.get("function"): expand_function = self.__last_matching_function_in_modules(rule_modules, expand_function_name) if not expand_function: message = ERROR_MESSAGE_RULE_FUNCTION_NOT_FOUND % expand_function_name diff --git a/lib/galaxy/jobs/runners/__init__.py b/lib/galaxy/jobs/runners/__init__.py index c14aea726f03..b612103f0475 100644 --- a/lib/galaxy/jobs/runners/__init__.py +++ b/lib/galaxy/jobs/runners/__init__.py @@ -217,8 +217,7 @@ def shutdown(self): for _ in range(len(self.work_threads)): self.work_queue.put((STOP_SIGNAL, None)) - join_timeout = self.app.config.monitor_thread_join_timeout - if join_timeout > 0: + if (join_timeout := self.app.config.monitor_thread_join_timeout) > 0: log.info("Waiting up to %d seconds for job worker threads to shutdown...", join_timeout) start = time.time() # NOTE: threads that have already joined by now are not going to be logged diff --git a/lib/galaxy/jobs/runners/aws.py b/lib/galaxy/jobs/runners/aws.py index bed35ec19c37..fa24add37e45 100644 --- a/lib/galaxy/jobs/runners/aws.py +++ b/lib/galaxy/jobs/runners/aws.py @@ -78,8 +78,7 @@ def _add_resource_requirements(destination_params): {"type": "VCPU", "value": str(destination_params.get("vcpu"))}, {"type": "MEMORY", "value": str(destination_params.get("memory"))}, ] - n_gpu = destination_params.get("gpu") - if n_gpu: + if n_gpu := destination_params.get("gpu"): rval.append({"type": "GPU", "value": str(n_gpu)}) return rval @@ -279,8 +278,7 @@ def _get_mount_volumes(self, destination_params): if destination_params.get("platform") == 'Fargate': # Fargate doesn't support host volumes return volumes, mount_points - ec2_host_volumes = destination_params.get("ec2_host_volumes") - if ec2_host_volumes: + if (ec2_host_volumes := destination_params.get("ec2_host_volumes")): for ix, vol in enumerate(ec2_host_volumes.split(",")): vol = vol.strip() vol_name = "host_vol_" + str(ix) @@ -356,8 +354,7 @@ def _register_job_definition(self, jd_name, container_image, destination_params) } ) other_kwargs = {} - retry_strategy = self._get_retry_strategy(destination_params) - if retry_strategy: + if (retry_strategy := self._get_retry_strategy(destination_params)): other_kwargs["retryStrategy"] = retry_strategy res = self._batch_client.register_job_definition( diff --git a/lib/galaxy/jobs/runners/chronos.py b/lib/galaxy/jobs/runners/chronos.py index 3d1264d8cb17..3bed4dc79a67 100644 --- a/lib/galaxy/jobs/runners/chronos.py +++ b/lib/galaxy/jobs/runners/chronos.py @@ -201,9 +201,8 @@ def recover(self, job, job_wrapper): @handle_exception_call def check_watched_item(self, job_state): job_name = job_state.job_id - job = self._retrieve_job(job_name) # TODO: how can stopped GxIT jobs be handled here? - if job: + if job := self._retrieve_job(job_name): succeeded = job["successCount"] errors = job["errorCount"] if succeeded > 0: diff --git a/lib/galaxy/jobs/runners/condor.py b/lib/galaxy/jobs/runners/condor.py index 6e9862ac9e02..31561b7b219d 100644 --- a/lib/galaxy/jobs/runners/condor.py +++ b/lib/galaxy/jobs/runners/condor.py @@ -76,8 +76,7 @@ def queue_job(self, job_wrapper): # HTCondor needs the image as 'docker_image' query_params.update({"docker_image": container.container_id}) - galaxy_slots = query_params.get("request_cpus", None) - if galaxy_slots: + if galaxy_slots := query_params.get("request_cpus", None): galaxy_slots_statement = f'GALAXY_SLOTS="{galaxy_slots}"; export GALAXY_SLOTS; GALAXY_SLOTS_CONFIGURED="1"; export GALAXY_SLOTS_CONFIGURED;' else: galaxy_slots_statement = 'GALAXY_SLOTS="1"; export GALAXY_SLOTS;' diff --git a/lib/galaxy/jobs/runners/drmaa.py b/lib/galaxy/jobs/runners/drmaa.py index 5c1d68f70490..6abb6fbef02e 100644 --- a/lib/galaxy/jobs/runners/drmaa.py +++ b/lib/galaxy/jobs/runners/drmaa.py @@ -105,8 +105,7 @@ def url_to_destination(self, url): """Convert a legacy URL to a job destination""" if not url: return - native_spec = url.split("/")[2] - if native_spec: + if native_spec := url.split("/")[2]: params = dict(nativeSpecification=native_spec) log.debug(f"Converted URL '{url}' to destination runner=drmaa, params={params}") return JobDestination(runner="drmaa", params=params) diff --git a/lib/galaxy/jobs/runners/kubernetes.py b/lib/galaxy/jobs/runners/kubernetes.py index 90d43aafe504..5709e12bfce9 100644 --- a/lib/galaxy/jobs/runners/kubernetes.py +++ b/lib/galaxy/jobs/runners/kubernetes.py @@ -527,8 +527,7 @@ def __get_k8s_containers(self, ajs): "volumeMounts": deduplicate_entries(mounts), } - resources = self.__get_resources(ajs.job_wrapper) - if resources: + if resources := self.__get_resources(ajs.job_wrapper): envs = [] cpu_val = None if "requests" in resources: @@ -585,23 +584,17 @@ def __get_k8s_containers(self, ajs): return [k8s_container] def __get_resources(self, job_wrapper): - mem_request = self.__get_memory_request(job_wrapper) - cpu_request = self.__get_cpu_request(job_wrapper) - - mem_limit = self.__get_memory_limit(job_wrapper) - cpu_limit = self.__get_cpu_limit(job_wrapper) - requests = {} limits = {} - if mem_request: + if mem_request := self.__get_memory_request(job_wrapper): requests["memory"] = mem_request - if cpu_request: + if cpu_request := self.__get_cpu_request(job_wrapper): requests["cpu"] = cpu_request - if mem_limit: + if mem_limit := self.__get_memory_limit(job_wrapper): limits["memory"] = mem_limit - if cpu_limit: + if cpu_limit := self.__get_cpu_limit(job_wrapper): limits["cpu"] = cpu_limit resources = {} diff --git a/lib/galaxy/jobs/runners/pbs.py b/lib/galaxy/jobs/runners/pbs.py index fa22c11b1a70..a1012d1a3705 100644 --- a/lib/galaxy/jobs/runners/pbs.py +++ b/lib/galaxy/jobs/runners/pbs.py @@ -132,8 +132,7 @@ def url_to_destination(self, url): # Determine the queue, set the PBS destination (not the same thing as a Galaxy job destination) pbs_destination = f"@{server}" - pbs_queue = url_split[3] or None - if pbs_queue is not None: + if (pbs_queue := url_split[3] or None) is not None: pbs_destination = f"{pbs_queue}{pbs_destination}" params = dict(destination=pbs_destination) diff --git a/lib/galaxy/jobs/runners/pulsar.py b/lib/galaxy/jobs/runners/pulsar.py index f9142ee8c59f..003af5a4d3c7 100644 --- a/lib/galaxy/jobs/runners/pulsar.py +++ b/lib/galaxy/jobs/runners/pulsar.py @@ -599,8 +599,7 @@ def get_client_from_wrapper(self, job_wrapper): if hasattr(job_wrapper, "task_id"): job_id = f"{job_id}_{job_wrapper.task_id}" params = job_wrapper.job_destination.params.copy() - user = job_wrapper.get_job().user - if user: + if user := job_wrapper.get_job().user: for key, value in params.items(): if value and isinstance(value, str): params[key] = model.User.expand_user_properties(user, value) diff --git a/lib/galaxy/jobs/runners/univa.py b/lib/galaxy/jobs/runners/univa.py index c0d2ecb730c3..3e3455c75e52 100644 --- a/lib/galaxy/jobs/runners/univa.py +++ b/lib/galaxy/jobs/runners/univa.py @@ -567,8 +567,7 @@ def _map_qstat_drmaa_states(self, job_id, state, extinfo): def _parse_time(tstring): tme = None - m = re.search("([0-9:.]+)", tstring) - if m is not None: + if (m := re.search("([0-9:.]+)", tstring)) is not None: timespl = m.group(1).split(":") tme = float(timespl[-1]) # sec if len(timespl) > 1: # min diff --git a/lib/galaxy/jobs/runners/util/env.py b/lib/galaxy/jobs/runners/util/env.py index b7a30d895055..3aa62164e17f 100644 --- a/lib/galaxy/jobs/runners/util/env.py +++ b/lib/galaxy/jobs/runners/util/env.py @@ -21,11 +21,9 @@ def env_to_statement(env): >>> env_to_statement(dict(execute="module load java/1.5.1")) 'module load java/1.5.1' """ - source_file = env.get("file", None) - if source_file: + if source_file := env.get("file", None): return f". {__escape(source_file, env)}" - execute = env.get("execute", None) - if execute: + if execute := env.get("execute", None): return execute name = env["name"] value = __escape(env["value"], env) diff --git a/lib/galaxy/jobs/runners/util/sudo.py b/lib/galaxy/jobs/runners/util/sudo.py index fdc8d74feda4..555625878787 100644 --- a/lib/galaxy/jobs/runners/util/sudo.py +++ b/lib/galaxy/jobs/runners/util/sudo.py @@ -16,9 +16,8 @@ def sudo_popen(*args, **kwargs): Helper method for building and executing Popen command. This is potentially sensetive code so should probably be centralized. """ - user = kwargs.get("user", None) full_command = [SUDO_PATH, SUDO_PRESERVE_ENVIRONMENT_ARG] - if user: + if user := kwargs.get("user", None): full_command.extend([SUDO_USER_ARG, user]) full_command.extend(args) log.info(f"About to execute the following sudo command - [{' '.join(full_command)}]") diff --git a/lib/galaxy/managers/base.py b/lib/galaxy/managers/base.py index f3abe35e7ceb..216aac5582c3 100644 --- a/lib/galaxy/managers/base.py +++ b/lib/galaxy/managers/base.py @@ -1139,8 +1139,7 @@ def _parse_fn_filter(self, attr, op, val): if not filter_fn: return None # parse the val from string using the 'val' parser if present (otherwise, leave as string) - val_parser = attr_map.get("val", None) - if val_parser: + if val_parser := attr_map.get("val", None): val = val_parser(val) # curry/partial and fold the val in there now @@ -1262,8 +1261,7 @@ def parse_date(self, date_string): except ValueError: pass - match = self.date_string_re.match(date_string) - if match: + if match := self.date_string_re.match(date_string): date_string = " ".join(group for group in match.groups() if group) return date_string raise ValueError("datetime strings must be in the ISO 8601 format and in the UTC") diff --git a/lib/galaxy/managers/collections.py b/lib/galaxy/managers/collections.py index 24c695db18b8..d46b74ba7f96 100644 --- a/lib/galaxy/managers/collections.py +++ b/lib/galaxy/managers/collections.py @@ -631,9 +631,8 @@ def __load_element(self, trans, element_identifier, hide_source_items, copy_elem message = message_template % element_identifier raise RequestParameterInvalidException(message) - tags = element_identifier.pop("tags", None) tag_str = "" - if tags: + if tags := element_identifier.pop("tags", None): tag_str = ",".join(str(_) for _ in tags) if src_type == "hda": hda = self.hda_manager.get_accessible(element_id, trans.user) diff --git a/lib/galaxy/managers/collections_util.py b/lib/galaxy/managers/collections_util.py index 60b47c3cdff0..dbf439364d45 100644 --- a/lib/galaxy/managers/collections_util.py +++ b/lib/galaxy/managers/collections_util.py @@ -156,8 +156,7 @@ def dictify_element_reference(element, rank_fuzzy_counts=None, recursive=True, s are clicked. """ dictified = element.to_dict(view="element") - element_object = element.element_object - if element_object is not None: + if (element_object := element.element_object) is not None: object_details = dict( id=element_object.id, model_class=element_object.__class__.__name__, diff --git a/lib/galaxy/managers/context.py b/lib/galaxy/managers/context.py index ec9b5e842998..23caedf81e66 100644 --- a/lib/galaxy/managers/context.py +++ b/lib/galaxy/managers/context.py @@ -234,8 +234,7 @@ def anonymous(self) -> bool: return self.user is None def get_current_user_roles(self) -> List[Role]: - user = self.user - if user: + if user := self.user: roles = user.all_roles() else: roles = [] diff --git a/lib/galaxy/managers/groups.py b/lib/galaxy/managers/groups.py index a0950a4063b8..e8919d4db72a 100644 --- a/lib/galaxy/managers/groups.py +++ b/lib/galaxy/managers/groups.py @@ -82,8 +82,7 @@ def update(self, trans: ProvidesAppContext, group_id: int, payload: GroupCreateP """ sa_session = trans.sa_session group = self._get_group(sa_session, group_id) - name = payload.name - if name: + if name := payload.name: self._check_duplicated_group_name(sa_session, name) group.name = name sa_session.add(group) diff --git a/lib/galaxy/managers/history_contents.py b/lib/galaxy/managers/history_contents.py index fa357af3e3b3..155785e1ca63 100644 --- a/lib/galaxy/managers/history_contents.py +++ b/lib/galaxy/managers/history_contents.py @@ -568,8 +568,7 @@ def get_filter(attr, op, val): return sql.column("state").in_(states) raise_filter_err(attr, op, val, "bad op in filter") - column_filter = get_filter(attr, op, val) - if column_filter is not None: + if (column_filter := get_filter(attr, op, val)) is not None: return self.parsed_filter(filter_type="orm", filter=column_filter) return super()._parse_orm_filter(attr, op, val) diff --git a/lib/galaxy/managers/jobs.py b/lib/galaxy/managers/jobs.py index a1ac6728591a..c8eef282b25b 100644 --- a/lib/galaxy/managers/jobs.py +++ b/lib/galaxy/managers/jobs.py @@ -868,8 +868,7 @@ def summarize_destination_params(trans, job): "Runner Job ID": job.job_runner_external_id, "Handler": job.handler, } - job_destination_params = job.destination_params - if job_destination_params: + if job_destination_params := job.destination_params: destination_params.update(job_destination_params) return destination_params diff --git a/lib/galaxy/managers/markdown_util.py b/lib/galaxy/managers/markdown_util.py index 5c4226e17bff..982aecc6b4a6 100644 --- a/lib/galaxy/managers/markdown_util.py +++ b/lib/galaxy/managers/markdown_util.py @@ -88,9 +88,8 @@ def ready_galaxy_markdown_for_import(trans, external_galaxy_markdown): _validate(external_galaxy_markdown, internal=False) def _remap(container, line): - id_match = re.search(ENCODED_ID_PATTERN, line) object_id = None - if id_match: + if id_match := re.search(ENCODED_ID_PATTERN, line): object_id = id_match.group(2) decoded_id = trans.security.decode_id(object_id) line = line.replace(id_match.group(), "%s=%d" % (id_match.group(1), decoded_id)) @@ -232,10 +231,9 @@ def _remap_container(container, line): return export_markdown def _encode_line(self, trans, line): - id_match = re.search(UNENCODED_ID_PATTERN, line) object_id = None encoded_id = None - if id_match: + if id_match := re.search(UNENCODED_ID_PATTERN, line): object_id = int(id_match.group(2)) encoded_id = trans.security.encode_id(object_id) line = line.replace(id_match.group(), f"{id_match.group(1)}={encoded_id}") @@ -524,9 +522,8 @@ def _display_dataset_content(self, hda, header="Contents"): def handle_dataset_as_image(self, line, hda): dataset = hda.dataset name = hda.name or "" - path_match = re.search(PATH_LABEL_PATTERN, line) - if path_match: + if path_match := re.search(PATH_LABEL_PATTERN, line): filepath = path_match.group(2) file = os.path.join(hda.extra_files_path, filepath) else: @@ -581,9 +578,8 @@ def handle_workflow_display(self, line, stored_workflow, workflow_version: Optio def handle_workflow_license(self, line, stored_workflow): # workflow_manager = self.trans.app.workflow_manager license_manager = LicensesManager() - license_id = stored_workflow.latest_workflow.license markdown = "*No license specified.*" - if license_id: + if license_id := stored_workflow.latest_workflow.license: try: license_metadata = license_manager.get_license_by_id(license_id) markdown = f"[{license_metadata.name}]({license_metadata.url})" diff --git a/lib/galaxy/managers/model_stores.py b/lib/galaxy/managers/model_stores.py index 1e817d130a60..a31e5059668f 100644 --- a/lib/galaxy/managers/model_stores.py +++ b/lib/galaxy/managers/model_stores.py @@ -265,8 +265,7 @@ def import_model_store(self, request: ImportModelStoreTaskRequest): import_options = ImportOptions( allow_library_creation=request.for_library, ) - history_id = request.history_id - if history_id: + if history_id := request.history_id: history = self._sa_session.get(model.History, history_id) else: history = None diff --git a/lib/galaxy/managers/notification.py b/lib/galaxy/managers/notification.py index 0db48f7bfb3e..b0da5b1b9d8e 100644 --- a/lib/galaxy/managers/notification.py +++ b/lib/galaxy/managers/notification.py @@ -409,7 +409,7 @@ def resolve_users(self, recipients: NotificationRecipients) -> List[User]: user_ids_from_roles_stmt = self._get_all_user_ids_from_roles_query(all_role_ids) union_stmt = union(user_ids_from_groups_stmt, user_ids_from_roles_stmt) - user_ids_from_groups_and_roles = set([id for id, in self.sa_session.execute(union_stmt)]) + user_ids_from_groups_and_roles = {id for id, in self.sa_session.execute(union_stmt)} unique_user_ids.update(user_ids_from_groups_and_roles) stmt = select(User).where(User.id.in_(unique_user_ids)) @@ -448,7 +448,7 @@ def _expand_group_and_roles_ids(self, group_ids: Set[int], role_ids: Set[int]) - .where(GroupRoleAssociation.role_id.in_(role_ids)) .distinct() ) - group_ids_from_roles = set([id for id, in self.sa_session.execute(stmt) if id is not None]) + group_ids_from_roles = {id for id, in self.sa_session.execute(stmt) if id is not None} new_group_ids = group_ids_from_roles - processed_group_ids # Get role IDs associated with any of the given group IDs @@ -458,7 +458,7 @@ def _expand_group_and_roles_ids(self, group_ids: Set[int], role_ids: Set[int]) - .where(GroupRoleAssociation.group_id.in_(group_ids)) .distinct() ) - role_ids_from_groups = set([id for id, in self.sa_session.execute(stmt) if id is not None]) + role_ids_from_groups = {id for id, in self.sa_session.execute(stmt) if id is not None} new_role_ids = role_ids_from_groups - processed_role_ids # Stop if there are no new group or role IDs to process diff --git a/lib/galaxy/managers/pages.py b/lib/galaxy/managers/pages.py index ded9b71b9b04..72eb50fb6775 100644 --- a/lib/galaxy/managers/pages.py +++ b/lib/galaxy/managers/pages.py @@ -263,8 +263,7 @@ def create_page(self, trans, payload: CreatePagePayload): page = trans.app.model.Page() page.title = payload.title page.slug = payload.slug - page_annotation = payload.annotation - if page_annotation is not None: + if (page_annotation := payload.annotation) is not None: page_annotation = sanitize_html(page_annotation) self.add_item_annotation(trans.sa_session, trans.get_user(), page, page_annotation) diff --git a/lib/galaxy/managers/rbac_secured.py b/lib/galaxy/managers/rbac_secured.py index 9ead418493fd..a63cd036447b 100644 --- a/lib/galaxy/managers/rbac_secured.py +++ b/lib/galaxy/managers/rbac_secured.py @@ -215,8 +215,7 @@ def _user_private_role(self, user): return self.user_manager.private_role(user) def _grant_role(self, dataset, role, flush=True): - existing = self.by_role(dataset, role) - if existing: + if existing := self.by_role(dataset, role): return existing return self._create(dataset, role, flush=flush) diff --git a/lib/galaxy/managers/workflows.py b/lib/galaxy/managers/workflows.py index 357ec0deae7c..b6625ac1b356 100644 --- a/lib/galaxy/managers/workflows.py +++ b/lib/galaxy/managers/workflows.py @@ -784,9 +784,8 @@ def _workflow_from_raw_description( steps_by_external_id: Dict[str, model.WorkflowStep] = {} # Preload dependent workflows with locally defined content_ids. - subworkflows = data.get("subworkflows") subworkflow_id_map = None - if subworkflows: + if subworkflows := data.get("subworkflows"): subworkflow_id_map = {} for key, subworkflow_dict in subworkflows.items(): subworkflow = self.__build_embedded_subworkflow( @@ -1749,8 +1748,7 @@ def __module_from_dict( self.__set_default_label(step, module, step_dict.get("tool_state")) module.save_to_step(step, detached=dry_run) - annotation = step_dict.get("annotation") - if annotation: + if annotation := step_dict.get("annotation"): annotation = sanitize_html(annotation) sa_session = None if dry_run else trans.sa_session self.add_item_annotation(sa_session, trans.get_user(), step, annotation) diff --git a/lib/galaxy/metadata/set_metadata.py b/lib/galaxy/metadata/set_metadata.py index 214fe001ff6d..90549c6ddf6b 100644 --- a/lib/galaxy/metadata/set_metadata.py +++ b/lib/galaxy/metadata/set_metadata.py @@ -115,8 +115,7 @@ def set_meta_with_tool_provided( # This is intentional due to interplay of overwrite kwd, the fact that some metadata # parameters may rely on the values of others, and that we are accepting the # values provided by the tool as Truth. - extension = dataset_instance.extension - if extension == "_sniff_": + if (extension := dataset_instance.extension) == "_sniff_": try: extension = sniff.handle_uploaded_dataset_file(dataset_instance.dataset.get_file_name(), datatypes_registry) # We need to both set the extension so it is available to set_meta diff --git a/lib/galaxy/model/__init__.py b/lib/galaxy/model/__init__.py index 6c79d51fccb6..0e178f8d98d8 100644 --- a/lib/galaxy/model/__init__.py +++ b/lib/galaxy/model/__init__.py @@ -522,8 +522,7 @@ def shrink_and_unicodify(what, stream): def log_str(self): extra = "" - safe_id = getattr(self, "id", None) - if safe_id is not None: + if (safe_id := getattr(self, "id", None)) is not None: extra += f"id={safe_id}" else: extra += "unflushed" @@ -782,8 +781,7 @@ def __init__(self, email=None, password=None, username=None): @property def extra_preferences(self): data = defaultdict(lambda: None) - extra_user_preferences = self.preferences.get("extra_user_preferences") - if extra_user_preferences: + if extra_user_preferences := self.preferences.get("extra_user_preferences"): try: data.update(json.loads(extra_user_preferences)) except Exception: @@ -794,8 +792,7 @@ def set_password_cleartext(self, cleartext): """ Set user password to the digest of `cleartext`. """ - message = validate_password_str(cleartext) - if message: + if message := validate_password_str(cleartext): raise Exception(f"Invalid password: {message}") if User.use_pbkdf2: self.password = galaxy.security.passwords.hash_password(cleartext) @@ -3819,8 +3816,7 @@ def __init__(self, history, action, role): class StorableObject: def flush(self): - sa_session = object_session(self) - if sa_session: + if sa_session := object_session(self): with transaction(sa_session): sa_session.commit() @@ -4034,8 +4030,7 @@ def store_by(self): return store_by def extra_files_path_name_from(self, object_store): - store_by = self.store_by - if store_by is not None: + if (store_by := self.store_by) is not None: return f"dataset_{getattr(self, store_by)}_files" else: return None @@ -4107,8 +4102,7 @@ def set_total_size(self): if self.file_size is None: self.set_size() self.total_size = self.file_size or 0 - rel_path = self._extra_files_rel_path - if rel_path is not None: + if (rel_path := self._extra_files_rel_path) is not None: if self.object_store.exists(self, extra_dir=rel_path, dir_only=True): for root, _, files in os.walk(self.extra_files_path): self.total_size += sum( @@ -4145,8 +4139,7 @@ def full_delete(self): self.object_store.delete(self) except galaxy.exceptions.ObjectNotFound: pass - rel_path = self._extra_files_rel_path - if rel_path is not None: + if (rel_path := self._extra_files_rel_path) is not None: if self.object_store.exists(self, extra_dir=rel_path, dir_only=True): self.object_store.delete(self, entire_dir=True, extra_dir=rel_path, dir_only=True) # TODO: purge metadata files @@ -7863,8 +7856,7 @@ def copy_to(self, copied_step, step_mapping, user=None): annotations.append(association) copied_step.annotations = annotations - subworkflow = self.subworkflow - if subworkflow: + if subworkflow := self.subworkflow: copied_subworkflow = subworkflow.copy() copied_step.subworkflow = copied_subworkflow for subworkflow_step, copied_subworkflow_step in zip(subworkflow.steps, copied_subworkflow.steps): @@ -8676,8 +8668,7 @@ def set_handler(self, handler): def log_str(self): extra = "" - safe_id = getattr(self, "id", None) - if safe_id is not None: + if (safe_id := getattr(self, "id", None)) is not None: extra += f"id={safe_id}" else: extra += "unflushed" @@ -9622,8 +9613,7 @@ def load(cls, token): @classmethod def destroy(cls, token): - partial = cls.load(token) - if partial: + if partial := cls.load(token): session = cls.sa_session session.execute(delete(partial)) with transaction(session): diff --git a/lib/galaxy/model/dataset_collections/types/paired.py b/lib/galaxy/model/dataset_collections/types/paired.py index 3ac8d7da4d89..cfbd19c04343 100644 --- a/lib/galaxy/model/dataset_collections/types/paired.py +++ b/lib/galaxy/model/dataset_collections/types/paired.py @@ -19,15 +19,13 @@ def __init__(self): pass def generate_elements(self, elements): - forward_dataset = elements.get(FORWARD_IDENTIFIER) - reverse_dataset = elements.get(REVERSE_IDENTIFIER) - if forward_dataset: + if forward_dataset := elements.get(FORWARD_IDENTIFIER): left_association = DatasetCollectionElement( element=forward_dataset, element_identifier=FORWARD_IDENTIFIER, ) yield left_association - if reverse_dataset: + if reverse_dataset := elements.get(REVERSE_IDENTIFIER): right_association = DatasetCollectionElement( element=reverse_dataset, element_identifier=REVERSE_IDENTIFIER, diff --git a/lib/galaxy/model/item_attrs.py b/lib/galaxy/model/item_attrs.py index 998536e07b7d..e361d5458441 100644 --- a/lib/galaxy/model/item_attrs.py +++ b/lib/galaxy/model/item_attrs.py @@ -96,8 +96,7 @@ def add_item_annotation(self, db_session, user, item, annotation): return add_item_annotation(db_session, user, item, annotation) def delete_item_annotation(self, db_session, user, item): - annotation_assoc = get_item_annotation_obj(db_session, user, item) - if annotation_assoc: + if annotation_assoc := get_item_annotation_obj(db_session, user, item): db_session.delete(annotation_assoc) with transaction(db_session): db_session.commit() diff --git a/lib/galaxy/model/store/__init__.py b/lib/galaxy/model/store/__init__.py index e8a6c95fb377..e18fa9ba71a5 100644 --- a/lib/galaxy/model/store/__init__.py +++ b/lib/galaxy/model/store/__init__.py @@ -1968,8 +1968,7 @@ def push_metadata_files(self): def export_job(self, job: model.Job, tool=None, include_job_data=True): self.export_jobs([job], include_job_data=include_job_data) - tool_source = getattr(tool, "tool_source", None) - if tool_source: + if tool_source := getattr(tool, "tool_source", None): with open(os.path.join(self.export_directory, "tool.xml"), "w") as out: out.write(tool_source.to_string()) @@ -2288,8 +2287,7 @@ def record_job(job): return jobs_dict[job.id] = job - icja = job.implicit_collection_jobs_association - if icja: + if icja := job.implicit_collection_jobs_association: implicit_collection_jobs = icja.implicit_collection_jobs implicit_collection_jobs_dict[implicit_collection_jobs.id] = implicit_collection_jobs diff --git a/lib/galaxy/model/store/discover.py b/lib/galaxy/model/store/discover.py index c08579cc3725..ae7143a5ff47 100644 --- a/lib/galaxy/model/store/discover.py +++ b/lib/galaxy/model/store/discover.py @@ -1004,8 +1004,7 @@ def __init__(self, as_dict, collector: Optional[CollectorT], filename, path=None def designation(self): # If collecting nested collection, grab identifier_0, # identifier_1, etc... and join on : to build designation. - element_identifiers = self.raw_element_identifiers - if element_identifiers: + if element_identifiers := self.raw_element_identifiers: return ":".join(element_identifiers) elif "designation" in self.as_dict: return self.as_dict.get("designation") diff --git a/lib/galaxy/model/store/load_objects.py b/lib/galaxy/model/store/load_objects.py index 3c3fbed2bc82..7666187764ca 100644 --- a/lib/galaxy/model/store/load_objects.py +++ b/lib/galaxy/model/store/load_objects.py @@ -35,8 +35,7 @@ def main(argv=None): api_url = f"{galaxy_url.rstrip('/')}/api" api_key = args.key assert api_key - history_id = args.history_id - if history_id: + if history_id := args.history_id: create_url = f"{api_url}/histories/{history_id}/contents_from_store?key={api_key}" else: create_url = f"{api_url}/histories/from_store?key={api_key}" diff --git a/lib/galaxy/model/tags.py b/lib/galaxy/model/tags.py index 739d8528195d..a62051b79eef 100644 --- a/lib/galaxy/model/tags.py +++ b/lib/galaxy/model/tags.py @@ -147,9 +147,8 @@ def remove_item_tag(self, user: "User", item, tag_name: str): """Remove a tag from an item.""" self._ensure_user_owns_item(user, item) # Get item tag association. - item_tag_assoc = self._get_item_tag_assoc(user, item, tag_name) # Remove association. - if item_tag_assoc: + if item_tag_assoc := self._get_item_tag_assoc(user, item, tag_name): # Delete association. self.sa_session.delete(item_tag_assoc) item.tags.remove(item_tag_assoc) diff --git a/lib/galaxy/model/tool_shed_install/__init__.py b/lib/galaxy/model/tool_shed_install/__init__.py index d406935c79fb..1d41d5c3c677 100644 --- a/lib/galaxy/model/tool_shed_install/__init__.py +++ b/lib/galaxy/model/tool_shed_install/__init__.py @@ -242,10 +242,9 @@ def get_shed_config_dict(self, app: HasToolBox) -> DynamicToolConfDict: def get_tool_relative_path(self, app: HasToolBox): # This is a somewhat public function, used by data_manager_manual for instance - shed_conf_dict = self.get_shed_config_dict(app) tool_path = None relative_path = None - if shed_conf_dict: + if shed_conf_dict := self.get_shed_config_dict(app): tool_path = shed_conf_dict["tool_path"] relative_path = os.path.join( self.tool_shed_path_name, "repos", self.owner, self.name, self.installed_changeset_revision @@ -411,8 +410,7 @@ def missing_tool_dependencies(self): return missing_dependencies def repo_files_directory(self, app: HasToolBox): - repo_path = self.repo_path(app) - if repo_path: + if repo_path := self.repo_path(app): return os.path.join(repo_path, self.name) return None diff --git a/lib/galaxy/model/unittest_utils/model_testing_utils.py b/lib/galaxy/model/unittest_utils/model_testing_utils.py index f67a5bf81d64..4f0797143612 100644 --- a/lib/galaxy/model/unittest_utils/model_testing_utils.py +++ b/lib/galaxy/model/unittest_utils/model_testing_utils.py @@ -97,8 +97,7 @@ def url_factory(tmp_directory: str) -> Callable[[], DbUrl]: def url() -> DbUrl: database = _generate_unique_database_name() - connection_url = _get_connection_url() - if connection_url: + if connection_url := _get_connection_url(): return _make_postgres_db_url(DbUrl(connection_url), database) else: return _make_sqlite_db_url(tmp_directory, database) @@ -115,8 +114,7 @@ def url(tmp_directory: str) -> str: """ # TODO this duplication should be removed (see url_factory). database = _generate_unique_database_name() - connection_url = _get_connection_url() - if connection_url: + if connection_url := _get_connection_url(): return _make_postgres_db_url(DbUrl(connection_url), database) else: return _make_sqlite_db_url(tmp_directory, database) diff --git a/lib/galaxy/navigation/components.py b/lib/galaxy/navigation/components.py index 34b677a7e16b..77da115784ef 100644 --- a/lib/galaxy/navigation/components.py +++ b/lib/galaxy/navigation/components.py @@ -255,8 +255,7 @@ def resolve_component_locator(self, path: Optional[str] = None) -> LocatorT: def arguments() -> Tuple[str, Optional[Dict[str, str]], Optional[str]]: assert path - match = CALL_ARGUMENTS_RE.match(path) - if match: + if match := CALL_ARGUMENTS_RE.match(path): component_name = match.group("SUBCOMPONENT") expression = match.group("ARGS") rest = match.group("REST") diff --git a/lib/galaxy/queue_worker.py b/lib/galaxy/queue_worker.py index e133a9ee399b..3d80addf28dd 100644 --- a/lib/galaxy/queue_worker.py +++ b/lib/galaxy/queue_worker.py @@ -216,9 +216,8 @@ def reload_sanitize_allowlist(app): def recalculate_user_disk_usage(app, **kwargs): - user_id = kwargs.get("user_id", None) sa_session = app.model.context - if user_id: + if user_id := kwargs.get("user_id", None): user = sa_session.get(User, user_id) if user: user.calculate_and_set_disk_usage(app.object_store) diff --git a/lib/galaxy/schema/drs/Checksum.py b/lib/galaxy/schema/drs/Checksum.py index 24cae8b6cac2..afa32f958e05 100644 --- a/lib/galaxy/schema/drs/Checksum.py +++ b/lib/galaxy/schema/drs/Checksum.py @@ -14,6 +14,6 @@ class Model(BaseModel): checksum: str = Field(..., description="The hex-string encoded checksum for the data") type: str = Field( ..., - description="The digest method used to create the checksum.\nThe value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://www.iana.org/assignments/named-information/named-information.xhtml#hash-alg[IANA Named Information Hash Algorithm Registry]. Other values MAY be used, as long as implementors are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920].\nGA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future. Until then, if implementors do choose such an algorithm (e.g. because it's implemented by their storage provider), they SHOULD use an existing standard `type` value such as `md5`, `etag`, `crc32c`, `trunc512`, or `sha1`.", + description="The digest method used to create the checksum.\nThe value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://www.iana.org/assignments/named-information/named-information.xhtml#hash-alg[IANA Named Information Hash Algorithm Registry]. Other values MAY be used, as long as implementers are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920].\nGA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future. Until then, if implementers do choose such an algorithm (e.g. because it's implemented by their storage provider), they SHOULD use an existing standard `type` value such as `md5`, `etag`, `crc32c`, `trunc512`, or `sha1`.", example="sha-256", ) diff --git a/lib/galaxy/schema/drs/DrsObject.py b/lib/galaxy/schema/drs/DrsObject.py index 98c98ba36339..21e8e14fc088 100644 --- a/lib/galaxy/schema/drs/DrsObject.py +++ b/lib/galaxy/schema/drs/DrsObject.py @@ -21,7 +21,7 @@ class Checksum(BaseModel): checksum: str = Field(..., description="The hex-string encoded checksum for the data") type: str = Field( ..., - description="The digest method used to create the checksum.\nThe value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://www.iana.org/assignments/named-information/named-information.xhtml#hash-alg[IANA Named Information Hash Algorithm Registry]. Other values MAY be used, as long as implementors are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920].\nGA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future. Until then, if implementors do choose such an algorithm (e.g. because it's implemented by their storage provider), they SHOULD use an existing standard `type` value such as `md5`, `etag`, `crc32c`, `trunc512`, or `sha1`.", + description="The digest method used to create the checksum.\nThe value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://www.iana.org/assignments/named-information/named-information.xhtml#hash-alg[IANA Named Information Hash Algorithm Registry]. Other values MAY be used, as long as implementers are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920].\nGA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future. Until then, if implementers do choose such an algorithm (e.g. because it's implemented by their storage provider), they SHOULD use an existing standard `type` value such as `md5`, `etag`, `crc32c`, `trunc512`, or `sha1`.", example="sha-256", ) diff --git a/lib/galaxy/security/object_wrapper.py b/lib/galaxy/security/object_wrapper.py index 15352cfa9fdd..1c7176a29b16 100644 --- a/lib/galaxy/security/object_wrapper.py +++ b/lib/galaxy/security/object_wrapper.py @@ -165,8 +165,7 @@ def __do_wrap(value): except Exception: wrapped_class_name = value.__class__.__name__ wrapped_class = value.__class__ - value_mod = inspect.getmodule(value) - if value_mod: + if value_mod := inspect.getmodule(value): wrapped_class_name = f"{value_mod.__name__}.{wrapped_class_name}" wrapped_class_name = ( f"SafeStringWrapper__{wrapped_class_name}__{'__'.join(sorted(c.__name__ for c in no_wrap_classes))}" diff --git a/lib/galaxy/security/validate_user_input.py b/lib/galaxy/security/validate_user_input.py index a5400bd0ee02..29e052db4dc3 100644 --- a/lib/galaxy/security/validate_user_input.py +++ b/lib/galaxy/security/validate_user_input.py @@ -129,8 +129,7 @@ def validate_publicname(trans, publicname, user=None): """ if user and user.username == publicname: return "" - message = validate_publicname_str(publicname) - if message: + if message := validate_publicname_str(publicname): return message stmt = select(trans.app.model.User).filter_by(username=publicname).limit(1) diff --git a/lib/galaxy/selenium/axe_results.py b/lib/galaxy/selenium/axe_results.py index 3f2707644348..fae862c61812 100644 --- a/lib/galaxy/selenium/axe_results.py +++ b/lib/galaxy/selenium/axe_results.py @@ -107,8 +107,7 @@ def assert_passes(self, id: str) -> None: def assert_does_not_violate(self, id: str) -> None: violations = self._json["violations"] - result = _check_list_for_id(violations, id) - if result: + if result := _check_list_for_id(violations, id): violation = Violation(result) raise AssertionError(violation.message) diff --git a/lib/galaxy/selenium/has_driver.py b/lib/galaxy/selenium/has_driver.py index 5792cec3d6fd..de7f904edcbd 100644 --- a/lib/galaxy/selenium/has_driver.py +++ b/lib/galaxy/selenium/has_driver.py @@ -286,8 +286,7 @@ def prepend_timeout_message( self, timeout_exception: SeleniumTimeoutException, message: str ) -> SeleniumTimeoutException: msg = message - timeout_msg = timeout_exception.msg - if timeout_msg: + if timeout_msg := timeout_exception.msg: msg += f" {timeout_msg}" return SeleniumTimeoutException( msg=msg, diff --git a/lib/galaxy/selenium/navigates_galaxy.py b/lib/galaxy/selenium/navigates_galaxy.py index f156f348703d..246955f8fc50 100644 --- a/lib/galaxy/selenium/navigates_galaxy.py +++ b/lib/galaxy/selenium/navigates_galaxy.py @@ -564,10 +564,9 @@ def published_grid_search_for(self, search_term=None): ) def get_logged_in_user(self) -> Optional[Dict[str, Any]]: - user_dict = self.api_get("users/current") # for user's not logged in - this just returns a {} so lets # key this on an id being available? - if "id" in user_dict: + if "id" in (user_dict := self.api_get("users/current")): return user_dict else: return None @@ -586,8 +585,7 @@ def get_api_key(self, force=False) -> Optional[str]: return self.api_post(f"users/{user_id}/api_key") def get_user_id(self) -> Optional[str]: - user = self.get_logged_in_user() - if user is not None: + if (user := self.get_logged_in_user()) is not None: return user["id"] else: return None @@ -2076,8 +2074,7 @@ def run_tour_step(self, step, step_index, tour_callback): element = self.tour_wait_for_element_present(element_str) assert element is not None - textinsert = step.get("textinsert", None) - if textinsert is not None: + if (textinsert := step.get("textinsert", None)) is not None: element.send_keys(textinsert) tour_callback.handle_step(step, step_index) diff --git a/lib/galaxy/selenium/sizzle.py b/lib/galaxy/selenium/sizzle.py index 8716a2c55b92..94d9e903b6ae 100644 --- a/lib/galaxy/selenium/sizzle.py +++ b/lib/galaxy/selenium/sizzle.py @@ -68,8 +68,7 @@ def find_element_by_sizzle(driver, sizzle_selector: str): :param sizzle_selector: The sizzle selector to use when finding element. """ - elements = driver.find_elements_by_sizzle(sizzle_selector) - if elements: + if elements := driver.find_elements_by_sizzle(sizzle_selector): return elements[0] else: raise NoSuchElementException(f"Unable to locate element by Sizzle: {sizzle_selector}") diff --git a/lib/galaxy/selenium/smart_components.py b/lib/galaxy/selenium/smart_components.py index 9400a706f1aa..9a6c2c61b257 100644 --- a/lib/galaxy/selenium/smart_components.py +++ b/lib/galaxy/selenium/smart_components.py @@ -125,8 +125,7 @@ def data_value(self, attribute: str): return attribute_value def assert_data_value(self, attribute: str, expected_value: str): - actual_value = self.data_value(attribute) - if actual_value != expected_value: + if (actual_value := self.data_value(attribute)) != expected_value: message = f"Expected data-{attribute} to have value [{expected_value}] but had value [{actual_value}]" raise AssertionError(message) diff --git a/lib/galaxy/tool_shed/galaxy_install/metadata/installed_repository_metadata_manager.py b/lib/galaxy/tool_shed/galaxy_install/metadata/installed_repository_metadata_manager.py index f8fa39bf80bb..aea14cacdd93 100644 --- a/lib/galaxy/tool_shed/galaxy_install/metadata/installed_repository_metadata_manager.py +++ b/lib/galaxy/tool_shed/galaxy_install/metadata/installed_repository_metadata_manager.py @@ -152,10 +152,9 @@ def reset_metadata_on_selected_repositories(self, user, **kwd): Inspect the repository changelog to reset metadata for all appropriate changeset revisions. This method is called from both Galaxy and the Tool Shed. """ - repository_ids = util.listify(kwd.get("repository_ids", None)) message = "" status = "done" - if repository_ids: + if repository_ids := util.listify(kwd.get("repository_ids", None)): successful_count = 0 unsuccessful_count = 0 for repository_id in repository_ids: diff --git a/lib/galaxy/tool_shed/galaxy_install/tools/data_manager.py b/lib/galaxy/tool_shed/galaxy_install/tools/data_manager.py index d3cce73744b5..f2cbcdc072af 100644 --- a/lib/galaxy/tool_shed/galaxy_install/tools/data_manager.py +++ b/lib/galaxy/tool_shed/galaxy_install/tools/data_manager.py @@ -52,8 +52,7 @@ def _data_manager_config_elems_to_xml_file(self, config_elems: List[Element], co Persist the current in-memory list of config_elems to a file named by the value of config_filename. """ - data_managers_path = self.data_managers_path - if data_managers_path: + if data_managers_path := self.data_managers_path: root_str = f'' else: root_str = '' diff --git a/lib/galaxy/tool_shed/galaxy_install/tools/tool_panel_manager.py b/lib/galaxy/tool_shed/galaxy_install/tools/tool_panel_manager.py index c68ba7fe4be3..e4d1dc3c19bd 100644 --- a/lib/galaxy/tool_shed/galaxy_install/tools/tool_panel_manager.py +++ b/lib/galaxy/tool_shed/galaxy_install/tools/tool_panel_manager.py @@ -243,10 +243,9 @@ def generate_tool_panel_dict_from_shed_tool_conf_entries(self, repository) -> Di shed_tool_conf, tool_path, relative_install_dir = get_tool_panel_config_tool_path_install_dir( self.app, repository ) - metadata = repository.metadata_ # Create a dictionary of tool guid and tool config file name for each tool in the repository. guids_and_configs = {} - if "tools" in metadata: + if "tools" in (metadata := repository.metadata_): for tool_dict in metadata["tools"]: guid = tool_dict["guid"] tool_config = tool_dict["tool_config"] diff --git a/lib/galaxy/tool_shed/metadata/metadata_generator.py b/lib/galaxy/tool_shed/metadata/metadata_generator.py index d797d1eba98c..71d3f666f7ad 100644 --- a/lib/galaxy/tool_shed/metadata/metadata_generator.py +++ b/lib/galaxy/tool_shed/metadata/metadata_generator.py @@ -135,8 +135,7 @@ def _generate_data_manager_metadata( tool_conf_name = os.path.join(tool_path, tool_conf_name) tools[tool_conf_name] = tool root = tree.getroot() - data_manager_tool_path = root.get("tool_path", None) - if data_manager_tool_path: + if data_manager_tool_path := root.get("tool_path", None): relative_data_manager_dir = os.path.join(relative_data_manager_dir, data_manager_tool_path) for i, data_manager_elem in enumerate(root.findall("data_manager")): tool_file = data_manager_elem.get("tool_file", None) diff --git a/lib/galaxy/tool_shed/util/dependency_display.py b/lib/galaxy/tool_shed/util/dependency_display.py index f4c2ef30a60a..61b427718250 100644 --- a/lib/galaxy/tool_shed/util/dependency_display.py +++ b/lib/galaxy/tool_shed/util/dependency_display.py @@ -197,8 +197,7 @@ def populate_containers_dict_from_repository_metadata(self, repository): when displaying repository dependencies for installed repositories and when displaying them for uninstalled repositories that are being reinstalled. """ - metadata = repository.metadata_ - if metadata: + if metadata := repository.metadata_: irm = InstalledRepositoryManager(self.app) # Handle repository dependencies. ( diff --git a/lib/galaxy/tool_util/deps/conda_util.py b/lib/galaxy/tool_util/deps/conda_util.py index f91203923cd2..9808bd788010 100644 --- a/lib/galaxy/tool_util/deps/conda_util.py +++ b/lib/galaxy/tool_util/deps/conda_util.py @@ -254,7 +254,7 @@ def exec_command(self, operation: str, args: List[str], stdout_path: Optional[st if self.condarc_override: env["CONDARC"] = self.condarc_override cmd_string = shlex_join(cmd) - kwds = dict() + kwds: Dict[str, Any] = dict() try: if stdout_path: kwds["stdout"] = open(stdout_path, "w") diff --git a/lib/galaxy/tools/__init__.py b/lib/galaxy/tools/__init__.py index 3168f6a52e13..d94f5b4d3c0f 100644 --- a/lib/galaxy/tools/__init__.py +++ b/lib/galaxy/tools/__init__.py @@ -340,8 +340,7 @@ class ToolNotFoundException(Exception): def create_tool_from_source(app, tool_source, config_file=None, **kwds): # Allow specifying a different tool subclass to instantiate - tool_module = tool_source.parse_tool_module() - if tool_module is not None: + if (tool_module := tool_source.parse_tool_module()) is not None: module, cls = tool_module mod = __import__(module, globals(), locals(), [cls]) ToolClass = getattr(mod, cls) @@ -444,8 +443,7 @@ def __init__(self, config_filenames, tool_root_dir, app, save_integrated_tool_pa save_integrated_tool_panel=save_integrated_tool_panel, ) - old_toolbox = getattr(app, "toolbox", None) - if old_toolbox: + if old_toolbox := getattr(app, "toolbox", None): self.dependency_manager = old_toolbox.dependency_manager else: self._init_dependency_manager() @@ -826,8 +824,7 @@ def __init__( self.job_search = self.app.job_search def remove_from_cache(self): - source_path = self.tool_source.source_path - if source_path: + if source_path := self.tool_source.source_path: for region in self.app.toolbox.cache_regions.values(): region.delete(source_path) @@ -1093,8 +1090,7 @@ def parse(self, tool_source: ToolSource, guid=None, dynamic=False): # Versioning for tools self.version_string_cmd = None - version_command = tool_source.parse_version_command() - if version_command is not None: + if (version_command := tool_source.parse_version_command()) is not None: self.version_string_cmd = version_command.strip() version_cmd_interpreter = tool_source.parse_version_command_interpreter() @@ -1261,8 +1257,7 @@ def __parse_legacy_features(self, tool_source): raise # User interface hints - uihints_elem = root.find("uihints") - if uihints_elem is not None: + if (uihints_elem := root.find("uihints")) is not None: for key, value in uihints_elem.attrib.items(): self.uihints[key] = value @@ -1272,8 +1267,7 @@ def __parse_config_files(self, tool_source): return root = tool_source.root - conf_parent_elem = root.find("configfiles") - if conf_parent_elem is not None: + if (conf_parent_elem := root.find("configfiles")) is not None: inputs_elem = conf_parent_elem.find("inputs") if inputs_elem is not None: name = inputs_elem.get("name") @@ -1300,13 +1294,11 @@ def __parse_trackster_conf(self, tool_source): return # Trackster configuration. - trackster_conf = tool_source.root.find("trackster_conf") - if trackster_conf is not None: + if (trackster_conf := tool_source.root.find("trackster_conf")) is not None: self.trackster_conf = TracksterConfig.parse(trackster_conf) def parse_tests(self): - tests_source = self.tool_source - if tests_source: + if tests_source := self.tool_source: try: self.__tests = json.dumps([t.to_dict() for t in parse_tests(self, tests_source)], indent=None) except Exception: @@ -1335,9 +1327,8 @@ def _repository_dir(self): return repository_base_dir def test_data_path(self, filename): - repository_dir = self._repository_dir test_data = None - if repository_dir: + if repository_dir := self._repository_dir: test_data = self.__walk_test_data(dir=repository_dir, filename=filename) else: if self.tool_dir: @@ -1380,8 +1371,7 @@ def tool_provided_metadata(self, job_wrapper): def parse_command(self, tool_source): """ """ # Command line (template). Optional for tools that do not invoke a local program - command = tool_source.parse_command() - if command is not None: + if (command := tool_source.parse_command()) is not None: self.command = command.lstrip() # get rid of leading whitespace # Must pre-pend this AFTER processing the cheetah command template self.interpreter = tool_source.parse_interpreter() @@ -1637,8 +1627,7 @@ def parse_param_elem(self, input_source: InputSource, enctypes, context) -> Tool enctypes. """ param = ToolParameter.build(self, input_source) - param_enctype = param.get_required_enctype() - if param_enctype: + if param_enctype := param.get_required_enctype(): enctypes.add(param_enctype) # If parameter depends on any other paramters, we must refresh the # form when it changes @@ -2343,8 +2332,7 @@ def to_archive(self): if os.path.exists(os.path.join(tool_path, "Dockerfile")): tarball_files.append((os.path.join(tool_path, "Dockerfile"), "Dockerfile")) # Find tests, and check them for test data. - tests = tool.tests - if tests is not None: + if (tests := tool.tests) is not None: for test in tests: # Add input file tuples to the list. for input in test.inputs: @@ -2651,8 +2639,7 @@ def map_to_history(value): source = hdca_source_dict else: return None - key = f"{value.hid}_{id}" - if key in source: + if (key := f"{value.hid}_{id}") in source: return source[key] elif id in source: return source[id] @@ -3373,10 +3360,9 @@ def produce_outputs(self, trans, out_data, output_collections, incoming, history for incoming_repeat in incoming["inputs"]: input_lists.append(incoming_repeat["input"]) - advanced = incoming.get("advanced", None) dupl_actions = "keep_first" suffix_pattern = None - if advanced is not None: + if (advanced := incoming.get("advanced", None)) is not None: dupl_actions = advanced["conflict"]["duplicate_options"] if dupl_actions in ["suffix_conflict", "suffix_every", "suffix_conflict_rest"]: diff --git a/lib/galaxy/tools/actions/model_operations.py b/lib/galaxy/tools/actions/model_operations.py index 5b71f55c0542..a1e7230b9eeb 100644 --- a/lib/galaxy/tools/actions/model_operations.py +++ b/lib/galaxy/tools/actions/model_operations.py @@ -126,8 +126,7 @@ def _produce_outputs( hdca_tags=hdca_tags, tag_handler=tag_handler, ) - mapped_over_elements = output_collections.dataset_collection_elements - if mapped_over_elements: + if mapped_over_elements := output_collections.dataset_collection_elements: for name, value in out_data.items(): if name in mapped_over_elements: value.visible = False diff --git a/lib/galaxy/tools/actions/upload_common.py b/lib/galaxy/tools/actions/upload_common.py index 696d21b8de38..a345abde954a 100644 --- a/lib/galaxy/tools/actions/upload_common.py +++ b/lib/galaxy/tools/actions/upload_common.py @@ -196,8 +196,7 @@ def __new_library_upload(trans, cntrller, uploaded_dataset, library_bunch, tag_h tag_from_filename = os.path.splitext(os.path.basename(uploaded_dataset.name))[0] tag_handler.apply_item_tag(item=ldda, user=trans.user, name="name", value=tag_from_filename, flush=False) - tags_list = uploaded_dataset.get("tags", False) - if tags_list: + if tags_list := uploaded_dataset.get("tags", False): for tag in tags_list: tag_handler.apply_item_tag(item=ldda, user=trans.user, name="name", value=tag, flush=False) diff --git a/lib/galaxy/tools/data_fetch.py b/lib/galaxy/tools/data_fetch.py index e3db469dc99f..19e272ca4b6b 100644 --- a/lib/galaxy/tools/data_fetch.py +++ b/lib/galaxy/tools/data_fetch.py @@ -90,9 +90,8 @@ def _fetch_target(upload_config: "UploadConfig", target): assert destination, "No destination defined." def expand_elements_from(target_or_item): - elements_from = target_or_item.get("elements_from", None) items = None - if elements_from: + if elements_from := target_or_item.get("elements_from", None): if elements_from == "archive": decompressed_directory = _decompress_target(upload_config, target_or_item) items = _directory_to_items(decompressed_directory) @@ -139,11 +138,10 @@ def _copy_and_validate_simple_attributes(src_item, target_metadata): info = src_item.get("info", None) created_from_basename = src_item.get("created_from_basename", None) tags = src_item.get("tags", []) - object_id = src_item.get("object_id", None) if info is not None: target_metadata["info"] = info - if object_id is not None: + if (object_id := src_item.get("object_id", None)) is not None: target_metadata["object_id"] = object_id if tags: target_metadata["tags"] = tags diff --git a/lib/galaxy/tools/error_reports/plugins/gitlab.py b/lib/galaxy/tools/error_reports/plugins/gitlab.py index 9127deb2943c..f85c3b2fd2e0 100644 --- a/lib/galaxy/tools/error_reports/plugins/gitlab.py +++ b/lib/galaxy/tools/error_reports/plugins/gitlab.py @@ -247,8 +247,7 @@ def _create_issue(self, issue_cache_key, error_title, error_message, project, ** issue_data = {"title": error_title, "description": error_message} # Assign the user to the issue - gl_userid = kwargs.get("gl_userid", None) - if gl_userid is not None: + if (gl_userid := kwargs.get("gl_userid", None)) is not None: issue_data["assignee_ids"] = [gl_userid] # Create the issue on GitLab diff --git a/lib/galaxy/tools/evaluation.py b/lib/galaxy/tools/evaluation.py index d06af3b01d53..2e0c40c2c3ff 100644 --- a/lib/galaxy/tools/evaluation.py +++ b/lib/galaxy/tools/evaluation.py @@ -613,8 +613,7 @@ def _build_command_line(self): self.command_line = command_line def _build_version_command(self): - version_string_cmd_raw = self.tool.version_string_cmd - if version_string_cmd_raw: + if version_string_cmd_raw := self.tool.version_string_cmd: version_command_template = string.Template(version_string_cmd_raw) version_command = version_command_template.safe_substitute( {"__tool_directory__": self.compute_environment.tool_directory()} @@ -694,12 +693,10 @@ def _build_environment_variables(self): environment_variable["job_directory_path"] = config_filename environment_variables.append(environment_variable) - home_dir = self.compute_environment.home_directory() - tmp_dir = self.compute_environment.tmp_directory() - if home_dir: + if home_dir := self.compute_environment.home_directory(): environment_variable = dict(name="HOME", value=f'"{home_dir}"', raw=True) environment_variables.append(environment_variable) - if tmp_dir: + if tmp_dir := self.compute_environment.tmp_directory(): for tmp_directory_var in self.tool.tmp_directory_vars: environment_variable = dict(name=tmp_directory_var, value=f'"{tmp_dir}"', raw=True) environment_variables.append(environment_variable) @@ -806,8 +803,7 @@ def _history(self): @property def _user(self): - history = self._history - if history: + if history := self._history: return history.user else: return self.job.user diff --git a/lib/galaxy/tools/execute.py b/lib/galaxy/tools/execute.py index 26d29598c740..e1ac8f9f6e25 100644 --- a/lib/galaxy/tools/execute.py +++ b/lib/galaxy/tools/execute.py @@ -140,8 +140,7 @@ def execute_single_job(execution_slice, completed_job, skip=False): execution_tracker.record_error(result) tool_action = tool.tool_action - check_inputs_ready = getattr(tool_action, "check_inputs_ready", None) - if check_inputs_ready: + if check_inputs_ready := getattr(tool_action, "check_inputs_ready", None): for params in execution_tracker.param_combinations: # This will throw an exception if the tool is not ready. try: diff --git a/lib/galaxy/tools/imp_exp/export_history.py b/lib/galaxy/tools/imp_exp/export_history.py index 4127d11770bb..340c19a203d4 100644 --- a/lib/galaxy/tools/imp_exp/export_history.py +++ b/lib/galaxy/tools/imp_exp/export_history.py @@ -40,9 +40,6 @@ def main(argv=None): ) parser.add_option("--file-sources", type=str, help="file sources json") (options, args) = parser.parse_args(argv) - galaxy_version = options.galaxy_version - if galaxy_version is None: - galaxy_version = "19.05" gzip = bool(options.gzip) assert len(args) >= 2 diff --git a/lib/galaxy/tools/parameters/basic.py b/lib/galaxy/tools/parameters/basic.py index ef6a7a19613c..af3e537a1beb 100644 --- a/lib/galaxy/tools/parameters/basic.py +++ b/lib/galaxy/tools/parameters/basic.py @@ -110,8 +110,7 @@ def is_runtime_context(trans, other_values): def parse_dynamic_options(param, input_source): - options_elem = input_source.parse_dynamic_options_elem() - if options_elem is not None: + if (options_elem := input_source.parse_dynamic_options_elem()) is not None: return dynamic_options.DynamicOptions(options_elem, param) return None @@ -180,8 +179,7 @@ def __init__(self, tool, input_source, context=None): self.is_dynamic = False self.label = input_source.parse_label() self.help = input_source.parse_help() - sanitizer_elem = input_source.parse_sanitizer_elem() - if sanitizer_elem is not None: + if (sanitizer_elem := input_source.parse_sanitizer_elem()) is not None: self.sanitizer = ToolParameterSanitizer.from_element(sanitizer_elem) else: self.sanitizer = None @@ -1618,8 +1616,7 @@ def recurse_option_elems(cur_options, option_elems): self.display = elem.get("display", None) self.hierarchy = elem.get("hierarchy", "exact") # exact or recurse self.separator = elem.get("separator", ",") - from_file = elem.get("from_file", None) - if from_file: + if from_file := elem.get("from_file", None): if not os.path.isabs(from_file): from_file = os.path.join(tool.app.config.tool_data_path, from_file) elem = XML(f"{open(from_file).read()}") @@ -1906,8 +1903,7 @@ def get_initial_value(self, trans, other_values): return RuntimeValue() if self.optional: return None - history = trans.history - if history is not None: + if (history := trans.history) is not None: dataset_matcher_factory = get_dataset_matcher_factory(trans) dataset_matcher = dataset_matcher_factory.dataset_matcher(self, other_values) if isinstance(self, DataToolParameter): @@ -2651,8 +2647,7 @@ def __init__(self, tool, input_source, context=None): def to_dict(self, trans, other_values=None): other_values = other_values or {} d = ToolParameter.to_dict(self, trans) - target_name = self.data_ref - if target_name in other_values: + if (target_name := self.data_ref) in other_values: target = other_values[target_name] if not is_runtime_value(target): d["target"] = { diff --git a/lib/galaxy/tools/parameters/dataset_matcher.py b/lib/galaxy/tools/parameters/dataset_matcher.py index c7fcf12fc759..e810abf538ec 100644 --- a/lib/galaxy/tools/parameters/dataset_matcher.py +++ b/lib/galaxy/tools/parameters/dataset_matcher.py @@ -246,8 +246,7 @@ def __valid_element(self, element): if element.ldda: return False - child_collection = element.child_collection - if child_collection: + if child_collection := element.child_collection: return self.dataset_collection_match(child_collection) hda = element.hda diff --git a/lib/galaxy/tools/parameters/grouping.py b/lib/galaxy/tools/parameters/grouping.py index 4f5795664455..ad18c4d55958 100644 --- a/lib/galaxy/tools/parameters/grouping.py +++ b/lib/galaxy/tools/parameters/grouping.py @@ -412,8 +412,7 @@ def get_file_name(file_name): return Bunch(type=None, path=None, name=None) def get_url_paste_urls_or_filename(group_incoming, override_name=None, override_info=None): - url_paste_file = group_incoming.get("url_paste", None) - if url_paste_file is not None: + if (url_paste_file := group_incoming.get("url_paste", None)) is not None: url_paste = open(url_paste_file).read() def start_of_url(content): diff --git a/lib/galaxy/tools/test.py b/lib/galaxy/tools/test.py index ea84995943aa..41921dd4eaea 100644 --- a/lib/galaxy/tools/test.py +++ b/lib/galaxy/tools/test.py @@ -369,8 +369,7 @@ def __init__(self, name, index=None, parent_context=None): def for_state(self): name = self.name if self.index is None else "%s_%d" % (self.name, self.index) - parent_for_state = self.parent_context.for_state() - if parent_for_state: + if parent_for_state := self.parent_context.for_state(): return f"{parent_for_state}|{name}" else: return name diff --git a/lib/galaxy/tools/wrappers.py b/lib/galaxy/tools/wrappers.py index 9e59536c6529..25e8ce9a9d4e 100644 --- a/lib/galaxy/tools/wrappers.py +++ b/lib/galaxy/tools/wrappers.py @@ -792,9 +792,8 @@ def __init__(self, input_datasets: Optional[Dict[str, Any]] = None) -> None: self.identifier_key_dict = {} def identifier(self, dataset_value: str, input_values: Dict[str, str]) -> Optional[str]: - identifier_key = self.identifier_key_dict.get(dataset_value, None) element_identifier = None - if identifier_key: + if identifier_key := self.identifier_key_dict.get(dataset_value, None): element_identifier = input_values.get(identifier_key, None) return element_identifier diff --git a/lib/galaxy/util/__init__.py b/lib/galaxy/util/__init__.py index 2db3e454bb22..af5c405d3609 100644 --- a/lib/galaxy/util/__init__.py +++ b/lib/galaxy/util/__init__.py @@ -57,7 +57,7 @@ remap, ) from requests.adapters import HTTPAdapter -from requests.packages.urllib3.util.retry import Retry +from requests.packages.urllib3.util.retry import Retry # type: ignore[import-untyped] from typing_extensions import Literal try: diff --git a/lib/galaxy/util/commands.py b/lib/galaxy/util/commands.py index 321dd71f2fad..6238431c0e44 100644 --- a/lib/galaxy/util/commands.py +++ b/lib/galaxy/util/commands.py @@ -55,7 +55,7 @@ def redirect_aware_commmunicate(p, sys=_sys): return out, err -def shell(cmds: Union[List[str], str], env: Optional[Dict[str, str]] = None, **kwds: Dict[str, Any]) -> int: +def shell(cmds: Union[List[str], str], env: Optional[Dict[str, str]] = None, **kwds: Any) -> int: """Run shell commands with `shell_process` and wait.""" sys = kwds.get("sys", _sys) assert sys is not None @@ -68,9 +68,7 @@ def shell(cmds: Union[List[str], str], env: Optional[Dict[str, str]] = None, **k return p.wait() -def shell_process( - cmds: Union[List[str], str], env: Optional[Dict[str, str]] = None, **kwds: Dict[str, Any] -) -> subprocess.Popen: +def shell_process(cmds: Union[List[str], str], env: Optional[Dict[str, str]] = None, **kwds: Any) -> subprocess.Popen: """A high-level method wrapping subprocess.Popen. Handles details such as environment extension and in process I/O diff --git a/lib/galaxy/util/resources.py b/lib/galaxy/util/resources.py index a16a78f7202b..071921a68b77 100644 --- a/lib/galaxy/util/resources.py +++ b/lib/galaxy/util/resources.py @@ -1,24 +1,38 @@ """Provide a consistent interface into and utilities for importlib file resources. """ -try: - from importlib.abc import Traversable # type: ignore[attr-defined] - from importlib.resources import files # type: ignore[attr-defined] -except ImportError: - # Python < 3.9 - from importlib_resources import files # type: ignore[no-redef] - from importlib_resources.abc import Traversable # type: ignore[no-redef] - - -def resource_path(package_or_requirement, resource_name): +import sys + +if sys.version_info >= (3, 12): + from importlib.resources import ( + Anchor, + as_file, + files, + ) + from importlib.resources.abc import Traversable +elif sys.version_info >= (3, 9): + from importlib.abc import Traversable + from importlib.resources import ( + as_file, + files, + Package as Anchor, + ) +else: + from importlib_resources import ( + as_file, + files, + Package as Anchor, + ) + from importlib_resources.abc import Traversable + + +def resource_path(package_or_requirement: Anchor, resource_name: str) -> Traversable: """ - Return specified resource as a string. - - Replacement function for pkg_resources.resource_string, but returns unicode string instead of bytestring. + Return specified resource as a Traversable. """ return files(package_or_requirement).joinpath(resource_name) -def resource_string(package_or_requirement, resource_name) -> str: +def resource_string(package_or_requirement: Anchor, resource_name: str) -> str: """ Return specified resource as a string. @@ -28,6 +42,7 @@ def resource_string(package_or_requirement, resource_name) -> str: __all__ = ( + "as_file", "files", "resource_string", "resource_path", diff --git a/lib/galaxy/visualization/data_providers/genome.py b/lib/galaxy/visualization/data_providers/genome.py index 7d01fd4f3558..0ef56f6b9810 100644 --- a/lib/galaxy/visualization/data_providers/genome.py +++ b/lib/galaxy/visualization/data_providers/genome.py @@ -1233,8 +1233,7 @@ def summarize_region(bbi, chrom, start, end, num_points): # Get summary; this samples at intervals of length # (end - start)/num_points -- i.e. drops any fractional component # of interval length. - summary = _summarize_bbi(bbi, chrom, start, end, num_points) - if summary: + if summary := _summarize_bbi(bbi, chrom, start, end, num_points): # mean = summary.sum_data / summary.valid_count # Standard deviation by bin, not yet used diff --git a/lib/galaxy/visualization/plugins/config_parser.py b/lib/galaxy/visualization/plugins/config_parser.py index c2867c13439b..85b1ccc79be9 100644 --- a/lib/galaxy/visualization/plugins/config_parser.py +++ b/lib/galaxy/visualization/plugins/config_parser.py @@ -148,18 +148,15 @@ def parse_visualization(self, xml_tree): # consider unifying the above into its own element and parsing method # load optional custom configuration specifiers - specs_section = xml_tree.find("specs") - if specs_section is not None: + if (specs_section := xml_tree.find("specs")) is not None: returned["specs"] = DictParser(specs_section) # load group specifiers - groups_section = xml_tree.find("groups") - if groups_section is not None: + if (groups_section := xml_tree.find("groups")) is not None: returned["groups"] = ListParser(groups_section) # load settings specifiers - settings_section = xml_tree.find("settings") - if settings_section is not None: + if (settings_section := xml_tree.find("settings")) is not None: returned["settings"] = ListParser(settings_section) return returned @@ -226,8 +223,7 @@ def parse(self, xml_tree): # to_params (optional, 0 or more) - tells the registry to set certain params based on the model_clas, tests returned["to_params"] = {} - to_params = self.parse_to_params(xml_tree.findall("to_param")) - if to_params: + if to_params := self.parse_to_params(xml_tree.findall("to_param")): returned["to_params"] = to_params return returned @@ -464,16 +460,14 @@ def parse(self, xml_tree): # NOTE: the interpretation of this list is deferred till parsing and based on param type # e.g. it could be 'val in constrain_to', or 'constrain_to is min, max for number', etc. # TODO: currently unused - constrain_to = xml_tree.get("constrain_to") - if constrain_to: + if constrain_to := xml_tree.get("constrain_to"): returned["constrain_to"] = constrain_to.split(",") # is the param a comma-separated-value list? returned["csv"] = xml_tree.get("csv") == "true" # remap keys in the params/query string to the var names used in the template - var_name_in_template = xml_tree.get("var_name_in_template") - if var_name_in_template: + if var_name_in_template := xml_tree.get("var_name_in_template"): returned["var_name_in_template"] = var_name_in_template return returned diff --git a/lib/galaxy/visualization/plugins/registry.py b/lib/galaxy/visualization/plugins/registry.py index ff050ec0f504..41b0cf2eeaed 100644 --- a/lib/galaxy/visualization/plugins/registry.py +++ b/lib/galaxy/visualization/plugins/registry.py @@ -247,8 +247,7 @@ def get_visualization(self, trans, visualization_name, target_object): `visualization_name` if it's applicable to `target_object` or `None` if it's not. """ - visualization = self.plugins.get(visualization_name, None) - if visualization is not None: + if (visualization := self.plugins.get(visualization_name, None)) is not None: data_sources = visualization.config["data_sources"] for data_source in data_sources: model_class = data_source["model_class"] diff --git a/lib/galaxy/web/framework/__init__.py b/lib/galaxy/web/framework/__init__.py index a62442893e9b..f08ff3137507 100644 --- a/lib/galaxy/web/framework/__init__.py +++ b/lib/galaxy/web/framework/__init__.py @@ -26,9 +26,8 @@ def legacy_url_for(mapper, *args, **kwargs) -> str: Re-establishes the mapper for legacy WSGI routes. """ rc = request_config() - environ = kwargs.pop("environ", None) rc.mapper = mapper - if environ: + if environ := kwargs.pop("environ", None): rc.environ = environ if hasattr(rc, "using_request_local"): rc.request_local = lambda: rc diff --git a/lib/galaxy/web/framework/base.py b/lib/galaxy/web/framework/base.py index baa1a07128e4..9c2b777257a7 100644 --- a/lib/galaxy/web/framework/base.py +++ b/lib/galaxy/web/framework/base.py @@ -426,8 +426,7 @@ def remote_hostname(self): @lazy_property def cookies(self): cookies = SimpleCookie() - cookie_header = self.environ.get("HTTP_COOKIE") - if cookie_header: + if cookie_header := self.environ.get("HTTP_COOKIE"): all_cookies = webob.cookies.parse_cookie(cookie_header) galaxy_cookies = {k.decode(): v.decode() for k, v in all_cookies if k.startswith(b"galaxy")} if galaxy_cookies: diff --git a/lib/galaxy/web/framework/decorators.py b/lib/galaxy/web/framework/decorators.py index 1db78d104542..1b00a59bf32d 100644 --- a/lib/galaxy/web/framework/decorators.py +++ b/lib/galaxy/web/framework/decorators.py @@ -236,8 +236,7 @@ def __extract_payload_from_request(trans, func, kwargs): # should ideally be in reverse, with the if clause being a check for application/json and the else clause assuming a standard encoding # such as multipart/form-data. Leaving it as is for backward compatibility, just in case. payload = loads(unicodify(trans.request.body)) - run_as = trans.request.headers.get("run-as") - if run_as: + if run_as := trans.request.headers.get("run-as"): payload["run_as"] = run_as return payload @@ -396,8 +395,7 @@ def validation_error_to_message_exception(e: ValidationError) -> MessageExceptio def api_error_message(trans, **kwds): - exception = kwds.get("exception", None) - if exception: + if exception := kwds.get("exception", None): # If we are passed a MessageException use err_msg. default_error_code = getattr(exception, "err_code", error_codes.UNKNOWN) default_error_message = getattr(exception, "err_msg", default_error_code.default_error_message) diff --git a/lib/galaxy/web/framework/helpers/grids.py b/lib/galaxy/web/framework/helpers/grids.py index 96e7114786ca..c4fd321c1d65 100644 --- a/lib/galaxy/web/framework/helpers/grids.py +++ b/lib/galaxy/web/framework/helpers/grids.py @@ -722,9 +722,8 @@ def __call__(self, trans, **kwargs): # Maintain sort state in generated urls extra_url_args = {} # Determine whether use_default_filter flag is set. - use_default_filter_str = kwargs.get("use_default_filter") use_default_filter = False - if use_default_filter_str: + if use_default_filter_str := kwargs.get("use_default_filter"): use_default_filter = use_default_filter_str.lower() == "true" # Process filtering arguments to (a) build a query that represents the filter and (b) build a # dictionary that denotes the current filter. diff --git a/lib/galaxy/web/framework/middleware/static.py b/lib/galaxy/web/framework/middleware/static.py index 1ac00814c577..d46ff6af592c 100644 --- a/lib/galaxy/web/framework/middleware/static.py +++ b/lib/galaxy/web/framework/middleware/static.py @@ -55,8 +55,7 @@ def __call__(self, environ, start_response): return self.__class__(full)(environ, start_response) if environ.get("PATH_INFO") and environ.get("PATH_INFO") != "/": return self.error_extra_path(environ, start_response) - if_none_match = environ.get("HTTP_IF_NONE_MATCH") - if if_none_match: + if if_none_match := environ.get("HTTP_IF_NONE_MATCH"): mytime = os.stat(full).st_mtime if str(mytime) == if_none_match: headers: List[Tuple[str, str]] = [] diff --git a/lib/galaxy/web/framework/middleware/xforwardedhost.py b/lib/galaxy/web/framework/middleware/xforwardedhost.py index 3e0e11958632..3376fd03c953 100644 --- a/lib/galaxy/web/framework/middleware/xforwardedhost.py +++ b/lib/galaxy/web/framework/middleware/xforwardedhost.py @@ -8,19 +8,16 @@ def __init__(self, app, global_conf=None): self.app = app def __call__(self, environ, start_response): - x_forwarded_host = environ.get("HTTP_X_FORWARDED_HOST", None) - if x_forwarded_host: + if x_forwarded_host := environ.get("HTTP_X_FORWARDED_HOST", None): environ["ORGINAL_HTTP_HOST"] = environ["HTTP_HOST"] environ["HTTP_HOST"] = x_forwarded_host.split(", ", 1)[0] - x_forwarded_for = environ.get("HTTP_X_FORWARDED_FOR", None) - if x_forwarded_for: + if x_forwarded_for := environ.get("HTTP_X_FORWARDED_FOR", None): environ["ORGINAL_REMOTE_ADDR"] = environ["REMOTE_ADDR"] environ["REMOTE_ADDR"] = x_forwarded_for.split(",", 1)[0].strip() x_forwarded_proto = environ.get("HTTP_X_FORWARDED_PROTO", None) if x_forwarded_proto: x_forwarded_proto = x_forwarded_proto.split(",", 1)[0].strip() - x_url_scheme = environ.get("HTTP_X_URL_SCHEME", x_forwarded_proto) - if x_url_scheme: + if x_url_scheme := environ.get("HTTP_X_URL_SCHEME", x_forwarded_proto): environ["original_wsgi.url_scheme"] = environ["wsgi.url_scheme"] environ["wsgi.url_scheme"] = x_url_scheme return self.app(environ, start_response) diff --git a/lib/galaxy/web/legacy_framework/grids.py b/lib/galaxy/web/legacy_framework/grids.py index 8b4fca1f8c5f..3b62e8665012 100644 --- a/lib/galaxy/web/legacy_framework/grids.py +++ b/lib/galaxy/web/legacy_framework/grids.py @@ -682,9 +682,8 @@ def __call__(self, trans, **kwargs): # Maintain sort state in generated urls extra_url_args = {} # Determine whether use_default_filter flag is set. - use_default_filter_str = kwargs.get("use_default_filter") use_default_filter = False - if use_default_filter_str: + if use_default_filter_str := kwargs.get("use_default_filter"): use_default_filter = use_default_filter_str.lower() == "true" # Process filtering arguments to (a) build a query that represents the filter and (b) build a # dictionary that denotes the current filter. diff --git a/lib/galaxy/web/statsd_client.py b/lib/galaxy/web/statsd_client.py index 99ebbabb091f..cf83b299bc52 100644 --- a/lib/galaxy/web/statsd_client.py +++ b/lib/galaxy/web/statsd_client.py @@ -54,8 +54,7 @@ def _effective_infix(self, path, tags): class PyTestGalaxyStatsdClient(VanillaGalaxyStatsdClient): def timing(self, path, time, tags=None): - metrics = CURRENT_TEST_METRICS - if metrics is not None: + if (metrics := CURRENT_TEST_METRICS) is not None: timing = metrics["timing"] if path not in timing: timing[path] = [] @@ -63,8 +62,7 @@ def timing(self, path, time, tags=None): super().timing(path, time, tags=tags) def incr(self, path, n=1, tags=None): - metrics = CURRENT_TEST_METRICS - if metrics is not None: + if (metrics := CURRENT_TEST_METRICS) is not None: counter = metrics["counter"] if path not in counter: counter[path] = [] @@ -72,8 +70,7 @@ def incr(self, path, n=1, tags=None): super().incr(path, n=n, tags=tags) def _effective_infix(self, path, tags): - current_test = CURRENT_TEST - if current_test is not None: + if (current_test := CURRENT_TEST) is not None: tags = tags or {} tags["test"] = current_test return super()._effective_infix(path, tags) diff --git a/lib/galaxy/webapps/base/api.py b/lib/galaxy/webapps/base/api.py index 73056bc88a09..a1804255f228 100644 --- a/lib/galaxy/webapps/base/api.py +++ b/lib/galaxy/webapps/base/api.py @@ -161,8 +161,7 @@ def add_sentry_middleware(app: FastAPI) -> None: def get_error_response_for_request(request: Request, exc: MessageException) -> JSONResponse: error_dict = api_error_message(None, exception=exc) status_code = exc.status_code - path = request.url.path - if "ga4gh" in path: + if "ga4gh" in (path := request.url.path): # When serving GA4GH APIs use limited exceptions to conform their expected # error schema. Tailored to DRS currently. message = error_dict["err_msg"] diff --git a/lib/galaxy/webapps/base/controller.py b/lib/galaxy/webapps/base/controller.py index 3a2eb11ac13f..6c0f41d96978 100644 --- a/lib/galaxy/webapps/base/controller.py +++ b/lib/galaxy/webapps/base/controller.py @@ -225,8 +225,7 @@ def _parse_serialization_params(self, kwd, default_view): # TODO: this will be replaced by lib.galaxy.schema.FilterQueryParams.build_order_by def _parse_order_by(self, manager, order_by_string): - ORDER_BY_SEP_CHAR = "," - if ORDER_BY_SEP_CHAR in order_by_string: + if (ORDER_BY_SEP_CHAR := ",") in order_by_string: return [manager.parse_order_by(o) for o in order_by_string.split(ORDER_BY_SEP_CHAR)] return manager.parse_order_by(order_by_string) @@ -1069,8 +1068,7 @@ def _get_genome_data(self, trans, dataset, dbkey=None): # If there are no messages (messages indicate data is not ready/available), get data. messages_list = [data_source_dict["message"] for data_source_dict in data_sources.values()] - message = self._get_highest_priority_msg(messages_list) - if message: + if message := self._get_highest_priority_msg(messages_list): rval = message else: # HACK: chromatin interactions tracks use data as source. diff --git a/lib/galaxy/webapps/base/webapp.py b/lib/galaxy/webapps/base/webapp.py index 8fc17986afec..97bd22c768d1 100644 --- a/lib/galaxy/webapps/base/webapp.py +++ b/lib/galaxy/webapps/base/webapp.py @@ -309,8 +309,7 @@ def __init__( super().__init__(environ) config = self.app.config self.debug = asbool(config.get("debug", False)) - x_frame_options = getattr(config, "x_frame_options", None) - if x_frame_options: + if x_frame_options := getattr(config, "x_frame_options", None): self.response.headers["X-Frame-Options"] = x_frame_options # Flag indicating whether we are in workflow building mode (means # that the current history should not be used for parameter values diff --git a/lib/galaxy/webapps/galaxy/api/__init__.py b/lib/galaxy/webapps/galaxy/api/__init__.py index b6a44a1f43ac..4c8df89bee77 100644 --- a/lib/galaxy/webapps/galaxy/api/__init__.py +++ b/lib/galaxy/webapps/galaxy/api/__init__.py @@ -214,9 +214,8 @@ def base(self) -> str: @property def url_path(self) -> str: scope = self.__request.scope - root_path = scope.get("root_path") url = self.base - if root_path: + if root_path := scope.get("root_path"): url = urljoin(url, root_path) return url @@ -558,8 +557,7 @@ class IndexQueryTag(NamedTuple): def as_markdown(self): desc = self.description - alias = self.alias - if alias: + if alias := self.alias: desc += f" (The tag `{alias}` can be used a short hand alias for this tag to filter on this attribute.)" if self.admin_only: desc += " This tag is only available for requests using admin keys and/or sessions." diff --git a/lib/galaxy/webapps/galaxy/api/annotations.py b/lib/galaxy/webapps/galaxy/api/annotations.py index fc56b54a45a3..f11fea9660a1 100644 --- a/lib/galaxy/webapps/galaxy/api/annotations.py +++ b/lib/galaxy/webapps/galaxy/api/annotations.py @@ -28,8 +28,7 @@ class BaseAnnotationsController(BaseGalaxyAPIController, UsesStoredWorkflowMixin @expose_api def index(self, trans: ProvidesHistoryContext, **kwd): idnum = kwd[self.tagged_item_id] - item = self._get_item_from_id(trans, idnum) - if item is not None: + if (item := self._get_item_from_id(trans, idnum)) is not None: return self.get_item_annotation_str(trans.sa_session, trans.user, item) @expose_api @@ -37,8 +36,7 @@ def create(self, trans: ProvidesHistoryContext, payload: dict, **kwd): if "text" not in payload: return "" idnum = kwd[self.tagged_item_id] - item = self._get_item_from_id(trans, idnum) - if item is not None: + if (item := self._get_item_from_id(trans, idnum)) is not None: new_annotation = payload.get("text") # TODO: sanitize on display not entry new_annotation = sanitize_html(new_annotation) @@ -52,8 +50,7 @@ def create(self, trans: ProvidesHistoryContext, payload: dict, **kwd): @expose_api def delete(self, trans: ProvidesHistoryContext, **kwd): idnum = kwd[self.tagged_item_id] - item = self._get_item_from_id(trans, idnum) - if item is not None: + if (item := self._get_item_from_id(trans, idnum)) is not None: return self.delete_item_annotation(trans.sa_session, trans.user, item) @expose_api diff --git a/lib/galaxy/webapps/galaxy/api/drs.py b/lib/galaxy/webapps/galaxy/api/drs.py index b5960ee49f4f..d0efa39c62e8 100644 --- a/lib/galaxy/webapps/galaxy/api/drs.py +++ b/lib/galaxy/webapps/galaxy/api/drs.py @@ -63,9 +63,8 @@ def service_info(self, request: Request) -> Service: artifact="drs", version="1.2.0", ) - environment = config.ga4gh_service_environment extra_kwds = {} - if environment: + if environment := config.ga4gh_service_environment: extra_kwds["environment"] = environment return Service( id=organization_id + ".drs", diff --git a/lib/galaxy/webapps/galaxy/api/library_contents.py b/lib/galaxy/webapps/galaxy/api/library_contents.py index fb8eddd6eff1..7f791ef6be2a 100644 --- a/lib/galaxy/webapps/galaxy/api/library_contents.py +++ b/lib/galaxy/webapps/galaxy/api/library_contents.py @@ -332,7 +332,6 @@ def _upload_library_dataset(self, trans, folder_id: int, **kwd): last_used_build = dbkey[0] else: last_used_build = dbkey - roles = kwd.get("roles", "") is_admin = trans.user_is_admin current_user_roles = trans.get_current_user_roles() folder = trans.sa_session.get(LibraryFolder, folder_id) @@ -344,7 +343,7 @@ def _upload_library_dataset(self, trans, folder_id: int, **kwd): error = False if upload_option == "upload_paths": validate_path_upload(trans) # Duplicate check made in _upload_dataset. - elif roles: + elif roles := kwd.get("roles", ""): # Check to see if the user selected roles to associate with the DATASET_ACCESS permission # on the dataset that would cause accessibility issues. vars = dict(DATASET_ACCESS_in=roles) diff --git a/lib/galaxy/webapps/galaxy/api/library_datasets.py b/lib/galaxy/webapps/galaxy/api/library_datasets.py index 2ce680ad6812..7f34ff0ab840 100644 --- a/lib/galaxy/webapps/galaxy/api/library_datasets.py +++ b/lib/galaxy/webapps/galaxy/api/library_datasets.py @@ -434,8 +434,7 @@ def load(self, trans, payload=None, **kwd): kwd["file_type"] = kwd.get("file_type", "auto") kwd["link_data_only"] = "link_to_files" if util.string_as_bool(kwd.get("link_data", False)) else "copy_files" kwd["tag_using_filenames"] = util.string_as_bool(kwd.get("tag_using_filenames", None)) - encoded_folder_id = kwd.get("encoded_folder_id", None) - if encoded_folder_id is not None: + if (encoded_folder_id := kwd.get("encoded_folder_id", None)) is not None: folder_id = self.folder_manager.cut_and_decode(trans, encoded_folder_id) else: raise exceptions.RequestParameterMissingException("The required attribute encoded_folder_id is missing.") diff --git a/lib/galaxy/webapps/galaxy/api/plugins.py b/lib/galaxy/webapps/galaxy/api/plugins.py index 68f6a3c1d931..1a1c88fd4f20 100644 --- a/lib/galaxy/webapps/galaxy/api/plugins.py +++ b/lib/galaxy/webapps/galaxy/api/plugins.py @@ -35,8 +35,7 @@ def index(self, trans, **kwargs): GET /api/plugins: """ registry = self._get_registry() - dataset_id = kwargs.get("dataset_id") - if dataset_id is not None: + if (dataset_id := kwargs.get("dataset_id")) is not None: hda = self.hda_manager.get_accessible(self.decode_id(dataset_id), trans.user) return registry.get_visualizations(trans, hda) else: @@ -49,8 +48,7 @@ def show(self, trans, id, **kwargs): GET /api/plugins/{id}: """ registry = self._get_registry() - history_id = kwargs.get("history_id") - if history_id is not None: + if (history_id := kwargs.get("history_id")) is not None: history = self.history_manager.get_owned( trans.security.decode_id(history_id), trans.user, current_history=trans.history ) diff --git a/lib/galaxy/webapps/galaxy/api/tool_shed_repositories.py b/lib/galaxy/webapps/galaxy/api/tool_shed_repositories.py index 471eb1d3b6b6..88ade5498482 100644 --- a/lib/galaxy/webapps/galaxy/api/tool_shed_repositories.py +++ b/lib/galaxy/webapps/galaxy/api/tool_shed_repositories.py @@ -318,8 +318,7 @@ def __parse_repository_from_payload(self, payload, include_changeset=False): @require_admin @expose_api def reset_metadata_on_selected_installed_repositories(self, trans, **kwd): - repository_ids = util.listify(kwd.get("repository_ids")) - if repository_ids: + if repository_ids := util.listify(kwd.get("repository_ids")): irmm = InstalledRepositoryMetadataManager(self.app) failed = [] successful = [] diff --git a/lib/galaxy/webapps/galaxy/api/tools.py b/lib/galaxy/webapps/galaxy/api/tools.py index 7e9d0b133b8c..38f346bffe8e 100644 --- a/lib/galaxy/webapps/galaxy/api/tools.py +++ b/lib/galaxy/webapps/galaxy/api/tools.py @@ -238,9 +238,8 @@ def build(self, trans: GalaxyWebTransaction, id, **kwd): """ kwd = _kwd_or_payload(kwd) tool_version = kwd.get("tool_version") - history_id = kwd.pop("history_id", None) history = None - if history_id: + if history_id := kwd.pop("history_id", None): history = self.history_manager.get_owned( self.decode_id(history_id), trans.user, current_history=trans.history ) @@ -275,8 +274,7 @@ def test_data_download(self, trans: GalaxyWebTransaction, id, **kwd): filename = kwd.get("filename") if filename is None: raise exceptions.ObjectNotFound("Test data filename not specified.") - path = tool.test_data_path(filename) - if path: + if path := tool.test_data_path(filename): if os.path.isfile(path): trans.response.headers["Content-Disposition"] = f'attachment; filename="{filename}"' return open(path, mode="rb") @@ -463,9 +461,8 @@ def to_dict(x): lineage_dict = tool.lineage.to_dict() else: lineage_dict = None - tool_shed_dependencies = tool.installed_tool_dependencies tool_shed_dependencies_dict: Optional[list] = None - if tool_shed_dependencies: + if tool_shed_dependencies := tool.installed_tool_dependencies: tool_shed_dependencies_dict = list(map(to_dict, tool_shed_dependencies)) return { "tool_id": tool.id, @@ -516,8 +513,7 @@ def conversion(self, trans: GalaxyWebTransaction, tool_id, payload, **kwd): ], "batch": input_src == "hdca", } - history_id = payload.get("history_id") - if history_id: + if history_id := payload.get("history_id"): decoded_id = self.decode_id(history_id) target_history = self.history_manager.get_owned(decoded_id, trans.user, current_history=trans.history) else: diff --git a/lib/galaxy/webapps/galaxy/api/users.py b/lib/galaxy/webapps/galaxy/api/users.py index 3deac727ac6d..1ab007693020 100644 --- a/lib/galaxy/webapps/galaxy/api/users.py +++ b/lib/galaxy/webapps/galaxy/api/users.py @@ -276,8 +276,7 @@ def usage( trans: ProvidesUserContext = DependsOnTrans, user_id: FlexibleUserIdType = FlexibleUserIdPathParam, ) -> List[UserQuotaUsage]: - user = self.service.get_user_full(trans, user_id, False) - if user: + if user := self.service.get_user_full(trans, user_id, False): rval = self.user_serializer.serialize_disk_usage(user) return rval else: @@ -294,11 +293,10 @@ def usage_for( user_id: FlexibleUserIdType = FlexibleUserIdPathParam, label: str = QuotaSourceLabelPathParam, ) -> Optional[UserQuotaUsage]: - user = self.service.get_user_full(trans, user_id, False) effective_label: Optional[str] = label if label == "__null__": effective_label = None - if user: + if user := self.service.get_user_full(trans, user_id, False): rval = self.user_serializer.serialize_disk_usage_for(user, effective_label) return rval else: @@ -907,8 +905,7 @@ def set_information(self, trans, id, payload=None, **kwd): if user.username != username: user.username = username # Update user custom form - user_info_form_id = payload.get("info|form_id") - if user_info_form_id: + if user_info_form_id := payload.get("info|form_id"): prefix = "info|" user_info_form = trans.sa_session.get(FormDefinition, trans.security.decode_id(user_info_form_id)) user_info_values = {} diff --git a/lib/galaxy/webapps/galaxy/api/workflows.py b/lib/galaxy/webapps/galaxy/api/workflows.py index e362befa9608..086ddc2f40af 100644 --- a/lib/galaxy/webapps/galaxy/api/workflows.py +++ b/lib/galaxy/webapps/galaxy/api/workflows.py @@ -372,9 +372,8 @@ def workflow_dict(self, trans: GalaxyWebTransaction, workflow_id, **kwd): style = kwd.get("style", "export") download_format = kwd.get("format") version = kwd.get("version") - history_id = kwd.get("history_id") history = None - if history_id: + if history_id := kwd.get("history_id"): history = self.history_manager.get_accessible( self.decode_id(history_id), trans.user, current_history=trans.history ) diff --git a/lib/galaxy/webapps/galaxy/buildapp.py b/lib/galaxy/webapps/galaxy/buildapp.py index d573a83b1233..06ef4f455a62 100644 --- a/lib/galaxy/webapps/galaxy/buildapp.py +++ b/lib/galaxy/webapps/galaxy/buildapp.py @@ -1084,8 +1084,7 @@ def wrap_in_middleware(app, global_conf, application_stack, **local_conf): # other middleware): app = wrap_if_allowed(app, stack, httpexceptions.make_middleware, name="paste.httpexceptions", args=(conf,)) # Statsd request timing and profiling - statsd_host = conf.get("statsd_host", None) - if statsd_host: + if statsd_host := conf.get("statsd_host", None): from galaxy.web.framework.middleware.statsd import StatsdMiddleware app = wrap_if_allowed( diff --git a/lib/galaxy/webapps/galaxy/controllers/admin.py b/lib/galaxy/webapps/galaxy/controllers/admin.py index 77142ca9669b..5495f24943fb 100644 --- a/lib/galaxy/webapps/galaxy/controllers/admin.py +++ b/lib/galaxy/webapps/galaxy/controllers/admin.py @@ -516,8 +516,7 @@ class ToolVersionsColumn(grids.TextColumn): def get_value(self, trans, grid, tool_version): tool_ids_str = "" toolbox = trans.app.toolbox - tool = toolbox._tools_by_id.get(tool_version.tool_id) - if tool: + if tool := toolbox._tools_by_id.get(tool_version.tool_id): for tool_id in tool.lineage.tool_ids: if toolbox.has_tool(tool_id, exact=True): link = url_for(controller="tool_runner", tool_id=tool_id) @@ -910,8 +909,7 @@ def impersonate(self, trans, **kwd): if not trans.app.config.allow_user_impersonation: return trans.show_error_message("User impersonation is not enabled in this instance of Galaxy.") user = None - user_id = kwd.get("id", None) - if user_id is not None: + if (user_id := kwd.get("id", None)) is not None: try: user = trans.sa_session.query(trans.app.model.User).get(trans.security.decode_id(user_id)) if user: diff --git a/lib/galaxy/webapps/galaxy/controllers/authnz.py b/lib/galaxy/webapps/galaxy/controllers/authnz.py index 88af61d8fa11..2f6cde7d1ebe 100644 --- a/lib/galaxy/webapps/galaxy/controllers/authnz.py +++ b/lib/galaxy/webapps/galaxy/controllers/authnz.py @@ -202,13 +202,12 @@ def get_logout_url(self, trans, provider=None, **kwargs): @web.expose @web.json def get_cilogon_idps(self, trans, **kwargs): - allowed_idps = trans.app.authnz_manager.get_allowed_idps() try: cilogon_idps = json.loads(url_get("https://cilogon.org/idplist/", params=dict(kwargs))) except Exception as e: raise Exception(f"Invalid server response. {str(e)}.") - if allowed_idps: + if allowed_idps := trans.app.authnz_manager.get_allowed_idps(): validated_idps = list(filter(lambda idp: idp["EntityID"] in allowed_idps, cilogon_idps)) if not (len(validated_idps) == len(allowed_idps)): diff --git a/lib/galaxy/webapps/galaxy/controllers/dataset.py b/lib/galaxy/webapps/galaxy/controllers/dataset.py index df9f1f2f9e93..ebebec96a3e1 100644 --- a/lib/galaxy/webapps/galaxy/controllers/dataset.py +++ b/lib/galaxy/webapps/galaxy/controllers/dataset.py @@ -137,8 +137,7 @@ def display( return data if "hdca" in kwd: raise RequestParameterInvalidException("Invalid request parameter 'hdca' encountered.") - hdca_id = kwd.get("hdca_id", None) - if hdca_id: + if hdca_id := kwd.get("hdca_id", None): hdca = self.app.dataset_collection_manager.get_dataset_collection_instance(trans, "history", hdca_id) del kwd["hdca_id"] kwd["hdca"] = hdca diff --git a/lib/galaxy/webapps/galaxy/controllers/user.py b/lib/galaxy/webapps/galaxy/controllers/user.py index 52587ee2d66e..e661f3c40afe 100644 --- a/lib/galaxy/webapps/galaxy/controllers/user.py +++ b/lib/galaxy/webapps/galaxy/controllers/user.py @@ -248,8 +248,7 @@ def is_outside_grace_period(self, trans, create_time): @web.expose @web.json def logout(self, trans, logout_all=False, **kwd): - message = trans.check_csrf_token(kwd) - if message: + if message := trans.check_csrf_token(kwd): return self.message_exception(trans, message) # Since logging an event requires a session, we'll log prior to ending the session trans.log_event("User logged out") @@ -341,8 +340,7 @@ def change_password(self, trans, payload=None, **kwd): def reset_password(self, trans, payload=None, **kwd): """Reset the user's password. Send an email with token that allows a password change.""" payload = payload or {} - message = self.user_manager.send_reset_email(trans, payload) - if message: + if message := self.user_manager.send_reset_email(trans, payload): return self.message_exception(trans, message) return {"message": "Reset link has been sent to your email."} diff --git a/lib/galaxy/webapps/galaxy/fast_app.py b/lib/galaxy/webapps/galaxy/fast_app.py index 464f57270b09..792a0a5f56d0 100644 --- a/lib/galaxy/webapps/galaxy/fast_app.py +++ b/lib/galaxy/webapps/galaxy/fast_app.py @@ -99,8 +99,7 @@ def is_allowed_origin(self, origin: str) -> bool: def add_galaxy_middleware(app: FastAPI, gx_app): - x_frame_options = gx_app.config.x_frame_options - if x_frame_options: + if x_frame_options := gx_app.config.x_frame_options: @app.middleware("http") async def add_x_frame_options(request: Request, call_next): diff --git a/lib/galaxy/webapps/galaxy/services/datasets.py b/lib/galaxy/webapps/galaxy/services/datasets.py index 37741b0cdc49..4a40e2e2576a 100644 --- a/lib/galaxy/webapps/galaxy/services/datasets.py +++ b/lib/galaxy/webapps/galaxy/services/datasets.py @@ -850,15 +850,13 @@ def _data( return dataset.conversion_messages.NO_DATA # Dataset check. - msg = self.hda_manager.data_conversion_status(dataset) - if msg: + if msg := self.hda_manager.data_conversion_status(dataset): return msg # Get datasources and check for messages. data_sources = dataset.get_datasources(trans) messages_list = [data_source_dict["message"] for data_source_dict in data_sources.values()] - return_message = self._get_highest_priority_msg(messages_list) - if return_message: + if return_message := self._get_highest_priority_msg(messages_list): return return_message extra_info = None @@ -953,8 +951,7 @@ def _raw_data( be slow because indexes need to be created. """ # Dataset check. - msg = self.hda_manager.data_conversion_status(dataset) - if msg: + if msg := self.hda_manager.data_conversion_status(dataset): return msg registry = self.data_provider_registry diff --git a/lib/galaxy/webapps/galaxy/services/history_contents.py b/lib/galaxy/webapps/galaxy/services/history_contents.py index be4727ae0f52..a6d2a3becf2e 100644 --- a/lib/galaxy/webapps/galaxy/services/history_contents.py +++ b/lib/galaxy/webapps/galaxy/services/history_contents.py @@ -885,8 +885,7 @@ def __update_dataset( ): # anon user: ensure that history ids match up and the history is the current, # check for uploading, and use only the subset of attribute keys manipulatable by anon users - hda = self.__datasets_for_update(trans, history, [id], payload)[0] - if hda: + if hda := self.__datasets_for_update(trans, history, [id], payload)[0]: self.__deserialize_dataset(trans, hda, payload) serialization_params.default_view = "detailed" return self.hda_serializer.serialize_to_view( @@ -933,13 +932,11 @@ def __index_legacy( """Legacy implementation of the `index` action.""" history = self._get_history(trans, history_id) legacy_params_dict = legacy_params.dict(exclude_defaults=True) - ids = legacy_params_dict.get("ids") - if ids: + if ids := legacy_params_dict.get("ids"): legacy_params_dict["ids"] = self.decode_ids(ids) object_store_ids = None - shareable = legacy_params.shareable - if shareable is not None: + if (shareable := legacy_params.shareable) is not None: object_store_ids = self.object_store.object_store_ids(private=not shareable) if object_store_ids: legacy_params_dict["object_store_ids"] = object_store_ids diff --git a/lib/galaxy/webapps/galaxy/services/jobs.py b/lib/galaxy/webapps/galaxy/services/jobs.py index 95ceb3ede2b3..ec9e42467482 100644 --- a/lib/galaxy/webapps/galaxy/services/jobs.py +++ b/lib/galaxy/webapps/galaxy/services/jobs.py @@ -130,8 +130,7 @@ def dictify_associations(self, trans, *association_lists) -> List[JobAssociation def __dictify_association(self, trans, job_dataset_association) -> JobAssociation: dataset_dict = None - dataset = job_dataset_association.dataset - if dataset: + if dataset := job_dataset_association.dataset: if isinstance(dataset, model.HistoryDatasetAssociation): dataset_dict = EncodedDatasetSourceId(src="hda", id=dataset.id) else: diff --git a/lib/galaxy/webapps/galaxy/services/notifications.py b/lib/galaxy/webapps/galaxy/services/notifications.py index 6ca78fafb568..12c86a218046 100644 --- a/lib/galaxy/webapps/galaxy/services/notifications.py +++ b/lib/galaxy/webapps/galaxy/services/notifications.py @@ -134,7 +134,7 @@ def update_user_notification( ): """Updates a single notification received by the user with the requested values.""" self.notification_manager.ensure_notifications_enabled() - updated_response = self.update_user_notifications(user_context, set([notification_id]), request) + updated_response = self.update_user_notifications(user_context, {notification_id}, request) if not updated_response.updated_count: self._raise_notification_not_found(notification_id) diff --git a/lib/galaxy/webapps/galaxy/services/tools.py b/lib/galaxy/webapps/galaxy/services/tools.py index 9265f51427f5..8bdb7eb0d5a5 100644 --- a/lib/galaxy/webapps/galaxy/services/tools.py +++ b/lib/galaxy/webapps/galaxy/services/tools.py @@ -134,8 +134,7 @@ def _create(self, trans: ProvidesHistoryContext, payload, **kwd): # Set running history from payload parameters. # History not set correctly as part of this API call for # dataset upload. - history_id = payload.get("history_id") - if history_id: + if history_id := payload.get("history_id"): history_id = trans.security.decode_id(history_id) if isinstance(history_id, str) else history_id target_history = self.history_manager.get_mutable(history_id, trans.user, current_history=trans.history) else: @@ -201,8 +200,7 @@ def _handle_inputs_output_to_api_response(self, trans, tool, target_history, var output_datasets = vars.get("out_data", []) rval: Dict[str, Any] = {"outputs": [], "output_collections": [], "jobs": [], "implicit_collections": []} rval["produces_entry_points"] = tool.produces_entry_points - job_errors = vars.get("job_errors", []) - if job_errors: + if job_errors := vars.get("job_errors", []): # If we are here - some jobs were successfully executed but some failed. rval["errors"] = job_errors diff --git a/lib/galaxy/webapps/openapi/utils.py b/lib/galaxy/webapps/openapi/utils.py index 5fa24c4597f8..6e6c79248f96 100644 --- a/lib/galaxy/webapps/openapi/utils.py +++ b/lib/galaxy/webapps/openapi/utils.py @@ -150,9 +150,8 @@ def get_openapi_operation_request_body( body_schema, _, _ = field_schema(body_field, model_name_map=model_name_map, ref_prefix=REF_PREFIX) field_info = cast(Body, body_field.field_info) request_media_type = field_info.media_type - required = body_field.required request_body_oai: Dict[str, Any] = {} - if required: + if required := body_field.required: request_body_oai["required"] = required request_media_content: Dict[str, Any] = {"schema": body_schema} if field_info.examples: diff --git a/lib/galaxy/webapps/reports/controllers/history.py b/lib/galaxy/webapps/reports/controllers/history.py index 4e36891fc0bb..cb6f184b55ab 100644 --- a/lib/galaxy/webapps/reports/controllers/history.py +++ b/lib/galaxy/webapps/reports/controllers/history.py @@ -159,7 +159,6 @@ def history_and_dataset_type(self, trans, **kwd): user_cutoff = int(kwd.get("user_cutoff", 60)) descending = 1 if kwd.get("descending", "desc") == "desc" else -1 reverse = descending == 1 - user_selection = kwd.get("user_selection", None) # select d.state, h.name # from dataset d, history h , history_dataset_association hda @@ -169,7 +168,7 @@ def history_and_dataset_type(self, trans, **kwd): galaxy.model.History.table, galaxy.model.HistoryDatasetAssociation.table, ] - if user_selection is not None: + if (user_selection := kwd.get("user_selection", None)) is not None: from_obj.append(galaxy.model.User.table) whereclause = and_( galaxy.model.Dataset.table.c.id == galaxy.model.HistoryDatasetAssociation.table.c.dataset_id, diff --git a/lib/galaxy/webapps/reports/controllers/jobs.py b/lib/galaxy/webapps/reports/controllers/jobs.py index e281f538b868..3fbad58ba29f 100644 --- a/lib/galaxy/webapps/reports/controllers/jobs.py +++ b/lib/galaxy/webapps/reports/controllers/jobs.py @@ -1306,7 +1306,6 @@ def get_monitor_id(trans, monitor_email): A convenience method to obtain the monitor job id. """ monitor_user_id = None - monitor_row = get_user_by_email(trans.sa_session, monitor_email) - if monitor_row is not None: + if (monitor_row := get_user_by_email(trans.sa_session, monitor_email)) is not None: monitor_user_id = monitor_row[0] return monitor_user_id diff --git a/lib/galaxy/workflow/extract.py b/lib/galaxy/workflow/extract.py index d349cb87bb26..199c096e1133 100644 --- a/lib/galaxy/workflow/extract.py +++ b/lib/galaxy/workflow/extract.py @@ -296,8 +296,7 @@ def __summarize_dataset_collection(self, dataset_collection): hid = dataset_collection.hid self.collection_types[hid] = dataset_collection.collection.collection_type - cja = dataset_collection.creating_job_associations - if cja: + if cja := dataset_collection.creating_job_associations: # Use the "first" job to represent all mapped jobs. representative_assoc = cja[0] representative_job = representative_assoc.job diff --git a/lib/galaxy/workflow/modules.py b/lib/galaxy/workflow/modules.py index 4b5f18bee32c..6105111dce89 100644 --- a/lib/galaxy/workflow/modules.py +++ b/lib/galaxy/workflow/modules.py @@ -313,8 +313,7 @@ def get_state(self, nested=True): """Return a serializable representation of the persistable state of the step. """ - inputs = self.get_inputs() - if inputs: + if inputs := self.get_inputs(): return self.state.encode(Bunch(inputs=inputs), self.trans.app, nested=nested) else: return self.state.inputs @@ -347,8 +346,7 @@ def recover_state(self, state, **kwds): state = self.step_state_to_tool_state(state or {}) self.state = DefaultToolState() - inputs = self.get_inputs() - if inputs: + if inputs := self.get_inputs(): self.state.decode(state, Bunch(inputs=inputs), self.trans.app) else: self.state.inputs = safe_loads(state) or {} @@ -1114,7 +1112,6 @@ def get_runtime_inputs(self, step, connections: Optional[Iterable[WorkflowStepCo collection_type = parameter_def["collection_type"] optional = parameter_def["optional"] tag = parameter_def["tag"] - formats = parameter_def.get("format") collection_param_source = dict( name="input", label=self.label, @@ -1123,7 +1120,7 @@ def get_runtime_inputs(self, step, connections: Optional[Iterable[WorkflowStepCo tag=tag, optional=optional, ) - if formats: + if formats := parameter_def.get("format"): collection_param_source["format"] = ",".join(listify(formats)) input_param = DataCollectionToolParameter(None, collection_param_source, self.trans) return dict(input=input_param) @@ -1148,8 +1145,7 @@ def get_all_outputs(self, data_only=False): def _parse_state_into_dict(self): state_as_dict = super()._parse_state_into_dict() - inputs = self.state.inputs - if "collection_type" in inputs: + if "collection_type" in (inputs := self.state.inputs): collection_type = inputs["collection_type"] else: collection_type = self.default_collection_type @@ -1824,8 +1820,7 @@ def save_to_step(self, step, detached=False): step.tool_version = self.get_version() else: step.tool_version = self.tool_version - tool_uuid = getattr(self, "tool_uuid", None) - if tool_uuid: + if tool_uuid := getattr(self, "tool_uuid", None): step.dynamic_tool = self.trans.app.dynamic_tool_manager.get_tool_by_uuid(tool_uuid) if not detached: for k, v in self.post_job_actions.items(): diff --git a/lib/galaxy/workflow/run_request.py b/lib/galaxy/workflow/run_request.py index a188dee32b2b..8797b1fb8fe1 100644 --- a/lib/galaxy/workflow/run_request.py +++ b/lib/galaxy/workflow/run_request.py @@ -202,8 +202,7 @@ def _step_parameters(step: "WorkflowStep", param_map: Dict, legacy: bool = False param_dict.update(param_map.get(str(step.id), {})) else: param_dict.update(param_map.get(str(step.order_index), {})) - step_uuid = step.uuid - if step_uuid: + if step_uuid := step.uuid: uuid_params = param_map.get(str(step_uuid), {}) param_dict.update(uuid_params) if param_dict: diff --git a/lib/galaxy/workflow/trs_proxy.py b/lib/galaxy/workflow/trs_proxy.py index a9a32909457a..7bf65631b46a 100644 --- a/lib/galaxy/workflow/trs_proxy.py +++ b/lib/galaxy/workflow/trs_proxy.py @@ -74,8 +74,7 @@ def server_from_url(self, trs_url): return TrsServer(trs_url) def match_url(self, url): - matches = re.match(TRS_URL_REGEX, url) - if matches: + if matches := re.match(TRS_URL_REGEX, url): match_dict = matches.groupdict() match_dict["tool_id"] = urllib.parse.unquote(match_dict["tool_id"]) return match_dict diff --git a/lib/galaxy_test/api/test_workflow_extraction.py b/lib/galaxy_test/api/test_workflow_extraction.py index f8f5c939852e..7b964223df19 100644 --- a/lib/galaxy_test/api/test_workflow_extraction.py +++ b/lib/galaxy_test/api/test_workflow_extraction.py @@ -495,9 +495,7 @@ def _assert_first_step_is_paired_input(self, downloaded_workflow): return collect_step_idx def _extract_and_download_workflow(self, history_id: str, **extract_payload): - reimport_as = extract_payload.get("reimport_as") - - if reimport_as: + if reimport_as := extract_payload.get("reimport_as"): history_name = reimport_as self.dataset_populator.wait_for_history(history_id) self.dataset_populator.rename_history(history_id, history_name) diff --git a/lib/galaxy_test/base/api.py b/lib/galaxy_test/base/api.py index 8198ae1b8ef0..964494a3dfc2 100644 --- a/lib/galaxy_test/base/api.py +++ b/lib/galaxy_test/base/api.py @@ -109,8 +109,7 @@ def _api_url(self, path, params=None, use_key=None, use_admin_key=None): params["key"] = self.galaxy_interactor.api_key if use_admin_key: params["key"] = self.galaxy_interactor.master_api_key - query = urlencode(params) - if query: + if query := urlencode(params): url = f"{url}?{query}" return url diff --git a/lib/galaxy_test/base/decorators.py b/lib/galaxy_test/base/decorators.py index a724c10d696d..710f7eda54ea 100644 --- a/lib/galaxy_test/base/decorators.py +++ b/lib/galaxy_test/base/decorators.py @@ -43,8 +43,7 @@ def using_requirement(tag: KnownRequirementT): """ requirement = f"requires_{tag}" skip_environment_variable = f"GALAXY_TEST_SKIP_IF_{requirement.upper()}" - env_value = os.environ.get(skip_environment_variable, "0") - if env_value != "0": + if (env_value := os.environ.get(skip_environment_variable, "0")) != "0": raise unittest.SkipTest(f"[{env_value}] Skipping due to {skip_environment_variable} being set to {env_value}") diff --git a/lib/galaxy_test/base/populators.py b/lib/galaxy_test/base/populators.py index 86cdba03f8e3..09c6b7244da0 100644 --- a/lib/galaxy_test/base/populators.py +++ b/lib/galaxy_test/base/populators.py @@ -1308,8 +1308,7 @@ def get_export_url(self, export_url) -> Response: def import_history(self, import_data): files = {} - archive_file = import_data.pop("archive_file", None) - if archive_file: + if archive_file := import_data.pop("archive_file", None): files["archive_file"] = archive_file import_response = self._post("histories", data=import_data, files=files) api_asserts.assert_status_code_is(import_response, 200) diff --git a/lib/galaxy_test/driver/driver_util.py b/lib/galaxy_test/driver/driver_util.py index de9712700633..ee79b007f000 100644 --- a/lib/galaxy_test/driver/driver_util.py +++ b/lib/galaxy_test/driver/driver_util.py @@ -854,8 +854,7 @@ def stop_servers(self): server_wrapper.stop() for th in threading.enumerate(): log.debug(f"After stopping all servers thread {th} is alive.") - active_count = threading.active_count() - if active_count > 100: + if (active_count := threading.active_count()) > 100: # For an unknown reason running iRODS tests results in application threads not shutting down immediately, # but if we've accumulated over 100 active threads something else is wrong that needs to be fixed. raise Exception( diff --git a/lib/galaxy_test/driver/integration_util.py b/lib/galaxy_test/driver/integration_util.py index 2d9309b083ec..1a38759c13f2 100644 --- a/lib/galaxy_test/driver/integration_util.py +++ b/lib/galaxy_test/driver/integration_util.py @@ -130,8 +130,7 @@ def tearDownClass(cls): cls._app_available = False def tearDown(self): - logs = self._test_driver.get_logs() - if logs: + if logs := self._test_driver.get_logs(): print(logs) return super().tearDown() diff --git a/lib/galaxy_test/selenium/framework.py b/lib/galaxy_test/selenium/framework.py index 2e5b67c14522..23d18b3f7478 100644 --- a/lib/galaxy_test/selenium/framework.py +++ b/lib/galaxy_test/selenium/framework.py @@ -587,8 +587,7 @@ def assert_item_hid_text(self, hid): class UsesWorkflowAssertions(NavigatesGalaxyMixin): @retry_assertion_during_transitions def _assert_showing_n_workflows(self, n): - actual_count = len(self.workflow_index_table_elements()) - if actual_count != n: + if (actual_count := len(self.workflow_index_table_elements())) != n: message = f"Expected {n} workflows to be displayed, based on DOM found {actual_count} workflow rows." raise AssertionError(message) diff --git a/lib/galaxy_test/selenium/test_pages_index.py b/lib/galaxy_test/selenium/test_pages_index.py index f7f82676b7e6..baca1d802e97 100644 --- a/lib/galaxy_test/selenium/test_pages_index.py +++ b/lib/galaxy_test/selenium/test_pages_index.py @@ -28,7 +28,6 @@ def new_page(self): @retry_assertion_during_transitions def _assert_showing_n_pages(self, n): - actual_count = len(self.pages_index_table_elements()) - if actual_count != n: + if (actual_count := len(self.pages_index_table_elements())) != n: message = f"Expected {n} pages to be displayed, based on DOM found {actual_count} page index rows." raise AssertionError(message) diff --git a/lib/galaxy_test/selenium/test_tool_form.py b/lib/galaxy_test/selenium/test_tool_form.py index 9dba37e40697..a70bae70f2b6 100644 --- a/lib/galaxy_test/selenium/test_tool_form.py +++ b/lib/galaxy_test/selenium/test_tool_form.py @@ -285,8 +285,7 @@ def test_bibtex_rendering(self): @retry_assertion_during_transitions def assert_citations_visible(): references = self.components.tool_form.reference.all() - references_rendered = len(references) - if references_rendered != citation_count: + if (references_rendered := len(references)) != citation_count: citations_api = self.api_get("tools/bibtex/citations") current_citation_count = len(citations_api) message = f"Expected {citation_count} references to be rendered, {references_rendered} actually rendered. Currently the API yields {current_citation_count} references" diff --git a/lib/tool_shed/dependencies/repository/relation_builder.py b/lib/tool_shed/dependencies/repository/relation_builder.py index 33811377d031..416282f78055 100644 --- a/lib/tool_shed/dependencies/repository/relation_builder.py +++ b/lib/tool_shed/dependencies/repository/relation_builder.py @@ -156,8 +156,7 @@ def get_repository_dependencies_for_changeset_revision(self): """ # Assume the current repository does not have repository dependencies defined for it. current_repository_key = None - metadata = self.repository_metadata.metadata - if metadata: + if metadata := self.repository_metadata.metadata: # The value of self.tool_shed_url must include the port, but doesn't have to include # the protocol. if "repository_dependencies" in metadata: diff --git a/lib/tool_shed/grids/repository_grids.py b/lib/tool_shed/grids/repository_grids.py index a61de72dc285..5c80c185ff38 100644 --- a/lib/tool_shed/grids/repository_grids.py +++ b/lib/tool_shed/grids/repository_grids.py @@ -352,9 +352,8 @@ def get_value(self, trans, grid, repository_metadata): use_paging = False def build_initial_query(self, trans, **kwd): - match_tuples = kwd.get("match_tuples", []) clause_list = [] - if match_tuples: + if match_tuples := kwd.get("match_tuples", []): for match_tuple in match_tuples: repository_id, changeset_revision = match_tuple clause_list.append( @@ -856,8 +855,7 @@ def get_value(self, trans, grid, repository): trans, repository ) metadata = repository_metadata.metadata - invalid_tools = metadata.get("invalid_tools", []) - if invalid_tools: + if invalid_tools := metadata.get("invalid_tools", []): for invalid_tool_config in invalid_tools: href_str = '{}'.format( trans.security.encode_id(repository.id), diff --git a/lib/tool_shed/managers/repositories.py b/lib/tool_shed/managers/repositories.py index c25918547b98..62f145f3aa56 100644 --- a/lib/tool_shed/managers/repositories.py +++ b/lib/tool_shed/managers/repositories.py @@ -458,8 +458,7 @@ def create_repository(trans: ProvidesUserContext, request: CreateRepositoryReque assert user category_ids = listify(request.category_ids) name = request.name - invalid_message = validate_repository_name(app, name, user) - if invalid_message: + if invalid_message := validate_repository_name(app, name, user): raise RequestParameterInvalidException(invalid_message) repo, _ = low_level_create_repository( diff --git a/lib/tool_shed/managers/trs.py b/lib/tool_shed/managers/trs.py index fbd1880b60b1..3c5cfb9e89e1 100644 --- a/lib/tool_shed/managers/trs.py +++ b/lib/tool_shed/managers/trs.py @@ -56,9 +56,8 @@ def service_info(app: ToolShedApp, request_url: URL): artifact="trs", version="2.1.0", ) - environment = config.ga4gh_service_environment extra_kwds = {} - if environment: + if environment := config.ga4gh_service_environment: extra_kwds["environment"] = environment return Service( id=organization_id + ".trs", diff --git a/lib/tool_shed/metadata/repository_metadata_manager.py b/lib/tool_shed/metadata/repository_metadata_manager.py index 2bc5e756a0d0..a5df2eddcf91 100644 --- a/lib/tool_shed/metadata/repository_metadata_manager.py +++ b/lib/tool_shed/metadata/repository_metadata_manager.py @@ -918,10 +918,9 @@ def reset_metadata_on_selected_repositories(self, **kwd): Inspect the repository changelog to reset metadata for all appropriate changeset revisions. This method is called from both Galaxy and the Tool Shed. """ - repository_ids = util.listify(kwd.get("repository_ids", None)) message = "" status = "done" - if repository_ids: + if repository_ids := util.listify(kwd.get("repository_ids", None)): successful_count = 0 unsuccessful_count = 0 for repository_id in repository_ids: diff --git a/lib/tool_shed/test/base/twillbrowser.py b/lib/tool_shed/test/base/twillbrowser.py index 65cf8c48eda3..1f4af8791678 100644 --- a/lib/tool_shed/test/base/twillbrowser.py +++ b/lib/tool_shed/test/base/twillbrowser.py @@ -14,6 +14,8 @@ ) tc.options["equiv_refresh_interval"] = 0 +# Resetting all repository metadata can take a really long time +tc.timeout(240) def visit_url(url: str, allowed_codes: List[int]) -> str: diff --git a/lib/tool_shed/util/hg_util.py b/lib/tool_shed/util/hg_util.py index 965013846c4f..a0225c0d1a05 100644 --- a/lib/tool_shed/util/hg_util.py +++ b/lib/tool_shed/util/hg_util.py @@ -151,8 +151,7 @@ def get_revision_label(app, repository, changeset_revision, include_date=True, i which includes the revision date if the receive include_date is True. """ repo = repository.hg_repo - ctx = get_changectx_for_changeset(repo, changeset_revision) - if ctx: + if ctx := get_changectx_for_changeset(repo, changeset_revision): return get_revision_label_from_ctx(ctx, include_date=include_date, include_hash=include_hash) else: if include_hash: @@ -168,8 +167,7 @@ def get_rev_label_changeset_revision_from_repository_metadata( repository = repository_metadata.repository repo = repository.hg_repo changeset_revision = repository_metadata.changeset_revision - ctx = get_changectx_for_changeset(repo, changeset_revision) - if ctx: + if ctx := get_changectx_for_changeset(repo, changeset_revision): rev = "%04d" % ctx.rev() if include_date: changeset_revision_date = get_readable_ctx_date(ctx) @@ -209,8 +207,7 @@ def get_rev_label_from_changeset_revision(repo, changeset_revision, include_date Given a changeset revision hash, return two strings, the changeset rev and the changeset revision hash which includes the revision date if the receive include_date is True. """ - ctx = get_changectx_for_changeset(repo, changeset_revision) - if ctx: + if ctx := get_changectx_for_changeset(repo, changeset_revision): rev = "%04d" % ctx.rev() label = get_revision_label_from_ctx(ctx, include_date=include_date) else: diff --git a/lib/tool_shed/util/shed_util_common.py b/lib/tool_shed/util/shed_util_common.py index ed4d160effda..99027ea17fc8 100644 --- a/lib/tool_shed/util/shed_util_common.py +++ b/lib/tool_shed/util/shed_util_common.py @@ -318,8 +318,7 @@ def is_path_within_dependency_dir(app: "ToolShedApp", path: str) -> bool: """ allowed = False resolved_path = os.path.realpath(path) - tool_dependency_dir = app.config.get("tool_dependency_dir", None) - if tool_dependency_dir: + if tool_dependency_dir := app.config.get("tool_dependency_dir", None): dependency_path = os.path.abspath(tool_dependency_dir) allowed = os.path.commonprefix([dependency_path, resolved_path]) == dependency_path return allowed diff --git a/lib/tool_shed/webapp/api/groups.py b/lib/tool_shed/webapp/api/groups.py index 14228462e675..3fd412dc7211 100644 --- a/lib/tool_shed/webapp/api/groups.py +++ b/lib/tool_shed/webapp/api/groups.py @@ -83,8 +83,7 @@ def create(self, trans, payload, **kwd): Content-Disposition: form-data; name="description" Group_Description """ group_dict = dict(message="", status="ok") - name = payload.get("name", "") - if name: + if name := payload.get("name", ""): description = payload.get("description", "") if not description: description = "" diff --git a/lib/tool_shed/webapp/api/repositories.py b/lib/tool_shed/webapp/api/repositories.py index 740f3a995421..713452202ca5 100644 --- a/lib/tool_shed/webapp/api/repositories.py +++ b/lib/tool_shed/webapp/api/repositories.py @@ -214,8 +214,7 @@ def get_installable_revisions(self, trans, **kwd): Returns a list of lists of changesets, in the format [ [ 0, fbb391dc803c ], [ 1, 9d9ec4d9c03e ], [ 2, 9b5b20673b89 ], [ 3, e8c99ce51292 ] ]. """ # Example URL: http://localhost:9009/api/repositories/get_installable_revisions?tsr_id=9d37e53072ff9fa4 - tsr_id = kwd.get("tsr_id", None) - if tsr_id is not None: + if (tsr_id := kwd.get("tsr_id", None)) is not None: repository = repository_util.get_repository_in_tool_shed( self.app, tsr_id, eagerload_columns=[model.Repository.downloadable_revisions] ) @@ -271,8 +270,7 @@ def index(self, trans, deleted=False, owner=None, name=None, **kwd): """ repository_dicts = [] deleted = util.asbool(deleted) - q = kwd.get("q", "") - if q: + if q := kwd.get("q", ""): page = kwd.get("page", 1) page_size = kwd.get("page_size", 10) try: @@ -288,8 +286,7 @@ def index(self, trans, deleted=False, owner=None, name=None, **kwd): else: response = json.dumps(search_results) return response - tool_ids = kwd.get("tool_ids", None) - if tool_ids is not None: + if (tool_ids := kwd.get("tool_ids", None)) is not None: tool_ids = util.listify(tool_ids) response = index_tool_ids(self.app, tool_ids) return json.dumps(response) diff --git a/lib/tool_shed/webapp/api2/__init__.py b/lib/tool_shed/webapp/api2/__init__.py index 3630038280f3..845e1a9a2cfc 100644 --- a/lib/tool_shed/webapp/api2/__init__.py +++ b/lib/tool_shed/webapp/api2/__init__.py @@ -291,7 +291,6 @@ def ensure_valid_session(trans: SessionRequestContext) -> None: sa_session = app.model.context request = trans.request # Try to load an existing session - secure_id = request.get_cookie(AUTH_COOKIE_NAME) galaxy_session = None prev_galaxy_session = None user_for_new_session = None @@ -299,7 +298,7 @@ def ensure_valid_session(trans: SessionRequestContext) -> None: # Track whether the session has changed so we can avoid calling flush # in the most common case (session exists and is valid). galaxy_session_requires_flush = False - if secure_id: + if secure_id := request.get_cookie(AUTH_COOKIE_NAME): session_key: Optional[str] = app.security.decode_guid(secure_id) if session_key: # We do NOT catch exceptions here, if the database is down the request should fail, diff --git a/lib/tool_shed/webapp/controllers/admin.py b/lib/tool_shed/webapp/controllers/admin.py index aec70e430121..73ddef546528 100644 --- a/lib/tool_shed/webapp/controllers/admin.py +++ b/lib/tool_shed/webapp/controllers/admin.py @@ -173,8 +173,7 @@ def create_category(self, trans, **kwd): def delete_repository(self, trans, **kwd): message = escape(kwd.get("message", "")) status = kwd.get("status", "done") - id = kwd.get("id", None) - if id: + if id := kwd.get("id", None): # Deleting multiple items is currently not allowed (allow_multiple=False), so there will only be 1 id. ids = util.listify(id) count = 0 @@ -222,8 +221,7 @@ def delete_repository(self, trans, **kwd): def delete_repository_metadata(self, trans, **kwd): message = escape(kwd.get("message", "")) status = kwd.get("status", "done") - id = kwd.get("id", None) - if id: + if id := kwd.get("id", None): ids = util.listify(id) count = 0 for repository_metadata_id in ids: @@ -382,8 +380,7 @@ def reset_metadata_on_selected_repositories_in_tool_shed(self, trans, **kwd): @web.require_admin def undelete_repository(self, trans, **kwd): message = escape(kwd.get("message", "")) - id = kwd.get("id", None) - if id: + if id := kwd.get("id", None): # Undeleting multiple items is currently not allowed (allow_multiple=False), so there will only be 1 id. ids = util.listify(id) count = 0 @@ -437,8 +434,7 @@ def mark_category_deleted(self, trans, **kwd): # sense to mark a category as deleted (category names and descriptions can be changed instead). # If we do this, and the following 2 methods can be eliminated. message = escape(kwd.get("message", "")) - id = kwd.get("id", None) - if id: + if id := kwd.get("id", None): ids = util.listify(id) message = "Deleted %d categories: " % len(ids) for category_id in ids: @@ -465,8 +461,7 @@ def purge_category(self, trans, **kwd): # Purging a deleted Category deletes all of the following from the database: # - RepoitoryCategoryAssociations where category_id == Category.id message = escape(kwd.get("message", "")) - id = kwd.get("id", None) - if id: + if id := kwd.get("id", None): ids = util.listify(id) count = 0 purged_categories = "" @@ -493,8 +488,7 @@ def purge_category(self, trans, **kwd): @web.require_admin def undelete_category(self, trans, **kwd): message = escape(kwd.get("message", "")) - id = kwd.get("id", None) - if id: + if id := kwd.get("id", None): ids = util.listify(id) count = 0 undeleted_categories = "" diff --git a/lib/tool_shed/webapp/controllers/repository.py b/lib/tool_shed/webapp/controllers/repository.py index 688e2397525b..d471402aa7d1 100644 --- a/lib/tool_shed/webapp/controllers/repository.py +++ b/lib/tool_shed/webapp/controllers/repository.py @@ -199,8 +199,7 @@ def browse_deprecated_repositories_i_own(self, trans, **kwd): @web.expose def browse_my_writable_repositories(self, trans, **kwd): - _redir = self._redirect_if_necessary(trans, **kwd) - if _redir is not None: + if (_redir := self._redirect_if_necessary(trans, **kwd)) is not None: return _redir selected_changeset_revision, repository = suc.get_repository_from_refresh_on_change(trans.app, **kwd) @@ -218,8 +217,7 @@ def browse_my_writable_repositories(self, trans, **kwd): @web.expose def browse_my_writable_repositories_missing_tool_test_components(self, trans, **kwd): - _redir = self._redirect_if_necessary(trans, **kwd) - if _redir is not None: + if (_redir := self._redirect_if_necessary(trans, **kwd)) is not None: return _redir if "message" not in kwd: @@ -237,8 +235,7 @@ def browse_my_writable_repositories_missing_tool_test_components(self, trans, ** @web.expose def browse_my_writable_repositories_with_invalid_tools(self, trans, **kwd): - _redir = self._redirect_if_necessary(trans, **kwd) - if _redir is not None: + if (_redir := self._redirect_if_necessary(trans, **kwd)) is not None: return _redir if "message" not in kwd: @@ -360,8 +357,7 @@ def browse_repositories_by_user(self, trans, **kwd): @web.expose def browse_repositories_i_can_administer(self, trans, **kwd): - _redir = self._redirect_if_necessary(trans, **kwd) - if _redir is not None: + if (_redir := self._redirect_if_necessary(trans, **kwd)) is not None: return _redir selected_changeset_revision, repository = suc.get_repository_from_refresh_on_change(trans.app, **kwd) @@ -379,8 +375,7 @@ def browse_repositories_i_can_administer(self, trans, **kwd): @web.expose def browse_repositories_i_own(self, trans, **kwd): - _redir = self._redirect_if_necessary(trans, **kwd) - if _redir is not None: + if (_redir := self._redirect_if_necessary(trans, **kwd)) is not None: return _redir selected_changeset_revision, repository = suc.get_repository_from_refresh_on_change(trans.app, **kwd) @@ -427,8 +422,7 @@ def browse_repositories_in_category(self, trans, **kwd): changeset_revision=selected_changeset_revision, ) ) - category_id = kwd.get("id", None) - if category_id: + if category_id := kwd.get("id", None): category = suc.get_category(trans.app, category_id) if category: trailing_string = f"in Category {str(category.name)}" @@ -444,8 +438,7 @@ def browse_repositories_in_category(self, trans, **kwd): @web.expose def browse_repositories_missing_tool_test_components(self, trans, **kwd): - _redir = self._redirect_if_necessary(trans, **kwd) - if _redir is not None: + if (_redir := self._redirect_if_necessary(trans, **kwd)) is not None: return _redir if "message" not in kwd: @@ -462,8 +455,7 @@ def browse_repositories_missing_tool_test_components(self, trans, **kwd): @web.expose def browse_repositories_with_invalid_tools(self, trans, **kwd): - _redir = self._redirect_if_necessary(trans, **kwd) - if _redir is not None: + if (_redir := self._redirect_if_necessary(trans, **kwd)) is not None: return _redir if "message" not in kwd: @@ -557,8 +549,7 @@ def browse_tool_dependencies(self, trans, **kwd): def browse_valid_categories(self, trans, **kwd): """Filter repositories per category by those that are valid for installing into Galaxy.""" # The request came from Galaxy, so restrict category links to display only valid repository changeset revisions. - galaxy_url = common_util.handle_galaxy_url(trans, **kwd) - if galaxy_url: + if galaxy_url := common_util.handle_galaxy_url(trans, **kwd): kwd["galaxy_url"] = galaxy_url if "f-free-text-search" in kwd: if kwd["f-free-text-search"] == "All": @@ -595,8 +586,7 @@ def browse_valid_categories(self, trans, **kwd): @web.expose def browse_valid_repositories(self, trans, **kwd): """Filter repositories to those that are installable into Galaxy.""" - galaxy_url = common_util.handle_galaxy_url(trans, **kwd) - if galaxy_url: + if galaxy_url := common_util.handle_galaxy_url(trans, **kwd): kwd["galaxy_url"] = galaxy_url repository_id = kwd.get("id", None) if "f-free-text-search" in kwd: @@ -1152,8 +1142,7 @@ def get_ctx_rev(self, trans, **kwd): changeset_revision = kwd["changeset_revision"] repository = repository_util.get_repository_by_name_and_owner(trans.app, repository_name, repository_owner) repo = repository.hg_repo - ctx = hg_util.get_changectx_for_changeset(repo, changeset_revision) - if ctx: + if ctx := hg_util.get_changectx_for_changeset(repo, changeset_revision): return str(ctx.rev()) return "" @@ -1428,8 +1417,7 @@ def get_updated_repository_information(self, trans, name, owner, changeset_revis includes_tools_for_display_in_tool_panel = False includes_workflows = False readme_files_dict = None - metadata = repository_metadata.metadata - if metadata: + if metadata := repository_metadata.metadata: if "data_manager" in metadata: includes_data_managers = True if "datatypes" in metadata: @@ -1505,12 +1493,11 @@ def index(self, trans, **kwd): status = kwd.get("status", "done") # See if there are any RepositoryMetadata records since menu items require them. repository_metadata = get_first_repository_metadata(trans.sa_session) - current_user = trans.user # TODO: move the following to some in-memory register so these queries can be done once # at startup. The in-memory register can then be managed during the current session. can_administer_repositories = False has_deprecated_repositories = False - if current_user: + if current_user := trans.user: # See if the current user has any repositories that have been marked as deprecated. for repository in current_user.active_repositories: if repository.deprecated: @@ -1727,8 +1714,7 @@ def manage_repository(self, trans, id, **kwd): if error: status = "error" allow_push_select_field = SelectField(name="allow_push", multiple=True) - current_allow_push = repository.allow_push() - if current_allow_push: + if current_allow_push := repository.allow_push(): current_allow_push_list = current_allow_push.split(",") else: current_allow_push_list = [] @@ -2118,8 +2104,7 @@ def reset_all_metadata(self, trans, id, **kwd): ) rmm.reset_all_metadata_on_repository_in_tool_shed() rmm_metadata_dict = rmm.get_metadata_dict() - rmm_invalid_file_tups = rmm.get_invalid_file_tups() - if rmm_invalid_file_tups: + if rmm_invalid_file_tups := rmm.get_invalid_file_tups(): message = tool_util.generate_message_for_invalid_tools( trans.app, rmm_invalid_file_tups, repository, rmm_metadata_dict ) @@ -2155,8 +2140,7 @@ def set_email_alerts(self, trans, **kwd): """Set email alerts for selected repositories.""" # This method is called from multiple grids, so the caller must be passed. caller = kwd["caller"] - user = trans.user - if user: + if user := trans.user: repository_ids = util.listify(kwd.get("id", "")) total_alerts_added = 0 total_alerts_removed = 0 @@ -2450,8 +2434,7 @@ def view_changeset(self, trans, id, ctx_str, **kwd): @web.expose def view_or_manage_repository(self, trans, **kwd): - repository_id = kwd.get("id", None) - if repository_id: + if repository_id := kwd.get("id", None): repository = repository_util.get_repository_in_tool_shed(trans.app, repository_id) user = trans.user if repository: diff --git a/lib/tool_shed/webapp/frontend/src/schema/schema.ts b/lib/tool_shed/webapp/frontend/src/schema/schema.ts index c49abf299742..399b26a1e64c 100644 --- a/lib/tool_shed/webapp/frontend/src/schema/schema.ts +++ b/lib/tool_shed/webapp/frontend/src/schema/schema.ts @@ -290,7 +290,7 @@ export interface components { * Type * @description The digest method used to create the checksum. * The value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://github.com/ga4gh-discovery/ga4gh-checksum/blob/master/hash-alg.csv[GA4GH Checksum Hash Algorithm Registry]. - * Other values MAY be used, as long as implementors are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920]. + * Other values MAY be used, as long as implementers are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920]. * GA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future. */ type: string diff --git a/lib/tool_shed/webapp/model/__init__.py b/lib/tool_shed/webapp/model/__init__.py index f748f7938735..2f2be9dccfbe 100644 --- a/lib/tool_shed/webapp/model/__init__.py +++ b/lib/tool_shed/webapp/model/__init__.py @@ -168,8 +168,7 @@ def set_disk_usage(self, bytes): total_disk_usage = property(get_disk_usage, set_disk_usage) def set_password_cleartext(self, cleartext): - message = validate_password_str(cleartext) - if message: + if message := validate_password_str(cleartext): raise Exception(f"Invalid password: {message}") # Set 'self.password' to the digest of 'cleartext'. self.password = new_insecure_hash(text_type=cleartext) diff --git a/lib/tool_shed/webapp/security/__init__.py b/lib/tool_shed/webapp/security/__init__.py index 8bf4d52fbdb7..ce61f1dba1dd 100644 --- a/lib/tool_shed/webapp/security/__init__.py +++ b/lib/tool_shed/webapp/security/__init__.py @@ -273,8 +273,7 @@ def user_can_import_repository_archive(self, user, archive_owner): if user.username == archive_owner: return True # A member of the IUC is authorized to create new repositories that are owned by another user. - iuc_group = get_iuc_group(self.sa_session) - if iuc_group is not None: + if (iuc_group := get_iuc_group(self.sa_session)) is not None: for uga in iuc_group.users: if uga.user.id == user.id: return True diff --git a/lib/tool_shed_client/schema/trs.py b/lib/tool_shed_client/schema/trs.py index fceff90e76f7..8d9984800b7f 100644 --- a/lib/tool_shed_client/schema/trs.py +++ b/lib/tool_shed_client/schema/trs.py @@ -22,7 +22,7 @@ class Checksum(BaseModel): checksum: str = Field(..., description="The hex-string encoded checksum for the data. ") type: str = Field( ..., - description="The digest method used to create the checksum.\nThe value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://github.com/ga4gh-discovery/ga4gh-checksum/blob/master/hash-alg.csv[GA4GH Checksum Hash Algorithm Registry].\nOther values MAY be used, as long as implementors are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920].\nGA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future.", + description="The digest method used to create the checksum.\nThe value (e.g. `sha-256`) SHOULD be listed as `Hash Name String` in the https://github.com/ga4gh-discovery/ga4gh-checksum/blob/master/hash-alg.csv[GA4GH Checksum Hash Algorithm Registry].\nOther values MAY be used, as long as implementers are aware of the issues discussed in https://tools.ietf.org/html/rfc6920#section-9.4[RFC6920].\nGA4GH may provide more explicit guidance for use of non-IANA-registered algorithms in the future.", ) diff --git a/mypy.ini b/mypy.ini index 0676824eb3b9..e9da196321af 100644 --- a/mypy.ini +++ b/mypy.ini @@ -1,5 +1,4 @@ [mypy] -enable_incomplete_feature = Unpack plugins = pydantic.mypy show_error_codes = True ignore_missing_imports = True diff --git a/packages/app/setup.cfg b/packages/app/setup.cfg index c8cc845deed1..02a35b4e3afd 100644 --- a/packages/app/setup.cfg +++ b/packages/app/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -51,10 +50,9 @@ install_requires = cloudauthz==0.6.0 dparse gxformat2 - importlib-metadata<5 # Work around https://github.com/celery/kombu/issues/1600 - kombu + kombu>=5.3 lagom - lxml + lxml!=4.2.2 Mako Markdown MarkupSafe @@ -77,7 +75,7 @@ install_requires = WebOb Whoosh packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.entry_points] console_scripts = diff --git a/packages/auth/setup.cfg b/packages/auth/setup.cfg index cca3a9b7ad7c..5dfbe3c629e2 100644 --- a/packages/auth/setup.cfg +++ b/packages/auth/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -35,8 +34,8 @@ install_requires = galaxy-data galaxy-util packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/config/setup.cfg b/packages/config/setup.cfg index 16d2815d2a2e..a4bbe8efb729 100644 --- a/packages/config/setup.cfg +++ b/packages/config/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -38,7 +37,7 @@ install_requires = pykwalify PyYAML packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.entry_points] console_scripts = @@ -46,4 +45,4 @@ console_scripts = [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/config/test-requirements.txt b/packages/config/test-requirements.txt index a8797797f1cf..4340e1a6c3e8 100644 --- a/packages/config/test-requirements.txt +++ b/packages/config/test-requirements.txt @@ -1,2 +1,2 @@ -gravity +gravity>=1.0 pytest diff --git a/packages/data/setup.cfg b/packages/data/setup.cfg index 02f74386b9d5..94a5497e512f 100644 --- a/packages/data/setup.cfg +++ b/packages/data/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -37,13 +36,13 @@ install_requires = galaxy-util[template] alembic alembic-utils - bdbag + bdbag>=1.6.3 bx-python dnspython galaxy-sequence-utils - h5grove + h5grove>=1.2.1 h5py - isa-rwval + isa-rwval>=0.10.10 MarkupSafe msal mrcfile @@ -61,7 +60,7 @@ install_requires = typing-extensions WebOb packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.entry_points] console_scripts = diff --git a/packages/files/setup.cfg b/packages/files/setup.cfg index 9f89c257b476..3f7f01acaf1b 100644 --- a/packages/files/setup.cfg +++ b/packages/files/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -36,7 +35,7 @@ install_requires = fs typing-extensions packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = diff --git a/packages/files/test-requirements.txt b/packages/files/test-requirements.txt index 000f71070273..ad572b378cec 100644 --- a/packages/files/test-requirements.txt +++ b/packages/files/test-requirements.txt @@ -1,3 +1,3 @@ pytest fs-gcsfs -s3fs +s3fs>=2023.1.0,<2024 diff --git a/packages/job_execution/setup.cfg b/packages/job_execution/setup.cfg index ea1943235b8a..1d77581d51ff 100644 --- a/packages/job_execution/setup.cfg +++ b/packages/job_execution/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -40,7 +39,7 @@ install_requires = MarkupSafe SQLAlchemy>=1.4.25,<2 packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.entry_points] console_scripts = @@ -49,4 +48,4 @@ console_scripts = [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/meta/setup.cfg b/packages/meta/setup.cfg index 516107f5088d..e3d3a152e651 100644 --- a/packages/meta/setup.cfg +++ b/packages/meta/setup.cfg @@ -10,7 +10,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -34,7 +33,7 @@ version = 22.5.0.dev0 [options] include_package_data = True packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.extras_require] postgresql = diff --git a/packages/navigation/setup.cfg b/packages/navigation/setup.cfg index 3b16102ad68c..7b346eaa30cb 100644 --- a/packages/navigation/setup.cfg +++ b/packages/navigation/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -35,8 +34,8 @@ install_requires = galaxy-util PyYAML packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/schema/setup.cfg b/packages/schema/setup.cfg index 507f563909ea..eec616559910 100644 --- a/packages/schema/setup.cfg +++ b/packages/schema/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -32,9 +31,9 @@ version = 23.1.0.dev0 include_package_data = True install_requires = galaxy-util - pydantic[email] + pydantic[email]<2 packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = diff --git a/packages/selenium/setup.cfg b/packages/selenium/setup.cfg index a95b3a449dfa..338943d2013e 100644 --- a/packages/selenium/setup.cfg +++ b/packages/selenium/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -39,7 +38,7 @@ install_requires = requests selenium!=4.11.0,!=4.11.1,!=4.11.2 packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.entry_points] console_scripts = @@ -47,4 +46,4 @@ console_scripts = [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/test_api/setup.cfg b/packages/test_api/setup.cfg index 2a09121053d3..a759e952956e 100644 --- a/packages/test_api/setup.cfg +++ b/packages/test_api/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -38,7 +37,7 @@ install_requires = requests tuspy packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.extras_require] driver = @@ -46,4 +45,4 @@ driver = [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/test_base/setup.cfg b/packages/test_base/setup.cfg index a1eec0ef392e..17c957eec67a 100644 --- a/packages/test_base/setup.cfg +++ b/packages/test_base/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -41,8 +40,8 @@ install_requires = PyYAML requests packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/test_driver/setup.cfg b/packages/test_driver/setup.cfg index cd64afd37a8c..9268dd3eb584 100644 --- a/packages/test_driver/setup.cfg +++ b/packages/test_driver/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -43,8 +42,8 @@ install_requires = graphene-sqlalchemy==3.0.0b3 # these are only needed by tool shed - which we've split out but the test driver loads starlette-graphene3 packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/packages/test_selenium/setup.cfg b/packages/test_selenium/setup.cfg index dca41568d040..177fbc9ba8ad 100644 --- a/packages/test_selenium/setup.cfg +++ b/packages/test_selenium/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -43,7 +42,7 @@ install_requires = requests selenium!=4.11.0,!=4.11.1,!=4.11.2 packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.extras_require] driver = diff --git a/packages/tool_shed/setup.cfg b/packages/tool_shed/setup.cfg index 50b32d282a99..304c61ed9f40 100644 --- a/packages/tool_shed/setup.cfg +++ b/packages/tool_shed/setup.cfg @@ -9,10 +9,10 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 + Programming Language :: Python :: 3.11 Topic :: Software Development Topic :: Software Development :: Code Generators Topic :: Software Development :: Testing @@ -34,7 +34,7 @@ install_requires = galaxy-web-stack galaxy-web-apps packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = diff --git a/packages/tool_util/setup.cfg b/packages/tool_util/setup.cfg index 817bd9080842..354417845ca6 100644 --- a/packages/tool_util/setup.cfg +++ b/packages/tool_util/setup.cfg @@ -34,7 +34,7 @@ include_package_data = True install_requires = galaxy-util>=22.1 conda-package-streaming - lxml + lxml!=4.2.2 MarkupSafe packaging pydantic<2 @@ -59,7 +59,7 @@ console_scripts = [options.extras_require] cwl = - cwltool==3.1.20221109155812 + cwltool>=3.1.20230624081518 mulled = jinja2 Whoosh diff --git a/packages/tours/setup.cfg b/packages/tours/setup.cfg index 1186d0ad6ccf..999022f00af8 100644 --- a/packages/tours/setup.cfg +++ b/packages/tours/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -36,7 +35,7 @@ install_requires = pydantic<2 PyYAML packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.entry_points] console_scripts = diff --git a/packages/util/setup.cfg b/packages/util/setup.cfg index 03afa41b853b..39708d11975a 100644 --- a/packages/util/setup.cfg +++ b/packages/util/setup.cfg @@ -34,8 +34,8 @@ include_package_data = True install_requires = bleach boltons - docutils - importlib_resources + docutils!=0.17,!=0.17.1 + importlib-resources;python_version<'3.9' packaging pyparsing PyYAML @@ -50,7 +50,7 @@ python_requires = >=3.7 jstree = dictobj template = - Cheetah3 + Cheetah3!=3.2.6.post2 future [options.packages.find] diff --git a/packages/web_apps/setup.cfg b/packages/web_apps/setup.cfg index 17de386f4c12..472f09cc1c85 100644 --- a/packages/web_apps/setup.cfg +++ b/packages/web_apps/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -42,12 +41,12 @@ install_requires = a2wsgi apispec Babel - Cheetah3 - fastapi>=0.68.2,!=0.69.0,!=0.70.0,!=0.70.1,<0.99 + Cheetah3!=3.2.6.post2 + fastapi>=0.71.0,!=0.89.0,<0.99 fastapi-utils gunicorn gxformat2 - importlib_resources + importlib-resources;python_version<'3.9' Mako MarkupSafe mercurial @@ -70,7 +69,7 @@ install_requires = WebOb Whoosh packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = diff --git a/packages/web_framework/setup.cfg b/packages/web_framework/setup.cfg index 99cce6a9e4c7..adceeced72ed 100644 --- a/packages/web_framework/setup.cfg +++ b/packages/web_framework/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -44,7 +43,7 @@ install_requires = WebOb packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = diff --git a/packages/web_stack/setup.cfg b/packages/web_stack/setup.cfg index 9d9e2022c398..6c1ff8aaee98 100644 --- a/packages/web_stack/setup.cfg +++ b/packages/web_stack/setup.cfg @@ -9,7 +9,6 @@ classifiers = Natural Language :: English Operating System :: POSIX Programming Language :: Python :: 3 - Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 @@ -36,8 +35,8 @@ install_requires = galaxy-util SQLAlchemy>=1.4.25,<2 packages = find: -python_requires = >=3.7 +python_requires = >=3.8 [options.packages.find] exclude = - tests* \ No newline at end of file + tests* diff --git a/pyproject.toml b/pyproject.toml index ec98c6f49ef2..625d43195168 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [tool.black] line-length = 120 -target-version = ['py37'] +target-version = ['py38'] include = '\.pyi?$' extend-exclude = ''' ^/( @@ -50,7 +50,7 @@ Cheetah3 = "!=3.2.6.post2" # yanked release, https://github.com/python-poetry/p cloudauthz = "==0.6.0" cloudbridge = "*" circus = "*" -cwltool = "==3.1.20221109155812" +cwltool = ">=3.1.20230624081518" # save time, minimum needed by cwl-1.0 branch conda-package-streaming = "*" dictobj = "*" dnspython = "*" @@ -68,10 +68,9 @@ gunicorn = "*" gxformat2 = "*" h5grove = ">=1.2.1" h5py = "*" -importlib-metadata = "<5" # Work around https://github.com/celery/kombu/issues/1600 -importlib-resources = "*" +importlib-resources = { version = "*", python = "<3.9" } # for importlib.{abc.Traversable,resources.{files, Package}} isa-rwval = ">=0.10.10" -kombu = "*" +kombu = ">=5.3" # for importlib-metadata fix lagom = "*" Mako = "*" Markdown = "*" @@ -93,9 +92,9 @@ pydantic = {version = "<2", extras = ["email"]} PyJWT = "*" pykwalify = "*" pylibmagic = "*" -pyparsing = "<3.1" # Needed by matplotlib on Python >=3.8 https://github.com/matplotlib/matplotlib/issues/26152 +pyparsing = "*" pysam = ">=0.21" # for Python 3.11 support on macOS -python = ">=3.7,<3.12" # Keep maximum version strict to appease numpy and scipy +python = ">=3.8,<3.12" # Keep maximum version strict to appease numpy and scipy python-dateutil = "*" python-magic = "*" python-multipart = "*" # required to support form parsing in FastAPI/Starlette @@ -155,13 +154,14 @@ pytest-postgresql = "!=3.0.0" # https://github.com/ClearcodeHQ/pytest-postgresq pytest-shard = "*" responses = "*" selenium = "*" +urllib3 = "<2" # Necessary for poetry for resolve deps for Python 3.8+ seletools = "*" Sphinx = ">=4.0" # support docutils 0.17 sphinx-rtd-theme = ">=1.0.0,<2" # https://github.com/python-poetry/poetry/issues/8194 statsd = "*" testfixtures = "*" tuspy = "*" -twill = "*" +twill = ">=3.2.1" # https://github.com/twill-tools/twill/issues/18 watchdog = "*" [tool.poetry.group.typecheck.dependencies] @@ -184,7 +184,7 @@ types-six = "*" # Enable: pycodestyle errors (E), Pyflakes (F), flake8-bugbear (B), # flake8-logging-format (G) and pyupgrade (UP) select = ["E", "F", "B", "G", "UP"] -target-version = "py37" +target-version = "py38" # Exceptions: # B008 Do not perform function calls in argument defaults (for FastAPI Depends and Body) # B9 flake8-bugbear opinionated warnings diff --git a/scripts/apply_tags.py b/scripts/apply_tags.py index 32de6df53e00..fabf9470eebf 100644 --- a/scripts/apply_tags.py +++ b/scripts/apply_tags.py @@ -136,9 +136,8 @@ def propagate_tags(self, history, current_history_id, parent_datasets_ids, datas self_tags = self.collect_hash_tags(own_tags[dataset_id]) # find unique tags from all parents all_tags_set = set(all_tags) - self_tags_set = set(self_tags) # update tags if there are new tags from parents - if all_tags_set != self_tags_set: + if all_tags_set != (self_tags_set := set(self_tags)): if not all_tags_set.issubset(self_tags_set): # append the tags of the child itself all_tags.extend(self_tags) diff --git a/scripts/check_model.py b/scripts/check_model.py index 3f411963270a..d1661df4975e 100644 --- a/scripts/check_model.py +++ b/scripts/check_model.py @@ -53,8 +53,7 @@ def load_indexes(metadata): all_indexes = set(mapping_indexes.keys()) | set(tsi_mapping_indexes.keys()) - missing_indexes = all_indexes - set(indexes_in_db.keys()) - if missing_indexes: + if missing_indexes := all_indexes - set(indexes_in_db.keys()): return [(mapping_indexes[index], index.table, index.column_names) for index in missing_indexes] diff --git a/scripts/check_python.py b/scripts/check_python.py index 99fd1c9fcbe8..62a8cfbfa59e 100644 --- a/scripts/check_python.py +++ b/scripts/check_python.py @@ -7,7 +7,7 @@ def check_python(): - if sys.version_info[:2] >= (3, 7): # noqa: UP036 + if sys.version_info[:2] >= (3, 8): # noqa: UP036 # supported return else: @@ -15,7 +15,7 @@ def check_python(): msg = ( """\ ERROR: Your Python version is: %s -Galaxy is currently supported on Python >=3.7 . +Galaxy is currently supported on Python >=3.8 . To run Galaxy, please install a supported Python version. If a supported version is already installed but is not your default, https://docs.galaxyproject.org/en/latest/admin/python.html contains instructions diff --git a/scripts/common_startup.sh b/scripts/common_startup.sh index 720f64a79110..e1fa46fdbac6 100755 --- a/scripts/common_startup.sh +++ b/scripts/common_startup.sh @@ -14,7 +14,7 @@ SKIP_NODE=${GALAXY_SKIP_NODE:-0} INSTALL_PREBUILT_CLIENT=${GALAXY_INSTALL_PREBUILT_CLIENT:-0} NODE_VERSION=${GALAXY_NODE_VERSION:-"$(cat client/.node_version)"} : "${YARN_INSTALL_OPTS:=--network-timeout 300000 --check-files}" -: "${GALAXY_CONDA_PYTHON_VERSION:=3.7}" +: "${GALAXY_CONDA_PYTHON_VERSION:=3.8}" for arg in "$@"; do if [ "$arg" = "--skip-venv" ]; then @@ -41,7 +41,7 @@ RMFILES=" lib/pkg_resources.pyc " -MIN_PYTHON_VERSION=3.7 +MIN_PYTHON_VERSION=3.8 MIN_PIP_VERSION=20.3 # return true if $1 is in $2 else false diff --git a/test/integration/test_celery_user_rate_limit.py b/test/integration/test_celery_user_rate_limit.py index 5d58d02f9025..ac69062dfda1 100644 --- a/test/integration/test_celery_user_rate_limit.py +++ b/test/integration/test_celery_user_rate_limit.py @@ -24,7 +24,7 @@ def mock_user_id_task(task_user_id: int): return task_user_id -@lru_cache() +@lru_cache def sqlite_url(): path = tempfile.NamedTemporaryFile().name dburl = f"sqlite:///{path}" @@ -32,7 +32,7 @@ def sqlite_url(): return dburl -@lru_cache() +@lru_cache def setup_users(dburl: str, num_users: int = 2): """ Setup test users in galaxy_user table with user id's starting from 2. diff --git a/test/integration/test_kubernetes_runner.py b/test/integration/test_kubernetes_runner.py index 62a353693ea5..728d2a4fbfdd 100644 --- a/test/integration/test_kubernetes_runner.py +++ b/test/integration/test_kubernetes_runner.py @@ -4,6 +4,7 @@ import collections import json import os +import shlex import string import subprocess import tempfile @@ -18,10 +19,7 @@ from typing_extensions import Literal from galaxy.tool_util.verify.wait import timeout_type -from galaxy.util import ( - shlex_join, - unicodify, -) +from galaxy.util import unicodify from galaxy_test.base.populators import ( DatasetPopulator, DEFAULT_TIMEOUT, @@ -361,7 +359,7 @@ def get_kubectl_logs(allow_wait: bool = True) -> Optional[str]: if allow_wait and "is waiting to start" in p.stderr: return None raise Exception( - f"Command '{shlex_join(log_cmd)}' failed with exit code: {p.returncode}.\nstdout: {p.stdout}\nstderr: {p.stderr}" + f"Command '{shlex.join(log_cmd)}' failed with exit code: {p.returncode}.\nstdout: {p.stdout}\nstderr: {p.stderr}" ) return p.stdout diff --git a/test/unit/app/jobs/test_rule_helper.py b/test/unit/app/jobs/test_rule_helper.py index eaf98dc0741e..1d1197a0dc78 100644 --- a/test/unit/app/jobs/test_rule_helper.py +++ b/test/unit/app/jobs/test_rule_helper.py @@ -56,8 +56,7 @@ def test_job_count(): def __assert_job_count_is(expected_count, rule_helper, **kwds): - actual_count = rule_helper.job_count(**kwds) - if expected_count != actual_count: + if expected_count != (actual_count := rule_helper.job_count(**kwds)): raise AssertionError(f"Expected job count {expected_count}, actual job count {actual_count} for params {kwds}") diff --git a/test/unit/app/managers/test_NotificationManager.py b/test/unit/app/managers/test_NotificationManager.py index 99d493b3ef3b..b644e20e7b10 100644 --- a/test/unit/app/managers/test_NotificationManager.py +++ b/test/unit/app/managers/test_NotificationManager.py @@ -95,14 +95,12 @@ def _assert_notification_expected(self, actual_notification: Any, expected_notif assert actual_notification.variant == expected_notification["variant"] assert actual_notification.category == expected_notification["category"] - expected_publication_time = expected_notification.get("publication_time") - if expected_publication_time: + if expected_publication_time := expected_notification.get("publication_time"): assert actual_notification.publication_time == expected_publication_time else: assert actual_notification.publication_time is not None - expected_expiration_time = expected_notification.get("expiration_time") - if expected_expiration_time: + if expected_expiration_time := expected_notification.get("expiration_time"): assert actual_notification.expiration_time == expected_expiration_time else: assert actual_notification.expiration_time is not None @@ -276,7 +274,7 @@ def test_update_user_notifications(self): assert user_notification.seen_time is None assert user_notification.deleted is False request = UserNotificationUpdateRequest(seen=True) - self.notification_manager.update_user_notifications(user, set([notification.id]), request) + self.notification_manager.update_user_notifications(user, {notification.id}, request) user_notification = self.notification_manager.get_user_notification(user, notification.id) assert user_notification.seen_time is not None assert user_notification.deleted is False diff --git a/test/unit/data/model/migrations/test_migrations.py b/test/unit/data/model/migrations/test_migrations.py index 20665cd1fdd5..51cba45265ab 100644 --- a/test/unit/data/model/migrations/test_migrations.py +++ b/test/unit/data/model/migrations/test_migrations.py @@ -43,7 +43,10 @@ drop_existing_database, url_factory, ) -from galaxy.util.resources import resource_path +from galaxy.util.resources import ( + as_file, + resource_path, +) # Revision numbers from test versions directories GXY_REVISION_0 = "62695fac6cc0" # oldest/base @@ -1128,10 +1131,13 @@ def db_state6_gxy_state3_tsi_no_sam(url_factory, metadata_state6_gxy_state3_tsi_ @pytest.fixture(autouse=True) def legacy_manage_db(monkeypatch): def get_alembic_cfg(): - path = resource_path("galaxy.model.migrations", "alembic.ini") - config = Config(path) - path1, path2 = _get_paths_to_version_locations() - config.set_main_option("version_locations", f"{path1};{path2}") + traversable = resource_path("galaxy.model.migrations", "alembic.ini") + with as_file(traversable) as path: + config = Config(path) + path1, path2 = _get_paths_to_version_locations() + config.set_main_option("version_locations", f"{path1};{path2}") + # config.set_main_option() calls config.file_config() which memoizes + # the temporary file path from the as_file() contextmanager return config monkeypatch.setattr(galaxy.model.migrations.scripts, "get_alembic_cfg", get_alembic_cfg) diff --git a/test/unit/data/test_galaxy_mapping.py b/test/unit/data/test_galaxy_mapping.py index c7a2d4eb8366..c22d51f45eae 100644 --- a/test/unit/data/test_galaxy_mapping.py +++ b/test/unit/data/test_galaxy_mapping.py @@ -1095,8 +1095,7 @@ def _make_owned(self, security_agent, user, hda): def _set_permissions(self, security_agent, dataset, permissions): # TODO: refactor set_all_dataset_permissions to actually throw an exception :| - error = security_agent.set_all_dataset_permissions(dataset, permissions) - if error: + if error := security_agent.set_all_dataset_permissions(dataset, permissions): raise Exception(error) def new_hda(self, history, **kwds): diff --git a/test/unit/tool_util/data/test_tool_data_bundles.py b/test/unit/tool_util/data/test_tool_data_bundles.py index 2e1a1f271740..9c6afddc5735 100644 --- a/test/unit/tool_util/data/test_tool_data_bundles.py +++ b/test/unit/tool_util/data/test_tool_data_bundles.py @@ -15,7 +15,10 @@ galaxy_directory, parse_xml, ) -from galaxy.util.resources import resource_path +from galaxy.util.resources import ( + as_file, + resource_path, +) TOOLS_DIRECTORY = os.path.abspath(os.path.join(galaxy_directory(), "test/functional/tools/")) @@ -51,8 +54,8 @@ def test_xml_parsing() -> None: def test_parsing_manual() -> None: - path = resource_path(__package__, "example_data_managers/manual.xml") - tree = parse_xml(path) + with as_file(resource_path(__package__, "example_data_managers/manual.xml")) as path: + tree = parse_xml(path) data_managers_el = tree.getroot() data_manager_el = data_managers_el.find("data_manager") description = convert_data_tables_xml(data_manager_el) @@ -61,8 +64,8 @@ def test_parsing_manual() -> None: def test_parsing_mothur() -> None: - path = resource_path(__package__, "example_data_managers/mothur.xml") - tree = parse_xml(path) + with as_file(resource_path(__package__, "example_data_managers/mothur.xml")) as path: + tree = parse_xml(path) data_managers_el = tree.getroot() data_manager_el = data_managers_el.find("data_manager") description = convert_data_tables_xml(data_manager_el) diff --git a/tox.ini b/tox.ini index 2bde302555f9..c68144f12885 100644 --- a/tox.ini +++ b/tox.ini @@ -39,6 +39,8 @@ passenv = GALAXY_CONFIG_OVERRIDE_DATABASE_CONNECTION APP_WEBSERVER TERM + TEST_PYTHON + TZ setenv = coverage: GALAXY_TEST_COVERAGE=1 first_startup: GALAXY_CONFIG_DATABASE_AUTO_MIGRATE=true