mirror of
https://github.com/crewAIInc/crewAI.git
synced 2025-12-16 04:18:35 +00:00
Compare commits
2 Commits
1.2.1
...
devin/1740
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
529bdbdd83 | ||
|
|
c6ed4eaaf6 |
@@ -11,6 +11,7 @@ from typing import Any, Dict, Optional, Union
|
||||
from pydantic import BaseModel
|
||||
|
||||
from crewai.flow.persistence.base import FlowPersistence
|
||||
from crewai.utilities.datetime_compat import UTC
|
||||
|
||||
|
||||
class SQLiteFlowPersistence(FlowPersistence):
|
||||
@@ -95,7 +96,7 @@ class SQLiteFlowPersistence(FlowPersistence):
|
||||
""", (
|
||||
flow_uuid,
|
||||
method_name,
|
||||
datetime.utcnow().isoformat(),
|
||||
datetime.now(UTC).isoformat(),
|
||||
json.dumps(state_dict),
|
||||
))
|
||||
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
import ast
|
||||
import datetime
|
||||
import json
|
||||
import time
|
||||
from datetime import UTC
|
||||
from datetime import datetime
|
||||
from difflib import SequenceMatcher
|
||||
from json import JSONDecodeError
|
||||
from textwrap import dedent
|
||||
@@ -18,6 +17,7 @@ from crewai.tools import BaseTool
|
||||
from crewai.tools.structured_tool import CrewStructuredTool
|
||||
from crewai.tools.tool_calling import InstructorToolCalling, ToolCalling
|
||||
from crewai.utilities import I18N, Converter, ConverterError, Printer
|
||||
from crewai.utilities.datetime_compat import UTC
|
||||
from crewai.utilities.events.crewai_event_bus import crewai_event_bus
|
||||
from crewai.utilities.events.tool_usage_events import (
|
||||
ToolSelectionErrorEvent,
|
||||
@@ -158,7 +158,7 @@ class ToolUsage:
|
||||
self.task.increment_tools_errors()
|
||||
|
||||
started_at = time.time()
|
||||
started_at_trace = datetime.datetime.now(UTC)
|
||||
started_at_trace = datetime.now(UTC)
|
||||
from_cache = False
|
||||
|
||||
result = None # type: ignore # Incompatible types in assignment (expression has type "None", variable has type "str")
|
||||
@@ -506,8 +506,8 @@ class ToolUsage:
|
||||
event_data = self._prepare_event_data(tool, tool_calling)
|
||||
event_data.update(
|
||||
{
|
||||
"started_at": datetime.datetime.fromtimestamp(started_at),
|
||||
"finished_at": datetime.datetime.fromtimestamp(finished_at),
|
||||
"started_at": datetime.fromtimestamp(started_at),
|
||||
"finished_at": datetime.fromtimestamp(finished_at),
|
||||
"from_cache": from_cache,
|
||||
}
|
||||
)
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import inspect
|
||||
import os
|
||||
from datetime import UTC, datetime
|
||||
from datetime import datetime
|
||||
from functools import wraps
|
||||
from typing import Any, Awaitable, Callable, Dict, List, Optional
|
||||
from uuid import uuid4
|
||||
@@ -14,6 +14,7 @@ from crewai.traces.models import (
|
||||
LLMResponse,
|
||||
ToolCall,
|
||||
)
|
||||
from crewai.utilities.datetime_compat import UTC
|
||||
|
||||
|
||||
class UnifiedTraceController:
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
from .converter import Converter, ConverterError
|
||||
from .datetime_compat import UTC
|
||||
from .file_handler import FileHandler
|
||||
from .i18n import I18N
|
||||
from .internal_instructor import InternalInstructor
|
||||
@@ -22,6 +23,7 @@ __all__ = [
|
||||
"Printer",
|
||||
"Prompts",
|
||||
"RPMController",
|
||||
"UTC",
|
||||
"YamlParser",
|
||||
"LLMContextLengthExceededException",
|
||||
"EmbeddingConfigurator",
|
||||
|
||||
23
src/crewai/utilities/datetime_compat.py
Normal file
23
src/crewai/utilities/datetime_compat.py
Normal file
@@ -0,0 +1,23 @@
|
||||
"""Compatibility module for datetime functionality across Python versions.
|
||||
|
||||
This module provides timezone constants that work consistently across different
|
||||
Python versions, particularly focusing on maintaining compatibility between
|
||||
Python 3.10 and newer versions.
|
||||
|
||||
Notes:
|
||||
- In Python 3.10, datetime.UTC is not available, so we use timezone.utc
|
||||
- In Python 3.11+, this provides equivalent functionality to datetime.UTC
|
||||
- This implementation maintains consistent behavior across versions for
|
||||
timezone-aware datetime operations
|
||||
- No known limitations or edge cases between versions
|
||||
- Safe to use with DST transitions and leap years
|
||||
- Maintains exact timezone offset (always UTC+00:00)
|
||||
|
||||
Example:
|
||||
>>> from datetime import datetime
|
||||
>>> from crewai.utilities.datetime_compat import UTC
|
||||
>>> dt = datetime.now(UTC) # Creates timezone-aware datetime with UTC
|
||||
"""
|
||||
from datetime import timezone
|
||||
|
||||
UTC = timezone.utc # Equivalent to datetime.UTC (Python 3.11+)
|
||||
@@ -1,7 +1,7 @@
|
||||
"""Test Agent creation and execution basic functionality."""
|
||||
|
||||
import os
|
||||
from datetime import UTC, datetime, timezone
|
||||
from datetime import datetime, timezone
|
||||
from unittest import mock
|
||||
from unittest.mock import patch
|
||||
|
||||
@@ -18,6 +18,7 @@ from crewai.tools import tool
|
||||
from crewai.tools.tool_calling import InstructorToolCalling
|
||||
from crewai.tools.tool_usage import ToolUsage
|
||||
from crewai.utilities import RPMController
|
||||
from crewai.utilities.datetime_compat import UTC
|
||||
from crewai.utilities.events import crewai_event_bus
|
||||
from crewai.utilities.events.tool_usage_events import ToolUsageFinishedEvent
|
||||
|
||||
@@ -916,9 +917,10 @@ def test_tool_result_as_answer_is_the_final_answer_for_the_agent():
|
||||
|
||||
@pytest.mark.vcr(filter_headers=["authorization"])
|
||||
def test_tool_usage_information_is_appended_to_agent():
|
||||
from datetime import UTC, datetime
|
||||
from datetime import datetime, timezone
|
||||
|
||||
from crewai.tools import BaseTool
|
||||
from crewai.utilities.datetime_compat import UTC
|
||||
|
||||
class MyCustomTool(BaseTool):
|
||||
name: str = "Decide Greetings"
|
||||
@@ -928,8 +930,9 @@ def test_tool_usage_information_is_appended_to_agent():
|
||||
return "Howdy!"
|
||||
|
||||
fixed_datetime = datetime(2025, 2, 10, 12, 0, 0, tzinfo=UTC)
|
||||
with patch("datetime.datetime") as mock_datetime:
|
||||
with patch("crewai.tools.tool_usage.datetime", autospec=True) as mock_datetime:
|
||||
mock_datetime.now.return_value = fixed_datetime
|
||||
mock_datetime.fromtimestamp = datetime.fromtimestamp
|
||||
mock_datetime.side_effect = lambda *args, **kw: datetime(*args, **kw)
|
||||
|
||||
agent1 = Agent(
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import os
|
||||
from datetime import UTC, datetime
|
||||
from datetime import datetime
|
||||
from unittest.mock import MagicMock, patch
|
||||
from uuid import UUID
|
||||
|
||||
@@ -21,6 +21,7 @@ from crewai.traces.unified_trace_controller import (
|
||||
trace_flow_step,
|
||||
trace_llm_call,
|
||||
)
|
||||
from crewai.utilities.datetime_compat import UTC
|
||||
|
||||
|
||||
class TestUnifiedTraceController:
|
||||
|
||||
35
tests/utilities/test_datetime_compat.py
Normal file
35
tests/utilities/test_datetime_compat.py
Normal file
@@ -0,0 +1,35 @@
|
||||
"""Test datetime compatibility module."""
|
||||
from datetime import datetime, timedelta, timezone
|
||||
|
||||
from crewai.utilities.datetime_compat import UTC
|
||||
|
||||
|
||||
def test_utc_timezone_compatibility():
|
||||
"""Test that UTC timezone is compatible with both Python 3.10 and 3.11+"""
|
||||
assert UTC == timezone.utc
|
||||
assert UTC.tzname(None) == "UTC"
|
||||
# Verify it works with datetime.now()
|
||||
dt = datetime.now(UTC)
|
||||
assert dt.tzinfo == timezone.utc
|
||||
|
||||
|
||||
def test_utc_timezone_edge_cases():
|
||||
"""Test UTC timezone handling in edge cases."""
|
||||
# Test with leap year
|
||||
leap_date = datetime(2024, 2, 29, tzinfo=UTC)
|
||||
assert leap_date.tzinfo == timezone.utc
|
||||
|
||||
# Test DST transition dates
|
||||
dst_date = datetime(2024, 3, 10, 2, 0, tzinfo=UTC) # US DST start
|
||||
assert dst_date.tzinfo == timezone.utc
|
||||
|
||||
# Test with minimum/maximum dates
|
||||
min_date = datetime.min.replace(tzinfo=UTC)
|
||||
max_date = datetime.max.replace(tzinfo=UTC)
|
||||
assert min_date.tzinfo == timezone.utc
|
||||
assert max_date.tzinfo == timezone.utc
|
||||
|
||||
# Test timezone offset calculations
|
||||
dt = datetime(2024, 1, 1, tzinfo=UTC)
|
||||
offset = dt.utcoffset()
|
||||
assert offset == timedelta(0) # UTC should always have zero offset
|
||||
Reference in New Issue
Block a user