ipulse-shared-core-ftredge 8.1.1__tar.gz → 9.1.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of ipulse-shared-core-ftredge might be problematic. Click here for more details.
- {ipulse_shared_core_ftredge-8.1.1/src/ipulse_shared_core_ftredge.egg-info → ipulse_shared_core_ftredge-9.1.1}/PKG-INFO +2 -2
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/setup.py +2 -2
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/base_api_response.py +12 -4
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/subscription.py +43 -32
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/user_status.py +17 -7
- ipulse_shared_core_ftredge-9.1.1/src/ipulse_shared_core_ftredge/utils/custom_json_encoder.py +46 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1/src/ipulse_shared_core_ftredge.egg-info}/PKG-INFO +2 -2
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge.egg-info/SOURCES.txt +1 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge.egg-info/requires.txt +1 -1
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/LICENCE +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/README.md +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/pyproject.toml +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/setup.cfg +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/__init__.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/dependencies/__init__.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/dependencies/auth_firebase_token_validation.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/dependencies/auth_protected_router.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/dependencies/authz_for_apis.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/dependencies/firestore_client.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/__init__.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/base_data_model.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/organization_profile.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/user_auth.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/user_profile.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/models/user_profile_update.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/services/__init__.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/services/base_firestore_service.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/services/base_service_exceptions.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/services/fastapiservicemon.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/services/servicemon.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/utils/__init__.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge/utils/json_encoder.py +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge.egg-info/dependency_links.txt +0 -0
- {ipulse_shared_core_ftredge-8.1.1 → ipulse_shared_core_ftredge-9.1.1}/src/ipulse_shared_core_ftredge.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: ipulse_shared_core_ftredge
|
|
3
|
-
Version:
|
|
3
|
+
Version: 9.1.1
|
|
4
4
|
Summary: Shared Core models and Logger util for the Pulse platform project. Using AI for financial advisory and investment management.
|
|
5
5
|
Home-page: https://github.com/TheFutureEdge/ipulse_shared_core
|
|
6
6
|
Author: Russlan Ramdowar
|
|
@@ -13,7 +13,7 @@ Requires-Dist: pydantic[email]~=2.5
|
|
|
13
13
|
Requires-Dist: python-dateutil~=2.8
|
|
14
14
|
Requires-Dist: fastapi~=0.115.8
|
|
15
15
|
Requires-Dist: pytest
|
|
16
|
-
Requires-Dist: ipulse_shared_base_ftredge>=
|
|
16
|
+
Requires-Dist: ipulse_shared_base_ftredge>=6.4.1
|
|
17
17
|
Dynamic: author
|
|
18
18
|
Dynamic: classifier
|
|
19
19
|
Dynamic: home-page
|
|
@@ -3,7 +3,7 @@ from setuptools import setup, find_packages
|
|
|
3
3
|
|
|
4
4
|
setup(
|
|
5
5
|
name='ipulse_shared_core_ftredge',
|
|
6
|
-
version='
|
|
6
|
+
version='9.1.1',
|
|
7
7
|
package_dir={'': 'src'}, # Specify the source directory
|
|
8
8
|
packages=find_packages(where='src'), # Look for packages in 'src'
|
|
9
9
|
install_requires=[
|
|
@@ -12,7 +12,7 @@ setup(
|
|
|
12
12
|
'python-dateutil~=2.8',
|
|
13
13
|
'fastapi~=0.115.8',
|
|
14
14
|
'pytest',
|
|
15
|
-
'ipulse_shared_base_ftredge>=
|
|
15
|
+
'ipulse_shared_base_ftredge>=6.4.1',
|
|
16
16
|
],
|
|
17
17
|
author='Russlan Ramdowar',
|
|
18
18
|
description='Shared Core models and Logger util for the Pulse platform project. Using AI for financial advisory and investment management.',
|
|
@@ -3,10 +3,7 @@ import datetime as dt
|
|
|
3
3
|
import json
|
|
4
4
|
from pydantic import BaseModel, ConfigDict
|
|
5
5
|
from fastapi.responses import JSONResponse
|
|
6
|
-
from ipulse_shared_core_ftredge.utils
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
6
|
+
from ipulse_shared_core_ftredge.utils import CustomJSONEncoder
|
|
10
7
|
|
|
11
8
|
|
|
12
9
|
T = TypeVar('T')
|
|
@@ -30,6 +27,17 @@ class PaginatedAPIResponse(BaseAPIResponse, Generic[T]):
|
|
|
30
27
|
|
|
31
28
|
class CustomJSONResponse(JSONResponse):
|
|
32
29
|
def render(self, content) -> bytes:
|
|
30
|
+
# Handle Pydantic models to exclude computed fields
|
|
31
|
+
if isinstance(content, dict) and "data" in content and hasattr(content["data"], "model_dump"):
|
|
32
|
+
# If content["data"] is a Pydantic model, use model_dump with exclude_unset=True
|
|
33
|
+
# and exclude_computed=True to prevent serialization of computed fields
|
|
34
|
+
content = dict(content) # Create a copy to avoid modifying the original
|
|
35
|
+
content["data"] = content["data"].model_dump(
|
|
36
|
+
exclude_unset=True,
|
|
37
|
+
exclude_computed=True
|
|
38
|
+
)
|
|
39
|
+
|
|
40
|
+
# Use the CustomJSONEncoder for serialization
|
|
33
41
|
return json.dumps(
|
|
34
42
|
content,
|
|
35
43
|
ensure_ascii=False,
|
|
@@ -2,7 +2,7 @@ from datetime import datetime, timezone
|
|
|
2
2
|
from dateutil.relativedelta import relativedelta
|
|
3
3
|
import uuid
|
|
4
4
|
from typing import Set, Optional, ClassVar, Dict, Any, List, Union
|
|
5
|
-
from pydantic import Field, ConfigDict
|
|
5
|
+
from pydantic import Field, ConfigDict
|
|
6
6
|
from ipulse_shared_base_ftredge import Layer, Module, list_as_lower_strings, Subject, SubscriptionPlan, SubscriptionStatus
|
|
7
7
|
from ipulse_shared_base_ftredge.enums.enums_iam import IAMUnitType
|
|
8
8
|
from .base_data_model import BaseDataModel
|
|
@@ -21,7 +21,7 @@ class Subscription(BaseDataModel):
|
|
|
21
21
|
|
|
22
22
|
model_config = ConfigDict(frozen=True, extra="forbid")
|
|
23
23
|
|
|
24
|
-
VERSION: ClassVar[float] =
|
|
24
|
+
VERSION: ClassVar[float] = 3.0 # Incremented version for direct fields instead of computed
|
|
25
25
|
DOMAIN: ClassVar[str] = "_".join(list_as_lower_strings(Layer.PULSE_APP, Module.CORE.name, Subject.SUBSCRIPTION.name))
|
|
26
26
|
OBJ_REF: ClassVar[str] = "subscription"
|
|
27
27
|
|
|
@@ -49,14 +49,11 @@ class Subscription(BaseDataModel):
|
|
|
49
49
|
description="Version of the subscription plan"
|
|
50
50
|
)
|
|
51
51
|
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
Example: "free_subscription_1"
|
|
58
|
-
"""
|
|
59
|
-
return f"{self.plan_name.value}_{self.plan_version}"
|
|
52
|
+
# Direct field instead of computed
|
|
53
|
+
plan_id: str = Field(
|
|
54
|
+
..., # Required field, no default
|
|
55
|
+
description="Combined plan identifier (plan_name_plan_version)"
|
|
56
|
+
)
|
|
60
57
|
|
|
61
58
|
# Cycle duration fields
|
|
62
59
|
cycle_start_date: datetime = Field(
|
|
@@ -64,7 +61,13 @@ class Subscription(BaseDataModel):
|
|
|
64
61
|
description="Subscription Cycle Start Date"
|
|
65
62
|
)
|
|
66
63
|
|
|
67
|
-
#
|
|
64
|
+
# Direct field instead of computed
|
|
65
|
+
cycle_end_date: datetime = Field(
|
|
66
|
+
..., # Required field, no default
|
|
67
|
+
description="Subscription Cycle End Date"
|
|
68
|
+
)
|
|
69
|
+
|
|
70
|
+
# Fields for cycle calculation
|
|
68
71
|
validity_time_length: int = Field(
|
|
69
72
|
..., # Required field, no default
|
|
70
73
|
description="Length of subscription validity period (e.g., 1, 3, 12)"
|
|
@@ -75,23 +78,6 @@ class Subscription(BaseDataModel):
|
|
|
75
78
|
description="Unit of subscription validity ('minute', 'hour', 'day', 'week', 'month', 'year')"
|
|
76
79
|
)
|
|
77
80
|
|
|
78
|
-
# Computed cycle_end_date based on start date and validity
|
|
79
|
-
@computed_field
|
|
80
|
-
def cycle_end_date(self) -> datetime:
|
|
81
|
-
"""Calculate the end date based on start date and validity period."""
|
|
82
|
-
if self.validity_time_unit == "minute":
|
|
83
|
-
return self.cycle_start_date + relativedelta(minutes=self.validity_time_length)
|
|
84
|
-
elif self.validity_time_unit == "hour":
|
|
85
|
-
return self.cycle_start_date + relativedelta(hours=self.validity_time_length)
|
|
86
|
-
elif self.validity_time_unit == "day":
|
|
87
|
-
return self.cycle_start_date + relativedelta(days=self.validity_time_length)
|
|
88
|
-
elif self.validity_time_unit == "week":
|
|
89
|
-
return self.cycle_start_date + relativedelta(weeks=self.validity_time_length)
|
|
90
|
-
elif self.validity_time_unit == "year":
|
|
91
|
-
return self.cycle_start_date + relativedelta(years=self.validity_time_length)
|
|
92
|
-
else: # Default to months
|
|
93
|
-
return self.cycle_start_date + relativedelta(months=self.validity_time_length)
|
|
94
|
-
|
|
95
81
|
# Renewal and status fields
|
|
96
82
|
auto_renew: bool = Field(
|
|
97
83
|
..., # Required field, no default
|
|
@@ -103,8 +89,7 @@ class Subscription(BaseDataModel):
|
|
|
103
89
|
description="Subscription Status (active, trial, pending_confirmation, etc.)"
|
|
104
90
|
)
|
|
105
91
|
|
|
106
|
-
#
|
|
107
|
-
# Update the type definition to use string keys for IAMUnitType
|
|
92
|
+
# IAM permissions structure
|
|
108
93
|
iam_domain_permissions: Dict[str, Dict[str, List[str]]] = Field(
|
|
109
94
|
..., # Required field, no default
|
|
110
95
|
description="IAM domain permissions granted by this subscription (domain -> IAM unit type -> list of unit references)"
|
|
@@ -125,7 +110,7 @@ class Subscription(BaseDataModel):
|
|
|
125
110
|
description="Reference to payment transaction"
|
|
126
111
|
)
|
|
127
112
|
|
|
128
|
-
#
|
|
113
|
+
# Credit management fields
|
|
129
114
|
subscription_based_insight_credits_per_update: int = Field(
|
|
130
115
|
default=0,
|
|
131
116
|
description="Number of insight credits to add on each update"
|
|
@@ -157,6 +142,23 @@ class Subscription(BaseDataModel):
|
|
|
157
142
|
description="Additional metadata for the subscription"
|
|
158
143
|
)
|
|
159
144
|
|
|
145
|
+
# Helper method to calculate cycle end date
|
|
146
|
+
@classmethod
|
|
147
|
+
def calculate_cycle_end_date(cls, start_date: datetime, validity_length: int, validity_unit: str) -> datetime:
|
|
148
|
+
"""Calculate the end date based on start date and validity period."""
|
|
149
|
+
if validity_unit == "minute":
|
|
150
|
+
return start_date + relativedelta(minutes=validity_length)
|
|
151
|
+
elif validity_unit == "hour":
|
|
152
|
+
return start_date + relativedelta(hours=validity_length)
|
|
153
|
+
elif validity_unit == "day":
|
|
154
|
+
return start_date + relativedelta(days=validity_length)
|
|
155
|
+
elif validity_unit == "week":
|
|
156
|
+
return start_date + relativedelta(weeks=validity_length)
|
|
157
|
+
elif validity_unit == "year":
|
|
158
|
+
return start_date + relativedelta(years=validity_length)
|
|
159
|
+
else: # Default to months
|
|
160
|
+
return start_date + relativedelta(months=validity_length)
|
|
161
|
+
|
|
160
162
|
# Methods for subscription management
|
|
161
163
|
def is_active(self) -> bool:
|
|
162
164
|
"""Check if the subscription is currently active."""
|
|
@@ -176,4 +178,13 @@ class Subscription(BaseDataModel):
|
|
|
176
178
|
now = datetime.now(timezone.utc)
|
|
177
179
|
if now > self.cycle_end_date:
|
|
178
180
|
return 0
|
|
179
|
-
|
|
181
|
+
|
|
182
|
+
# Get time difference
|
|
183
|
+
time_diff = self.cycle_end_date - now
|
|
184
|
+
|
|
185
|
+
# If there's any time remaining but less than a day, return 1
|
|
186
|
+
if time_diff.days == 0 and time_diff.seconds > 0:
|
|
187
|
+
return 1
|
|
188
|
+
|
|
189
|
+
# Otherwise return the number of complete days
|
|
190
|
+
return time_diff.days
|
|
@@ -47,7 +47,7 @@ class UserStatus(BaseDataModel):
|
|
|
47
47
|
model_config = ConfigDict(frozen=False, extra="forbid")
|
|
48
48
|
|
|
49
49
|
# Class constants
|
|
50
|
-
VERSION: ClassVar[float] = 5.
|
|
50
|
+
VERSION: ClassVar[float] = 5.1 # Incremented version for removing computed fields
|
|
51
51
|
DOMAIN: ClassVar[str] = "_".join(list_as_lower_strings(Layer.PULSE_APP, Module.CORE.name, Subject.USER.name))
|
|
52
52
|
OBJ_REF: ClassVar[str] = "userstatus"
|
|
53
53
|
|
|
@@ -353,14 +353,14 @@ class UserStatus(BaseDataModel):
|
|
|
353
353
|
"""
|
|
354
354
|
return self.update_iam_unit_refs_from_subscription(subscription)
|
|
355
355
|
|
|
356
|
-
|
|
356
|
+
# Method instead of computed field
|
|
357
357
|
def is_subscription_active(self) -> bool:
|
|
358
358
|
"""Check if the user has an active subscription."""
|
|
359
359
|
if self.active_subscription:
|
|
360
360
|
return self.active_subscription.is_active()
|
|
361
361
|
return False
|
|
362
362
|
|
|
363
|
-
|
|
363
|
+
# Method instead of computed field
|
|
364
364
|
def subscription_expires_in_days(self) -> Optional[int]:
|
|
365
365
|
"""Get days until subscription expiration."""
|
|
366
366
|
if self.active_subscription and self.active_subscription.is_active():
|
|
@@ -464,21 +464,31 @@ class UserStatus(BaseDataModel):
|
|
|
464
464
|
if plan_version is None or validity_time_length is None or validity_time_unit is None:
|
|
465
465
|
return
|
|
466
466
|
|
|
467
|
-
#
|
|
467
|
+
# Calculate directly assigned fields
|
|
468
|
+
plan_id = f"{plan_name_str}_{plan_version}"
|
|
469
|
+
cycle_start_date = datetime.now(timezone.utc)
|
|
470
|
+
cycle_end_date = Subscription.calculate_cycle_end_date(
|
|
471
|
+
cycle_start_date,
|
|
472
|
+
validity_time_length,
|
|
473
|
+
validity_time_unit
|
|
474
|
+
)
|
|
475
|
+
|
|
476
|
+
# Create subscription object with direct fields instead of computed
|
|
468
477
|
subscription = Subscription(
|
|
469
478
|
plan_name=plan_name,
|
|
470
479
|
plan_version=plan_version,
|
|
471
|
-
|
|
480
|
+
plan_id=plan_id,
|
|
481
|
+
cycle_start_date=cycle_start_date,
|
|
482
|
+
cycle_end_date=cycle_end_date,
|
|
472
483
|
validity_time_length=validity_time_length,
|
|
473
484
|
validity_time_unit=validity_time_unit,
|
|
474
|
-
auto_renew=plan_data.get("plan_auto_renewal", False),
|
|
485
|
+
auto_renew=plan_data.get("plan_auto_renewal", False),
|
|
475
486
|
status=SubscriptionStatus.ACTIVE,
|
|
476
487
|
iam_domain_permissions=iam_domain_permissions,
|
|
477
488
|
fallback_plan_id=plan_data.get("fallback_plan_id_if_current_plan_expired"),
|
|
478
489
|
price_paid_usd=plan_data.get("plan_per_cycle_price_usd") or 0.0,
|
|
479
490
|
created_by=source,
|
|
480
491
|
updated_by=source,
|
|
481
|
-
# Direct attributes for credit-related fields
|
|
482
492
|
subscription_based_insight_credits_per_update=plan_data.get("subscription_based_insight_credits_per_update") or 0,
|
|
483
493
|
subscription_based_insight_credits_update_freq_h=plan_data.get("subscription_based_insight_credits_update_freq_h") or 24,
|
|
484
494
|
extra_insight_credits_per_cycle=plan_data.get("extra_insight_credits_per_cycle") or 0,
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import json
|
|
2
|
+
import datetime
|
|
3
|
+
from typing import Any
|
|
4
|
+
from enum import Enum
|
|
5
|
+
from uuid import UUID
|
|
6
|
+
from decimal import Decimal
|
|
7
|
+
from pydantic import BaseModel
|
|
8
|
+
|
|
9
|
+
class CustomJSONEncoder(json.JSONEncoder):
|
|
10
|
+
"""Custom JSON encoder to handle special types like datetimes, UUIDs, and Pydantic models."""
|
|
11
|
+
|
|
12
|
+
def default(self, obj: Any) -> Any:
|
|
13
|
+
# Handle datetime objects
|
|
14
|
+
if isinstance(obj, datetime.datetime):
|
|
15
|
+
return obj.isoformat()
|
|
16
|
+
|
|
17
|
+
# Handle date objects
|
|
18
|
+
elif isinstance(obj, datetime.date):
|
|
19
|
+
return obj.isoformat()
|
|
20
|
+
|
|
21
|
+
# Handle time objects
|
|
22
|
+
elif isinstance(obj, datetime.time):
|
|
23
|
+
return obj.isoformat()
|
|
24
|
+
|
|
25
|
+
# Handle UUID objects
|
|
26
|
+
elif isinstance(obj, UUID):
|
|
27
|
+
return str(obj)
|
|
28
|
+
|
|
29
|
+
# Handle Decimal objects
|
|
30
|
+
elif isinstance(obj, Decimal):
|
|
31
|
+
return float(obj)
|
|
32
|
+
|
|
33
|
+
# Handle Enum objects
|
|
34
|
+
elif isinstance(obj, Enum):
|
|
35
|
+
return obj.value
|
|
36
|
+
|
|
37
|
+
# Handle Pydantic models - exclude computed fields
|
|
38
|
+
elif isinstance(obj, BaseModel):
|
|
39
|
+
return obj.model_dump(exclude_computed=True)
|
|
40
|
+
|
|
41
|
+
# Handle sets by converting to sorted lists for consistent output
|
|
42
|
+
elif isinstance(obj, set):
|
|
43
|
+
return sorted(list(obj))
|
|
44
|
+
|
|
45
|
+
# For everything else, use the default encoder
|
|
46
|
+
return super().default(obj)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: ipulse_shared_core_ftredge
|
|
3
|
-
Version:
|
|
3
|
+
Version: 9.1.1
|
|
4
4
|
Summary: Shared Core models and Logger util for the Pulse platform project. Using AI for financial advisory and investment management.
|
|
5
5
|
Home-page: https://github.com/TheFutureEdge/ipulse_shared_core
|
|
6
6
|
Author: Russlan Ramdowar
|
|
@@ -13,7 +13,7 @@ Requires-Dist: pydantic[email]~=2.5
|
|
|
13
13
|
Requires-Dist: python-dateutil~=2.8
|
|
14
14
|
Requires-Dist: fastapi~=0.115.8
|
|
15
15
|
Requires-Dist: pytest
|
|
16
|
-
Requires-Dist: ipulse_shared_base_ftredge>=
|
|
16
|
+
Requires-Dist: ipulse_shared_base_ftredge>=6.4.1
|
|
17
17
|
Dynamic: author
|
|
18
18
|
Dynamic: classifier
|
|
19
19
|
Dynamic: home-page
|
|
@@ -28,4 +28,5 @@ src/ipulse_shared_core_ftredge/services/base_service_exceptions.py
|
|
|
28
28
|
src/ipulse_shared_core_ftredge/services/fastapiservicemon.py
|
|
29
29
|
src/ipulse_shared_core_ftredge/services/servicemon.py
|
|
30
30
|
src/ipulse_shared_core_ftredge/utils/__init__.py
|
|
31
|
+
src/ipulse_shared_core_ftredge/utils/custom_json_encoder.py
|
|
31
32
|
src/ipulse_shared_core_ftredge/utils/json_encoder.py
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|