Coverage for /pythoncovmergedfiles/medio/medio/usr/local/lib/python3.8/site-packages/pendulum/parser.py: 80%

44 statements  

« prev     ^ index     » next       coverage.py v7.3.1, created at 2023-09-30 06:11 +0000

1from __future__ import annotations 

2 

3import datetime 

4import typing as t 

5 

6import pendulum 

7 

8from pendulum.duration import Duration 

9from pendulum.parsing import _Interval 

10from pendulum.parsing import parse as base_parse 

11from pendulum.tz.timezone import UTC 

12 

13 

14if t.TYPE_CHECKING: 

15 from pendulum.date import Date 

16 from pendulum.datetime import DateTime 

17 from pendulum.interval import Interval 

18 from pendulum.time import Time 

19 

20try: 

21 from _pendulum import Duration as RustDuration 

22except ImportError: 

23 RustDuration = None # type: ignore[assignment,misc] 

24 

25 

26def parse(text: str, **options: t.Any) -> Date | Time | DateTime | Duration: 

27 # Use the mock now value if it exists 

28 options["now"] = options.get("now") 

29 

30 return _parse(text, **options) 

31 

32 

33def _parse(text: str, **options: t.Any) -> Date | DateTime | Time | Duration | Interval: 

34 """ 

35 Parses a string with the given options. 

36 

37 :param text: The string to parse. 

38 """ 

39 # Handling special cases 

40 if text == "now": 

41 return pendulum.now() 

42 

43 parsed = base_parse(text, **options) 

44 

45 if isinstance(parsed, datetime.datetime): 

46 return pendulum.datetime( 

47 parsed.year, 

48 parsed.month, 

49 parsed.day, 

50 parsed.hour, 

51 parsed.minute, 

52 parsed.second, 

53 parsed.microsecond, 

54 tz=parsed.tzinfo or options.get("tz", UTC), 

55 ) 

56 

57 if isinstance(parsed, datetime.date): 

58 return pendulum.date(parsed.year, parsed.month, parsed.day) 

59 

60 if isinstance(parsed, datetime.time): 

61 return pendulum.time( 

62 parsed.hour, parsed.minute, parsed.second, parsed.microsecond 

63 ) 

64 

65 if isinstance(parsed, _Interval): 

66 if parsed.duration is not None: 

67 duration = parsed.duration 

68 

69 if parsed.start is not None: 

70 dt = pendulum.instance(parsed.start, tz=options.get("tz", UTC)) 

71 

72 return pendulum.interval( 

73 dt, 

74 dt.add( 

75 years=duration.years, 

76 months=duration.months, 

77 weeks=duration.weeks, 

78 days=duration.remaining_days, 

79 hours=duration.hours, 

80 minutes=duration.minutes, 

81 seconds=duration.remaining_seconds, 

82 microseconds=duration.microseconds, 

83 ), 

84 ) 

85 

86 dt = pendulum.instance( 

87 t.cast(datetime.datetime, parsed.end), tz=options.get("tz", UTC) 

88 ) 

89 

90 return pendulum.interval( 

91 dt.subtract( 

92 years=duration.years, 

93 months=duration.months, 

94 weeks=duration.weeks, 

95 days=duration.remaining_days, 

96 hours=duration.hours, 

97 minutes=duration.minutes, 

98 seconds=duration.remaining_seconds, 

99 microseconds=duration.microseconds, 

100 ), 

101 dt, 

102 ) 

103 

104 return pendulum.interval( 

105 pendulum.instance( 

106 t.cast(datetime.datetime, parsed.start), tz=options.get("tz", UTC) 

107 ), 

108 pendulum.instance( 

109 t.cast(datetime.datetime, parsed.end), tz=options.get("tz", UTC) 

110 ), 

111 ) 

112 

113 if isinstance(parsed, Duration): 

114 return parsed 

115 

116 if RustDuration is not None and isinstance(parsed, RustDuration): 

117 return pendulum.duration( 

118 years=parsed.years, 

119 months=parsed.months, 

120 weeks=parsed.weeks, 

121 days=parsed.days, 

122 hours=parsed.hours, 

123 minutes=parsed.minutes, 

124 seconds=parsed.seconds, 

125 microseconds=parsed.microseconds, 

126 ) 

127 

128 raise NotImplementedError