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

Feat/v1.1.6 #12

Merged
merged 2 commits into from
May 15, 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
2 changes: 1 addition & 1 deletion .github/workflows/code-quality.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ jobs:
strategy:
# You can use PyPy versions in python-version.
matrix:
python-version: ["3.6", "3.7", "3.8", "3.9", "3.10", "3.11"]
python-version: ["3.6", "3.7", "3.8", "3.9", "3.10", "3.11", "3.12"]

steps:
- uses: actions/checkout@v3
Expand Down
6 changes: 3 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -165,7 +165,7 @@ Note that a flag value change listener is bound to a specific user and flag key.
The flag value change listener will be notified whenever the SDK receives any change to any feature flag's configuration,
or to a user segment that is referenced by a feature flag. To register a flag value change listener, use `add_flag_value_may_changed_listener` or `add_flag_value_changed_listener`

When you track a flag change using `add_flag_value_may_changed_listener`, this does not necessarily mean the flag's value has changed for any particular flag, only that some part of the flag configuration was changed so that it *_MAY_* return a different value than it previously returned for some user.
When you track a flag change using `add_flag_value_maybe_changed_listener`, this does not necessarily mean the flag's value has changed for any particular flag, only that some part of the flag configuration was changed so that it *_MAY_* return a different value than it previously returned for some user.

If you want to track a flag whose value *_MUST_* be changed, `add_flag_value_changed_listener` will register a listener that will be notified if and only if the flag value changes.

Expand All @@ -175,9 +175,9 @@ If the SDK is in offline mode, then it cannot know when there is a change, becau
```python
if client.initialize:
# flag value may be changed
client.flag_tracker.add_flag_value_may_changed_listener(flag_key, user, callback_fn)
client.flag_tracker.add_flag_value_maybe_changed_listener(flag_key, user, flag_value_maybe_changed_callback_fn)
# flag value must be changed
client.flag_tracker.add_flag_value_changed_listener(flag_key, user, callback_fn)
client.flag_tracker.add_flag_value_changed_listener(flag_key, user, flag_value_changed_callback_fn)

```
`flag_key`: the key of the feature flag to track
Expand Down
4 changes: 2 additions & 2 deletions fbclient/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -343,7 +343,7 @@ def track_metric(self, user: dict, event_name: str, metric_value: float = 1.0):
:param event_name: the name of the event, which may correspond to a goal in A/B tests
:param metric_value: a numeric value used by the experiment, default value is 1.0
"""
if not event_name or metric_value <= 0:
if not event_name:
log.warning('FB Python SDK: event/metric invalid')
return
try:
Expand Down Expand Up @@ -375,7 +375,7 @@ def track_metrics(self, user: dict, metrics: Mapping[str, float]):

metric_event = MetricEvent(fb_user)
for event_name, metric_value in metrics.items():
if event_name and metric_value > 0:
if event_name:
metric_event.add(Metric(event_name, metric_value))
self._event_handler(metric_event)

Expand Down
29 changes: 15 additions & 14 deletions fbclient/flag_change_notification.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ def __init__(self,
flag_key: str,
user: dict,
evaluate_fn: Callable[[str, dict, Any], Any],
flag_value_changed_fn: Callable[[str, Any], None]):
flag_value_changed_fn: Callable[[str, Any, Any], None]):
self.__flag_key = flag_key
self.__user = user
self.__evaluate_fn = evaluate_fn
Expand All @@ -51,20 +51,20 @@ def on_flag_change(self, notice: FlagChangedNotice):
prev_flag_value = self.__prvious_flag_value
curr_flag_value = self.__evaluate_fn(self.__flag_key, self.__user, None)
if prev_flag_value != curr_flag_value:
self.__fn(self.__flag_key, curr_flag_value)
self.__fn(self.__flag_key, prev_flag_value, curr_flag_value)
self.__prvious_flag_value = curr_flag_value


class FlagValueMayChangedListener(FlagChangedListener):
class FlagValueMaybeChangedListener(FlagChangedListener):
def __init__(self,
flag_key: str,
user: dict,
evaluate_fn: Callable[[str, dict, Any], Any],
flag_value_changed_fn: Callable[[str, Any], None]):
flag_value_maybe_changed_fn: Callable[[str, Any], None]):
self.__flag_key = flag_key
self.__user = user
self.__evaluate_fn = evaluate_fn
self.__fn = flag_value_changed_fn
self.__fn = flag_value_maybe_changed_fn

def on_flag_change(self, notice: FlagChangedNotice):
if notice.flag_key == self.__flag_key:
Expand Down Expand Up @@ -95,7 +95,7 @@ def __init__(self,
def add_flag_value_changed_listener(self,
flag_key: str,
user: dict,
flag_value_changed_fn: Callable[[str, Any], None]) -> FlagValueChangedListener:
flag_value_changed_fn: Callable[[str, Any, Any], None]) -> FlagValueChangedListener:
"""
Registers a listener to be notified of a change in a specific feature flag's value for a specific FeatBit user.

Expand All @@ -110,7 +110,8 @@ def add_flag_value_changed_listener(self,
:param user: The user to evaluate the flag value
:param flag_value_changed_fn: The function to be called only when this flag value changes
* the first argument is the flag key
* the second argument is the latest flag value, this value must be different from the previous value
* the second argument is the previous flag value
* the third argument is the current flag value

:return: A listener object that can be used to remove it later on.
"""
Expand All @@ -128,10 +129,10 @@ def add_flag_value_changed_listener(self,
self.add_flag_changed_listener(listener)
return listener

def add_flag_value_may_changed_listener(self,
flag_key: str,
user: dict,
flag_value_changed_fn: Callable[[str, Any], None]) -> FlagValueMayChangedListener:
def add_flag_value_maybe_changed_listener(self,
flag_key: str,
user: dict,
flag_value_maybe_changed_fn: Callable[[str, Any], None]) -> FlagValueMaybeChangedListener:
"""
Registers a listener to be notified of a change in a specific feature flag's value for a specific FeatBit user.

Expand All @@ -145,7 +146,7 @@ def add_flag_value_may_changed_listener(self,

:param flag_key: The key of the feature flag to track
:param user: The user to evaluate the flag value
:param flag_value_changed_fn: The function to be called only if any changes to a specific flag
:param flag_value_maybe_changed_fn: The function to be called if any changes to a specific flag
* the first argument is the flag key
* the second argument is the latest flag value, this value may be same as the previous value

Expand All @@ -159,10 +160,10 @@ def add_flag_value_may_changed_listener(self,
# check user
FBUser.from_dict(user)
# check flag_value_changed_fn
if not isinstance(flag_value_changed_fn, Callable) or not flag_value_changed_fn:
if not isinstance(flag_value_maybe_changed_fn, Callable) or not flag_value_maybe_changed_fn:
raise ValueError('flag_value_changed_fn must be a callable function')

listener = FlagValueMayChangedListener(flag_key, user, self.__evaluate_fn, flag_value_changed_fn)
listener = FlagValueMaybeChangedListener(flag_key, user, self.__evaluate_fn, flag_value_maybe_changed_fn)
self.add_flag_changed_listener(listener)
return listener

Expand Down
2 changes: 1 addition & 1 deletion fbclient/utils/rwlock.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ def release_read_lock(self):
with self._read_ready:
self._readers = self._readers - 1 if self._readers > 0 else 0
if self._readers == 0:
self._read_ready.notifyAll()
self._read_ready.notify_all()

def write_lock(self):
""" Acquire a write lock. Blocks until there are no
Expand Down
1 change: 0 additions & 1 deletion fbclient/version.py

This file was deleted.

2 changes: 1 addition & 1 deletion release/package.json
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
{
"version":"1.1.5"
"version":"1.1.6"
}
3 changes: 2 additions & 1 deletion setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,10 +50,11 @@ def parse_requirements(filename):
'Programming Language :: Python :: 3.9',
'Programming Language :: Python :: 3.10',
'Programming Language :: Python :: 3.11',
'Programming Language :: Python :: 3.12',
],
extras_require={
"dev": dev_reqs
},
tests_require=dev_reqs,
python_requires='>=3.6, <=3.11'
python_requires='>=3.6, <=3.12'
)
Loading