@@ -35,6 +35,7 @@ import (
3535 "github.com/uber/submitqueue/submitqueue/extension/changeprovider"
3636 "github.com/uber/submitqueue/submitqueue/extension/conflict"
3737 "github.com/uber/submitqueue/submitqueue/extension/speculation/speculator"
38+ "github.com/uber/submitqueue/submitqueue/extension/validator"
3839)
3940
4041func TestValidateProfileQueueTenants (t * testing.T ) {
@@ -122,13 +123,15 @@ queues:
122123 resolved := cfg .resolve (cfg .Queues [0 ])
123124 assert .Equal (t , analyzerTypeNone , resolved .Analyzer .Type )
124125 assert .Equal (t , changeProviderTypeFake , resolved .ChangeProvider .Type )
126+ assert .Equal (t , validatorTypeFake , resolved .Validator .Type )
125127 assert .Equal (t , buildRunnerTypeFake , resolved .BuildRunner .Type )
126128}
127129
128130func TestLoadProfilesConfig_AppliesForgeDefaults (t * testing.T ) {
129131 path := writeProfiles (t , `
130132defaults:
131133 changeProvider: {type: github}
134+ validator: {type: github}
132135 buildRunner: {type: githubactions, owner: uber, repo: sq-sandbox, workflow: validate.yml}
133136` )
134137
@@ -138,6 +141,9 @@ defaults:
138141 require .NotNil (t , cfg .Defaults .ChangeProvider .GitHub )
139142 assert .Equal (t , defaultGitHubTokenEnv , cfg .Defaults .ChangeProvider .GitHub .TokenEnv )
140143 assert .Equal (t , defaultGitHubBaseURL , cfg .Defaults .ChangeProvider .GitHub .BaseURL )
144+ assert .Equal (t , defaultGitHubTokenEnv , cfg .Defaults .Validator .TokenEnv )
145+ assert .Equal (t , defaultGitHubBaseURL , cfg .Defaults .Validator .BaseURL )
146+ assert .Equal (t , defaultGitHubHost , cfg .Defaults .Validator .Host )
141147 assert .Equal (t , defaultGitHubTokenEnv , cfg .Defaults .BuildRunner .TokenEnv )
142148 assert .Equal (t , defaultGitHubBaseURL , cfg .Defaults .BuildRunner .BaseURL )
143149}
@@ -146,6 +152,7 @@ func TestLoadProfilesConfig_EmptyFileIsAllFakes(t *testing.T) {
146152 cfg , err := loadProfilesConfig (writeProfiles (t , "" ))
147153 require .NoError (t , err )
148154 assert .Equal (t , changeProviderTypeFake , cfg .Defaults .ChangeProvider .Type )
155+ assert .Equal (t , validatorTypeFake , cfg .Defaults .Validator .Type )
149156 assert .Equal (t , buildRunnerTypeFake , cfg .Defaults .BuildRunner .Type )
150157 assert .Equal (t , analyzerTypeAll , cfg .Defaults .Analyzer .Type )
151158}
@@ -170,6 +177,14 @@ func TestLoadProfilesConfig_Rejects(t *testing.T) {
170177 name : "unknown change provider" ,
171178 contents : "defaults:\n changeProvider: {type: gitlab}\n " ,
172179 },
180+ {
181+ name : "unknown validator" ,
182+ contents : "defaults:\n validator: {type: lint}\n " ,
183+ },
184+ {
185+ name : "unknown validator on a queue" ,
186+ contents : "queues:\n - name: a\n validator: {type: lint}\n " ,
187+ },
173188 {
174189 name : "unknown build runner" ,
175190 contents : "defaults:\n buildRunner: {type: jenkins}\n " ,
@@ -308,18 +323,70 @@ func TestNewProfiles_ResolvesPerQueueAnalyzers(t *testing.T) {
308323func TestNewProfiles_FailsWhenAForgeTokenIsMissing (t * testing.T ) {
309324 // Failing at startup beats accepting land requests and discovering the
310325 // credential gap one API call into the first merge.
311- t .Setenv ("TEST_GH_TOKEN_UNSET" , "" )
326+ tests := []struct {
327+ name string
328+ contents string
329+ }{
330+ {
331+ name : "github change provider" ,
332+ contents : "defaults:\n changeProvider:\n type: github\n github: {tokenEnv: TEST_GH_TOKEN_UNSET}\n " ,
333+ },
334+ {
335+ name : "github validator" ,
336+ contents : "queues:\n - name: gh\n validator: {type: github, tokenEnv: TEST_GH_TOKEN_UNSET}\n " ,
337+ },
338+ }
339+
340+ for _ , tt := range tests {
341+ t .Run (tt .name , func (t * testing.T ) {
342+ t .Setenv ("TEST_GH_TOKEN_UNSET" , "" )
343+ cfg , err := loadProfilesConfig (writeProfiles (t , tt .contents ))
344+ require .NoError (t , err )
345+
346+ _ , err = newProfiles (context .Background (), zaptest .NewLogger (t ), tally .NoopScope , nil , nil , cfg )
347+ require .Error (t , err )
348+ })
349+ }
350+ }
351+
352+ func TestNewProfiles_ResolvesPerQueueValidators (t * testing.T ) {
353+ // A change URI on another GitHub host is one the GitHub validator rejects
354+ // without calling GitHub, so the two types differ observably offline.
355+ t .Setenv ("TEST_GH_TOKEN" , "token" )
312356 path := writeProfiles (t , `
313- defaults:
314- changeProvider:
315- type: github
316- github: {tokenEnv: TEST_GH_TOKEN_UNSET}
357+ queues:
358+ - name: gh
359+ validator: {type: github, tokenEnv: TEST_GH_TOKEN}
317360` )
318361 cfg , err := loadProfilesConfig (path )
319362 require .NoError (t , err )
363+ profiles , err := newProfiles (context .Background (), zaptest .NewLogger (t ), tally .NoopScope , nil , nil , cfg )
364+ require .NoError (t , err )
320365
321- _ , err = newProfiles (context .Background (), zaptest .NewLogger (t ), tally .NoopScope , nil , nil , cfg )
322- require .Error (t , err )
366+ foreignHost := entity.Request {Change : change.Change {URIs : []string {
367+ "github://github.example.com/acme/widgets/pull/1/" + strings .Repeat ("a" , 40 ),
368+ }}}
369+
370+ tests := []struct {
371+ queue string
372+ wantReject bool
373+ }{
374+ {queue : "gh" , wantReject : true },
375+ {queue : "unlisted-falls-back-to-fake" },
376+ }
377+ for _ , tt := range tests {
378+ t .Run (tt .queue , func (t * testing.T ) {
379+ v , err := profiles .ValidatorFactory ().For (validator.Config {QueueName : tt .queue })
380+ require .NoError (t , err )
381+
382+ err = v .Validate (context .Background (), foreignHost )
383+ if tt .wantReject {
384+ assert .Error (t , err )
385+ } else {
386+ assert .NoError (t , err )
387+ }
388+ })
389+ }
323390}
324391
325392func TestNewProfiles_RoutingFallsBackToFakeWithoutTokens (t * testing.T ) {
0 commit comments