MCPcopy
hub / github.com/caddyserver/caddy / Provision

Method Provision

modules/caddytls/ech.go:80–144  ·  view source on GitHub ↗

Provision loads or creates ECH configs and returns outer names (for certificate management), but does not publish any ECH configs. The DNS module is used as a default for later publishing if needed.

(ctx caddy.Context)

Source from the content-addressed store, hash-verified

78// management), but does not publish any ECH configs. The DNS module is used as
79// a default for later publishing if needed.
80func (ech *ECH) Provision(ctx caddy.Context) ([]string, error) {
81 ech.configsMu = new(sync.RWMutex)
82
83 logger := ctx.Logger().Named("ech")
84
85 // set up publication modules before we need to obtain a lock in storage,
86 // since this is strictly internal and doesn't require synchronization
87 for i, pub := range ech.Publication {
88 mods, err := ctx.LoadModule(pub, "PublishersRaw")
89 if err != nil {
90 return nil, fmt.Errorf("loading ECH publication modules: %v", err)
91 }
92 for _, modIface := range mods.(map[string]any) {
93 ech.Publication[i].publishers = append(ech.Publication[i].publishers, modIface.(ECHPublisher))
94 }
95 }
96
97 // the rest of provisioning needs an exclusive lock so that instances aren't
98 // stepping on each other when setting up ECH configs
99 storage := ctx.Storage()
100 if err := storage.Lock(ctx, echStorageLockName); err != nil {
101 return nil, err
102 }
103 defer func() {
104 if err := storage.Unlock(ctx, echStorageLockName); err != nil {
105 logger.Error("unable to unlock ECH provisioning in storage", zap.Error(err))
106 }
107 }()
108
109 ech.configsMu.Lock()
110 defer ech.configsMu.Unlock()
111
112 outerNames, err := ech.setConfigsFromStorage(ctx, logger)
113 if err != nil {
114 return nil, fmt.Errorf("loading configs from storage: %w", err)
115 }
116
117 // see if we need to make any new ones based on the input configuration
118 for _, cfg := range ech.Configs {
119 publicName := strings.ToLower(strings.TrimSpace(cfg.PublicName))
120
121 if list, ok := ech.configs[publicName]; !ok || len(list) == 0 {
122 // no config with this public name was loaded, so create one
123 echCfg, err := generateAndStoreECHConfig(ctx, publicName)
124 if err != nil {
125 return nil, err
126 }
127 logger.Debug("generated new ECH config",
128 zap.String("public_name", echCfg.RawPublicName),
129 zap.Uint8("id", echCfg.ConfigID))
130 ech.configs[publicName] = append(ech.configs[publicName], echCfg)
131 outerNames = append(outerNames, publicName)
132 }
133 }
134
135 // convert the configs into a structure ready for the std lib to use
136 ech.updateKeyList()
137

Callers

nothing calls this directly

Calls 9

setConfigsFromStorageMethod · 0.95
updateKeyListMethod · 0.95
rotateECHKeysMethod · 0.95
LoadModuleMethod · 0.80
StorageMethod · 0.80
LoggerMethod · 0.45
ErrorMethod · 0.45
StringMethod · 0.45

Tested by

no test coverage detected