By default, SDKs check for updates to your flag logic in the background. When you save and activate a new commit from the Hypertune UI, SDKs will fetch your new flag logic and use it on the next flag evaluation.
You can change the frequency at which the SDK checks for updates by setting initDataRefreshIntervalMs
in your createSource
options:
TypeScript (Server) TypeScript (Browser) Python Rust Go
Copy import { createSource } from "../generated/hypertune";
const hypertuneSource = createSource({
token: process.env.HYPERTUNE_TOKEN!,
initDataRefreshIntervalMs: 5_000,
});
export default async function getHypertune() {
// Get flag updates in serverless environments
// await hypertuneSource.initIfNeeded();
return hypertuneSource.root({
args: {
context: {
environment:
process.env.NODE_ENV === "development"
? "development"
: "production",
user: { id: "1", name: "Test", email: "hi@test.com" },
},
},
});
}
src/components/AppHypertuneProvider.tsx
Copy import { HypertuneProvider } from "../generated/hypertune.react";
export default function AppHypertuneProvider({
children,
}: {
children: React.ReactNode;
}) {
return (
<HypertuneProvider
createSourceOptions={{
token: import.meta.env.VITE_HYPERTUNE_TOKEN!,
initDataRefreshIntervalMs: 5_000,
}}
rootArgs={{
context: {
environment:
process.env.NODE_ENV === "development"
? "development"
: "production",
user: { id: "1", name: "Test", email: "hi@test.com" },
},
}}
>
{children}
</HypertuneProvider>
);
}
Copy import generated.hypertune as hypertune
root_node = hypertune.create_source(
init_data_refresh_interval_ms=5_000
).root({
"context": {
"environment": "development",
"user": {
"id": "test_id",
"name": "Test",
"email": "hi@test.com",
}
}
})
root_node.wait_for_initialization()
Copy use hypertune::CreateOptions;
mod hypertune;
fn main() {
let root_node = hypertune::initialize_hypertune(
hypertune::VariableValues {},
Some(CreateOptions {
init_data_refresh_interval_ms: 5_000,
..Default::default()
})
)
.unwrap()
.root(hypertune::RootArgs {
context: hypertune::Context {
environment: hypertune::Environment::DEVELOPMENT,
user: hypertune::User {
id: "test_id".to_string(),
name: "Test".to_string(),
email: "test@test.com".to_string(),
},
},
});
root_node.wait_for_initialization();
}
Copy package main
import (
"fmt"
"log"
"os"
"time"
sdk "github.com/hypertunehq/hypertune-go"
// Update to your project path.
"github.com/myTeam/myProject/pkg/hypertune"
)
func main() {
var token = os.Getenv("HYPERTUNE_TOKEN")
source, err := hypertune.CreateSource(
&token,
sdk.WithInitDataRefreshInterval(5*time.Second),
)
if err != nil {
panic(err)
}
defer source.Close()
source.WaitForInitialization()
rootNode := source.Root(hypertune.RootArgs{
Context: hypertune.Context{
Environment: hypertune.Development,
User: hypertune.User{
Id: "test_id",
Name: "Test",
Email: "hi@test.com",
},
},
})
}
You can disable checking for updates by setting the shouldRefreshInitData
option to false
:
TypeScript (Server) TypeScript (Browser) Python Rust Go
Copy import { createSource } from "../generated/hypertune";
const hypertuneSource = createSource({
token: process.env.HYPERTUNE_TOKEN!,
shouldRefreshInitData: false,
});
export default async function getHypertune() {
// Get flag updates in serverless environments
// await hypertuneSource.initIfNeeded();
return hypertuneSource.root({
args: {
context: {
environment:
process.env.NODE_ENV === "development"
? "development"
: "production",
user: { id: "1", name: "Test", email: "hi@test.com" },
},
},
});
}
src/components/AppHypertuneProvider.tsx
Copy import { HypertuneProvider } from "../generated/hypertune.react";
export default function AppHypertuneProvider({
children,
}: {
children: React.ReactNode;
}) {
return (
<HypertuneProvider
createSourceOptions={{
token: import.meta.env.VITE_HYPERTUNE_TOKEN!,
shouldRefreshInitData: false,
}}
rootArgs={{
context: {
environment:
process.env.NODE_ENV === "development"
? "development"
: "production",
user: { id: "1", name: "Test", email: "hi@test.com" },
},
}}
>
{children}
</HypertuneProvider>
);
}
Copy import generated.hypertune as hypertune
root_node = hypertune.create_source(
init_data_refresh_interval_ms=0
).root({
"context": {
"environment": "development",
"user": {
"id": "test_id",
"name": "Test",
"email": "hi@test.com",
}
}
})
root_node.wait_for_initialization()
Copy use hypertune::CreateOptions;
mod hypertune;
fn main() {
let root_node = hypertune::initialize_hypertune(
hypertune::VariableValues {},
Some(CreateOptions {
init_data_refresh_interval_ms: 0,
..Default::default()
})
)
.unwrap()
.root(hypertune::RootArgs {
context: hypertune::Context {
environment: hypertune::Environment::DEVELOPMENT,
user: hypertune::User {
id: "test_id".to_string(),
name: "Test".to_string(),
email: "test@test.com".to_string(),
},
},
});
root_node.wait_for_initialization();
}
Copy package main
import (
"fmt"
"log"
"os"
sdk "github.com/hypertunehq/hypertune-go"
// Update to your project path.
"github.com/myTeam/myProject/pkg/hypertune"
)
func main() {
var token = os.Getenv("HYPERTUNE_TOKEN")
source, err := hypertune.CreateSource(
&token,
sdk.WithInitDataRefreshInterval(0),
)
if err != nil {
panic(err)
}
defer source.Close()
source.WaitForInitialization()
rootNode := source.Root(hypertune.RootArgs{
Context: hypertune.Context{
Environment: hypertune.Development,
User: hypertune.User{
Id: "test_id",
Name: "Test",
Email: "hi@test.com",
},
},
})
}
Manually check for flag updates
You can manually check for flag updates with the initIfNeeded
method:
Copy import { createSource } from "../generated/hypertune";
const hypertuneSource = createSource({
token: process.env.HYPERTUNE_TOKEN!,
initDataRefreshIntervalMs: 5_000,
});
export default async function getHypertune() {
await hypertuneSource.initIfNeeded(); // Check for flag updates
return hypertuneSource.root({
args: {
context: {
environment:
process.env.NODE_ENV === "development"
? "development"
: "production",
user: { id: "1", name: "Test", email: "hi@test.com" },
},
},
});
}
When using initIfNeeded
, the initDataRefreshIntervalMs
option specifies the minimum time between initialization requests.
For example, if you set this to 5_000
, initIfNeeded
will only trigger a new initialization request if the last one was over 5 seconds ago.
So you can await initIfNeeded
on every backend request to ensure flag values are fresh while minimizing network latency and bandwidth.
This is particularly useful in serverless and edge environments like Vercel deployments, Cloudflare Workers, AWS Lambdas, etc, where background SDK tasks like fetching updates aren't guaranteed to execute.
Subscribing to flag updates
You can add and remove listeners to be notified of updates with:
Copy hypertune.addUpdateListener(listener: (newStateHash: string) => void)
hypertune.removeUpdateListener(listener: (newStateHash: string) => void)
You can also get the current state hash with:
Copy hypertune.getStateHash(): string | null