-
Notifications
You must be signed in to change notification settings - Fork 153
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
refactor: unleash implementation #15263
base: main
Are you sure you want to change the base?
Conversation
unleash-proxy-clientAuthor: @Unleash Description: A browser client that can be used together with Unleash Edge or the Unleash Frontend API. Homepage: /~https://github.com/unleash/unleash-proxy-client-js#readme
@unleash/proxy-client-reactAuthor: Unknown Description: React interface for working with unleash Homepage: /~https://github.com/Unleash/unleash-proxy-react#readme
New dependencies added: |
@@ -115,7 +114,7 @@ export const TOOLS_URL: any = "https://tools.artsy.net" | |||
export const TRACK_PAGELOAD_PATHS: any = null | |||
export const UNLEASH_API: any = null | |||
export const UNLEASH_APP_NAME: any = null | |||
export const UNLEASH_INSTANCE_ID: any = null |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wasn't used
@@ -93,6 +93,7 @@ | |||
"@styled-system/theme-get": "5.1.2", | |||
"@swc-node/register": "^1.10.9", | |||
"@swc/helpers": "^0.5.15", | |||
"@unleash/proxy-client-react": "^4.5.2", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In case it saves others some confusion, I want to clarify a non-obvious point. While the unleash proxy is deprecated, the proxy-client
s are not. They are still necessary to interface with our self-hosted unleash
instances. So we can now spin down the artsy-unleash-web-proxy
deployment and replace it with unleash edge
or just point request directly to our web deployment
@@ -178,7 +179,8 @@ | |||
"superagent": "3.8.3", | |||
"tti-polyfill": "0.2.2", | |||
"underscore.string": "3.3.5", | |||
"unleash-client": "^3.12.0", | |||
"unleash-client": "^6.5.0", | |||
"unleash-proxy-client": "^3.7.3", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Both unleash-proxy-client
and @unleash/proxy-client-react
are needed.
export function getOrInitUnleashServerClient(): Promise<Unleash> { | ||
const config = { | ||
url: UNLEASH_API, | ||
appName: UNLEASH_APP_NAME, | ||
refreshInterval: 10000, | ||
environment: NODE_ENV, | ||
customHeaders: { | ||
Authorization: UNLEASH_SERVER_KEY, | ||
}, | ||
} | ||
|
||
return startUnleash(config) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should only ever return a single instance of the Unleash
client since we're using startUnleash
, which implements a singleton. I'll monitor this in staging, though.
Also, I acknowledge the name is a lot, but I wanted to clearly differentiate from the frontend proxy client. So I didn't want to use useUnleashServerClient
, for example, since prepending a name with use
is a react hook convention.
const unleashConfig = { | ||
url: `${sd.UNLEASH_API}frontend/`, | ||
clientKey: sd.UNLEASH_CLIENT_KEY, | ||
refreshInterval: 15, | ||
appName: sd.UNLEASH_APP_NAME, | ||
environment: sd.NODE_ENV, | ||
context: { | ||
userId: props.user?.id, | ||
sessionId: sd.SESSION_ID, | ||
}, | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Considered moving this into its own file, but prefer it here. If you have strong opinions, LMK.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
A common pattern is to keep everything self-contained in our own component, added somewhere in the system
directory (with other feature flag stuff):
import { FlagProvider } from '...'
const FeatureFlagProvider: React.FC<React.PropsWithChildren> = ({ children }) => {
const { user } = useSystemContext()
const unleashConfig = {
url: `${getENV("UNLEASH_API")}frontend/`,
clientKey: getENV("UNLEASH_CLIENT_KEY"),
refreshInterval: 15,
appName: getENV("UNLEASH_APP_NAME"),
environment: getENV("NODE_ENV"),
context: {
userId: user?.id,
sessionId: getENV("SESSION_ID"),
},
}
return <FlagProvider ... >{children}></FlagProvider>
}
Then import ☝️ in boot
|
||
return variant | ||
} | ||
|
||
export function useTrackFeatureVariant({ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Variant tracking will remain unchanged.
@@ -84,6 +83,7 @@ export const bootstrapSharify = () => { | |||
"SEGMENT_AMP_WRITE_KEY", | |||
"SEGMENT_WRITE_KEY", | |||
"SENTRY_PUBLIC_DSN", | |||
"SESSION_ID", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I was surprised this wasn't already in here. I know we have access to it after we the app boots (in this use case its needed before boot), but I couldn't find exactly where that happens.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is such a nice simplifying PR 👍
The type of this PR is: Refactor
This PR solves PHIRE-1620
Description
This PR refactors the existing unleash implementation with the following goals:
unleash-proxy-client
to retrieve flags and variants when in a browser context. This replaces the existing approach of eagerly loading all flags inexpress
middleware
on every request and usingsharify
to expose them to both server and client.Motivations
unleash
node
SDK in a custom class, introducing an unnecessary level of abstraction. The idea of making it easier to swap in different flag provider easily, while well intentioned, has proven not worth the tradeoff.unleash
's documentation, removing some additional maintenance.Considerations
edge
instance, we just need to change theUNLEASH_URL
to point to the instance. I'll need to investigate this a bit more.Usage
When working client side (in
react
), developers can follow the unleash "how to use" instructions:When working server side (in
node
), developers just need to retrieve the client first using thegetOrInitUnleashServerClient
function, and then follow the "how to use" instructions:TODO
env
unleash edge
(non-blocking)I haven't pushed these yet because I wanted the implementation changes to be easier to review: