nuxt-feature-flags
Version:
Feature flags for Nuxt
71 lines (67 loc) • 2.62 kB
JavaScript
import { existsSync } from 'node:fs';
import { defu } from 'defu';
import { useLogger, defineNuxtModule, createResolver, addServerImportsDir, addPlugin, addImports, addServerHandler, addTypeTemplate } from '@nuxt/kit';
import { loadConfig } from 'c12';
const logger = useLogger("nuxt-feature-flags");
const module = defineNuxtModule({
meta: {
name: "nuxt-feature-flags",
compatibility: {
nuxt: ">=3.1.0",
bridge: false
},
configKey: "featureFlags"
},
async setup(options, nuxt) {
const resolver = createResolver(import.meta.url);
nuxt.options.runtimeConfig.public.featureFlags = defu(nuxt.options.runtimeConfig.public.featureFlags, options);
nuxt.options.alias["#feature-flags/types"] = "./types/nuxt-feature-flags.d.ts";
nuxt.options.alias["#feature-flags/handler"] = resolver.resolve("./runtime/server/handlers/feature-flags");
let configPath = resolver.resolve("./runtime/feature-flags.config");
if (options.config) {
try {
const { config: configFlags, configFile } = await loadConfig({
configFile: options.config.replace(/\.\w+$/, ""),
cwd: nuxt.options.rootDir,
jitiOptions: {
interopDefault: true,
moduleCache: true,
alias: {
"#feature-flags/handler": resolver.resolve("./runtime/server/handlers/feature-flags")
}
}
});
if (!existsSync(configFile)) {
throw new Error(`${configFile} does not exist`);
}
options.flags = defu(options.flags, configFlags || {});
configPath = configFile;
} catch (error) {
logger.error("Failed to load feature flags configuration:", error);
}
}
nuxt.options.alias["#feature-flags/config"] = configPath;
addServerImportsDir(resolver.resolve("./runtime/server/utils"));
addPlugin(resolver.resolve("./runtime/app/plugins/feature-flag.server"));
addImports({
name: "useFeatureFlags",
from: resolver.resolve("./runtime/app/composables/feature-flags")
});
addServerHandler({
handler: resolver.resolve("./runtime/server/api/feature-flags.get"),
route: "/api/_feature-flags/feature-flags",
method: "get"
});
addTypeTemplate({
filename: "types/nuxt-feature-flags.d.ts",
getContents: () => {
const flags = options.flags || {};
const flagEntries = Object.entries(flags).map(([key, value]) => ` ${key}: ${typeof value}`).join("\n");
return `export interface FlagsSchema {
${flagEntries}
}`;
}
});
}
});
export { module as default };