Skip to content

Commit 5150c44

Browse files
merged main
2 parents c7f6f75 + 157de54 commit 5150c44

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

47 files changed

+4143
-5025
lines changed

api/bean/gitOps/GitOpsConfig.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ import "time"
44

55
type GitOpsConfigDto struct {
66
Id int `json:"id,omitempty"`
7-
Provider string `json:"provider"`
7+
Provider string `json:"provider" validate:"oneof=GITLAB GITHUB AZURE_DEVOPS BITBUCKET_CLOUD"`
88
Username string `json:"username"`
99
Token string `json:"token"`
1010
GitLabGroupId string `json:"gitLabGroupId"`

api/helm-app/service/HelmAppService.go

Lines changed: 36 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,7 @@ type HelmAppService interface {
7373
ValidateOCIRegistry(ctx context.Context, OCIRegistryRequest *gRPC.RegistryCredential) bool
7474
GetRevisionHistoryMaxValue(appType bean.SourceAppType) int32
7575
GetResourceTreeForExternalResources(ctx context.Context, clusterId int, clusterConfig *gRPC.ClusterConfig, resources []*gRPC.ExternalResourceDetail) (*gRPC.ResourceTreeResponse, error)
76+
CheckIfNsExistsForClusterIds(clusterIdToNsMap map[int]string) error
7677
}
7778

7879
type HelmAppServiceImpl struct {
@@ -536,15 +537,13 @@ func (impl *HelmAppServiceImpl) DeleteApplication(ctx context.Context, app *AppI
536537
//handles the case when a user deletes namespace using kubectl but created it using devtron dashboard in
537538
//that case DeleteApplication returned with grpc error and the user was not able to delete the
538539
//cd-pipeline after helm app is created in that namespace.
539-
exists, err := impl.checkIfNsExists(app)
540+
clusterIdToNsMap := map[int]string{
541+
app.ClusterId: app.Namespace,
542+
}
543+
err = impl.CheckIfNsExistsForClusterIds(clusterIdToNsMap)
540544
if err != nil {
541-
impl.logger.Errorw("error in checking if namespace exists or not", "err", err, "clusterId", app.ClusterId)
542545
return nil, err
543546
}
544-
if !exists {
545-
return nil, models.NamespaceNotExistError{Err: fmt.Errorf("namespace %s does not exist", app.Namespace)}
546-
}
547-
548547
req := &gRPC.ReleaseIdentifier{
549548
ClusterConfig: config,
550549
ReleaseName: app.ReleaseName,
@@ -571,23 +570,19 @@ func (impl *HelmAppServiceImpl) DeleteApplication(ctx context.Context, app *AppI
571570
return response, nil
572571
}
573572

574-
func (impl *HelmAppServiceImpl) checkIfNsExists(app *AppIdentifier) (bool, error) {
575-
clusterBean, err := impl.clusterService.FindById(app.ClusterId)
576-
if err != nil {
577-
impl.logger.Errorw("error in getting cluster bean", "error", err, "clusterId", app.ClusterId)
578-
return false, err
579-
}
573+
func (impl *HelmAppServiceImpl) checkIfNsExists(namespace string, clusterBean *cluster.ClusterBean) (bool, error) {
574+
580575
config, err := clusterBean.GetClusterConfig()
581576
if err != nil {
582-
impl.logger.Errorw("error in getting cluster config", "error", err, "clusterId", app.ClusterId)
577+
impl.logger.Errorw("error in getting cluster config", "error", err, "clusterId", clusterBean.Id)
583578
return false, err
584579
}
585580
v12Client, err := impl.K8sUtil.GetCoreV1Client(config)
586581
if err != nil {
587582
impl.logger.Errorw("error in getting k8s client", "err", err, "clusterHost", config.Host)
588583
return false, err
589584
}
590-
exists, err := impl.K8sUtil.CheckIfNsExists(app.Namespace, v12Client)
585+
exists, err := impl.K8sUtil.CheckIfNsExists(namespace, v12Client)
591586
if err != nil {
592587
if IsClusterUnReachableError(err) {
593588
impl.logger.Errorw("k8s cluster unreachable", "err", err)
@@ -1114,3 +1109,30 @@ func (impl *HelmAppServiceImpl) GetRevisionHistoryMaxValue(appType bean.SourceAp
11141109
return 0
11151110
}
11161111
}
1112+
func (impl *HelmAppServiceImpl) CheckIfNsExistsForClusterIds(clusterIdToNsMap map[int]string) error {
1113+
clusterIds := make([]int, 0)
1114+
for clusterId, _ := range clusterIdToNsMap {
1115+
clusterIds = append(clusterIds, clusterId)
1116+
}
1117+
clusterBeans, err := impl.clusterService.FindByIds(clusterIds)
1118+
if err != nil {
1119+
impl.logger.Errorw("error in getting cluster bean", "error", err, "clusterIds", clusterIds)
1120+
return err
1121+
}
1122+
for _, clusterBean := range clusterBeans {
1123+
if clusterBean.IsVirtualCluster {
1124+
continue
1125+
}
1126+
if namespace, ok := clusterIdToNsMap[clusterBean.Id]; ok {
1127+
exists, err := impl.checkIfNsExists(namespace, &clusterBean)
1128+
if err != nil {
1129+
impl.logger.Errorw("error in checking if namespace exists or not", "err", err, "clusterId", clusterBean.Id)
1130+
return err
1131+
}
1132+
if !exists {
1133+
return &util.ApiError{InternalMessage: models.NamespaceNotExistError{Err: fmt.Errorf("namespace %s does not exist", namespace)}.Error(), Code: strconv.Itoa(http.StatusNotFound), HttpStatusCode: http.StatusNotFound, UserMessage: fmt.Sprintf("Namespace %s does not exist.", namespace)}
1134+
}
1135+
}
1136+
}
1137+
return nil
1138+
}

api/restHandler/GitOpsConfigRestHandler.go

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ import (
2121
"encoding/json"
2222
"errors"
2323
bean2 "github.com/devtron-labs/devtron/api/bean/gitOps"
24+
"github.com/devtron-labs/devtron/api/util"
2425
"net/http"
2526
"strconv"
2627

@@ -93,7 +94,7 @@ func (impl GitOpsConfigRestHandlerImpl) CreateGitOpsConfig(w http.ResponseWriter
9394
err = impl.validator.Struct(bean)
9495
if err != nil {
9596
impl.logger.Errorw("validation err, createGitOpsConfig", "err", err, "payload", bean)
96-
common.WriteJsonResp(w, err, nil, http.StatusBadRequest)
97+
common.WriteJsonResp(w, util.CustomizeValidationError(err), nil, http.StatusBadRequest)
9798
return
9899
}
99100
detailedErrorGitOpsConfigResponse, err := impl.gitOpsConfigService.ValidateAndCreateGitOpsConfig(&bean)
@@ -141,7 +142,7 @@ func (impl GitOpsConfigRestHandlerImpl) UpdateGitOpsConfig(w http.ResponseWriter
141142
err = impl.validator.Struct(bean)
142143
if err != nil {
143144
impl.logger.Errorw("validation err, updateGitOpsConfig", "err", err, "payload", bean)
144-
common.WriteJsonResp(w, err, nil, http.StatusBadRequest)
145+
common.WriteJsonResp(w, util.CustomizeValidationError(err), nil, http.StatusBadRequest)
145146
return
146147
}
147148
detailedErrorGitOpsConfigResponse, err := impl.gitOpsConfigService.ValidateAndUpdateGitOpsConfig(&bean)

api/util/errorUtils.go

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
package util
2+
3+
import (
4+
"errors"
5+
"fmt"
6+
"gopkg.in/go-playground/validator.v9"
7+
)
8+
9+
func CustomizeValidationError(err error) error {
10+
if validatorErr := (validator.ValidationErrors{}); errors.As(err, &validatorErr) {
11+
fieldErr := validatorErr[0]
12+
switch fieldErr.Tag() {
13+
case "required":
14+
return fmt.Errorf("field %s is required %v", fieldErr.Field(), err)
15+
case "oneof":
16+
return fmt.Errorf("value %s is unsupported %v", fieldErr.Value(), err)
17+
}
18+
}
19+
return err
20+
}

client/argocdServer/application/Application.go

Lines changed: 9 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -332,22 +332,21 @@ func (c ServiceClientImpl) buildPodMetadata(resp *v1alpha1.ApplicationTree, resp
332332
}
333333
}
334334

335-
//podMetaData := make([]*PodMetadata, 0)
336-
duplicateCheck := make(map[string]bool)
335+
//duplicatePodToReplicasetMapping can contain following data {Pod1: RS1, Pod2: RS1, Pod4: RS2, Pod5:RS2}, it contains pod
336+
//to replica set mapping, where key is podName and value is its respective replicaset name, multiple keys(podName) can have
337+
//single value (replicasetName)
338+
duplicatePodToReplicasetMapping := make(map[string]string)
337339
if len(newReplicaSets) > 0 {
338-
results := buildPodMetadataFromReplicaSet(resp, newReplicaSets, replicaSetManifests)
340+
results, duplicateMapping := buildPodMetadataFromReplicaSet(resp, newReplicaSets, replicaSetManifests)
339341
for _, meta := range results {
340-
duplicateCheck[meta.Name] = true
341342
podMetaData = append(podMetaData, meta)
342343
}
344+
duplicatePodToReplicasetMapping = duplicateMapping
343345
}
346+
344347
if newPodNames != nil {
345-
results := buildPodMetadataFromPod(resp, podManifests, newPodNames)
346-
for _, meta := range results {
347-
if _, ok := duplicateCheck[meta.Name]; !ok {
348-
podMetaData = append(podMetaData, meta)
349-
}
350-
}
348+
podsMetadataFromPods := buildPodMetadataFromPod(resp, podManifests, newPodNames)
349+
podMetaData = updateMetadataOfDuplicatePods(podsMetadataFromPods, duplicatePodToReplicasetMapping, podMetaData)
351350
}
352351
return
353352
}

client/argocdServer/application/ApplicationUtil.go

Lines changed: 67 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -52,11 +52,11 @@ func parseResult(resp *v1alpha1.ApplicationTree, query *application.ResourcesQue
5252
}
5353
needPods := false
5454
queryNodes := make([]v1alpha1.ResourceNode, 0)
55-
podParents := make([]string, 0)
55+
podParents := make(map[string]v1alpha1.ResourceNode)
5656
for _, node := range resp.Nodes {
5757
if node.Kind == "Pod" {
5858
for _, pr := range node.ParentRefs {
59-
podParents = append(podParents, pr.Name)
59+
podParents[pr.Name] = node
6060
}
6161
}
6262
}
@@ -65,11 +65,8 @@ func parseResult(resp *v1alpha1.ApplicationTree, query *application.ResourcesQue
6565
queryNodes = append(queryNodes, node)
6666
}
6767
if node.Kind == "ReplicaSet" {
68-
for _, pr := range podParents {
69-
if pr == node.Name {
70-
queryNodes = append(queryNodes, node)
71-
break
72-
}
68+
if _, ok := podParents[node.Name]; ok {
69+
queryNodes = append(queryNodes, node)
7370
}
7471
}
7572
if node.Kind == "StatefulSet" || node.Kind == "DaemonSet" || node.Kind == "Workflow" {
@@ -84,6 +81,10 @@ func parseResult(resp *v1alpha1.ApplicationTree, query *application.ResourcesQue
8481

8582
c.logger.Debugw("needPods", "pods", needPods)
8683

84+
for _, node := range podParents {
85+
queryNodes = append(queryNodes, node)
86+
}
87+
8788
if needPods {
8889
for _, node := range resp.Nodes {
8990
if node.Kind == "Pod" {
@@ -398,8 +399,10 @@ func getPodInitContainers(resource map[string]interface{}) []*string {
398399
return containers
399400
}
400401

401-
func buildPodMetadataFromReplicaSet(resp *v1alpha1.ApplicationTree, newReplicaSets []string, replicaSetManifests []map[string]interface{}) (podMetadata []*argoApplication.PodMetadata) {
402+
func buildPodMetadataFromReplicaSet(resp *v1alpha1.ApplicationTree, newReplicaSets []string, replicaSetManifests []map[string]interface{}) ([]*argoApplication.PodMetadata, map[string]string) {
402403
replicaSets := make(map[string]map[string]interface{})
404+
podToReplicasetMapping := make(map[string]string)
405+
var podMetadata []*argoApplication.PodMetadata
403406
for _, replicaSet := range replicaSetManifests {
404407
replicaSets[getResourceName(replicaSet)] = replicaSet
405408
}
@@ -421,12 +424,13 @@ func buildPodMetadataFromReplicaSet(resp *v1alpha1.ApplicationTree, newReplicaSe
421424
}
422425
replicaSet := replicaSets[parentName]
423426
containers, intContainers := getReplicaSetContainers(replicaSet)
427+
podToReplicasetMapping[node.Name] = parentName
424428
metadata := argoApplication.PodMetadata{Name: node.Name, UID: node.UID, Containers: containers, InitContainers: intContainers, IsNew: isNew}
425429
podMetadata = append(podMetadata, &metadata)
426430
}
427431
}
428432
}
429-
return
433+
return podMetadata, podToReplicasetMapping
430434
}
431435

432436
func getReplicaSetContainers(resource map[string]interface{}) (containers []*string, intContainers []*string) {
@@ -511,3 +515,57 @@ func getJobsNewPods(jobManifest map[string]interface{}, podManifests []map[strin
511515
//TODO - new or old logic
512516
return
513517
}
518+
519+
func updateMetadataOfDuplicatePods(podsMetadataFromPods []*argoApplication.PodMetadata, duplicatePodToReplicasetMapping map[string]string, podMetaData []*argoApplication.PodMetadata) []*argoApplication.PodMetadata {
520+
// Initialize mappings for containers
521+
containersPodMapping := make(map[string][]*string) // Mapping from pod name to container names
522+
initContainersPodMapping := make(map[string][]*string)
523+
// iterate over pod metadata extracted from pods' manifests
524+
for _, podMetadataFromPod := range podsMetadataFromPods {
525+
// If pod is not a duplicate
526+
if _, ok := duplicatePodToReplicasetMapping[podMetadataFromPod.Name]; !ok {
527+
// if pod is not a duplicate append pod metadata to the final result
528+
podMetaData = append(podMetaData, podMetadataFromPod)
529+
} else {
530+
// update init and sidecar container data into podsMetadataFromPods array's pods obj. if pod is a duplicate found in duplicatePodToReplicasetMapping,
531+
for _, podMetadataFromReplicaSet := range podMetaData {
532+
if podMetadataFromReplicaSet.Name == podMetadataFromPod.Name {
533+
// Update containers mapping
534+
if podMetadataFromPod.Containers != nil {
535+
containersPodMapping[podMetadataFromPod.Name] = podMetadataFromPod.Containers
536+
// Update containers mapping for other duplicate pods with the same replicaset
537+
// because we are only fetching manifest for one pod
538+
// and propagate to other pods having same parent
539+
currentPodParentName := duplicatePodToReplicasetMapping[podMetadataFromPod.Name]
540+
for podName, podParentName := range duplicatePodToReplicasetMapping {
541+
if podParentName == currentPodParentName {
542+
containersPodMapping[podName] = podMetadataFromPod.Containers
543+
}
544+
}
545+
}
546+
if podMetadataFromPod.InitContainers != nil {
547+
initContainersPodMapping[podMetadataFromPod.Name] = podMetadataFromPod.InitContainers
548+
currentPodParentName := duplicatePodToReplicasetMapping[podMetadataFromPod.Name]
549+
for podName, podParentName := range duplicatePodToReplicasetMapping {
550+
if podParentName == currentPodParentName {
551+
initContainersPodMapping[podName] = podMetadataFromPod.InitContainers
552+
}
553+
}
554+
}
555+
}
556+
}
557+
}
558+
}
559+
560+
// Update pod metadata with containers mapping
561+
for _, metadata := range podMetaData {
562+
if containers, ok := containersPodMapping[metadata.Name]; ok {
563+
metadata.Containers = containers
564+
}
565+
if initContainers, ok := initContainersPodMapping[metadata.Name]; ok {
566+
metadata.InitContainers = initContainers
567+
}
568+
}
569+
// Return updated pod metadata
570+
return podMetaData
571+
}

go.mod

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ go 1.20
55
require (
66
github.com/Masterminds/semver v1.5.0
77
github.com/Pallinder/go-randomdata v1.2.0
8-
github.com/argoproj/argo-cd/v2 v2.8.14
8+
github.com/argoproj/argo-cd/v2 v2.8.17
99
github.com/argoproj/argo-workflows/v3 v3.4.3
1010
github.com/argoproj/gitops-engine v0.7.1-0.20231013183858-f15cf615b814
1111
github.com/aws/aws-sdk-go v1.44.290
@@ -69,7 +69,7 @@ require (
6969
go.opentelemetry.io/otel/sdk v1.20.0
7070
go.opentelemetry.io/otel/trace v1.20.0
7171
go.uber.org/zap v1.21.0
72-
golang.org/x/crypto v0.19.0
72+
golang.org/x/crypto v0.21.0
7373
golang.org/x/exp v0.0.0-20240222234643-814bf88cf225
7474
golang.org/x/oauth2 v0.11.0
7575
google.golang.org/grpc v1.59.0
@@ -248,10 +248,10 @@ require (
248248
go.uber.org/atomic v1.10.0 // indirect
249249
go.uber.org/multierr v1.11.0 // indirect
250250
golang.org/x/mod v0.15.0 // indirect
251-
golang.org/x/net v0.21.0 // indirect
251+
golang.org/x/net v0.23.0 // indirect
252252
golang.org/x/sync v0.6.0 // indirect
253253
golang.org/x/sys v0.18.0 // indirect
254-
golang.org/x/term v0.17.0 // indirect
254+
golang.org/x/term v0.18.0 // indirect
255255
golang.org/x/text v0.14.0 // indirect
256256
golang.org/x/time v0.3.0 // indirect
257257
golang.org/x/tools v0.18.0 // indirect

go.sum

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -114,8 +114,8 @@ github.com/apparentlymart/go-textseg v1.0.0 h1:rRmlIsPEEhUTIKQb7T++Nz/A5Q6C9IuX2
114114
github.com/apparentlymart/go-textseg v1.0.0/go.mod h1:z96Txxhf3xSFMPmb5X/1W05FF/Nj9VFpLOpjS5yuumk=
115115
github.com/apparentlymart/go-textseg/v13 v13.0.0 h1:Y+KvPE1NYz0xl601PVImeQfFyEy6iT90AvPUL1NNfNw=
116116
github.com/apparentlymart/go-textseg/v13 v13.0.0/go.mod h1:ZK2fH7c4NqDTLtiYLvIkEghdlcqw7yxLeM89kiTRPUo=
117-
github.com/argoproj/argo-cd/v2 v2.8.14 h1:sxRIFxcmORSkBEcbVD5j7NokaLIno8BrjIJyobyIrTs=
118-
github.com/argoproj/argo-cd/v2 v2.8.14/go.mod h1:3GmH9xEJtiWZNfZ5hx1qdzbF2t9gIS/3vNV5vJBmI/g=
117+
github.com/argoproj/argo-cd/v2 v2.8.17 h1:PPAGPj37RBoxWfplu2HSjLJ6bZY75FPgy9h4mcKyxqQ=
118+
github.com/argoproj/argo-cd/v2 v2.8.17/go.mod h1:qdkZvAPT+uurfySoFIlptZ402k/h1ZWuEJ511yd8GOE=
119119
github.com/argoproj/argo-workflows/v3 v3.4.3 h1:4pt7+Rjy9Lzq/r6dWp6wL8mr3ucPHSsGIlWwoP3fueM=
120120
github.com/argoproj/argo-workflows/v3 v3.4.3/go.mod h1:Od1rQK5j9/WefqFaUsIwAqTialDhLlhups0RE/WYzz4=
121121
github.com/argoproj/gitops-engine v0.7.1-0.20231013183858-f15cf615b814 h1:oTaLRbCwjnGtScIX2ZRdIEDsiDxonwh9/BbUxdXrjYc=
@@ -921,8 +921,8 @@ golang.org/x/crypto v0.6.0/go.mod h1:OFC/31mSvZgRz0V1QTNCzfAI1aIRzbiufJtkMIlEp58
921921
golang.org/x/crypto v0.7.0/go.mod h1:pYwdfH91IfpZVANVyUOhSIPZaFoJGxTFbZhFTx+dXZU=
922922
golang.org/x/crypto v0.9.0/go.mod h1:yrmDGqONDYtNj3tH8X9dzUun2m2lzPa9ngI6/RUPGR0=
923923
golang.org/x/crypto v0.10.0/go.mod h1:o4eNf7Ede1fv+hwOwZsTHl9EsPFO6q6ZvYR8vYfY45I=
924-
golang.org/x/crypto v0.19.0 h1:ENy+Az/9Y1vSrlrvBSyna3PITt4tiZLf7sgCjZBX7Wo=
925-
golang.org/x/crypto v0.19.0/go.mod h1:Iy9bg/ha4yyC70EfRS8jz+B6ybOBKMaSxLj6P6oBDfU=
924+
golang.org/x/crypto v0.21.0 h1:X31++rzVUdKhX5sWmSOFZxx8UW/ldWx55cbf08iNAMA=
925+
golang.org/x/crypto v0.21.0/go.mod h1:0BP7YvVV9gBbVKyeTG0Gyn+gZm94bibOW5BjDEYAOMs=
926926
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
927927
golang.org/x/exp v0.0.0-20190306152737-a1d7652674e8/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
928928
golang.org/x/exp v0.0.0-20190510132918-efd6b22b2522/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8=
@@ -1021,8 +1021,8 @@ golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
10211021
golang.org/x/net v0.8.0/go.mod h1:QVkue5JL9kW//ek3r6jTKnTFis1tRmNAW2P1shuFdJc=
10221022
golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
10231023
golang.org/x/net v0.11.0/go.mod h1:2L/ixqYpgIVXmeoSA/4Lu7BzTG4KIyPIryS4IsOd1oQ=
1024-
golang.org/x/net v0.21.0 h1:AQyQV4dYCvJ7vGmJyKki9+PBdyvhkSd8EIx/qb0AYv4=
1025-
golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44=
1024+
golang.org/x/net v0.23.0 h1:7EYJ93RZ9vYSZAIb2x3lnuvqO5zneoD6IvWjuhfxjTs=
1025+
golang.org/x/net v0.23.0/go.mod h1:JKghWKKOSdJwpW2GEx0Ja7fmaKnMsbu+MWVZTokSYmg=
10261026
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
10271027
golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
10281028
golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
@@ -1127,8 +1127,8 @@ golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k=
11271127
golang.org/x/term v0.6.0/go.mod h1:m6U89DPEgQRMq3DNkDClhWw02AUbt2daBVO4cn4Hv9U=
11281128
golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo=
11291129
golang.org/x/term v0.9.0/go.mod h1:M6DEAAIenWoTxdKrOltXcmDY3rSplQUkrvaDU5FcQyo=
1130-
golang.org/x/term v0.17.0 h1:mkTF7LCd6WGJNL3K1Ad7kwxNfYAW6a8a8QqtMblp/4U=
1131-
golang.org/x/term v0.17.0/go.mod h1:lLRBjIVuehSbZlaOtGMbcMncT+aqLLLmKrsjNrUguwk=
1130+
golang.org/x/term v0.18.0 h1:FcHjZXDMxI8mM3nwhX9HlKop4C0YQvCVCdwYl2wOtE8=
1131+
golang.org/x/term v0.18.0/go.mod h1:ILwASektA3OnRv7amZ1xhE/KTR+u50pbXfZ03+6Nx58=
11321132
golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
11331133
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
11341134
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=

0 commit comments

Comments
 (0)