@marcel91200 / caddy Mirror · read-only / commits / 1a20fe33
Fork 0

Fast and extensible multi-platform HTTP/1-2-3 web server with automatic HTTPS

Mirrored from https://github.com/Slazee/caddy.git

Synced Nov 14, 05:15 UTC

Improve godoc for contexts

Matthew Holt committed May 17, 2019 at 08:48 UTC 1a20fe330ecc39e8b98b5669b836f3b1b185f622
2 files changed +58 -12
context.go
+38 -1
@@ -10,12 +10,30 @@ import (
10 "github.com/mholt/certmagic"
11 )
12
13 +// Context is a type which defines the lifetime of modules that
14 +// are loaded and provides access to the parent configuration
15 +// that spawned the modules which are loaded. It should be used
16 +// with care and only wrapped with derivation functions from
17 +// the standard context package if you don't need the Caddy
18 +// specific features. These contexts are cancelled when the
19 +// lifetime of the modules loaded from it are over.
20 +//
21 +// Use NewContext() to get a valid value (but most modules will
22 +// not actually need to do this).
23 type Context struct {
24 context.Context
25 moduleInstances map[string][]interface{}
26 cfg *Config
27 }
28
29 +// NewContext provides a new context derived from the given
30 +// context ctx. Normally, you will not need to call this
31 +// function unless you are loading modules which have a
32 +// different lifespan than the ones for the context the
33 +// module was provisioned with. Be sure to call the cancel
34 +// func when the context is to be cleaned up so that
35 +// modules which are loaded will be properly unloaded.
36 +// See standard library context package's documentation.
37 func NewContext(ctx Context) (Context, context.CancelFunc) {
38 newCtx := Context{moduleInstances: make(map[string][]interface{}), cfg: ctx.cfg}
39 c, cancel := context.WithCancel(ctx.Context)
@@ -36,6 +54,14 @@ func NewContext(ctx Context) (Context, context.CancelFunc) {
54 return newCtx, wrappedCancel
55 }
56
57 +// LoadModule decodes rawMsg into a new instance of mod and
58 +// returns the value. If mod.New() does not return a pointer
59 +// value, it is converted to one so that it is unmarshaled
60 +// into the underlying concrete type. If mod.New is nil, an
61 +// error is returned. If the module implements Validator or
62 +// Provisioner interfaces, those methods are invoked to
63 +// ensure the module is fully configured and valid before
64 +// being used.
65 func (ctx Context) LoadModule(name string, rawMsg json.RawMessage) (interface{}, error) {
66 modulesMu.Lock()
67 mod, ok := modules[name]
@@ -74,7 +100,7 @@ func (ctx Context) LoadModule(name string, rawMsg json.RawMessage) (interface{},
100 }
101
102 if validator, ok := val.(Validator); ok {
77 - err := validator.Validate(ctx)
103 + err := validator.Validate()
104 if err != nil {
105 if cleanerUpper, ok := val.(CleanerUpper); ok {
106 err2 := cleanerUpper.Cleanup()
@@ -91,6 +117,17 @@ func (ctx Context) LoadModule(name string, rawMsg json.RawMessage) (interface{},
117 return val, nil
118 }
119
120 +// LoadModuleInline loads a module from a JSON raw message which decodes
121 +// to a map[string]interface{}, where one of the keys is moduleNameKey
122 +// and the corresponding value is the module name as a string, which
123 +// can be found in the given scope.
124 +//
125 +// This allows modules to be decoded into their concrete types and
126 +// used when their names cannot be the unique key in a map, such as
127 +// when there are multiple instances in the map or it appears in an
128 +// array (where there are no custom keys). In other words, the key
129 +// containing the module name is treated special/separate from all
130 +// the other keys.
131 func (ctx Context) LoadModuleInline(moduleNameKey, moduleScope string, raw json.RawMessage) (interface{}, error) {
132 moduleName, err := getModuleNameInline(moduleNameKey, raw)
133 if err != nil {
modules.go
+20 -11
@@ -136,23 +136,32 @@ func getModuleNameInline(moduleNameKey string, raw json.RawMessage) (string, err
136 return moduleName, nil
137 }
138
139 -// Validator is implemented by modules which can verify that their
140 -// configurations are valid. This method will be called after New()
141 -// instantiations of modules (if implemented). Validation should
142 -// always be fast (imperceptible running time) and an error should
143 -// be returned only if the value's configuration is invalid.
144 -type Validator interface {
145 - Validate(Context) error
146 -}
147 -
139 // Provisioner is implemented by modules which may need to perform
140 // some additional "setup" steps immediately after being loaded.
150 -// This method will be called after Validate() (if implemented).
141 +// Provisioning should be fast (imperceptible running time). If
142 +// any side-effects result in the execution of this function (e.g.
143 +// creating global state, any other allocations which require
144 +// garbage collection, opening files, starting goroutines etc.),
145 +// be sure to clean up properly by implementing the CleanerUpper
146 +// interface to avoid leaking resources.
147 type Provisioner interface {
148 Provision(Context) error
149 }
150
155 -// TODO: different name...
151 +// Validator is implemented by modules which can verify that their
152 +// configurations are valid. This method will be called after
153 +// Provision() (if implemented). Validation should always be fast
154 +// (imperceptible running time) and an error should be returned only
155 +// if the value's configuration is invalid.
156 +type Validator interface {
157 + Validate() error
158 +}
159 +
160 +// CleanerUpper is implemented by modules which may have side-effects
161 +// such as opened files, spawned goroutines, or allocated some sort
162 +// of non-local state when they were provisioned. This method should
163 +// deallocate/cleanup those resources to prevent memory leaks. Cleanup
164 +// should be fast and efficient.
165 type CleanerUpper interface {
166 Cleanup() error
167 }