Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion sdk/appconfiguration/app-configuration/assets.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,5 @@
"AssetsRepo": "Azure/azure-sdk-assets",
"AssetsRepoPrefixPath": "js",
"TagPrefix": "js/appconfiguration/app-configuration",
"Tag": "js/appconfiguration/app-configuration_bdaf29d71a"
"Tag": "js/appconfiguration/app-configuration_48f15db7c6"
}
Original file line number Diff line number Diff line change
Expand Up @@ -141,11 +141,12 @@ export interface FeatureFlagValue {
name: string;
parameters?: Record<string, unknown>;
}[];
requirementType?: "All" | "Any";
};
description?: string;
displayName?: string;
enabled: boolean;
id?: string;
id: string;
}

// @public
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ export async function main() {
isReadOnly: false,
contentType: featureFlagContentType,
value: {
id: featureFlagName,
enabled: false,
description: "I'm a description",
conditions: {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ async function main() {
isReadOnly: false,
contentType: featureFlagContentType,
value: {
id: "sample-feature-flag",
enabled: false,
description: "I'm a description",
conditions: {
Expand Down Expand Up @@ -79,8 +80,8 @@ async function main() {
`\n...clientFilter - "${clientFilter.name}"...\nparams => ${JSON.stringify(
clientFilter.parameters,
null,
1
)}\n`
1,
)}\n`,
);
switch (clientFilter.name) {
// Tweak the client filters of the feature flag
Expand Down Expand Up @@ -126,8 +127,8 @@ async function main() {
`\n...clientFilter - "${clientFilter.name}"...\nparams => ${JSON.stringify(
clientFilter.parameters,
null,
1
)}\n`
1,
)}\n`,
);
}
await cleanupSampleValues([originalFeatureFlag.key], appConfigClient);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ export async function main() {
isReadOnly: false,
contentType: featureFlagContentType,
value: {
id: "sample-feature-flag",
enabled: false,
description: "I'm a description",
conditions: {
Expand Down Expand Up @@ -82,8 +83,8 @@ export async function main() {
`\n...clientFilter - "${clientFilter.name}"...\nparams => ${JSON.stringify(
clientFilter.parameters,
null,
1
)}\n`
1,
)}\n`,
);
switch (clientFilter.name) {
// Tweak the client filters of the feature flag
Expand Down Expand Up @@ -129,8 +130,8 @@ export async function main() {
`\n...clientFilter - "${clientFilter.name}"...\nparams => ${JSON.stringify(
clientFilter.parameters,
null,
1
)}\n`
1,
)}\n`,
);
}
await cleanupSampleValues([originalFeatureFlag.key], appConfigClient);
Expand Down Expand Up @@ -172,7 +173,7 @@ function isTargetingClientFilter(clientFilter: any): clientFilter is {
* typeguard - for timewindow client filter
*/
export function isTimeWindowClientFilter(
clientFilter: any
clientFilter: any,
): clientFilter is { parameters: { Start: string; End: string } } {
return (
clientFilter.name === "Microsoft.TimeWindow" &&
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ async function main() {
isReadOnly: false,
contentType: featureFlagContentType,
value: {
id: featureFlagName,
enabled: false,
description: "I'm a description",
conditions: {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,17 @@ import {
ConfigurationSetting,
featureFlagContentType,
featureFlagPrefix,
FeatureFlagValue
FeatureFlagValue,
} from "@azure/app-configuration";
import { DefaultAzureCredential } from "@azure/identity";

// Use configuration provider and feature management library to consume feature flags
import { load } from "@azure/app-configuration-provider";
import { ConfigurationMapFeatureFlagProvider, FeatureManager, ITargetingContext } from "@microsoft/feature-management";
import {
ConfigurationMapFeatureFlagProvider,
FeatureManager,
ITargetingContext,
} from "@microsoft/feature-management";

// Load the .env file if it exists
import * as dotenv from "dotenv";
Expand All @@ -30,6 +34,7 @@ export async function main() {
isReadOnly: false,
contentType: featureFlagContentType,
value: {
id: featureFlagName,
enabled: false,
description: "I'm a description",
conditions: {
Expand Down Expand Up @@ -77,13 +82,14 @@ export async function main() {
refresh: {
enabled: true,
// refreshIntervalInMs: 30_000, // Optional. Default: 30 seconds
}
}
},
},
});

console.log(`Use feature management library to consume feature flags`);
const featureManager = new FeatureManager(
new ConfigurationMapFeatureFlagProvider(appConfigProvider));
new ConfigurationMapFeatureFlagProvider(appConfigProvider),
);

let isEnabled = await featureManager.isEnabled(featureFlagName);
console.log(`Is featureFlag enabled? ${isEnabled}`);
Expand All @@ -109,7 +115,7 @@ export async function main() {
// The feature flag will not be enabled for everyone as targeting filter is configured
isEnabled = await featureManager.isEnabled(featureFlagName);
console.log(`Is featureFlag enabled? ${isEnabled}`);

isEnabled = await featureManager.isEnabled(featureFlagName, targetingContext);
console.log(`Is featureFlag enabled for [email protected]? ${isEnabled}`);
}
Expand Down
12 changes: 11 additions & 1 deletion sdk/appconfiguration/app-configuration/src/featureFlag.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ export interface FeatureFlagValue {
/**
* Id for the feature flag.
*/
id?: string;
id: string;
/**
* A Feature filter consistently evaluates the state of a feature flag.
* Our feature management library supports three types of built-in filters: Targeting, TimeWindow, and Percentage.
Expand All @@ -32,6 +32,7 @@ export interface FeatureFlagValue {
*/
conditions: {
clientFilters: { name: string; parameters?: Record<string, unknown> }[];
requirementType?: "All" | "Any";
};
/**
* Description of the feature.
Expand Down Expand Up @@ -76,6 +77,11 @@ export const FeatureFlagHelper = {
display_name: featureFlag.value.displayName,
};

if (featureFlag.value.conditions.requirementType) {
jsonFeatureFlagValue.conditions.requirement_type =
featureFlag.value.conditions.requirementType;
}

const configSetting = {
...featureFlag,
key,
Expand Down Expand Up @@ -117,6 +123,10 @@ export function parseFeatureFlag(
key,
contentType: featureFlagContentType,
};

if (jsonFeatureFlagValue.conditions.requirement_type) {
featureflag.value.conditions.requirementType = jsonFeatureFlagValue.conditions.requirement_type;
}
return featureflag;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,11 @@
export type JsonFeatureFlagValue = {
conditions: {
client_filters: { name: string; parameters?: Record<string, unknown> }[];
requirement_type?: "All" | "Any";
};
description?: string;
enabled: boolean;
id?: string;
id: string;
display_name?: string;
};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ describe("AppConfigurationClient - FeatureFlag", () => {
baseSetting = {
value: {
conditions: {
requirementType: "Any",
clientFilters: [
{
name: "Microsoft.TimeWindow",
Expand All @@ -51,6 +52,7 @@ describe("AppConfigurationClient - FeatureFlag", () => {
{ name: "Microsoft.Percentage", parameters: { Value: 25 } },
],
},
id: "name-1",
enabled: false,
description: "I'm a description",
displayName: "for display",
Expand Down Expand Up @@ -202,7 +204,7 @@ describe("AppConfigurationClient - FeatureFlag", () => {
`name-1${Math.floor(Math.random() * 1000)}`,
)}`,
isReadOnly: false,
value: { conditions: { clientFilters: [] }, enabled: true },
value: { conditions: { clientFilters: [] }, id: "name-1", enabled: true },
};
});

Expand Down