golang-spf13-viper

Configure layered Go application settings with spf13/viper across flags, env vars, files, and defaults.

Updated Jun 15, 2026
One-click install
npx skills add https://github.com/2877389577/novels_ai_gen --skill golang-spf13-viper-2877389577
Or copy as Structured Prompt for Agent▼
Please help me install this Agent Skill.
Skill: golang-spf13-viper
Source: https://github.com/2877389577/novels_ai_gen/tree/main/.agents/skills/golang-spf13-viper
Command: npx skills add https://github.com/2877389577/novels_ai_gen --skill golang-spf13-viper-2877389577

SYSTEM DOCUMENTATION & REQUIREMENTS

💡 This Skill requires github.com/spf13/viper, github.com/mitchellh/mapstructure, and includes references (resource) components.

What problem does it solve? Go applications need configuration from multiple sources — command-line flags, environment variables, config files, and remote KV stores — and resolving which value wins is error-prone. This Skill guides correct use of spf13/viper's fixed precedence pipeline, preventing common bugs like broken env binding for nested keys, nil-pointer panics from Sub(), and flaky tests caused by global viper state. ## Core Features & Use Cases - Layered precedence resolution: Implements the flag > env > file > KV > default pipeline with BindPFlag, SetEnvPrefix, SetEnvKeyReplacer, and AutomaticEnv wired together correctly. - Struct unmarshaling and hot reload: Maps resolved config into structs with mapstructure tags and DecodeHooks, and applies WatchConfig/OnConfigChange with race-safe, validate-then-swap reload patterns. - Test isolation: Uses viper.New() per test instead of the global instance to eliminate order-dependent test failures. - Use Case: A Go HTTP service reads database.host from MYAPP_DATABASE_HOST, an optional YAML file, and flag defaults — this Skill ensures the env replacer, graceful ConfigFileNotFoundError handling, and mapstructure tags are all set up correctly. ## Quick Start Ask the agent to set up viper configuration for your Go service with env prefix, key replacer, optional config file handling, and unmarshaling into a tagged struct.

Frequently Asked Questions about golang-spf13-viper

High-intent search queries and answers about installing and using this skill.

FAQPage Schema
How do I bind environment variables to nested viper config keys in Go?▼

Call SetEnvPrefix, SetEnvKeyReplacer with strings.NewReplacer(".", "_"), and AutomaticEnv together. Without the key replacer, viper looks up MYAPP_DATABASE.HOST with the dot preserved, so nested keys like database.host never match MYAPP_DATABASE_HOST.

Should I use viper with cobra or can viper work alone?▼

Viper works alone for services that only need config resolution, such as HTTP servers reading YAML and env vars. Cobra owns the command tree and flags; add it only when you need subcommands, binding flags to viper via BindPFlag in init() or PersistentPreRunE.

Why does viper.Sub() panic with a nil pointer dereference?▼

viper.Sub returns nil when the requested key does not exist, and calling Unmarshal on nil panics. Nil-check the result, or use viper.UnmarshalKey("database", &cfg) which avoids the nil risk entirely.

How do I make the viper config file optional in Go?▼

Use errors.As with *viper.ConfigFileNotFoundError after ReadInConfig and only propagate errors that are not the not-found type. This lets the service run on flags and env vars alone while still surfacing real errors like malformed YAML.

Why are my viper-based Go tests flaky and order-dependent?▼

The top-level viper functions share one global instance, so state set in one test leaks into the next. Create viper.New() per test and inject the instance into your application code instead of using the global.

Why does viper.WatchConfig not fire when I save in vim?▼

Vim and many editors write atomically via rename, replacing the inode that fsnotify watches, so the OnConfigChange callback may not fire. Test hot reload with direct writes like os.WriteFile rather than editor saves.