Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package python-pyupgrade for 
openSUSE:Factory checked in at 2023-06-03 00:07:25
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-pyupgrade (Old)
 and      /work/SRC/openSUSE:Factory/.python-pyupgrade.new.15902 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "python-pyupgrade"

Sat Jun  3 00:07:25 2023 rev:30 rq:1090388 version:3.4.0

Changes:
--------
--- /work/SRC/openSUSE:Factory/python-pyupgrade/python-pyupgrade.changes        
2022-12-03 12:48:35.698140645 +0100
+++ 
/work/SRC/openSUSE:Factory/.python-pyupgrade.new.15902/python-pyupgrade.changes 
    2023-06-03 00:07:33.478107359 +0200
@@ -1,0 +2,7 @@
+Thu Jun  1 20:18:41 UTC 2023 - Dirk Müller <dmuel...@suse.com>
+
+- update to 3.4.0:
+  * drop python37 support
+  * remove use of deprecated ast
+
+-------------------------------------------------------------------

Old:
----
  python-pyupgrade-3.2.2.tar.gz

New:
----
  python-pyupgrade-3.4.0.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ python-pyupgrade.spec ++++++
--- /var/tmp/diff_new_pack.JqJBRh/_old  2023-06-03 00:07:34.114111115 +0200
+++ /var/tmp/diff_new_pack.JqJBRh/_new  2023-06-03 00:07:34.122111162 +0200
@@ -1,7 +1,7 @@
 #
 # spec file for package python-pyupgrade
 #
-# Copyright (c) 2022 SUSE LLC
+# Copyright (c) 2023 SUSE LLC
 #
 # All modifications and additions to the file contributed by third parties
 # remain the property of their copyright owners, unless otherwise agreed
@@ -16,10 +16,9 @@
 #
 
 
-%{?!python_module:%define python_module() python-%{**} python3-%{**}}
-%define skip_python2 1
+%{?sle15_python_module_pythons}
 Name:           python-pyupgrade
-Version:        3.2.2
+Version:        3.4.0
 Release:        0
 Summary:        A tool to automatically upgrade syntax for newer versions
 License:        MIT

++++++ python-pyupgrade-3.2.2.tar.gz -> python-pyupgrade-3.4.0.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/.github/workflows/main.yml 
new/pyupgrade-3.4.0/.github/workflows/main.yml
--- old/pyupgrade-3.2.2/.github/workflows/main.yml      1970-01-01 
01:00:00.000000000 +0100
+++ new/pyupgrade-3.4.0/.github/workflows/main.yml      2023-05-06 
23:09:25.000000000 +0200
@@ -0,0 +1,19 @@
+name: main
+
+on:
+  push:
+    branches: [main, test-me-*]
+    tags:
+  pull_request:
+
+jobs:
+  main-windows:
+    uses: asottile/workflows/.github/workflows/tox.yml@v1.0.0
+    with:
+      env: '["py38"]'
+      os: windows-latest
+  main-linux:
+    uses: asottile/workflows/.github/workflows/tox.yml@v1.0.0
+    with:
+      env: '["py38", "py39", "py310"]'
+      os: ubuntu-latest
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/.pre-commit-config.yaml 
new/pyupgrade-3.4.0/.pre-commit-config.yaml
--- old/pyupgrade-3.2.2/.pre-commit-config.yaml 2022-11-10 16:38:09.000000000 
+0100
+++ new/pyupgrade-3.4.0/.pre-commit-config.yaml 2023-05-06 23:09:25.000000000 
+0200
@@ -1,6 +1,6 @@
 repos:
 -   repo: https://github.com/pre-commit/pre-commit-hooks
-    rev: v4.3.0
+    rev: v4.4.0
     hooks:
     -   id: trailing-whitespace
     -   id: end-of-file-fixer
@@ -17,26 +17,26 @@
     rev: v3.9.0
     hooks:
     -   id: reorder-python-imports
-        args: [--py37-plus, --add-import, 'from __future__ import annotations']
+        args: [--py38-plus, --add-import, 'from __future__ import annotations']
 -   repo: https://github.com/asottile/add-trailing-comma
-    rev: v2.3.0
+    rev: v2.4.0
     hooks:
     -   id: add-trailing-comma
         args: [--py36-plus]
 -   repo: https://github.com/asottile/pyupgrade
-    rev: v3.2.2
+    rev: v3.4.0
     hooks:
     -   id: pyupgrade
-        args: [--py37-plus]
+        args: [--py38-plus]
 -   repo: https://github.com/pre-commit/mirrors-autopep8
-    rev: v2.0.0
+    rev: v2.0.2
     hooks:
     -   id: autopep8
 -   repo: https://github.com/PyCQA/flake8
-    rev: 5.0.4
+    rev: 6.0.0
     hooks:
     -   id: flake8
 -   repo: https://github.com/pre-commit/mirrors-mypy
-    rev: v0.982
+    rev: v1.2.0
     hooks:
     -   id: mypy
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/README.md 
new/pyupgrade-3.4.0/README.md
--- old/pyupgrade-3.2.2/README.md       2022-11-10 16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/README.md       2023-05-06 23:09:25.000000000 +0200
@@ -1,5 +1,4 @@
-[![Build 
Status](https://dev.azure.com/asottile/asottile/_apis/build/status/asottile.pyupgrade?branchName=main)](https://dev.azure.com/asottile/asottile/_build/latest?definitionId=2&branchName=main)
-[![Azure DevOps 
coverage](https://img.shields.io/azure-devops/coverage/asottile/asottile/2/main.svg)](https://dev.azure.com/asottile/asottile/_build/latest?definitionId=2&branchName=main)
+[![build 
status](https://github.com/asottile/pyupgrade/actions/workflows/main.yml/badge.svg)](https://github.com/asottile/pyupgrade/actions/workflows/main.yml)
 [![pre-commit.ci 
status](https://results.pre-commit.ci/badge/github/asottile/pyupgrade/main.svg)](https://results.pre-commit.ci/latest/github/asottile/pyupgrade/main)
 
 pyupgrade
@@ -22,7 +21,7 @@
 
 ```yaml
 -   repo: https://github.com/asottile/pyupgrade
-    rev: v3.2.2
+    rev: v3.4.0
     hooks:
     -   id: pyupgrade
 ```
@@ -694,3 +693,16 @@
 -def f(x: 'queue.Queue[int]') -> C:
 +def f(x: queue.Queue[int]) -> C:
 ```
+
+
+### use `datetime.UTC` alias
+
+Availability:
+- `--py311-plus` is passed on the commandline.
+
+```diff
+ import datetime
+
+-datetime.timezone.utc
++datetime.UTC
+```
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/azure-pipelines.yml 
new/pyupgrade-3.4.0/azure-pipelines.yml
--- old/pyupgrade-3.2.2/azure-pipelines.yml     2022-11-10 16:38:09.000000000 
+0100
+++ new/pyupgrade-3.4.0/azure-pipelines.yml     1970-01-01 01:00:00.000000000 
+0100
@@ -1,23 +0,0 @@
-trigger:
-  branches:
-    include: [main, test-me-*]
-  tags:
-    include: ['*']
-
-resources:
-  repositories:
-    - repository: asottile
-      type: github
-      endpoint: github
-      name: asottile/azure-pipeline-templates
-      ref: refs/tags/v2.4.1
-
-jobs:
-- template: job--python-tox.yml@asottile
-  parameters:
-    toxenvs: [py37]
-    os: windows
-- template: job--python-tox.yml@asottile
-  parameters:
-    toxenvs: [py37, py38, py39]
-    os: linux
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/pyupgrade/_plugins/datetime_utc_alias.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/datetime_utc_alias.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/datetime_utc_alias.py        
1970-01-01 01:00:00.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/datetime_utc_alias.py        
2023-05-06 23:09:25.000000000 +0200
@@ -0,0 +1,35 @@
+from __future__ import annotations
+
+import ast
+import functools
+from typing import Iterable
+
+from tokenize_rt import Offset
+
+from pyupgrade._ast_helpers import ast_to_offset
+from pyupgrade._data import register
+from pyupgrade._data import State
+from pyupgrade._data import TokenFunc
+from pyupgrade._token_helpers import replace_name
+
+
+@register(ast.Attribute)
+def visit_Attribute(
+        state: State,
+        node: ast.Attribute,
+        parent: ast.AST,
+) -> Iterable[tuple[Offset, TokenFunc]]:
+    if (
+            state.settings.min_version >= (3, 11) and
+            node.attr == 'utc' and
+            isinstance(node.value, ast.Attribute) and
+            node.value.attr == 'timezone' and
+            isinstance(node.value.value, ast.Name) and
+            node.value.value.id == 'datetime'
+    ):
+        func = functools.partial(
+            replace_name,
+            name='utc',
+            new='datetime.UTC',
+        )
+        yield ast_to_offset(node), func
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/pyupgrade/_plugins/default_encoding.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/default_encoding.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/default_encoding.py  2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/default_encoding.py  2023-05-06 
23:09:25.000000000 +0200
@@ -29,12 +29,18 @@
         parent: ast.AST,
 ) -> Iterable[tuple[Offset, TokenFunc]]:
     if (
-            isinstance(node.func, ast.Attribute) and
-            isinstance(node.func.value, (ast.Str, ast.JoinedStr)) and
+            isinstance(node.func, ast.Attribute) and (
+                (
+                    isinstance(node.func.value, ast.Constant) and
+                    isinstance(node.func.value.value, str)
+                ) or
+                isinstance(node.func.value, ast.JoinedStr)
+            ) and
             node.func.attr == 'encode' and
             not has_starargs(node) and
             len(node.args) == 1 and
-            isinstance(node.args[0], ast.Str) and
-            is_codec(node.args[0].s, 'utf-8')
+            isinstance(node.args[0], ast.Constant) and
+            isinstance(node.args[0].value, str) and
+            is_codec(node.args[0].value, 'utf-8')
     ):
         yield ast_to_offset(node), _fix_default_encoding
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/format_locals.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/format_locals.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/format_locals.py     2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/format_locals.py     2023-05-06 
23:09:25.000000000 +0200
@@ -35,7 +35,8 @@
     if (
             state.settings.min_version >= (3, 6) and
             isinstance(node.func, ast.Attribute) and
-            isinstance(node.func.value, ast.Str) and
+            isinstance(node.func.value, ast.Constant) and
+            isinstance(node.func.value.value, str) and
             node.func.attr == 'format' and
             len(node.args) == 0 and
             len(node.keywords) == 1 and
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/fstrings.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/fstrings.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/fstrings.py  2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/fstrings.py  2023-05-06 
23:09:25.000000000 +0200
@@ -4,6 +4,7 @@
 from typing import Iterable
 
 from tokenize_rt import Offset
+from tokenize_rt import parse_string_literal
 from tokenize_rt import Token
 from tokenize_rt import tokens_to_src
 
@@ -43,7 +44,12 @@
 
     parts = []
     i = 0
-    for s, name, spec, conv in parse_format('f' + src):
+
+    # need to remove `u` prefix so it isn't invalid syntax
+    prefix, rest = parse_string_literal(src)
+    new_src = 'f' + prefix.translate({ord('u'): None, ord('U'): None}) + rest
+
+    for s, name, spec, conv in parse_format(new_src):
         if name is not None:
             k, dot, rest = name.partition('.')
             name = ''.join((params[k or str(i)], dot, rest))
@@ -93,12 +99,13 @@
 
     if (
             isinstance(node.func, ast.Attribute) and
-            isinstance(node.func.value, ast.Str) and
+            isinstance(node.func.value, ast.Constant) and
+            isinstance(node.func.value.value, str) and
             node.func.attr == 'format' and
             not has_starargs(node)
     ):
         try:
-            parsed = parse_format(node.func.value.s)
+            parsed = parse_format(node.func.value.value)
         except ValueError:
             return
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/pyupgrade/_plugins/identity_equality.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/identity_equality.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/identity_equality.py 2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/identity_equality.py 2023-05-06 
23:09:25.000000000 +0200
@@ -12,8 +12,6 @@
 from pyupgrade._data import State
 from pyupgrade._data import TokenFunc
 
-LITERAL_TYPES = (ast.Str, ast.Num, ast.Bytes)
-
 
 def _fix_is_literal(
         i: int,
@@ -35,6 +33,14 @@
         tokens[i] = Token('EMPTY', '')
 
 
+def _is_literal(n: ast.AST) -> bool:
+    return (
+        isinstance(n, ast.Constant) and
+        n.value not in {True, False} and
+        isinstance(n.value, (str, bytes, int, float))
+    )
+
+
 @register(ast.Compare)
 def visit_Compare(
         state: State,
@@ -45,10 +51,7 @@
     for op, right in zip(node.ops, node.comparators):
         if (
                 isinstance(op, (ast.Is, ast.IsNot)) and
-                (
-                    isinstance(left, LITERAL_TYPES) or
-                    isinstance(right, LITERAL_TYPES)
-                )
+                (_is_literal(left) or _is_literal(right))
         ):
             func = functools.partial(_fix_is_literal, op=op)
             yield ast_to_offset(right), func
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/imports.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/imports.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/imports.py   2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/imports.py   2023-05-06 
23:09:25.000000000 +0200
@@ -281,6 +281,7 @@
     mod_start: int
     mod_end: int
     names: tuple[int, ...]
+    ends: tuple[int, ...]
     end: int
 
     @classmethod
@@ -310,11 +311,14 @@
             for j in range(import_token + 1, end)
             if tokens[j].name == 'NAME'
         ]
+        ends_by_offset = {}
         for i in reversed(range(len(names))):
             if tokens[names[i]].src == 'as':
+                ends_by_offset[names[i - 1]] = names[i + 1]
                 del names[i:i + 2]
+        ends = tuple(ends_by_offset.get(pos, pos) for pos in names)
 
-        return cls(start, mod_start, mod_end + 1, tuple(names), end)
+        return cls(start, mod_start, mod_end + 1, tuple(names), ends, end)
 
     def remove_self(self, tokens: list[Token]) -> None:
         del tokens[self.start:self.end]
@@ -327,10 +331,10 @@
             if idx == 0:  # look forward until next name and del
                 del tokens[self.names[idx]:self.names[idx + 1]]
             else:  # look backward for comma and del
-                j = end = self.names[idx]
+                j = self.names[idx]
                 while tokens[j].src != ',':
                     j -= 1
-                del tokens[j:end + 1]
+                del tokens[j:self.ends[idx] + 1]
 
 
 def _alias_to_s(alias: ast.alias) -> str:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/lru_cache.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/lru_cache.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/lru_cache.py 2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/lru_cache.py 2023-05-06 
23:09:25.000000000 +0200
@@ -28,7 +28,7 @@
 ) -> bool:
     return (
         keyword.arg == name and
-        isinstance(keyword.value, ast.NameConstant) and
+        isinstance(keyword.value, ast.Constant) and
         keyword.value.value is value
     )
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/pyupgrade/_plugins/native_literals.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/native_literals.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/native_literals.py   2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/native_literals.py   2023-05-06 
23:09:25.000000000 +0200
@@ -44,7 +44,11 @@
         not has_starargs(node) and
         (
             len(node.args) == 0 or
-            (len(node.args) == 1 and isinstance(node.args[0], ast.Str))
+            (
+                len(node.args) == 1 and
+                isinstance(node.args[0], ast.Constant) and
+                isinstance(node.args[0].value, str)
+            )
         )
     )
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/open_mode.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/open_mode.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/open_mode.py 2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/open_mode.py 2023-05-06 
23:09:25.000000000 +0200
@@ -81,10 +81,14 @@
             ) and
             not has_starargs(node)
     ):
-        if len(node.args) >= 2 and isinstance(node.args[1], ast.Str):
+        if (
+                len(node.args) >= 2 and
+                isinstance(node.args[1], ast.Constant) and
+                isinstance(node.args[1].value, str)
+        ):
             if (
-                node.args[1].s in MODE_REPLACE or
-                (len(node.args) == 2 and node.args[1].s in MODE_REMOVE)
+                node.args[1].value in MODE_REPLACE or
+                (len(node.args) == 2 and node.args[1].value in MODE_REMOVE)
             ):
                 func = functools.partial(_fix_open_mode, arg_idx=1)
                 yield ast_to_offset(node), func
@@ -99,10 +103,11 @@
             )
             if (
                 mode is not None and
-                isinstance(mode.value, ast.Str) and
+                isinstance(mode.value, ast.Constant) and
+                isinstance(mode.value.value, str) and
                 (
-                    mode.value.s in MODE_REMOVE or
-                    mode.value.s in MODE_REPLACE
+                    mode.value.value in MODE_REMOVE or
+                    mode.value.value in MODE_REPLACE
                 )
             ):
                 func = functools.partial(
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/percent_format.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/percent_format.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/percent_format.py    2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/percent_format.py    2023-05-06 
23:09:25.000000000 +0200
@@ -184,18 +184,18 @@
 
     for k in node_right.keys:
         # not a string key
-        if not isinstance(k, ast.Str):
+        if not isinstance(k, ast.Constant) or not isinstance(k.value, str):
             return
         # duplicate key
-        elif k.s in seen_keys:
+        elif k.value in seen_keys:
             return
         # not an identifier
-        elif not k.s.isidentifier():
+        elif not k.value.isidentifier():
             return
         # a keyword
-        elif k.s in KEYWORDS:
+        elif k.value in KEYWORDS:
             return
-        seen_keys.add(k.s)
+        seen_keys.add(k.value)
         keys[ast_to_offset(k)] = k
 
     # TODO: this is overly timid
@@ -212,13 +212,13 @@
         if key is None:
             continue
         # we found the key, but the string didn't match (implicit join?)
-        elif ast.literal_eval(token.src) != key.s:
+        elif ast.literal_eval(token.src) != key.value:
             return
         # the map uses some strange syntax that's not `'key': value`
         elif tokens[j + 1].src != ':' or tokens[j + 2].src != ' ':
             return
         else:
-            key_indices.append((j, key.s))
+            key_indices.append((j, key.value))
     assert not keys, keys
 
     tokens[brace_end] = tokens[brace_end]._replace(src=')')
@@ -238,10 +238,11 @@
     if (
             not state.settings.keep_percent_format and
             isinstance(node.op, ast.Mod) and
-            isinstance(node.left, ast.Str)
+            isinstance(node.left, ast.Constant) and
+            isinstance(node.left.value, str)
     ):
         try:
-            parsed = _parse_percent_format(node.left.s)
+            parsed = _parse_percent_format(node.left.value)
         except ValueError:
             pass
         else:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/six_calls.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/six_calls.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/six_calls.py 2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/six_calls.py 2023-05-06 
23:09:25.000000000 +0200
@@ -2,7 +2,6 @@
 
 import ast
 import functools
-import sys
 from typing import Iterable
 
 from tokenize_rt import Offset
@@ -21,10 +20,8 @@
 
 _EXPR_NEEDS_PARENS: tuple[type[ast.expr], ...] = (
     ast.Await, ast.BinOp, ast.BoolOp, ast.Compare, ast.GeneratorExp, ast.IfExp,
-    ast.Lambda, ast.UnaryOp,
+    ast.Lambda, ast.UnaryOp, ast.NamedExpr,
 )
-if sys.version_info >= (3, 8):  # pragma: >=3.8 cover
-    _EXPR_NEEDS_PARENS += (ast.NamedExpr,)
 
 SIX_CALLS = {
     'u': '{args[0]}',
@@ -143,7 +140,8 @@
             not node.keywords and
             not has_starargs(node) and
             len(node.args) == 1 and
-            isinstance(node.args[0], ast.Str)
+            isinstance(node.args[0], ast.Constant) and
+            isinstance(node.args[0].value, str)
     ):
         yield ast_to_offset(node), _fix_six_b
     elif (
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/pyupgrade/_plugins/type_of_primitive.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/type_of_primitive.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/type_of_primitive.py 2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/type_of_primitive.py 2023-05-06 
23:09:25.000000000 +0200
@@ -14,7 +14,10 @@
 from pyupgrade._token_helpers import find_closing_bracket
 from pyupgrade._token_helpers import find_open_paren
 
-NUM_TYPES = {
+_TYPES = {
+    bool: 'bool',
+    bytes: 'bytes',
+    str: 'str',
     int: 'int',
     float: 'float',
     complex: 'complex',
@@ -42,23 +45,12 @@
     if (
             isinstance(node.func, ast.Name) and
             node.func.id == 'type' and
-            len(node.args) == 1
+            len(node.args) == 1 and
+            isinstance(node.args[0], ast.Constant) and
+            node.args[0].value not in {Ellipsis, None}
     ):
-        if isinstance(node.args[0], ast.Str):
-            func = functools.partial(
-                _rewrite_type_of_primitive,
-                src='str',
-            )
-            yield ast_to_offset(node), func
-        elif isinstance(node.args[0], ast.Bytes):
-            func = functools.partial(
-                _rewrite_type_of_primitive,
-                src='bytes',
-            )
-            yield ast_to_offset(node), func
-        elif isinstance(node.args[0], ast.Num):
-            func = functools.partial(
-                _rewrite_type_of_primitive,
-                src=NUM_TYPES[type(node.args[0].n)],
-            )
-            yield ast_to_offset(node), func
+        func = functools.partial(
+            _rewrite_type_of_primitive,
+            src=_TYPES[type(node.args[0].value)],
+        )
+        yield ast_to_offset(node), func
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/typing_classes.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/typing_classes.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/typing_classes.py    2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/typing_classes.py    2023-05-06 
23:09:25.000000000 +0200
@@ -38,14 +38,19 @@
         else:
             slice_s = _unparse(node_slice)
         return f'{_unparse(node.value)}[{slice_s}]'
-    elif isinstance(node, (ast.Str, ast.Bytes)):
-        return repr(node.s)
-    elif isinstance(node, ast.Ellipsis):
+    elif (
+            isinstance(node, ast.Constant) and
+            isinstance(node.value, (str, bytes))
+    ):
+        return repr(node.value)
+    elif isinstance(node, ast.Constant) and node.value is Ellipsis:
         return '...'
     elif isinstance(node, ast.List):
         return '[{}]'.format(', '.join(_unparse(elt) for elt in node.elts))
-    elif isinstance(node, ast.NameConstant):
+    elif isinstance(node, ast.Constant) and node.value in {True, False, None}:
         return repr(node.value)
+    elif isinstance(node, ast.BinOp) and isinstance(node.op, ast.BitOr):
+        return f'{_unparse(node.left)} | {_unparse(node.right)}'
     else:
         raise NotImplementedError(ast.dump(node))
 
@@ -95,7 +100,7 @@
 
 def _fix_named_tuple(i: int, tokens: list[Token], *, call: ast.Call) -> None:
     types = {
-        tup.elts[0].s: tup.elts[1]
+        tup.elts[0].value: tup.elts[1]
         for tup in call.args[1].elts  # type: ignore  # (checked below)
     }
     end, attrs = _typed_class_replacement(tokens, i, call, types)
@@ -121,7 +126,7 @@
         call: ast.Call,
 ) -> None:
     types = {
-        k.s: v
+        k.value: v
         for k, v in zip(
             call.args[1].keys,  # type: ignore  # (checked below)
             call.args[1].values,  # type: ignore  # (checked below)
@@ -158,8 +163,9 @@
             isinstance(node.targets[0], ast.Name) and
             isinstance(node.value, ast.Call) and
             len(node.value.args) >= 1 and
-            isinstance(node.value.args[0], ast.Str) and
-            node.targets[0].id == node.value.args[0].s and
+            isinstance(node.value.args[0], ast.Constant) and
+            isinstance(node.value.args[0].value, str) and
+            node.targets[0].id == node.value.args[0].value and
             not has_starargs(node.value)
     ):
         if (
@@ -176,9 +182,10 @@
                 all(
                     isinstance(tup, ast.Tuple) and
                     len(tup.elts) == 2 and
-                    isinstance(tup.elts[0], ast.Str) and
-                    tup.elts[0].s.isidentifier() and
-                    tup.elts[0].s not in KEYWORDS
+                    isinstance(tup.elts[0], ast.Constant) and
+                    isinstance(tup.elts[0].value, str) and
+                    tup.elts[0].value.isidentifier() and
+                    tup.elts[0].value not in KEYWORDS
                     for tup in node.value.args[1].elts
                 )
         ):
@@ -222,9 +229,10 @@
                 isinstance(node.value.args[1], ast.Dict) and
                 node.value.args[1].keys and
                 all(
-                    isinstance(k, ast.Str) and
-                    k.s.isidentifier() and
-                    k.s not in KEYWORDS
+                    isinstance(k, ast.Constant) and
+                    isinstance(k.value, str) and
+                    k.value.isidentifier() and
+                    k.value not in KEYWORDS
                     for k in node.value.args[1].keys
                 )
         ):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/typing_pep563.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/typing_pep563.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/typing_pep563.py     2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/typing_pep563.py     2023-05-06 
23:09:25.000000000 +0200
@@ -113,8 +113,8 @@
             nodes.extend(_process_call(node))
         elif isinstance(node, ast.Subscript):
             nodes.extend(_process_subscript(node))
-        elif isinstance(node, ast.Str):
-            func = functools.partial(_dequote, new=node.s)
+        elif isinstance(node, ast.Constant) and isinstance(node.value, str):
+            func = functools.partial(_dequote, new=node.value)
             yield ast_to_offset(node), func
         else:
             for name in node._fields:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_plugins/typing_pep604.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/typing_pep604.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/typing_pep604.py     2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/typing_pep604.py     2023-05-06 
23:09:25.000000000 +0200
@@ -128,9 +128,16 @@
 
 def _any_arg_is_str(node_slice: ast.expr) -> bool:
     return (
-        isinstance(node_slice, ast.Str) or (
+        (
+            isinstance(node_slice, ast.Constant) and
+            isinstance(node_slice.value, str)
+        ) or (
             isinstance(node_slice, ast.Tuple) and
-            any(isinstance(elt, ast.Str) for elt in node_slice.elts)
+            any(
+                isinstance(elt, ast.Constant) and
+                isinstance(elt.value, str)
+                for elt in node_slice.elts
+            )
         )
     )
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/pyupgrade/_plugins/unpack_list_comprehension.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/unpack_list_comprehension.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/unpack_list_comprehension.py 
2022-11-10 16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/unpack_list_comprehension.py 
2023-05-06 23:09:25.000000000 +0200
@@ -12,11 +12,10 @@
 from pyupgrade._data import State
 from pyupgrade._data import TokenFunc
 from pyupgrade._token_helpers import find_closing_bracket
-from pyupgrade._token_helpers import find_comprehension_opening_bracket
 
 
 def _replace_list_comprehension(i: int, tokens: list[Token]) -> None:
-    start = find_comprehension_opening_bracket(i, tokens)
+    start = i
     end = find_closing_bracket(tokens, start)
     tokens[start] = tokens[start]._replace(src='(')
     tokens[end] = tokens[end]._replace(src=')')
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/pyupgrade/_plugins/versioned_branches.py 
new/pyupgrade-3.4.0/pyupgrade/_plugins/versioned_branches.py
--- old/pyupgrade-3.2.2/pyupgrade/_plugins/versioned_branches.py        
2022-11-10 16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_plugins/versioned_branches.py        
2023-05-06 23:09:25.000000000 +0200
@@ -3,7 +3,6 @@
 import ast
 from typing import cast
 from typing import Iterable
-from typing import List
 
 from tokenize_rt import Offset
 from tokenize_rt import Token
@@ -69,8 +68,8 @@
 def _eq(test: ast.Compare, n: int) -> bool:
     return (
         isinstance(test.ops[0], ast.Eq) and
-        isinstance(test.comparators[0], ast.Num) and
-        test.comparators[0].n == n
+        isinstance(test.comparators[0], ast.Constant) and
+        test.comparators[0].value == n
     )
 
 
@@ -83,14 +82,17 @@
             isinstance(test.ops[0], op) and
             isinstance(test.comparators[0], ast.Tuple) and
             len(test.comparators[0].elts) >= 1 and
-            all(isinstance(n, ast.Num) for n in test.comparators[0].elts)
+            all(
+                isinstance(n, ast.Constant) and isinstance(n.value, int)
+                for n in test.comparators[0].elts
+            )
     ):
         return False
 
     # checked above but mypy needs help
-    ast_elts = cast('List[ast.Num]', test.comparators[0].elts)
+    ast_elts = cast('list[ast.Constant]', test.comparators[0].elts)
     # padding a 0 for compatibility with (3,) used as a spec
-    elts = tuple(e.n for e in ast_elts) + (0,)
+    elts = tuple(e.value for e in ast_elts) + (0,)
 
     return elts[:2] == (3, minor) and all(n == 0 for n in elts[2:])
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/pyupgrade/_token_helpers.py 
new/pyupgrade-3.4.0/pyupgrade/_token_helpers.py
--- old/pyupgrade-3.2.2/pyupgrade/_token_helpers.py     2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/pyupgrade/_token_helpers.py     2023-05-06 
23:09:25.000000000 +0200
@@ -2,7 +2,6 @@
 
 import ast
 import keyword
-import sys
 from typing import NamedTuple
 from typing import Sequence
 
@@ -64,28 +63,11 @@
     return i
 
 
-if sys.version_info >= (3, 8):  # pragma: >=3.8 cover
-    # python 3.8 fixed the offsets of generators / tuples
-    def _arg_token_index(tokens: list[Token], i: int, arg: ast.expr) -> int:
-        idx = _search_until(tokens, i, arg) + 1
-        while idx < len(tokens) and tokens[idx].name in NON_CODING_TOKENS:
-            idx += 1
-        return idx
-else:  # pragma: <3.8 cover
-    def _arg_token_index(tokens: list[Token], i: int, arg: ast.expr) -> int:
-        # lists containing non-tuples report the first element correctly
-        if isinstance(arg, ast.List):
-            # If the first element is a tuple, the ast lies to us about its col
-            # offset.  We must find the first `(` token after the start of the
-            # list element.
-            if isinstance(arg.elts[0], ast.Tuple):
-                i = _search_until(tokens, i, arg)
-                return find_open_paren(tokens, i)
-            else:
-                return _search_until(tokens, i, arg.elts[0])
-            # others' start position points at their first child node already
-        else:
-            return _search_until(tokens, i, arg)
+def _arg_token_index(tokens: list[Token], i: int, arg: ast.expr) -> int:
+    idx = _search_until(tokens, i, arg) + 1
+    while idx < len(tokens) and tokens[idx].name in NON_CODING_TOKENS:
+        idx += 1
+    return idx
 
 
 def victims(
@@ -499,17 +481,6 @@
     tokens[start_idx:end_idx] = [Token('SRC', new)]
 
 
-def find_comprehension_opening_bracket(i: int, tokens: list[Token]) -> int:
-    """Find opening bracket of comprehension given first argument."""
-    if sys.version_info < (3, 8):  # pragma: <3.8 cover
-        i -= 1
-        while not (tokens[i].name == 'OP' and tokens[i].src == '[') and i:
-            i -= 1
-        return i
-    else:  # pragma: >=3.8 cover
-        return i
-
-
 def has_space_before(i: int, tokens: list[Token]) -> bool:
     return i >= 1 and tokens[i - 1].name in {UNIMPORTANT_WS, 'INDENT'}
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/setup.cfg 
new/pyupgrade-3.4.0/setup.cfg
--- old/pyupgrade-3.2.2/setup.cfg       2022-11-10 16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/setup.cfg       2023-05-06 23:09:25.000000000 +0200
@@ -1,6 +1,6 @@
 [metadata]
 name = pyupgrade
-version = 3.2.2
+version = 3.4.0
 description = A tool to automatically upgrade syntax for newer versions.
 long_description = file: README.md
 long_description_content_type = text/markdown
@@ -20,7 +20,7 @@
 packages = find:
 install_requires =
     tokenize-rt>=3.2.0
-python_requires = >=3.7
+python_requires = >=3.8
 
 [options.packages.find]
 exclude =
@@ -42,7 +42,6 @@
 disallow_any_generics = true
 disallow_incomplete_defs = true
 disallow_untyped_defs = true
-no_implicit_optional = true
 warn_redundant_casts = true
 warn_unused_ignores = true
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/tests/features/datetime_utc_alias_test.py 
new/pyupgrade-3.4.0/tests/features/datetime_utc_alias_test.py
--- old/pyupgrade-3.2.2/tests/features/datetime_utc_alias_test.py       
1970-01-01 01:00:00.000000000 +0100
+++ new/pyupgrade-3.4.0/tests/features/datetime_utc_alias_test.py       
2023-05-06 23:09:25.000000000 +0200
@@ -0,0 +1,41 @@
+from __future__ import annotations
+
+import pytest
+
+from pyupgrade._data import Settings
+from pyupgrade._main import _fix_plugins
+
+
+@pytest.mark.parametrize(
+    ('s',),
+    (
+        pytest.param(
+            'import datetime\n'
+            'print(datetime.timezone(-1))',
+
+            id='not rewriting timezone object to alias',
+        ),
+    ),
+)
+def test_fix_datetime_utc_alias_noop(s):
+    assert _fix_plugins(s, settings=Settings(min_version=(3,))) == s
+    assert _fix_plugins(s, settings=Settings(min_version=(3, 11))) == s
+
+
+@pytest.mark.parametrize(
+    ('s', 'expected'),
+    (
+        pytest.param(
+            'import datetime\n'
+            'print(datetime.timezone.utc)',
+
+            'import datetime\n'
+            'print(datetime.UTC)',
+
+            id='rewriting to alias',
+        ),
+    ),
+)
+def test_fix_datetime_utc_alias(s, expected):
+    assert _fix_plugins(s, settings=Settings(min_version=(3,))) == s
+    assert _fix_plugins(s, settings=Settings(min_version=(3, 11))) == expected
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/tests/features/fstrings_test.py 
new/pyupgrade-3.4.0/tests/features/fstrings_test.py
--- old/pyupgrade-3.2.2/tests/features/fstrings_test.py 2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/tests/features/fstrings_test.py 2023-05-06 
23:09:25.000000000 +0200
@@ -64,6 +64,11 @@
             r'f"\N{snowman} {a}"',
             id='named escape sequences',
         ),
+        pytest.param(
+            'u"foo{}".format(1)',
+            'f"foo{1}"',
+            id='u-prefixed format',
+        ),
     ),
 )
 def test_fix_fstrings(s, expected):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/tests/features/import_replaces_test.py 
new/pyupgrade-3.4.0/tests/features/import_replaces_test.py
--- old/pyupgrade-3.2.2/tests/features/import_replaces_test.py  2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/tests/features/import_replaces_test.py  2023-05-06 
23:09:25.000000000 +0200
@@ -305,6 +305,13 @@
             'from collections.abc import Callable\n',
             id='typing.Callable is rewritable in 3.10+ only',
         ),
+        pytest.param(
+            'from typing import Optional, Sequence as S\n',
+            (3, 10),
+            'from typing import Optional\n'
+            'from collections.abc import Sequence as S\n',
+            id='aliasing in multi from import',
+        ),
     ),
 )
 def test_import_replaces(s, min_version, expected):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/tests/features/six_test.py 
new/pyupgrade-3.4.0/tests/features/six_test.py
--- old/pyupgrade-3.2.2/tests/features/six_test.py      2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/tests/features/six_test.py      2023-05-06 
23:09:25.000000000 +0200
@@ -1,7 +1,5 @@
 from __future__ import annotations
 
-import sys
-
 import pytest
 
 from pyupgrade._data import Settings
@@ -387,17 +385,6 @@
             'x = map(str, ints)\n',
             id='six.moves builtin attrs',
         ),
-    ),
-)
-def test_fix_six(s, expected):
-    ret = _fix_plugins(s, settings=Settings())
-    assert ret == expected
-
-
-@pytest.mark.xfail(sys.version_info < (3, 8), reason='walrus')
-@pytest.mark.parametrize(
-    ('s', 'expected'),
-    (
         pytest.param(
             'for _ in six.itervalues(x := y): pass',
             'for _ in (x := y).values(): pass',
@@ -405,7 +392,7 @@
         ),
     ),
 )
-def test_fix_six_py38_plus(s, expected):
+def test_fix_six(s, expected):
     ret = _fix_plugins(s, settings=Settings())
     assert ret == expected
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/tests/features/type_of_primitive_test.py 
new/pyupgrade-3.4.0/tests/features/type_of_primitive_test.py
--- old/pyupgrade-3.2.2/tests/features/type_of_primitive_test.py        
2022-11-10 16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/tests/features/type_of_primitive_test.py        
2023-05-06 23:09:25.000000000 +0200
@@ -14,6 +14,10 @@
             id='NoneType',
         ),
         pytest.param(
+            'type(...)\n',
+            id='ellipsis',
+        ),
+        pytest.param(
             'foo = "foo"\n'
             'type(foo)\n',
             id='String assigned to variable',
@@ -62,6 +66,13 @@
 
             id='Empty bytes string -> bytes',
         ),
+        pytest.param(
+            'type(True)\n',
+
+            'bool\n',
+
+            id='bool',
+        ),
     ),
 )
 def test_fix_type_of_primitive(s, expected):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/pyupgrade-3.2.2/tests/features/typing_classes_test.py 
new/pyupgrade-3.4.0/tests/features/typing_classes_test.py
--- old/pyupgrade-3.2.2/tests/features/typing_classes_test.py   2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/tests/features/typing_classes_test.py   2023-05-06 
23:09:25.000000000 +0200
@@ -210,6 +210,16 @@
 
             id='preserves comments without alignment',
         ),
+        pytest.param(
+            'from typing import NamedTuple\n'
+            'Foo = NamedTuple("Foo", [("union", str | None)])',
+
+            'from typing import NamedTuple\n'
+            'class Foo(NamedTuple):\n'
+            '    union: str | None',
+
+            id='BitOr unparse error',
+        ),
     ),
 )
 def test_fix_typing_named_tuple(s, expected):
@@ -393,6 +403,16 @@
 
             id='right after a dedent',
         ),
+        pytest.param(
+            'from typing import TypedDict\n'
+            'Foo = TypedDict("Foo", {"union": str | int | None})',
+
+            'from typing import TypedDict\n'
+            'class Foo(TypedDict):\n'
+            '    union: str | int | None',
+
+            id='BitOr unparse error',
+        ),
     ),
 )
 def test_typing_typed_dict(s, expected):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/tests/features/typing_pep563_test.py 
new/pyupgrade-3.4.0/tests/features/typing_pep563_test.py
--- old/pyupgrade-3.2.2/tests/features/typing_pep563_test.py    2022-11-10 
16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/tests/features/typing_pep563_test.py    2023-05-06 
23:09:25.000000000 +0200
@@ -1,7 +1,5 @@
 from __future__ import annotations
 
-import sys
-
 import pytest
 
 from pyupgrade._data import Settings
@@ -338,27 +336,19 @@
 
             id='NamedTuple with no args (invalid syntax)',
         ),
+        pytest.param(
+            'from __future__ import annotations\n'
+            'def foo(var0, /, var1: "MyClass") -> "MyClass":\n'
+            '   x: "MyClass"\n',
+
+            'from __future__ import annotations\n'
+            'def foo(var0, /, var1: MyClass) -> MyClass:\n'
+            '   x: MyClass\n',
+
+            id='posonly args',
+        ),
     ),
 )
 def test_fix_typing_pep563(s, expected):
     ret = _fix_plugins(s, settings=Settings(min_version=(3, 7)))
     assert ret == expected
-
-
-@pytest.mark.xfail(
-    sys.version_info < (3, 8),
-    reason='posonly args not available in Python3.7',
-)
-def test_fix_typing_pep563_posonlyargs():
-    s = (
-        'from __future__ import annotations\n'
-        'def foo(var0, /, var1: "MyClass") -> "MyClass":\n'
-        '   x: "MyClass"\n'
-    )
-    expected = (
-        'from __future__ import annotations\n'
-        'def foo(var0, /, var1: MyClass) -> MyClass:\n'
-        '   x: MyClass\n'
-    )
-    ret = _fix_plugins(s, settings=Settings(min_version=(3, 8)))
-    assert ret == expected
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/pyupgrade-3.2.2/tox.ini new/pyupgrade-3.4.0/tox.ini
--- old/pyupgrade-3.2.2/tox.ini 2022-11-10 16:38:09.000000000 +0100
+++ new/pyupgrade-3.4.0/tox.ini 2023-05-06 23:09:25.000000000 +0200
@@ -1,5 +1,5 @@
 [tox]
-envlist = py37,py38,py39,pypy3,pre-commit
+envlist = py,pypy3,pre-commit
 
 [testenv]
 deps = -rrequirements-dev.txt

Reply via email to