@@ -11,6 +11,7 @@ import (
1111 "github.com/devtron-labs/devtron/internal/sql/repository/security"
1212 "github.com/devtron-labs/devtron/pkg/appClone"
1313 "github.com/devtron-labs/devtron/pkg/appWorkflow"
14+ "github.com/devtron-labs/devtron/pkg/bulkAction"
1415 "github.com/devtron-labs/devtron/pkg/chart"
1516 request "github.com/devtron-labs/devtron/pkg/cluster"
1617 "github.com/devtron-labs/devtron/pkg/pipeline"
@@ -24,6 +25,7 @@ import (
2425 "go.uber.org/zap"
2526 "gopkg.in/go-playground/validator.v9"
2627 "net/http"
28+ "strconv"
2729 "strings"
2830)
2931
@@ -36,13 +38,15 @@ type BulkUpdateRestHandler interface {
3638 BulkUnHibernate (w http.ResponseWriter , r * http.Request )
3739 BulkDeploy (w http.ResponseWriter , r * http.Request )
3840 BulkBuildTrigger (w http.ResponseWriter , r * http.Request )
41+
42+ HandleCdPipelineBulkAction (w http.ResponseWriter , r * http.Request )
3943}
4044type BulkUpdateRestHandlerImpl struct {
4145 pipelineBuilder pipeline.PipelineBuilder
4246 ciPipelineRepository pipelineConfig.CiPipelineRepository
4347 ciHandler pipeline.CiHandler
4448 logger * zap.SugaredLogger
45- bulkUpdateService pipeline .BulkUpdateService
49+ bulkUpdateService bulkAction .BulkUpdateService
4650 chartService chart.ChartService
4751 propertiesConfigService pipeline.PropertiesConfigService
4852 dbMigrationService pipeline.DbMigrationService
@@ -67,7 +71,7 @@ type BulkUpdateRestHandlerImpl struct {
6771}
6872
6973func NewBulkUpdateRestHandlerImpl (pipelineBuilder pipeline.PipelineBuilder , logger * zap.SugaredLogger ,
70- bulkUpdateService pipeline .BulkUpdateService ,
74+ bulkUpdateService bulkAction .BulkUpdateService ,
7175 chartService chart.ChartService ,
7276 propertiesConfigService pipeline.PropertiesConfigService ,
7377 dbMigrationService pipeline.DbMigrationService ,
@@ -129,7 +133,7 @@ func (handler BulkUpdateRestHandlerImpl) FindBulkUpdateReadme(w http.ResponseWri
129133 return
130134 }
131135 //auth free, only login required
132- var responseArr []* pipeline .BulkUpdateSeeExampleResponse
136+ var responseArr []* bulkAction .BulkUpdateSeeExampleResponse
133137 responseArr = append (responseArr , response )
134138 common .WriteJsonResp (w , nil , responseArr , http .StatusOK )
135139}
@@ -151,7 +155,7 @@ func (handler BulkUpdateRestHandlerImpl) CheckAuthForImpactedObjects(AppId int,
151155}
152156func (handler BulkUpdateRestHandlerImpl ) GetImpactedAppsName (w http.ResponseWriter , r * http.Request ) {
153157 decoder := json .NewDecoder (r .Body )
154- var script pipeline .BulkUpdateScript
158+ var script bulkAction .BulkUpdateScript
155159 err := decoder .Decode (& script )
156160 if err != nil {
157161 common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
@@ -206,7 +210,7 @@ func (handler BulkUpdateRestHandlerImpl) CheckAuthForBulkUpdate(AppId int, EnvId
206210}
207211func (handler BulkUpdateRestHandlerImpl ) BulkUpdate (w http.ResponseWriter , r * http.Request ) {
208212 decoder := json .NewDecoder (r .Body )
209- var script pipeline .BulkUpdateScript
213+ var script bulkAction .BulkUpdateScript
210214 err := decoder .Decode (& script )
211215 if err != nil {
212216 common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
@@ -255,7 +259,7 @@ func (handler BulkUpdateRestHandlerImpl) BulkHibernate(w http.ResponseWriter, r
255259 return
256260 }
257261 decoder := json .NewDecoder (r .Body )
258- var request pipeline .BulkApplicationForEnvironmentPayload
262+ var request bulkAction .BulkApplicationForEnvironmentPayload
259263 err = decoder .Decode (& request )
260264 if err != nil {
261265 common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
@@ -292,7 +296,7 @@ func (handler BulkUpdateRestHandlerImpl) BulkUnHibernate(w http.ResponseWriter,
292296 return
293297 }
294298 decoder := json .NewDecoder (r .Body )
295- var request pipeline .BulkApplicationForEnvironmentPayload
299+ var request bulkAction .BulkApplicationForEnvironmentPayload
296300 err = decoder .Decode (& request )
297301 if err != nil {
298302 common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
@@ -329,7 +333,7 @@ func (handler BulkUpdateRestHandlerImpl) BulkDeploy(w http.ResponseWriter, r *ht
329333 return
330334 }
331335 decoder := json .NewDecoder (r .Body )
332- var request pipeline .BulkApplicationForEnvironmentPayload
336+ var request bulkAction .BulkApplicationForEnvironmentPayload
333337 err = decoder .Decode (& request )
334338 if err != nil {
335339 common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
@@ -365,7 +369,7 @@ func (handler BulkUpdateRestHandlerImpl) BulkBuildTrigger(w http.ResponseWriter,
365369 return
366370 }
367371 decoder := json .NewDecoder (r .Body )
368- var request pipeline .BulkApplicationForEnvironmentPayload
372+ var request bulkAction .BulkApplicationForEnvironmentPayload
369373 err = decoder .Decode (& request )
370374 if err != nil {
371375 common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
@@ -403,3 +407,85 @@ func (handler BulkUpdateRestHandlerImpl) checkAuthForBulkActions(token string, a
403407 }
404408 return true
405409}
410+
411+ func (handler BulkUpdateRestHandlerImpl ) HandleCdPipelineBulkAction (w http.ResponseWriter , r * http.Request ) {
412+ decoder := json .NewDecoder (r .Body )
413+ userId , err := handler .userAuthService .GetLoggedInUser (r )
414+ if userId == 0 || err != nil {
415+ common .WriteJsonResp (w , err , "Unauthorized User" , http .StatusUnauthorized )
416+ return
417+ }
418+ var cdPipelineBulkActionReq bulkAction.CdBulkActionRequestDto
419+ err = decoder .Decode (& cdPipelineBulkActionReq )
420+ cdPipelineBulkActionReq .UserId = userId
421+ if err != nil {
422+ handler .logger .Errorw ("request err, HandleCdPipelineBulkAction" , "err" , err , "payload" , cdPipelineBulkActionReq )
423+ common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
424+ return
425+ }
426+
427+ v := r .URL .Query ()
428+ forceDelete := false
429+ forceDeleteParam := v .Get ("forceDelete" )
430+ if len (forceDeleteParam ) > 0 {
431+ forceDelete , err = strconv .ParseBool (forceDeleteParam )
432+ if err != nil {
433+ handler .logger .Errorw ("request err, HandleCdPipelineBulkAction" , "err" , err , "payload" , cdPipelineBulkActionReq )
434+ common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
435+ return
436+ }
437+ }
438+ cdPipelineBulkActionReq .ForceDelete = forceDelete
439+
440+ dryRun := false
441+ dryRunParam := v .Get ("dryRun" )
442+ if len (dryRunParam ) > 0 {
443+ dryRun , err = strconv .ParseBool (dryRunParam )
444+ if err != nil {
445+ handler .logger .Errorw ("request err, HandleCdPipelineBulkAction" , "err" , err , "payload" , cdPipelineBulkActionReq )
446+ common .WriteJsonResp (w , err , nil , http .StatusBadRequest )
447+ return
448+ }
449+ }
450+ handler .logger .Infow ("request payload, HandleCdPipelineBulkAction" , "payload" , cdPipelineBulkActionReq )
451+ impactedPipelines , impactedAppWfIds , impactedCiPipelineIds , err := handler .bulkUpdateService .GetBulkActionImpactedPipelinesAndWfs (& cdPipelineBulkActionReq )
452+ if err != nil {
453+ handler .logger .Errorw ("service err, GetBulkActionImpactedPipelinesAndWfs" , "err" , err , "payload" , cdPipelineBulkActionReq )
454+ common .WriteJsonResp (w , err , nil , http .StatusInternalServerError )
455+ return
456+ }
457+ token := r .Header .Get ("token" )
458+
459+ appsHavingRbacChecked := make (map [string ]bool )
460+ for _ , impactedPipeline := range impactedPipelines {
461+ //check to avoid same rbac matching multiple times
462+ if _ , ok := appsHavingRbacChecked [impactedPipeline .App .AppName ]; ! ok {
463+ resourceName := handler .enforcerUtil .GetAppRBACName (impactedPipeline .App .AppName )
464+ if ok := handler .enforcer .Enforce (token , casbin .ResourceApplications , casbin .ActionUpdate , resourceName ); ! ok {
465+ common .WriteJsonResp (w , fmt .Errorf ("unauthorized user" ), "Unauthorized User" , http .StatusForbidden )
466+ return
467+ } else {
468+ appsHavingRbacChecked [impactedPipeline .App .AppName ] = true
469+ }
470+ }
471+ object := handler .enforcerUtil .GetAppRBACByAppNameAndEnvId (impactedPipeline .App .AppName , impactedPipeline .EnvironmentId )
472+ if ok := handler .enforcer .Enforce (token , casbin .ResourceEnvironment , casbin .ActionUpdate , object ); ! ok {
473+ common .WriteJsonResp (w , fmt .Errorf ("unauthorized user" ), "Unauthorized User" , http .StatusForbidden )
474+ return
475+ }
476+ }
477+ acdToken , err := handler .argoUserService .GetLatestDevtronArgoCdUserToken ()
478+ if err != nil {
479+ handler .logger .Errorw ("error in getting acd token" , "err" , err )
480+ common .WriteJsonResp (w , err , nil , http .StatusInternalServerError )
481+ return
482+ }
483+ ctx := context .WithValue (r .Context (), "token" , acdToken )
484+ resp , err := handler .bulkUpdateService .PerformBulkActionOnCdPipelines (& cdPipelineBulkActionReq , impactedPipelines , ctx , dryRun , impactedAppWfIds , impactedCiPipelineIds )
485+ if err != nil {
486+ handler .logger .Errorw ("service err, HandleCdPipelineBulkAction" , "err" , err , "payload" , cdPipelineBulkActionReq )
487+ common .WriteJsonResp (w , err , nil , http .StatusInternalServerError )
488+ return
489+ }
490+ common .WriteJsonResp (w , nil , resp , http .StatusOK )
491+ }
0 commit comments