Skip to content
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
2 changes: 1 addition & 1 deletion CLAUDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ Marvin is a lightweight AI engineering toolkit for building natural language int
### Finding Things
- Use `rg` for searching, not grep
- Use `ls` and `tree` for navigation
- Check git context with `gh` and `git` commands
- Check git context with using the GitHub MCP server
- Think like a hacker with good intentions - search in site-packages when needed

### Linter Philosophy
Expand Down
2 changes: 1 addition & 1 deletion docs/api-reference/marvin-agents-actor.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ class Actor(name: str, instructions: str | None = None, description: str | None
```
- **`get_current`**
```python
def get_current(cls) -> Optional[Actor]
def get_current(cls) -> Actor | None
```
Get the current actor from context.
- **`get_end_turn_tools`**
Expand Down
2 changes: 1 addition & 1 deletion docs/api-reference/marvin-engine-orchestrator.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ class Orchestrator(tasks: list[Task[Any]], thread: Thread | str | None = None, h
- ready: tasks that are ready to be run
- **`get_current`**
```python
def get_current(cls) -> Optional[Orchestrator]
def get_current(cls) -> Orchestrator | None
```
Get the current orchestrator from context.
- **`handle_event`**
Expand Down
2 changes: 1 addition & 1 deletion docs/api-reference/marvin-thread.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ Main runtime object for managing conversation context.
Add a user message to the thread.
- **`get_current`**
```python
def get_current(cls) -> Optional[Thread]
def get_current(cls) -> Thread | None
```
Get the current thread from context.
- **`get_llm_calls`**
Expand Down
2 changes: 1 addition & 1 deletion docs/api-reference/marvin-utilities-jsonschema.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,7 @@ Create a field with simplified default handling.

### `create_numeric_type`
```python
def create_numeric_type(base: Type[Union[int, float]], schema: Mapping[str, Any]) -> type | Annotated[Any, ...]
def create_numeric_type(base: Type[int | float], schema: Mapping[str, Any]) -> type | Annotated[Any, ...]
```
Create numeric type with optional constraints.

Expand Down
6 changes: 3 additions & 3 deletions docs/api-reference/marvin-utilities-types.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -96,12 +96,12 @@ Attributes:
function (Callable): The original function object.
signature (inspect.Signature): The signature object of the function.
name (str): The name of the function.
docstring (Optional[str]): The docstring of the function.
docstring (str | None): The docstring of the function.
parameters (List[ParameterModel]): The parameters of the function.
return_annotation (Optional[Any]): The return annotation of the function.
return_annotation (Any | None): The return annotation of the function.
source_code (str): The source code of the function.
bound_parameters (dict[str, Any]): The parameters of the function bound with values.
return_value (Optional[Any]): The return value of the function call.
return_value (Any | None): The return value of the function call.

**Methods:**

Expand Down
14 changes: 7 additions & 7 deletions src/marvin/_internal/deprecation.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
import functools
import warnings
from datetime import datetime, timedelta
from typing import Any, Callable, Optional, TypeVar
from typing import Any, Callable, TypeVar

from typing_extensions import ParamSpec

Expand All @@ -22,8 +22,8 @@ class MarvinDeprecationWarning(DeprecationWarning):

def generate_deprecation_message(
name: str,
start_date: Optional[datetime] = None,
end_date: Optional[datetime] = None,
start_date: datetime | None = None,
end_date: datetime | None = None,
help: str = "",
) -> str:
"""Generate a deprecation warning message."""
Expand All @@ -45,8 +45,8 @@ def generate_deprecation_message(

def deprecated_class(
*,
start_date: Optional[datetime] = None,
end_date: Optional[datetime] = None,
start_date: datetime | None = None,
end_date: datetime | None = None,
stacklevel: int = 2,
help: str = "",
) -> Callable[[type[T]], type[T]]:
Expand Down Expand Up @@ -85,8 +85,8 @@ def new_init(self: T, *args: Any, **kwargs: Any) -> None:

def deprecated_callable(
*,
start_date: Optional[datetime] = None,
end_date: Optional[datetime] = None,
start_date: datetime | None = None,
end_date: datetime | None = None,
stacklevel: int = 2,
help: str = "",
) -> Callable[[Callable[P, R]], Callable[P, R]]:
Expand Down
6 changes: 3 additions & 3 deletions src/marvin/agents/actor.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
from contextvars import ContextVar
from dataclasses import dataclass, field
from pathlib import Path
from typing import TYPE_CHECKING, Any, Optional, Sequence, TypeVar
from typing import TYPE_CHECKING, Any, Sequence, TypeVar

import pydantic_ai
from pydantic_ai.agent import AgentRunResult
Expand All @@ -22,7 +22,7 @@
from marvin.handlers.handlers import AsyncHandler, Handler
T = TypeVar("T")
# Global context var for current actor
_current_actor: ContextVar[Optional["Actor"]] = ContextVar(
_current_actor: ContextVar["Actor | None"] = ContextVar(
"current_actor",
default=None,
)
Expand Down Expand Up @@ -79,7 +79,7 @@ def __exit__(self, exc_type: Any, exc_val: Any, exc_tb: Any):
_current_actor.reset(self._tokens.pop())

@classmethod
def get_current(cls) -> Optional["Actor"]:
def get_current(cls) -> "Actor | None":
"""Get the current actor from context."""
return _current_actor.get()

Expand Down
4 changes: 2 additions & 2 deletions src/marvin/engine/orchestrator.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
from contextvars import ContextVar
from dataclasses import dataclass
from pathlib import Path
from typing import Any, Literal, Optional, Sequence, TypeVar
from typing import Any, Literal, Sequence, TypeVar

from pydantic_ai.agent import AgentRunResult
from pydantic_ai.mcp import MCPServer
Expand Down Expand Up @@ -348,7 +348,7 @@ async def _get_messages(
return user_prompt, [system_prompt] + message_history

@classmethod
def get_current(cls) -> Optional["Orchestrator"]:
def get_current(cls) -> "Orchestrator | None":
"""Get the current orchestrator from context."""
return _current_orchestrator.get()

Expand Down
6 changes: 3 additions & 3 deletions src/marvin/memory/providers/postgres.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import uuid
from typing import Dict, Optional
from typing import Dict

# async pg
import anyio
Expand Down Expand Up @@ -103,8 +103,8 @@ class PostgresMemory(MemoryProvider):
)

# We'll store an async engine + session factory:
_engine: Optional[AsyncEngine] = None
_SessionLocal: Optional[async_sessionmaker[AsyncSession]] = None
_engine: AsyncEngine | None = None
_SessionLocal: async_sessionmaker[AsyncSession] | None = None

# Cache for dynamically generated table classes
_table_class_cache: Dict[str, Base] = {}
Expand Down
3 changes: 1 addition & 2 deletions src/marvin/tasks/task.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@
AsyncGenerator,
Generic,
Literal,
Optional,
Sequence,
TypeAlias,
TypeVar,
Expand Down Expand Up @@ -45,7 +44,7 @@
NOTSET: Literal["__NOTSET__"] = "__NOTSET__"

# Global context var for current task
_current_task: ContextVar[Optional["Task[Any]"]] = ContextVar(
_current_task: ContextVar["Task[Any] | None"] = ContextVar(
"current_task",
default=None,
)
Expand Down
8 changes: 4 additions & 4 deletions src/marvin/thread.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
from contextvars import ContextVar
from dataclasses import dataclass, field
from datetime import datetime
from typing import Any, Optional, Sequence
from typing import Any, Sequence

from pydantic import TypeAdapter
from pydantic_ai.messages import UserContent
Expand Down Expand Up @@ -95,13 +95,13 @@ async def get_messages_async(self) -> LLMCallMessages:


# Global context var for current thread
_current_thread: ContextVar[Optional["Thread"]] = ContextVar(
_current_thread: ContextVar["Thread | None"] = ContextVar(
"current_thread",
default=None,
)

# Track the last thread globally
_last_thread: Optional["Thread"] = None
_last_thread: "Thread | None" = None


@dataclass
Expand Down Expand Up @@ -422,7 +422,7 @@ def __exit__(self, exc_type: Any, exc_val: Any, exc_tb: Any):
_current_thread.reset(self._tokens.pop())

@classmethod
def get_current(cls) -> Optional["Thread"]:
def get_current(cls) -> "Thread | None":
"""Get the current thread from context."""
return _current_thread.get()

Expand Down
28 changes: 18 additions & 10 deletions src/marvin/utilities/jsonschema.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,6 @@
ForwardRef,
Literal,
Mapping,
Optional,
Type,
Union,
)
Expand Down Expand Up @@ -180,7 +179,7 @@ def create_string_type(schema: Mapping[str, Any]) -> type | Annotated[Any, ...]:


def create_numeric_type(
base: Type[Union[int, float]], schema: Mapping[str, Any]
base: Type[int | float], schema: Mapping[str, Any]
) -> type | Annotated[Any, ...]:
"""Create numeric type with optional constraints."""
if "const" in schema:
Expand Down Expand Up @@ -216,6 +215,8 @@ def create_array_type(
if isinstance(items, list):
# Handle positional item schemas
item_types = [schema_to_type(s, schemas) for s in items]
from typing import Union

combined = Union[tuple(item_types)]
base = list[combined]
else:
Expand Down Expand Up @@ -296,7 +297,12 @@ def schema_to_type(
has_null = type(None) in types
types = [t for t in types if t is not type(None)]
if has_null:
return Optional[Union[tuple(types)] if len(types) > 1 else types[0]]
from typing import Union

combined = Union[tuple(types)] if len(types) > 1 else types[0]
return combined | None
from typing import Union

return Union[tuple(types)]

return _get_from_type_handler(schema, schemas)(schema)
Expand Down Expand Up @@ -411,7 +417,9 @@ def create_dataclass(
elif is_required:
fields.append((field_name, field_type, field_def))
else:
fields.append((field_name, Optional[field_type], field_def))
# Use Union[field_type, None] instead of field_type | None
# to maintain compatibility with code that expects __origin__
fields.append((field_name, Union[field_type, None], field_def))

cls = make_dataclass(sanitized_name, fields, kw_only=True)

Expand Down Expand Up @@ -494,7 +502,7 @@ def merge_defaults(


class JSONSchema(TypedDict):
type: NotRequired[Union[str, list[str]]]
type: NotRequired[str | list[str]]
properties: NotRequired[dict[str, "JSONSchema"]]
required: NotRequired[list[str]]
additionalProperties: NotRequired[Union[bool, "JSONSchema"]]
Expand All @@ -515,11 +523,11 @@ class JSONSchema(TypedDict):
pattern: NotRequired[str]
minLength: NotRequired[int]
maxLength: NotRequired[int]
minimum: NotRequired[Union[int, float]]
maximum: NotRequired[Union[int, float]]
exclusiveMinimum: NotRequired[Union[int, float]]
exclusiveMaximum: NotRequired[Union[int, float]]
multipleOf: NotRequired[Union[int, float]]
minimum: NotRequired[int | float]
maximum: NotRequired[int | float]
exclusiveMinimum: NotRequired[int | float]
exclusiveMaximum: NotRequired[int | float]
multipleOf: NotRequired[int | float]
uniqueItems: NotRequired[bool]
minItems: NotRequired[int]
maxItems: NotRequired[int]
Expand Down
6 changes: 3 additions & 3 deletions src/marvin/utilities/types.py
Original file line number Diff line number Diff line change
Expand Up @@ -285,12 +285,12 @@ class PythonFunction(Generic[P, R]):
function (Callable): The original function object.
signature (inspect.Signature): The signature object of the function.
name (str): The name of the function.
docstring (Optional[str]): The docstring of the function.
docstring (str | None): The docstring of the function.
parameters (List[ParameterModel]): The parameters of the function.
return_annotation (Optional[Any]): The return annotation of the function.
return_annotation (Any | None): The return annotation of the function.
source_code (str): The source code of the function.
bound_parameters (dict[str, Any]): The parameters of the function bound with values.
return_value (Optional[Any]): The return value of the function call.
return_value (Any | None): The return value of the function call.

"""

Expand Down
Loading