@@ -130,23 +130,54 @@ func New(
130130 if generationProvider == nil {
131131 return nil , errors .New ("structured generation provider is required" )
132132 }
133+ config , err := normalizeConfig (config )
134+ if err != nil {
135+ return nil , err
136+ }
137+ ctx , cancel := context .WithCancel (context .Background ())
138+ manager := & Manager {
139+ provider : generationProvider , config : config , ctx : ctx , cancel : cancel ,
140+ queue : make (chan string , config .QueueSize ), jobs : make (map [string ]* jobState ),
141+ byRequest : make (map [string ]string ), cache : make (map [string ]cacheEntry ),
142+ now : time .Now , done : make (chan struct {}),
143+ }
144+ for index := 0 ; index < config .Workers ; index ++ {
145+ manager .wait .Add (1 )
146+ go manager .worker ()
147+ }
148+ manager .wait .Add (1 )
149+ go manager .cleanupWorker ()
150+ go func () {
151+ manager .wait .Wait ()
152+ close (manager .done )
153+ }()
154+ return manager , nil
155+ }
156+
157+ // ValidateConfig applies the same limits as New without starting workers.
158+ func ValidateConfig (config Config ) error {
159+ _ , err := normalizeConfig (config )
160+ return err
161+ }
162+
163+ func normalizeConfig (config Config ) (Config , error ) {
133164 if config .Workers <= 0 {
134165 config .Workers = 2
135166 }
136167 if config .Workers > 32 {
137- return nil , errors .New ("generation workers must not exceed 32" )
168+ return Config {} , errors .New ("generation workers must not exceed 32" )
138169 }
139170 if config .QueueSize <= 0 {
140171 config .QueueSize = 64
141172 }
142173 if config .QueueSize > 4096 {
143- return nil , errors .New ("generation queue size must not exceed 4096" )
174+ return Config {} , errors .New ("generation queue size must not exceed 4096" )
144175 }
145176 if config .MaxJobs <= 0 {
146177 config .MaxJobs = 512
147178 }
148179 if config .MaxJobs < config .QueueSize || config .MaxJobs > 16384 {
149- return nil , errors .New ("generation max jobs must be between queue size and 16384" )
180+ return Config {} , errors .New ("generation max jobs must be between queue size and 16384" )
150181 }
151182 if config .JobTTL <= 0 {
152183 config .JobTTL = 30 * time .Minute
@@ -155,7 +186,7 @@ func New(
155186 config .CacheEntries = 256
156187 }
157188 if config .CacheEntries > 16384 {
158- return nil , errors .New ("generation cache entries must not exceed 16384" )
189+ return Config {} , errors .New ("generation cache entries must not exceed 16384" )
159190 }
160191 if config .CacheTTL <= 0 {
161192 config .CacheTTL = 30 * time .Minute
@@ -164,15 +195,17 @@ func New(
164195 config .MaxOutputBytes = 512 * 1024
165196 }
166197 if config .MaxOutputBytes < 1024 || config .MaxOutputBytes > 4 * 1024 * 1024 {
167- return nil , errors .New ("generation output limit must be between 1 KiB and 4 MiB" )
198+ return Config {}, errors .New (
199+ "generation output limit must be between 1 KiB and 4 MiB" ,
200+ )
168201 }
169202 if config .MaxRetainedBytes == 0 {
170203 config .MaxRetainedBytes = 64 << 20
171204 }
172205 minimumRetained := uint64 (config .MaxOutputBytes )* 2 + (64 << 10 )
173206 if config .MaxRetainedBytes < minimumRetained ||
174207 config .MaxRetainedBytes > 1 << 30 {
175- return nil , errors .New (
208+ return Config {} , errors .New (
176209 "generation retained-memory limit must fit two outputs plus 64 KiB and not exceed 1 GiB" ,
177210 )
178211 }
@@ -181,29 +214,11 @@ func New(
181214 }
182215 if config .CleanupInterval < 10 * time .Millisecond ||
183216 config .CleanupInterval > time .Hour {
184- return nil , errors .New (
217+ return Config {} , errors .New (
185218 "generation cleanup interval must be between 10 ms and 1 hour" ,
186219 )
187220 }
188-
189- ctx , cancel := context .WithCancel (context .Background ())
190- manager := & Manager {
191- provider : generationProvider , config : config , ctx : ctx , cancel : cancel ,
192- queue : make (chan string , config .QueueSize ), jobs : make (map [string ]* jobState ),
193- byRequest : make (map [string ]string ), cache : make (map [string ]cacheEntry ),
194- now : time .Now , done : make (chan struct {}),
195- }
196- for index := 0 ; index < config .Workers ; index ++ {
197- manager .wait .Add (1 )
198- go manager .worker ()
199- }
200- manager .wait .Add (1 )
201- go manager .cleanupWorker ()
202- go func () {
203- manager .wait .Wait ()
204- close (manager .done )
205- }()
206- return manager , nil
221+ return config , nil
207222}
208223
209224func (m * Manager ) Submit (request protocol.GenerationRequest ) (protocol.GenerationJobSubmission , error ) {
0 commit comments