This PR adds potentially stale events as available to all addons and
adds a formatted message.
## Discussion
I'd still be interested in hearing input on whether the event type
should be selectable by addons or not before we start emitting the
event. I'm leaning towards "yes", but I'll take your thoughts into
consideration.
This PR does **one** thing:
it changes the events for potentially stale to:
- Only being emitted when potentially stale gets turned on
- In doing so, it also simplifies the event that's getting emitted,
removing the `data` property.
- The event is also renamed to better match the existing
`feature-stale-on` and `...-off` events.
The addon listening was broken out into a separate PR (#4279)
## Old description
This change lets all addons listen for events when features get marked
or unmarked as potentially stale.
### Discussion
#### All addons?
Should this be available to all addons? I can't see a reason why it
shouldn't be available to all addons, but I might be missing
something.
**Update**: spoke to a couple people. Can see no reason why this isn't
okay.
#### Should it be behind a flag?
The feature is still behind a flag, but the event type is not. Should
we gate the event being available until we actually emit the event?
That would require some more code, but could yield less potential
confusion.
Open to hearing your thoughts.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
wrap reorder event creation to strategy variant feature
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Fixes a bug around createStrategy
Fix: Create/Store strategy reorder event only when feature is on
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
This PR updates the feature type service by adding a new
`updateLifetime` method. This method handles the connection between the
API (#4256) and the store (#4252).
I've also added some new e2e tests to ensure that the API behaves as
expected.
This PR adds an operation and accompanying openapi docs for the new
"update feature type lifetime" API operation.
It also fixes an oversight where the other endpoint on the same
controller didn't use `respondWithValidation`.
Note: the API here is a suggestion. I'd like to hear whether you agree
with this implementation or not.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
When reordering strategies for a feature environment:
- Adds stop when CR are enabled
- Emits an event
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
This PR activates the event emission that was prepared for in
https://github.com/Unleash/unleash/pull/4239.
It emits events (behind a flag) when something is marked as potentially
stale or the opposite.
It takes the features returned from the store and creates events out of
them.
The events only contain data, no preData. This is because the preData
can easily be inferred and because it gives a nicer event in the event
log.
Here is an image of the difference. The top event uses only data, so it
shows the name of the feature and the new potentiallyStale status. The
bottom event uses both preData and data, so it only shows the new
potentiallyStale status and not the feature name (unless you show the
raw event):
![image](https://github.com/Unleash/unleash/assets/17786332/5ec0fbef-f4cf-4dc6-9af6-9203fca30e5d)
Should not be merged before #4239. Merge that and then rebase this off
main or cherry the commit.
## Discussion
### `preData`
Should we also use preData or is it enough to use only data? It seems
unnecessary in this event, but I'm open to hearing your thoughts.
### event author: `createdBy`
I've set `unleash-system` as the `createdBy` property on these events
because they are generated by the system. I found the same string used
some other places. However, it may be that there we want to use a
different author.
This PR adds updates the potentially stale status change events whenever
the potentially stale update function is run.
No events are emitted yet. While the emission is only a few lines of
code, I'd like to do that in a separate PR so that we can give it the
attention it deserves in the form of tests, etc.
This PR also moves the potentially stale update functionality from the
`update` method to only being done in the
`updatePotentiallyStaleFeatures` method. This keeps all functionality
related to marking `potentiallyStale` in one place.
The emission implementation was removed in
4fb7cbde03
## The update queries
While it would be possible to do the state updates in a single query
instead of three separate ones, wrangling this into knex proved to be
troublesome (and would also probably be harder to understand and reason
about). The current solution uses three smaller queries (one select, two
updates), as Jaanus suggested in a private slack thread.
This reverts commit 16e3799b9a.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
https://linear.app/unleash/issue/2-1232/implement-first-iteration-of-the-new-slack-app-addon
This PR implements the first iteration of the new Slack App addon.
Unlike the old Slack addon, this one uses a Slack App (bot) that is
installed to Slack workspaces in order to post messages. This uses
`@slack/web-api`, which internally uses the latest Slack API endpoints
like `postMessage`.
This is currently behind a flag: `slackAppAddon`.
The current flow is that the Unleash Slack App is installed from
whatever source:
- Unleash addons page;
- Direct link;
- https://unleash-slack-app.vercel.app/ (temporary URL);
- Slack App Directory (in the future);
- Etc;
After installed, we resolve the authorization to an `access_token` that
the user can paste into the Unleash Slack App addon configuration form.
https://github.com/Unleash/unleash/assets/14320932/6a6621b9-5b8a-4921-a279-30668be6d46c
Co-authored by: @daveleek
---------
Co-authored-by: David Leek <david@getunleash.io>
This PR lays most of the groundwork required for emitting events when
features are marked as potentially stale by Unleash. It does **not**
emit any events just yet. The summary is:
- periodically look for features that are potentially stale and mark
them (set to run every 10 seconds for now; can be changed)
- when features are updated, if the update data contains changes to the
feature's type or createdAt date, also update the potentially stale
status.
It is currently about 220 lines of tests and about 100 lines of
application code (primarily db migration and two new methods on the
IFeatureToggleStore interface).
The reason I wanted to put this into a single PR (instead of just the db
migration, then just the potentially stale marking, then the update
logic) is:
If users get the db migration first, but not the rest of the update
logic until the events are fired, then they could get a bunch of new
events for features that should have been marked as potentially stale
several days/weeks/months ago. That seemed undesirable to me, so I
decided to bunch those changes together. Of course, I'd be happy to
break it into smaller parts.
## Rules
A toggle will be marked as potentially stale iff:
- it is not already stale
- its createdAt date is older than its feature type's expected lifetime
would dictate
## Migration
The migration adds a new `potentially_stale` column to the features
table and sets this to true for any toggles that have exceeded their
expected lifetime and that have not already been marked as `stale`.
## Discussion
### The `currentTime` parameter of `markPotentiallyStaleFeatures`
The `markPotentiallyStaleFetaures` method takes an optional
`currentTime` parameter. This was added to make it easier to test (so
you can test "into the future"), but it's not used in the application.
We can rewrite the tests to instead update feature toggles manually, but
that wouldn't test the actual marking method. Happy to discuss.
## About the changes
Fix un-awaited promise on batch variant update - reduce function allowed
TS to skip Promise type.
---------
Co-authored-by: Gastón Fournier <gaston@getunleash.io>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Wraps the whole `registerClientMetrics` function with try/catch to
return 400 on error
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-1037](https://linear.app/unleash/issue/1-1037/return-4xx-error-for-incorrect-metrics-input)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
![Screenshot 2023-07-10 at 14 23
13](https://github.com/Unleash/unleash/assets/104830839/5417fb39-ce24-4b70-b3d3-c63374a29a12)
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
## About the changes
- Adding descriptions and examples to tag and tag types schemas
- Adding standard errors, summaries, and descriptions to tag and tag
types endpoints
- Some improvements on compilation errors
---------
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
Make each error class have to define its own status code. This makes
it easier for developers to see which code an error corresponds to and
means less jumping back and forth between files. In other words:
improved locality.
Unfortunately, the long switch needs to stay in case we get errors
thrown that aren't of the Unleash Error type, but we can move it to
the `fromLegacyError` file instead.
Tradeoff analysis by @kwasniew:
+ I like the locality of error to code reasoning
- now HTTP leaks to the non-HTTP code that throws those errors e.g. application services
If we had other delivery mechanisms other than HTTP then it wouldn't make sense to couple error codes to one protocol (HTTP). But since we're mostly doing web it may not be a problem.
@thomasheartman's response:
This is a good point and something I hadn't considered. The same data was always available on those errors (by using the same property), I've just made the declaration local to each error instead of something that the parent class handles. The idea was to make it easier to create new error classes with their corresponding error codes. Because the errors are intended to be API errors (or at least, I've always considered them to be that), I think that makes sense.
Taking your comment into consideration, I still think it's the right thing to do, but I'm not bullish about it. We could always walk it back later if we find that it's not appropriate. The old code is still available and we could easily enough roll back this change if we find that we want to decouple it later.
## About the changes
Include a new configuration parameter to be able to specify
source_type_name. This is an opt-in feature which provides backward
compatibility to our existing users.
![image](https://github.com/Unleash/unleash/assets/455064/0e65584f-f601-4f17-b7a5-e73dae55772e)
Closes#4109
## Discussion points
Maybe this should be hardcoded to `Unleash` but this gives additional
flexibility
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Adds description and summary to `favorite` endpoints
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-1098](https://linear.app/unleash/issue/1-1098/openapi-features-favorites)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
In some of the places we used `NoAccessError` for permissions, other
places we used it for a more generic 403 error with a different
message. This refactoring splits the error type into two distinct
types instead to make the error messages more consistent.
### What
Adds a quick and dirty description to requestPerSeconds and
segmentedRequestPerSecondsSchema so the enterprise /rps endpoint has
better API docs.
---------
Co-authored-by: Simon Hornby <liquidwicked64@gmail.com>
This PR fixes an issue where events generated during a db transaction
would get published before the transaction was complete. This caused
errors in some of our services that expected the data to be stored
before the transaction had been commited. Refer to [linear issue
1-1049](https://linear.app/unleash/issue/1-1049/event-emitter-should-emit-events-after-db-transaction-is-commited-not)
for more info.
Fixes 1-1049.
## Changes
The most important change here is that the `eventStore` no longer emits
events when they happen (because that can be in the middle of a
transaction). Instead, events are stored with a new `announced` column.
The new event announcer service runs on a schedule (every second) and
publishes any new events that have not been published.
Parts of the code have largely been lifted from the
`client-application-store`, which uses a similar logic.
I have kept the emitting of the event within the event store because a
lot of other services listen to events from this store, so removing that
would require a large rewrite. It's something we could look into down
the line, but it seems like too much of a change to do right now.
## Discussion
### Terminology:
Published vs announced? We should settle on one or the other. Announced
is consistent with the client-application store, but published sounds
more fitting for events.
### Publishing and marking events as published
The current implementation fetches all events that haven't been marked
as announced, sets them as announced, and then emits them. It's possible
that Unleash would crash in the interim or something else might happen,
causing the events not to get published. Maybe it would make sense to
just fetch the events and only mark them as published after the
announcement? On the other hand, that might get us into other problems.
Any thoughts on this would be much appreciated.
## About the changes
Fix OpenAPI definitions for endpoint
`/api/admin/projects/{projectId}/features/{featureName}/environments/{environment}`
and similar.
Apparently Jest doesn't like it when you use multiple stringContaining
statements for one property. Only the last `stringContaining`
statement is evaluated while the others are ignored.
This means that a lot of these assertions were never checked. To fix
that, I've extracted them into separate assertions.
### What
This PR adds documentation for our endpoints that are covered by our
"Events" tag. It also adds a type for all valid events, and then uses
this as valid values for type argument.
This PR updates endpoints and schemas for the API tokens tag.
As part of that, they also handle oneOf openapi validation errors and improve the console output for the enforcer tests.
###What
Adds an optional sensitive parameter for customHeaders to all current
addons. It is sensitive because the user might be including api key headers.
## What
This adds openapi documentation for the Auth tagged operations and
connected schemas.
## Discussion points
Our user schema seems to be exposing quite a bit of internal fields, I
flagged the isApi field as deprecated, I can imagine quite a few of
these fields also being deprecated to prepare for removal in next major
version, but I was unsure which ones were safe to do so with.
## Observation
We have some technical debt around the shape of the schema we're
claiming we're returning and what we actually are returning. I believe
@gastonfournier also observed this when we turned on validation for our
endpoints.
---------
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
This removes the experimental feature flag that defaulted to turn off
telemetry collection
Catch cases where the segment doesn't exist and populate that error
message with more info: it now says that a segment
with <id> doesn't exist instead of just 'No row'.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
Adds a UI that shows current status of version and feature usage
collection configuration, and a presence in the configuration menu +
menu bar.
Configuring these features is done by setting environment variables. The
version info collection is an existing feature that we're making more
visible, the feature usage collection feature is a new feature that has
it's own environment configuration but also depends on version info
collection being active to work.
When version collection is turned off and the experimental feature flag
for feature usage collection is turned off:
<img width="1269" alt="image"
src="https://github.com/Unleash/unleash/assets/707867/435a07da-d238-4b5b-a150-07e3bd6b816f">
When version collection is turned on and the experimental feature flag
is off:
<img width="1249" alt="image"
src="https://github.com/Unleash/unleash/assets/707867/8d1a76c5-99c9-4551-9a4f-86d477bbbf6f">
When the experimental feature flag is enabled, and version+telemetry is
turned off:
<img width="1239" alt="image"
src="https://github.com/Unleash/unleash/assets/707867/e0bc532b-be94-4076-bee1-faef9bc48a5b">
When version collection is turned on, the experimental feature flag is
enabled, and telemetry collection is turned off:
<img width="1234" alt="image"
src="https://github.com/Unleash/unleash/assets/707867/1bd190c1-08fe-4402-bde3-56f863a33289">
When version collection is turned on, the experimental feature flag is
enabled, and telemetry collection is turned on:
<img width="1229" alt="image"
src="https://github.com/Unleash/unleash/assets/707867/848912cd-30bd-43cf-9b81-c58a4cbad1e4">
When version collection is turned off, the experimental feature flag is
enabled, and telemetry collection is turned on:
<img width="1241" alt="image"
src="https://github.com/Unleash/unleash/assets/707867/d2b981f2-033f-4fae-a115-f93e0653729b">
---------
Co-authored-by: sighphyre <liquidwicked64@gmail.com>
Co-authored-by: Nuno Góis <github@nunogois.com>
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
### What
Added documentation for context fields and endpoints tagged with the
"Context" tag.
---------
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
This PR adds strategy titles as an optional bit of data added to client
features. It's only added when prompted.
![image](https://github.com/Unleash/unleash/assets/17786332/99509679-2aab-4c2a-abff-c6e6f27d8074)
## Discussion points:
### getPlaygroundFeatures
The optional `includeStrategyId` parameter has been replaced by a
`getPlaygroundFeatures` in the service (and in the underlying store).
The playground was the only place that used this specific include, so
instead of adding more and making the interface for that method more
complex, I created a new method that deals specifically with the
playground.
The underlying store still uses an `optionalIncludes` parameter,
however. I have a plan to make that interface more fluid, but I'd like
to propose that in a follow-up PR.
As part of the move to a unified domain this PR updates the default
EMAIL_SENDER to noreply@getunleash.io . Should not be merged/deployed
until we've verified DMARC, DKIM for the new domain.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Remove strategy improvements flag
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-1048](https://linear.app/unleash/issue/1-1048/remove-strategyimprovements-flag)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
## About the changes
This makes these permissions not available for selection. In particular
`UPDATE_ROLE`, `CREATE_API_TOKEN`, `UPDATE_API_TOKEN`,
`DELETE_API_TOKEN`, `READ_API_TOKEN` are long-lived and should be taken
out with special care which is why we have
https://linear.app/unleash/issue/2-1158/add-delete-migration-to-clean-up-no-longer-used-permissions
## Discussion points
If a role has this permission assigned, it will be displayed but will
not be able to remove it. Because the application code does not rely on
these permissions, this shouldn't be a problem. Later when we remove
them from the DB, the permission will be removed as well from the role
by the migration
## About the changes
This PR enables or disables create API token button based on the
permissions.
**Note:** the button is only displayed if you have READ permissions on
some API token. This is a minor limitation as having CREATE permissions
should also grant READ permissions, but right now this is up to the user
to set up the custom role with the correct permissions
**Note 2:** Project-specific API tokens are also ruled by the
project-specific permission to create API tokens in a project (just
having the root permissions to create a client token or frontend token
does not grant access to create a project-specific API token). The
permissions to access the creation of a project-specific API token then
rely on the root permissions to allow the user to create either a client
token or a frontend token.
---------
Co-authored-by: David Leek <david@getunleash.io>
## About the changes
`getUserRootRoles` should also consider custom root roles
This introduces test cases that unveiled a dependency between stores
(this happens actually at the DB layer having access-service access
tables from two different stores but skipping the store layer).
https://linear.app/unleash/issue/2-1161/a-user-with-custom-root-role-and-permission-to-create-client-api
---------
Co-authored-by: Nuno Góis <github@nunogois.com>
This PR changes the OpenAPI schema for the advanced playground to not
accept empty lists of environments and to not accept environment names
that don't match the env name pattern we use.
The pattern is the same as the one we use for controlling environment
names on creation.
However, there is a (small) chance that these may get out of sync later,
so we could do something to only define this pattern once (and import it
in the enterprise package), but that may be more work than is necessary,
and I'd suggest we do that later.
I've also added a minLength to the string items although it isn't
strictly necessary. It's primarily to give the users better feedback if
the name is empty.
This change adds an "edit" link to all playground strategies when they
are returned from the API, allowing the user to jump directly to the
evaluated strategy edit screen.
This change applies to both old and new strategies, so it should even
work in the old playground.
This does not use this information in the frontend yet.
## Discussion points:
Should "links" be an object or a singular string? I know the
notifications service uses just "link", but using an object will make
it easier to potentially add more actions in the future (such as
"enable"/"disable", maybe?)
Do we need to supply basePath? I noticed that the notifications links
only ever use an empty string for base path, so it might not be
necessary and can potentially be left out.
## Changes
I've implemented the link building in a new view model file. Inspecting
the output after the result is fully ready requires some gnarly
introspection and mapping, but it's tested.
Further, I've done a little bit of work to stop the playground service
using the schema types directly as the schema types now contain extra
information.
This PR also updates the `urlFriendlyString` arbitrary to not produce
strings that contain only periods. This causes issues when parsing URLs
(and is also something we struggle with in the UI).
https://github.com/Unleash/unleash/pull/4019 introduced a bug where API
token filtering was not taking into account ADMIN permissions, which
means the API tokens were not being displayed on the UI.
This PR fixes an issue where trying to use an admin token to import
features via the API resulted in a 500 (due to missing properties).
The solution is to catch when the user is using and admin token in the
controller, throw a 400, and tell them to use personal access tokens or
service accounts.
The PR includes a new test file for this specific use case. We don't
really test these cases many other places, so it seemed the logical
choice.
## What
As part of the move to enable custom-root-roles, our permissions model
was found to not be granular enough to allow service accounts to only be
allowed to create read-only tokens (client, frontend), but not be
allowed to create admin tokens to avoid opening up a path for privilege
escalation.
## How
This PR adds 12 new roles, a CRUD set for each of the three token types
(admin, client, frontend). To access the `/api/admin/api-tokens`
endpoints you will still need the existing permission (CREATE_API_TOKEN,
DELETE_API_TOKEN, READ_API_TOKEN, UPDATE_API_TOKEN). Once this PR has
been merged the token type you're modifying will also be checked, so if
you're trying to create a CLIENT api-token, you will need
`CREATE_API_TOKEN` and `CREATE_CLIENT_API_TOKEN` permissions. If the
user performing the create call does not have these two permissions or
the `ADMIN` permission, the creation will be rejected with a `403 -
FORBIDDEN` status.
### Discussion points
The test suite tests all operations using a token with
operation_CLIENT_API_TOKEN permission and verifies that it fails trying
to do any of the operations against FRONTEND and ADMIN tokens. During
development the operation_FRONTEND_API_TOKEN and
operation_ADMIN_API_TOKEN permission has also been tested in the same
way. I wonder if it's worth it to re-add these tests in order to verify
that the permission checker works for all operations, or if this is
enough. Since we're running them using e2e tests, I've removed them for
now, to avoid hogging too much processing time.
As requested in
[Linear](https://linear.app/unleash/issue/2-1147/unleash-cloud-make-keepalive-configurable)
this PR makes the serverKeepAliveTimeout configurable via the
SERVER_KEEPALIVE_TIMEOUT environment variable. This was already
configurable when starting Unleash programmatically, but it's nice to
have as an env variable as well
https://linear.app/unleash/issue/2-1137/roles-unification-on-the-ui
Root and project roles should be managed in a similar manner, which
means using the same roles route and tab for both.
Additionally, this includes a big revamp to the project roles to align
them more closely with the modern and standardized custom root roles
that were recently developed. They mostly use the same components.
There are still more things we want to improve and unify, but we've left
some of that out of this PR due to PR size concerns.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
Adds an environment variable for switching off feature telemetry in
version check
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Implements the Advanced Playground Table
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-1007](https://linear.app/unleash/issue/1-1007/env-aware-results-table)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
![Screenshot 2023-06-14 at 15 04
08](https://github.com/Unleash/unleash/assets/104830839/2f76d6f5-f92b-4586-bb4b-265f26eeb836)
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
This change adds a little more detail to the client metrics schema. The
description for variants felt a
little unclear.
---------
Co-authored-by: Christopher Kolstad <chriswk@getunleash.ai>
## About the changes
Implements custom root roles, encompassing a lot of different areas of
the project, and slightly refactoring the current roles logic. It
includes quite a clean up.
This feature itself is behind a flag: `customRootRoles`
This feature covers root roles in:
- Users;
- Service Accounts;
- Groups;
Apologies in advance. I may have gotten a bit carried away 🙈
### Roles
We now have a new admin tab called "Roles" where we can see all root
roles and manage custom ones. We are not allowed to edit or remove
*predefined* roles.
![image](https://github.com/Unleash/unleash/assets/14320932/1ad8695c-8c3f-440d-ac32-39746720d588)
This meant slightly pushing away the existing roles to `project-roles`
instead. One idea we want to explore in the future is to unify both
types of roles in the UI instead of having 2 separate tabs. This
includes modernizing project roles to fit more into our current design
and decisions.
Hovering the permissions cell expands detailed information about the
role:
![image](https://github.com/Unleash/unleash/assets/14320932/81c4aae7-8b4d-4cb4-92d1-8f1bc3ef1f2a)
### Create and edit role
Here's how the role form looks like (create / edit):
![image](https://github.com/Unleash/unleash/assets/14320932/85baec29-bb10-48c5-a207-b3e9a8de838a)
Here I categorized permissions so it's easier to visualize and manage
from a UX perspective.
I'm using the same endpoint as before. I tried to unify the logic and
get rid of the `projectRole` specific hooks. What distinguishes custom
root roles from custom project roles is the extra `root-custom` type we
see on the payload. By default we assume `custom` (custom project role)
instead, which should help in terms of backwards compatibility.
### Delete role
When we delete a custom role we try to help the end user make an
informed decision by listing all the entities which currently use this
custom root role:
![image](https://github.com/Unleash/unleash/assets/14320932/352ed529-76be-47a8-88da-5e924fb191d4)
~~As mentioned in the screenshot, when deleting a custom role, we demote
all entities associated with it to the predefined `Viewer` role.~~
**EDIT**: Apparently we currently block this from the API
(access-service deleteRole) with a message:
![image](https://github.com/Unleash/unleash/assets/14320932/82a8e50f-8dc5-4c18-a2ba-54e2ae91b91c)
What should the correct behavior be?
### Role selector
I added a new easy-to-use role selector component that is present in:
- Users
![image](https://github.com/Unleash/unleash/assets/14320932/76953139-7fb6-437e-b3fa-ace1d9187674)
- Service Accounts
![image](https://github.com/Unleash/unleash/assets/14320932/2b80bd55-9abb-4883-b715-15650ae752ea)
- Groups
![image](https://github.com/Unleash/unleash/assets/14320932/ab438f7c-2245-4779-b157-2da1689fe402)
### Role description
I also added a new role description component that you can see below the
dropdown in the selector component, but it's also used to better
describe each role in the respective tables:
![image](https://github.com/Unleash/unleash/assets/14320932/a3eecac1-2a34-4500-a68c-e3f62ebfa782)
I'm not listing all the permissions of predefined roles. Those simply
show the description in the tooltip:
![image](https://github.com/Unleash/unleash/assets/14320932/7e5b2948-45f0-4472-8311-bf533409ba6c)
### Role badge
Groups is a bit different, since it uses a list of cards, so I added yet
another component - Role badge:
![image](https://github.com/Unleash/unleash/assets/14320932/1d62c3db-072a-4c97-b86f-1d8ebdd3523e)
I'm using this same component on the profile tab:
![image](https://github.com/Unleash/unleash/assets/14320932/214272db-a828-444e-8846-4f39b9456bc6)
## Discussion points
- Are we being defensive enough with the use of the flag? Should we
cover more?
- Are we breaking backwards compatibility in any way?
- What should we do when removing a role? Block or demote?
- Maybe some existing permission-related issues will surface with this
change: Are we being specific enough with our permissions? A lot of
places are simply checking for `ADMIN`;
- We may want to get rid of the API roles coupling we have with the
users and SAs and instead use the new hooks (e.g. `useRoles`)
explicitly;
- We should update the docs;
- Maybe we could allow the user to add a custom role directly from the
role selector component;
---------
Co-authored-by: Gastón Fournier <gaston@getunleash.io>
## About the changes
Unleash version should be the one best representing its runtime. In this
regard, enterpriseVersion trumps unleash-server version.
This version is the one that's sent as part of our metrics.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
Adds feature usage info and custom strategy counters to the version
check object.
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
## About the changes
When a feature is not found in a project we should fail with a NotFound
error. If the feature belongs to a different project, it should not be a
permission issue, because the user might not be aware (lack of
permissions/visibility) of that other project, so even in this case the
error should be NotFound (this also works if we ever allow the same
feature name in different projects)
Fixes#3726
---------
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
## About the changes
Edit application under
https://app.unleash-hosted.com/demo/applications/test-app is currently
not working as the appName is expected to come in the request body, but
it's actually part of the url. We have two options here:
1. We change the UI to adapt to the expectations of the request by
adding appName to the request body (and eventually removing appName from
the URL, which would be a breaking change)
2. We remove the restriction of only sending the appName in the body and
take the one that comes in the URL. We have a validation that verifies
that at least one of the two sets the appName
([here](e376088668/src/lib/services/client-metrics/instance-service.ts (L208))
we validate using [this
schema](e376088668/src/lib/services/client-metrics/schema.ts (L55-L70)))
In terms of REST API, we can assume that the appName will be present in
the resource `/api/admin/metrics/applications` (an endpoint we don't
have), but when we're updating an application we should refer to that
application by its URL: `/api/admin/metrics/applications/<appName>` and
the presence of an appName in the body might indicate that we're trying
to change the name of the application (something we currently not
support)
Based on the above, I believe going with the second option is best, as
it adheres to REST principles and does not require a breaking change.
Despite that, we only support updating applications as the creation is
done from metrics ingestion
Fixes: #3580
This PR aims to handle the increased log alarm volume seen by the SREs.
It appears that we get a large number of alarms because a client
disconnects early from the front-end API. These errors are then
converted into 500s because of missing handling. These errors appear to
be caused by the `http-errors` library in a dependency.
We also introduced a log line whenever we see errors now a while back,
and I don't think we need this logging (I was also the one who
introduced it).
The changes in this PR are specifically:
- When converting from arbitrary errors, give `BadRequestError` a 400
status code, not a 500.
- Add a dependency on `http-errors` (which is already a transitive
dependency because of the body parser) and use that to check whether an
error is an http-error.
- If an error is an http error, then propagate it to the user with the
status code and message.
- Remove warning logs when an error occurs. This was introduced to make
it easier to correlate an API error and the logs, but the system hasn't
been set up for that (yet?), so it's just noise now.
- When logging errors as errors, only do that if their status code would
be 500.
This change makes the logs that happen when we encounter an error a
little bit clearer. It logs the error message before the error ID and
also logs the full serialized message just in case.
This PR improves our handling of internal Joi errors, to make them more
sensible to the end user. It does that by providing a better description
of the errors and by telling the user what they value they provided was.
Previous conversion:
```json
{
"id": "705a8dc0-1198-4894-9015-f1e5b9992b48",
"name": "BadDataError",
"message": "\"value\" must contain at least 1 items",
"details": [
{
"message": "\"value\" must contain at least 1 items",
"description": "\"value\" must contain at least 1 items"
}
]
}
```
New conversion:
```json
{
"id": "87fb4715-cbdd-48bb-b4d7-d354e7d97380",
"name": "BadDataError",
"message": "Request validation failed: your request body contains invalid data. Refer to the `details` list for more information.",
"details": [
{
"description": "\"value\" must contain at least 1 items. You provided [].",
"message": "\"value\" must contain at least 1 items. You provided []."
}
]
}
```
## Restructuring
This PR moves some code out of `unleash-error.ts` and into a new file.
The purpose of this is twofold:
1. avoid circular dependencies (we need imports from both UnleashError
and BadDataError)
2. carve out a clearer separation of concerns, keeping `unleash-error` a
little more focused.
This change lowers the log level from warning to debug for when we see
unexpected error types.
Right now this triggers for Joi errors, which we still rely on pretty
heavily. Lowering this should clear up logs for most users.
If apiTokens are enabled breaks middleware chain with a 401 if no token
is found for requests to client and frontend apis. Previously the
middleware allowed the chain to process.
Removes the regex search for multiple slashes, and instead configures
the apiTokenMiddleware to reject unauthorized requests.
After a Team Retro, one of our squads felt like we needed more data on
our test suites. This is the first effort to make our test results
easier to grab. It uses the test-reporter action to add a github check
to our main build and PR builds with our test results.
This at least should make it easier to parse which tests are failing.
However, it does not give us trends. So it does not yet make it easier
to decide which tests are flaky just from a quick view.
---------
Co-authored-by: Gastón Fournier <gaston@getunleash.io>
https://linear.app/unleash/issue/2-1071/prevent-users-from-disabling-password-authentication-when-there-are-no
Improves the behavior of disabling password based login by adding some
relevant information and a confirmation dialog with a warning. This felt
better than trying to disable the toggle, by still allowing the end
users to make the decision, except now it should be a properly informed
decision with confirmation.
![image](https://github.com/Unleash/unleash/assets/14320932/2ca754d8-cfa2-4fda-984d-0c34b89750f3)
- **Password based administrators**: Admin accounts that have a password
set;
- **Other administrators**: Other admin users that do not have a
password. May be SSO, but may also be users that did not set a password
yet;
- **Admin service accounts**: Service accounts that have the admin root
role. Depending on how you're using the SA this may not necessarily mean
locking yourself out of an admin account, especially if you secured its
token beforehand;
- **Admin API tokens**: Similar to the above. If you secured an admin
API token beforehand, you still have access to all features through the
API;
Each one of them link to the respective page inside Unleash (e.g. users
page, service accounts page, tokens page...);
If you try to disable and press "save", and only in that scenario, you
are presented with the following confirmation dialog:
![image](https://github.com/Unleash/unleash/assets/14320932/5ad6d105-ad47-4d31-a1df-04737aed4e00)
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
Improves the openapi schema specifications for the schemas belonging to
the "Projects" tag.
Expected error codes/http statues, descriptions, and example data
---------
Co-authored-by: Christopher Kolstad <chriswk@getunleash.ai>
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
Variants were not being properly handled in the `flag-resolver`: The
fact that the default value of the variant is not falsy made it so we
never asked the external flag resolver for the value.
This also moves the logic from `Variant | undefined` to `Variant` where
we use the `getDefaultVariant()` helper method to return us a [default
variant](55274e4953/src/variant.ts (L37-L42)).
### What
In the demo when listing possible users to grant access to your project,
we inadvertently expose emails when listing users you can grant access
to. This PR anonymises the access list on the way out.
This PR adds the missing serialization of the AuthenticationRequired
response back in. It was mistakenly removed in #3633.
This PR also adds another test to verify that it the options property is
present.
This PR reuses the revision Id information from the "optimal 304 for
server SDKs" to improve the freshness of the frontend API config data.
In addition it allows us to reduce the polling (and eventually remove it
when we are confident).
---------
Co-authored-by: Gastón Fournier <gaston@getunleash.io>
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
Adds a migration that renames `token_name` back to `username`, then adds
a new optional column named `token_name`
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
I've added fallbacks for resolving username/tokenname on insert and on
making rows from results.
But this adds another column renaming, which is worth discussing
properly
This PR attempts to improve the error handling introduced in #3607.
## About the changes
## **tl;dr:**
- Make `UnleashError` constructor protected
- Make all custom errors inherit from `UnleashError`.
- Add tests to ensure that all special error cases include their
relevant data
- Remove `PasswordMismatchError` and `BadRequestError`. These don't
exist.
- Add a few new error types: `ContentTypeError`, `NotImplementedError`,
`UnauthorizedError`
- Remove the `...rest` parameter from error constructor
- Add an unexported `GenericUnleashError` class
- Move OpenAPI conversion function to `BadDataError` clas
- Remove explicit `Error.captureStackTrace`. This is done automatically.
- Extract `getPropFromString` function and add tests
### **In a more verbose fashion**
The main thing is that all our internal errors now inherit
from`UnleashError`. This allows us to simplify the `UnleashError`
constructor and error handling in general while still giving us the
extra benefits we added to that class. However, it _does_ also mean that
I've had to update **all** existing error classes.
The constructor for `UnleashError` is now protected and all places that
called that constructor directly have been updated. Because the base
error isn't available anymore, I've added three new errors to cover use
cases that we didn't already have covered: `NotImplementedError`,
`UnauthorizedError`, `ContentTypeError`. This is to stay consistent in
how we report errors to the user.
There is also an internal class, `GenericUnleashError` that inherits
from the base error. This class is only used in conversions for cases
where we don't know what the error is. It is not exported.
In making all the errors inherit, I've also removed the `...rest`
parameter from the `UnleashError` constructor. We don't need this
anymore.
Following on from the fixes with missing properties in #3638, I have
added tests for all errors that contain extra data.
Some of the error names that were originally used when creating the list
don't exist in the backend. `BadRequestError` and
`PasswordMismatchError` have been removed.
The `BadDataError` class now contains the conversion code for OpenAPI
validation errors. In doing so, I extracted and tested the
`getPropFromString` function.
### Main files
Due to the nature of the changes, there's a lot of files to look at. So
to make it easier to know where to turn your attention:
The changes in `api-error.ts` contain the main changes: protected
constructor, removal of OpenAPI conversion (moved into `BadDataError`.
`api-error.test.ts` contains tests to make sure that errors work as
expected.
Aside from `get-prop-from-string.ts` and the tests, everything else is
just the required updates to go through with the changes.
## Discussion points
I've gone for inheritance of the Error type over composition. This is in
large part because throwing actual Error instances instead of just
objects is preferable (because they collect stack traces, for instance).
However, it's quite possible that we could solve the same thing in a
more elegant fashion using composition.
## For later / suggestions for further improvements
The `api-error` files still contain a lot of code. I think it might be
beneficial to break each Error into a separate folder that includes the
error, its tests, and its schema (if required). It would help decouple
it a bit.
We don't currently expose the schema anywhere, so it's not available in
the openapi spec. We should look at exposing it too.
Finally, it would be good to go through each individual error message
and update each one to be as helpful as possible.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
OpenAPI schema updates for Personal Access Tokens, http statuses,
property types and examples, return types
---------
Co-authored-by: Nuno Góis <github@nunogois.com>
Co-authored-by: mergify[bot] <37929162+mergify[bot]@users.noreply.github.com>
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
This PR removes the usage of crOnVariants flag, but keeps the behaviour,
so CR are now enabled on variants.
---------
Co-authored-by: Nuno Góis <github@nunogois.com>
When using PATs if the user that the PAT is for has been removed, we
currently log the missing user at ERROR level. Since this is not
something our SREs can fix, this PR downgrades the NotFoundError to
WARN, instead of ERROR.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
This expands the segment limits to 1000, this should have no impact on
OSS since this feature isn't exposed. This is overridden to 250 in
hosted `pro` instances and 1000 in hosted `enterprise` customers. This
only affects self hosted enterprise instances
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
- Creates a dialog when the feature has ONLY disabled strategies and the
environment in turned on
- Adds functionality to either `enable` the strategies or add the
default one (if a project specific default strategy is set, uses it)
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Uploading Screen Recording 2023-05-05 at 17.40.48.mov…
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
- Removed `strategyTitle` and `strategyDisable` flags. Unified under
`strategyImprovements` flag
- Implements the default strategy UI
- Bug fixes
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-875](https://linear.app/unleash/issue/1-875/default-strategy-frontend)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
![Screenshot 2023-05-04 at 11 21
05](https://user-images.githubusercontent.com/104830839/236149232-84601829-1327-42af-9527-5cc15196517a.png)
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
## About the changes
This PR removes the optimal304 flag after being tested in production.
We're keeping the existing configuration that allows users to disable
cache mainly because it's useful for testing.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
This deprecates the `username` properties on api-token schemas, and adds
a `tokenName` property.
DB field `username` has been renamed to `token_name`, migration added
for the rename.
Both `username` and `tokenName` can be used when consuming the service,
but only one of them.
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
There's a couple of things I'd like to get opinions on and discuss:
- Frontend still uses the deprecated `username` property
- ApiTokenSchema is used both for input and output of `Create`
controller endpoints and should be split out into separate schemas. I'll
set up a task for this
---------
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
Co-authored-by: mergify[bot] <37929162+mergify[bot]@users.noreply.github.com>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
set feature.enabled to false when all strategies are deactivated
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
Co-authored-by: Prabodh Meshram <prabodh.meshram7@gmail.com>
## What
This PR changes our AJV configuration to return all errors it finds with
a schema instead of stopping at the first one.
Because of this, a number of the snapshot tests that we have must be
updated.
## Why
DX! As someone using an API: if I send a faulty request, I'd rather have
the API tell me about the five things that are wrong than for me to
learn about one thing, send a new request, learn about another thing,
send a new request, .... etc.
Co-authored-by: mergify[bot] <37929162+mergify[bot]@users.noreply.github.com>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Adds default strategy to project environment link table
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-876](https://linear.app/unleash/issue/1-876/default-strategy-backend)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
When adding a strategy using a context field that did not exist, we
threw an unknown error.
This changes to throw NotFoundError so that our users can better know
what they did wrong.
## What
This fixes a bug where the owasp validation response that came back from
the server no longer contained all its validation errors. This caused
the UI to slightly break and for the password validation box not to
update correctly.
This is a quick fix (but with tests!). I'm working on a better design
for this on the side, but it seemed pertinent to get this out ASAP.
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
We used to use the `details` property to return a list of errors on a
lot of our errors, but the new format doesn't do this anymore. However,
some of the admin UI still expects this to be present, even when the
data could go into `message`. So for now, the solution is to duplicate
the data and put it both in `message` and in the first element of the
`details` list. If the error has its own details lust (such as openapi
errors etc), then they will overwrite this default `details` property.
I've copied most of the descriptions from what we did for batch metrics
under the Edge tag, however there are a couple of top level descriptions
that are "fine" but I'm definitely open to suggestions.
---------
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
Moves the access tab for Google Auth behind a flag. The elements
are still accessible but hidden by default so this is a soft change.
This is a deprecated feature and is on its way out.
### What
We've had this marked as deprecated through our v4, this PR removes it.
### Worth noting
This updates the deprecation notices with removal notices in the
documentation as well.
### Considerations
The tags API is still located under
/api/admin/features/{featureName}/tags. It should be moved to
/api/admin/projects/{project}/features/{featureName}/tags. I vote we do
that in a separate PR, we'd probably also need to deprecate the existing
tags endpoints for v5 and remove in v6. We could use 308s to signify
that they are moved.
---------
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
This PR fixes a broken e2e test by relaxing what it checks for. It must
have been developed in parallel so that the test wasn't included before
merging into main.
This PR implements the first version of a suggested unification (and
documentation) of the errors that we return from the API today.
The goal is for this to be the first step towards the error type defined
in this internal [linear
task](https://linear.app/unleash/issue/1-629/define-the-error-type
'Define the new API error type').
## The state of things today
As things stand, we currently have no (or **very** little) documentation
of the errors that are returned from the API. We mention error codes,
but never what the errors may contain.
Second, there is no specified format for errors, so what they return is
arbitrary, and based on ... Who knows? As a result, we have multiple
different errors returned by the API depending on what operation you're
trying to do. What's more, with OpenAPI validation in the mix, it's
absolutely possible for you to get two completely different error
objects for operations to the same endpoint.
Third, the errors we do return are usually pretty vague and don't really
provide any real help to the user. "You don't have the right
permissions". Great. Well what permissions do I need? And how would I
know? "BadDataError". Sick. Why is it bad?
... You get it.
## What we want to achieve
The ultimate goal is for error messages to serve both humans and
machines. When the user provides bad data, we should tell them what
parts of the data are bad and what they can do to fix it. When they
don't have the right permissions, we should tell them what permissions
they need.
Additionally, it would be nice if we could provide an ID for each error
instance, so that you (or an admin) can look through the logs and locate
he incident.
## What's included in **this** PR?
This PR does not aim to implement everything above. It's not intended to
magically fix everything. Its goal is to implement the necessary
**breaking** changes, so that they can be included in v5. Changing error
messages is a slightly grayer area than changing APIs directly, but
changing the format is definitely something I'd consider breaking.
So this PR:
- defines a minimal version of the error type defined in the [API error
definition linear
task](https://linear.app/unleash/issue/1-629/define-the-error-type).
- aims to catch all errors we return today and wrap them in the error
type
- updates tests to match the new expectations.
An important point: because we are cutting v5 very soon and because work
for this wasn't started until last week, the code here isn't necessarily
very polished. But it doesn't need to be. The internals can be as messy
as we want, as long as the API surface is stable.
That said, I'm very open to feedback about design and code completeness,
etc, but this has intentionally been done quickly.
Please also see my inline comments on the changes for more specific
details.
### Proposed follow-ups
As mentioned, this is the first step to implementing the error type. The
public API error type only exposes `id`, `name`, and `message`. This is
barely any more than most of the previous messages, but they are now all
using the same format. Any additional properties, such as `suggestion`,
`help`, `documentationLink` etc can be added as features without
breaking the current format. This is an intentional limitation of this
PR.
Regarding additional properties: there are some error responses that
must contain extra properties. Some of these are documented in the types
of the new error constructor, but not all. This includes `path` and
`type` properties on 401 errors, `details` on validation errors, and
more.
Also, because it was put together quickly, I don't yet know exactly how
we (as developers) would **prefer** to use these new error messages
within the code, so the internal API (the new type, name, etc), is just
a suggestion. This can evolve naturally over time if (based on feedback
and experience) without changing the public API.
## Returning multiple errors
Most of the time when we return errors today, we only return a single
error (even if many things are wrong). AJV, the OpenAPI integration we
use does have a setting that allows it to return all errors in a request
instead of a single one. I suggest we turn that on, but that we do it in
a separate PR (because it updates a number of other snapshots).
When returning errors that point to `details`, the objects in the
`details` now contain a new `description` property. This "deprecates"
the `message` property. Due to our general deprecation policy, this
should be kept around for another full major and can be removed in v6.
```json
{
"name": "BadDataError",
"message": "Something went wrong. Check the `details` property for more information."
"details": [{
"message": "The .params property must be an object. You provided an array.",
"description": "The .params property must be an object. You provided an array.",
}]
}
```
Add 'default' when creating or throw error when updating a
flexibleRollout strategy with empty stickiness
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-863](https://linear.app/unleash/issue/1-836/update-endpoints-for-tag-public-signup-tokens)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Adds enabled field to feature strategies
Filter out disabled strategies when returning/evaluating
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-865](https://linear.app/unleash/issue/1-865/allow-for-enablingdisabling-strategies-in-place-backend)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
## About the changes
Ref:
https://docs.getunleash.io/reference/deploy/configuring-unleash#further-customization
> **eventHook** (`function(event, data)`) - (_deprecated in Unleash 4.3_
in favor of the [Webhook addon](../addons/webhook.md)) If provided, this
function will be invoked whenever a feature is mutated. The possible
values for `event` are `'feature-created'`, `'feature-archived'` and
`'feature-revived'`. The `data` argument contains information about the
mutation. Its fields are `type` (string) - the event type (same as
`event`); `createdBy` (string) - the user who performed the mutation;
`data` - the contents of the change. The contents in `data` differs
based on the event type; For `'feature-archived'` and
`'feature-revived'`, the only field will be `name` - the name of the
feature. For `'feature-created'` the data follows a schema defined in
the code
[here](7b7f0b84e8/src/lib/schema/feature-schema.ts (L77)).
See an [api here](/reference/api/legacy/unleash/admin/events).
Related to: https://github.com/Unleash/unleash/issues/1265
feat: adds a way to specify a root role on a group, which will cause any user entering into that group to take on the permissions of that root role
Co-authored-by: Nuno Góis <github@nunogois.com>
From the discussion here
https://github.com/Unleash/unleash/pull/3496#discussion_r1163745860
This PR checks the existence of the feature before trying to get tags
for the feature. Doing so by stealing the exists method from the feature
store, since that's what we need to know exists, and avoiding having the
feature store as a dependency to the featureTagStore seemed reasonable.
BREAKING CHANGE: This changes the `name` property of a small number of error responses that we return. The property would have been `TypeError`, but is now `ValidationError` instead. It's a grey area, but I'd rather be strict.
---
This change removes uses of the `TypeError` type from user-facing code.
Type errors are used by typescript when you provide it the wrong type.
This is a valid concern. However, in the API, they're usually a signal
that **we've** done something wrong rather than the user having done
something wrong. As such, it makes more sense to return them as
validation errors or bad request errors.
## Breaking changes
Note that because of the way we handle errors, some of these changes
will be made visible to the end user, but only in the response body.
```ts
{ "name": "TypeError", "message": "Something is wrong", "isJoi": true }
```
will become
```ts
{ "name": "ValidationError", "message": "Something is wrong", "isJoi": true }
```
Technically, this could be considered a breaking change. However, as
we're gearing up for v5, this might be a good time to merge that?
## A return to 500
This PR also makes TypeErrors a 500-type error again because they should
never be caused by invalid data provided by the user
This PR updates the OpenAPI schemas for all the operations tagged with
"addons". In doing so, I also uncovered a few bugs and inconsistencies.
These have also been fixed.
## Changes
I've added inline comments to the changed files to call out anything
that I think is worth clarifying specifically. As an overall
description, this PR does the following:
Splits `addon-schema` into `addon-schema` and
`addon-create-update-schema`. The former is used when describing addons
that exist within Unleash and contain IDs and `created_at` timestamps.
The latter is used when creating or updating addons.
Adds examples and descriptions to all relevant schemas (and their
dependencies).
Updates addons operations descriptions and response codes (including the
recently introduced 413 and 415).
Fixes a bug where the server would crash if it didn't recognize the
addon provider (test added).
Fixes a bug where updating an addon wouldn't return anything, even if
the API said that it would. (test added)
Resolves some inconsistencies in handling of addon description. (tests
added)
### Addon descriptions
when creating addons, descriptions are optional. The original
`addonSchema` said they could be `null | string | undefined`. This
caused some inconsistencies in return values. Sometimes they were
returned, other times not. I've made it so that `descriptions` are now
always returned from the API. If it's not defined or if it's set to
`null`, the API will return `description: null`.
### `IAddonDto`
`IAddonDto`, the type we used internally to model the incoming addons
(for create and update) says that `description` is required. This hasn't
been true at least since we introduced OpenAPI schemas. As such, the
update and insert methods that the service uses were incompatible with
the **actual** data that we require.
I've changed the type to reflect reality for now. Assuming the tests
pass, this **should** all be good, but I'd like the reviewer(s) to give
this a think too.
---------
Co-authored-by: Christopher Kolstad <chriswk@getunleash.ai>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Adds title column to strategies, feature_strategies and features_view in
the db
Updates model/schemas
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
[1-855](https://linear.app/unleash/issue/1-855/allow-for-title-on-strategy-backend)
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
Adding documentation for the edge endpoints. Also separating request and
response schema for our validate endpoint to make clear that we expect a
list of strings as input, but yield tokens as output.
---------
Co-authored-by: Gastón Fournier <gaston@getunleash.io>
Co-authored-by: Thomas Heartman <thomas@getunleash.ai>
## About the changes
This rule defines that all properties should have a description
We also considered enforcing an example but we noticed that in some
cases that's not needed.
## About the changes
This enables us to validate the shape of our OpenAPI schemas by defining
specific json-schema rules that will be evaluated against all our open
API schemas.
Because we know there are things we need to improve, we've added a list
of `knownExceptions`. When fixing some of the known exceptions the tests
will force us to remove the exception from the list, that way
contributing to reducing the number of violations to our own rules.
Co-authored-by: Mateusz Kwasniewski <kwasniewski.mateusz@gmail.com>
Co-authored-by: Thomas Heartman <thomas@getunleash.io>
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Backports stickiness fixes
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
---------
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
Co-authored-by: Gastón Fournier <gaston@getunleash.io>
Co-authored-by: GitHub Actions Bot <>
Co-authored-by: Mateusz Kwasniewski <kwasniewski.mateusz@gmail.com>
## About the changes
1. Create tag should not throw a 500 when bad data is provided
2. Added summary, description and examples to open API endpoints
---------
Co-authored-by: Nuno Góis <github@nunogois.com>
## Add the ability to disable Personal Access Tokens (PAT) admin API
This PR disables PAT admin endpoints so it's not possible to create or
get PATs the kill switch is enabled, the UI is hidden but the existing
PATs will continue to work if they were created before. The delete
endpoint still works allowing an admin to delete old PATs
By default the kill switch is disabled (i.e. PAT is enabled by default)
<!-- Thanks for creating a PR! To make it easier for reviewers and
everyone else to understand what your changes relate to, please add some
relevant content to the headings below. Feel free to ignore or delete
sections that you don't think are relevant. Thank you! ❤️ -->
Remove enum for defaultStickiness from joi schema
## About the changes
<!-- Describe the changes introduced. What are they and why are they
being introduced? Feel free to also add screenshots or steps to view the
changes if they're visual. -->
<!-- Does it close an issue? Multiple? -->
Closes #
<!-- (For internal contributors): Does it relate to an issue on public
roadmap? -->
<!--
Relates to [roadmap](https://github.com/orgs/Unleash/projects/10) item:
#
-->
### Important files
<!-- PRs can contain a lot of changes, but not all changes are equally
important. Where should a reviewer start looking to get an overview of
the changes? Are any files particularly important? -->
## Discussion points
<!-- Anything about the PR you'd like to discuss before it gets merged?
Got any questions or doubts? -->
Signed-off-by: andreas-unleash <andreas@getunleash.ai>
## About the changes
Fix issue when running multiple calls to the /frontend endpoint concurrently, which ends up creating many instances of unleash SDK client.