gcfg

package
v0.26.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 5, 2026 License: Apache-2.0, BSD-3-Clause Imports: 15 Imported by: 0

Documentation

Overview

All errors are handled via Go's built-in error convention. Warnings regarding data errors are wrapped around ErrSyntaxWarning, so that it can be more easily identified by consumers. This library do not cause panics.

Data errors cause gcfg to return a non-nil error value. This includes the case when there are extra unknown key-value definitions in the configuration data (extra data). However, in some occasions it is desirable to be able to proceed in situations when the only data error is that of extra data. These errors are handled at a different (warning) priority and can be filtered out programmatically. To ignore extra data warnings, wrap the gcfg.Read*Into invocation into a call to gcfg.FatalOnly.

TODO

The following is a list of changes under consideration:

  • documentation
  • self-contained syntax documentation
  • more practical examples
  • move TODOs to issue tracker (eventually)
  • syntax
  • reconsider valid escape sequences (gitconfig doesn't support \r in value, \t in subsection name, etc.)
  • reading / parsing gcfg files
  • define internal representation structure
  • support multiple inputs (readers, strings, files)
  • support declaring encoding (?)
  • support varying fields sets for subsections (?)
  • writing gcfg files
  • error handling
  • make error context accessible programmatically?
  • limit input size?

Index

Examples

Constants

This section is empty.

Variables

View Source
var (
	ErrSyntaxWarning = errors.New("syntax warning")

	ErrMissingEscapeSequence = errors.New("missing escape sequence")
	ErrMissingEndQuote       = errors.New("missing end quote")
)
View Source
var (
	ErrUnsupportedType             = errors.New("unsupported type")
	ErrBlankUnsupported            = errors.New("blank value not supported for type")
	ErrConfigMustBePointerToStruct = errors.New("config must be a pointer to a struct")
	ErrInvalidMapFieldForSection   = errors.New("map field for section must have string keys and pointer-to-struct values")
	ErrInvalidFieldForSection      = errors.New("field for section must be a map or a struct")
)

Functions

func FatalOnly

func FatalOnly(err error) error

FatalOnly filters the results of a Read*Into invocation and returns only fatal errors. That is, errors (warnings) indicating data for unknown sections / variables is ignored. Example invocation:

err := gcfg.FatalOnly(gcfg.ReadFileInto(&cfg, configFile))
if err != nil {
    ...

func ReadFileInto

func ReadFileInto(config any, filename string) error

ReadFileInto reads gcfg formatted data from the file filename and sets the values into the corresponding fields in config.

func ReadInto

func ReadInto(config any, reader io.Reader) error

ReadInto reads gcfg formatted data from reader and sets the values into the corresponding fields in config.

func ReadStringInto

func ReadStringInto(config any, str string) error

ReadStringInto reads gcfg formatted data from str and sets the values into the corresponding fields in config.

Example
package main

import (
	"fmt"
	"log"

	"github.com/antgroup/hugescm/modules/gcfg"
)

func main() {
	cfgStr := `; Comment line
[section]
name=value # comment`
	cfg := struct {
		Section struct {
			Name string
		}
	}{}
	err := gcfg.ReadStringInto(&cfg, cfgStr)
	if err != nil {
		log.Fatalf("Failed to parse gcfg data: %s", err)
	}
	fmt.Println(cfg.Section.Name)
}
Output:
value
Example (Bool)
package main

import (
	"fmt"
	"log"

	"github.com/antgroup/hugescm/modules/gcfg"
)

func main() {
	cfgStr := `; Comment line
[section]
switch=on`
	cfg := struct {
		Section struct {
			Switch bool
		}
	}{}
	err := gcfg.ReadStringInto(&cfg, cfgStr)
	if err != nil {
		log.Fatalf("Failed to parse gcfg data: %s", err)
	}
	fmt.Println(cfg.Section.Switch)
}
Output:
true
Example (Hyphens)
package main

import (
	"fmt"
	"log"

	"github.com/antgroup/hugescm/modules/gcfg"
)

func main() {
	cfgStr := `; Comment line
[section-name]
variable-name=value # comment`
	cfg := struct {
		Section_Name struct {
			Variable_Name string
		}
	}{}
	err := gcfg.ReadStringInto(&cfg, cfgStr)
	if err != nil {
		log.Fatalf("Failed to parse gcfg data: %s", err)
	}
	fmt.Println(cfg.Section_Name.Variable_Name)
}
Output:
value
Example (Multivalue)
package main

import (
	"fmt"
	"log"

	"github.com/antgroup/hugescm/modules/gcfg"
)

func main() {
	cfgStr := `; Comment line
[section]
multi=value1
multi=value2`
	cfg := struct {
		Section struct {
			Multi []string
		}
	}{}
	err := gcfg.ReadStringInto(&cfg, cfgStr)
	if err != nil {
		log.Fatalf("Failed to parse gcfg data: %s", err)
	}
	fmt.Println(cfg.Section.Multi)
}
Output:
[value1 value2]
Example (Subsections)
package main

import (
	"fmt"
	"log"

	"github.com/antgroup/hugescm/modules/gcfg"
)

func main() {
	cfgStr := `; Comment line
[profile "A"]
color = white

[profile "B"]
color = black
`
	cfg := struct {
		Profile map[string]*struct {
			Color string
		}
	}{}
	err := gcfg.ReadStringInto(&cfg, cfgStr)
	if err != nil {
		log.Fatalf("Failed to parse gcfg data: %s", err)
	}
	fmt.Printf("%s %s\n", cfg.Profile["A"].Color, cfg.Profile["B"].Color)
}
Output:
white black
Example (Tags)
package main

import (
	"fmt"
	"log"

	"github.com/antgroup/hugescm/modules/gcfg"
)

func main() {
	cfgStr := `; Comment line
[section]
var-name=value # comment`
	cfg := struct {
		Section struct {
			FieldName string `gcfg:"var-name"`
		}
	}{}
	err := gcfg.ReadStringInto(&cfg, cfgStr)
	if err != nil {
		log.Fatalf("Failed to parse gcfg data: %s", err)
	}
	fmt.Println(cfg.Section.FieldName)
}
Output:
value
Example (Unicode)
package main

import (
	"fmt"
	"log"

	"github.com/antgroup/hugescm/modules/gcfg"
)

func main() {
	cfgStr := `; Comment line
[甲]
乙=丙 # comment`
	cfg := struct {
		X甲 struct {
			X乙 string
		}
	}{}
	err := gcfg.ReadStringInto(&cfg, cfgStr)
	if err != nil {
		log.Fatalf("Failed to parse gcfg data: %s", err)
	}
	fmt.Println(cfg.X甲.X乙)
}
Output:

func ReadWithCallback

func ReadWithCallback(reader io.Reader, callback func(string, string, string, string, bool) error) error

ReadWithCallback reads gcfg formatted data from reader and calls callback with each section and option found.

Callback is called with section, subsection, option key, option value and blank value flag as arguments.

When a section is found, callback is called with nil subsection, option key and option value.

When a subsection is found, callback is called with nil option key and option value.

If blank value flag is true, it means that the value was not set for an option (as opposed to set to empty string).

If callback returns an error, ReadWithCallback terminates with an error too.

Types

This section is empty.

Directories

Path Synopsis
Package scanner implements a scanner for gcfg configuration text.
Package scanner implements a scanner for gcfg configuration text.
Package token defines constants representing the lexical tokens of the gcfg configuration syntax and basic operations on tokens (printing, predicates).
Package token defines constants representing the lexical tokens of the gcfg configuration syntax and basic operations on tokens (printing, predicates).
Package types defines helpers for type conversions.
Package types defines helpers for type conversions.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL