Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remove 3.8 support #2467

Merged
merged 10 commits into from
Oct 2, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 1 addition & 4 deletions .github/workflows/test_be.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -38,11 +38,8 @@ jobs:
matrix:
os: [ubuntu-latest, macos-latest, windows-latest]
dependencies: ['core', 'core,optional']
python-version: ['3.8']
python-version: ['3.9']
include:
- os: ubuntu-latest
python-version: '3.9'
dependencies: 'core'
- os: ubuntu-latest
python-version: '3.10'
dependencies: 'core'
Expand Down
11 changes: 0 additions & 11 deletions marimo/_convert/ipynb.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,10 +26,6 @@ def transform_fixup_multiple_definitions(sources: List[str]) -> List[str]:
This only takes effect if the declaration and reference are in
the same cell.
"""
if sys.version_info < (3, 9):
# ast.unparse not available in Python 3.8
return sources

try:
cells = [
compile_cell(source, cell_id=str(i))
Expand Down Expand Up @@ -355,10 +351,6 @@ def rename_named_node(


def _transform_aug_assign(sources: List[str]) -> List[str]:
if sys.version_info < (3, 9):
# ast.unparse unavailable
return sources

new_sources = sources.copy()
for i, source in enumerate(sources):
try:
Expand Down Expand Up @@ -433,9 +425,6 @@ def transform_duplicate_definitions(sources: List[str]) -> List[str]:
print(a_2)
```
"""
if sys.version_info < (3, 9):
# ast.unparse not available in Python 3.8
return sources

# Find all definitions in the AST
def find_definitions(node: ast.AST) -> List[str]:
Expand Down
7 changes: 0 additions & 7 deletions marimo/_plugins/ui/_impl/batch.py
Original file line number Diff line number Diff line change
@@ -1,13 +1,6 @@
# Copyright 2024 Marimo. All rights reserved.
from __future__ import annotations

import sys

if sys.version_info < (3, 9):
from typing import ItemsView, ValuesView
else:
pass

from typing import (
TYPE_CHECKING,
Any,
Expand Down
7 changes: 1 addition & 6 deletions marimo/_runtime/copy.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
from __future__ import annotations

import inspect
import sys
import weakref
from copy import copy
from typing import (
Expand All @@ -16,11 +15,7 @@
)

T = TypeVar("T")
if sys.version_info < (3, 9):
# Future does not seem to work for this in CI.
Ref = Union["weakref.ReferenceType[T]", Callable[[], T]]
else:
Ref = Union[weakref.ReferenceType[T], Callable[[], T]]
Ref = Union[weakref.ReferenceType[T], Callable[[], T]]


class CloneError(Exception):
Expand Down
7 changes: 1 addition & 6 deletions marimo/_runtime/primitives.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@

import inspect
import numbers
import sys
import weakref
from typing import TYPE_CHECKING, Any, Callable, Optional, Union

Expand All @@ -18,11 +17,7 @@
# reference.
CLONE_PRIMITIVES = (weakref.ref,) + PRIMITIVES

if sys.version_info < (3, 9):
# Future does not seem to work for this in CI.
FN_CACHE_TYPE = Optional["dict[Union[Callable[..., Any], type], bool]"]
else:
FN_CACHE_TYPE = Optional[dict[Union[Callable[..., Any], type], bool]]
FN_CACHE_TYPE = Optional[dict[Union[Callable[..., Any], type], bool]]


def is_external(value: Any) -> bool:
Expand Down
22 changes: 13 additions & 9 deletions marimo/_runtime/runtime.py
Original file line number Diff line number Diff line change
Expand Up @@ -522,12 +522,15 @@ def _install_execution_context(
self.execution_context = ExecutionContext(
cell_id, setting_element_value
)
with get_context().provide_ui_ids(str(cell_id)), redirect_streams(
cell_id,
stream=self.stream,
stdout=self.stdout,
stderr=self.stderr,
stdin=self.stdin,
with (
get_context().provide_ui_ids(str(cell_id)),
redirect_streams(
cell_id,
stream=self.stream,
stdout=self.stdout,
stderr=self.stderr,
stdin=self.stdin,
),
):
modules = None
try:
Expand Down Expand Up @@ -1590,9 +1593,10 @@ def debug(title: str, message: str) -> None:
else:
found = True
LOGGER.debug("Executing RPC %s", request)
with self._install_execution_context(
cell_id=function.cell_id
), ctx.provide_ui_ids(str(uuid4())):
with (
self._install_execution_context(cell_id=function.cell_id),
ctx.provide_ui_ids(str(uuid4())),
):
# Usually UI element IDs are deterministic, based on
# cell id, so that element values can be matched up
# with objects on notebook/app re-connection.
Expand Down
17 changes: 4 additions & 13 deletions marimo/_server/api/lifespans.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,25 +5,16 @@
import contextlib
import socket
import sys
from collections.abc import AsyncIterator, Callable, Sequence
from contextlib import AbstractAsyncContextManager

from starlette.applications import Starlette

from marimo._server.api.deps import AppState, AppStateBase
from marimo._server.file_router import AppFileRouter
from marimo._server.sessions import SessionManager
from marimo._server.tokens import AuthToken

if sys.version_info < (3, 9):
from typing import (
AsyncContextManager as AbstractAsyncContextManager,
AsyncIterator,
Callable,
Sequence,
)
else:
from collections.abc import AsyncIterator, Callable, Sequence
from contextlib import AbstractAsyncContextManager

from starlette.applications import Starlette

if sys.version_info < (3, 10):
from typing_extensions import TypeAlias
else:
Expand Down
6 changes: 1 addition & 5 deletions marimo/_utils/paths.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,11 @@
from __future__ import annotations

import os
import sys
from typing import Any


def import_files(filename: str) -> Any:
if sys.version_info < (3, 9):
from importlib_resources import files as importlib_files
else:
from importlib.resources import files as importlib_files
from importlib.resources import files as importlib_files

return importlib_files(filename)

Expand Down
6 changes: 2 additions & 4 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,6 @@ dynamic = ["version"]
dependencies = [
# For maintainable cli
"click>=8.0,<9",
# For python 3.8 compatibility
"importlib_resources>=5.10.2; python_version < \"3.9\"",
# code completion
"jedi>=0.18.0",
# compile markdown to html
Expand Down Expand Up @@ -51,7 +49,7 @@ dependencies = [
]
readme = "README.md"
license = { file = "LICENSE" }
requires-python = ">=3.8"
requires-python = ">=3.9"
classifiers = [
"Operating System :: OS Independent",
"License :: OSI Approved :: Apache Software License",
Expand All @@ -61,10 +59,10 @@ classifiers = [
"Intended Audience :: Science/Research",
"Intended Audience :: Education",
"Programming Language :: Python",
"Programming Language :: Python :: 3.8",
"Programming Language :: Python :: 3.9",
"Programming Language :: Python :: 3.10",
"Programming Language :: Python :: 3.11",
"Programming Language :: Python :: 3.12",
"Programming Language :: Python :: 3 :: Only",
]

Expand Down
25 changes: 12 additions & 13 deletions tests/_cli/test_file_path.py
Original file line number Diff line number Diff line change
Expand Up @@ -165,17 +165,15 @@ def test_generic_url_reader() -> None:
def test_file_content_reader() -> None:
reader = FileContentReader()

with patch.object(
LocalFileReader, "read"
) as mock_local_read, patch.object(
GitHubIssueReader, "read"
) as mock_github_issue_read, patch.object(
StaticNotebookReader, "read"
) as mock_static_notebook_read, patch.object(
GitHubSourceReader, "read"
) as mock_github_source_read, patch.object(
GenericURLReader, "read"
) as mock_generic_url_read:
with (
patch.object(LocalFileReader, "read") as mock_local_read,
patch.object(GitHubIssueReader, "read") as mock_github_issue_read,
patch.object(
StaticNotebookReader, "read"
) as mock_static_notebook_read,
patch.object(GitHubSourceReader, "read") as mock_github_source_read,
patch.object(GenericURLReader, "read") as mock_generic_url_read,
):
mock_local_read.return_value = ("local content", "local.py")
mock_github_issue_read.return_value = ("issue content", "issue.py")
mock_static_notebook_read.return_value = (
Expand Down Expand Up @@ -337,8 +335,9 @@ def test_validate_name_with_relative_and_absolute_paths():
relative_path = "relative/path/file.py"
absolute_path = "/absolute/path/file.py"

with patch("os.path.exists", return_value=True), patch(
"pathlib.Path.is_file", return_value=True
with (
patch("os.path.exists", return_value=True),
patch("pathlib.Path.is_file", return_value=True),
):
assert (
validate_name(
Expand Down
16 changes: 6 additions & 10 deletions tests/_runtime/test_trace.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,10 +22,7 @@ def test_script_trace() -> None:

result = p.stderr.decode()
assert "NameError: name 'y' is not defined" in result
assert (
'tests/_runtime/script_data/script_exception.py", line 10'
in result
)
assert 'script_exception.py", line 10' in result
assert "y = y / x" in result
# Test col_offset
# Expected output:
Expand All @@ -50,10 +47,7 @@ def test_script_trace_with_output() -> None:

result = p.stderr.decode()
assert "ZeroDivisionError: division by zero" in result
assert (
'tests/_runtime/script_data/script_exception_with_output.py"'
", line 11"
) in result
assert ('script_exception_with_output.py"' ", line 11") in result
assert "y / x" in result

@staticmethod
Expand All @@ -75,8 +69,10 @@ def test_script_trace_with_imported_file() -> None:
assert f'{file_path}", line 3' in result

assert (
'tests/_runtime/script_data/script_exception_with_imported_function.py"'
+ ", line 11"
os.path.normpath(
"tests/_runtime/script_data/script_exception_with_imported_function.py" # noqa: E501
)
+ '", line 11'
in result
)
assert "y = y / x" in result
Expand Down
Loading