github.com/ouraigua/jenkins-library@v0.0.0-20231028010029-fbeaf2f3aa9b/pkg/codeql/codeql.go (about)

     1  package codeql
     2  
     3  import (
     4  	"context"
     5  
     6  	piperGithub "github.com/SAP/jenkins-library/pkg/github"
     7  	"github.com/google/go-github/v45/github"
     8  )
     9  
    10  type CodeqlScanAudit interface {
    11  	GetVulnerabilities(analyzedRef string, state string) error
    12  }
    13  
    14  type githubCodeqlScanningService interface {
    15  	ListAlertsForRepo(ctx context.Context, owner, repo string, opts *github.AlertListOptions) ([]*github.Alert, *github.Response, error)
    16  }
    17  
    18  const auditStateOpen string = "open"
    19  const auditStateDismissed string = "dismissed"
    20  const codeqlToolName string = "CodeQL"
    21  const perPageCount int = 100
    22  
    23  func NewCodeqlScanAuditInstance(serverUrl, owner, repository, token string, trustedCerts []string) CodeqlScanAuditInstance {
    24  	return CodeqlScanAuditInstance{serverUrl: serverUrl, owner: owner, repository: repository, token: token, trustedCerts: trustedCerts}
    25  }
    26  
    27  type CodeqlScanAuditInstance struct {
    28  	serverUrl        string
    29  	owner            string
    30  	repository       string
    31  	token            string
    32  	trustedCerts     []string
    33  	alertListoptions github.AlertListOptions
    34  }
    35  
    36  func (codeqlScanAudit *CodeqlScanAuditInstance) GetVulnerabilities(analyzedRef string) ([]CodeqlFindings, error) {
    37  	apiUrl := getApiUrl(codeqlScanAudit.serverUrl)
    38  	ctx, client, err := piperGithub.
    39  		NewClientBuilder(codeqlScanAudit.token, apiUrl).
    40  		WithTrustedCerts(codeqlScanAudit.trustedCerts).Build()
    41  	if err != nil {
    42  		return []CodeqlFindings{}, err
    43  	}
    44  
    45  	return getVulnerabilitiesFromClient(ctx, client.CodeScanning, analyzedRef, codeqlScanAudit)
    46  }
    47  
    48  func getVulnerabilitiesFromClient(ctx context.Context, codeScanning githubCodeqlScanningService, analyzedRef string, codeqlScanAudit *CodeqlScanAuditInstance) ([]CodeqlFindings, error) {
    49  	page := 1
    50  	audited := 0
    51  	totalAlerts := 0
    52  
    53  	for page != 0 {
    54  		alertOptions := github.AlertListOptions{
    55  			State: "",
    56  			Ref:   analyzedRef,
    57  			ListOptions: github.ListOptions{
    58  				Page:    page,
    59  				PerPage: perPageCount,
    60  			},
    61  		}
    62  
    63  		alerts, response, err := codeScanning.ListAlertsForRepo(ctx, codeqlScanAudit.owner, codeqlScanAudit.repository, &alertOptions)
    64  		if err != nil {
    65  			return []CodeqlFindings{}, err
    66  		}
    67  
    68  		page = response.NextPage
    69  
    70  		for _, alert := range alerts {
    71  			if *alert.Tool.Name != codeqlToolName {
    72  				continue
    73  			}
    74  
    75  			if *alert.State == auditStateDismissed {
    76  				audited += 1
    77  				totalAlerts += 1
    78  			}
    79  
    80  			if *alert.State == auditStateOpen {
    81  				totalAlerts += 1
    82  			}
    83  		}
    84  	}
    85  
    86  	auditAll := CodeqlFindings{
    87  		ClassificationName: "Audit All",
    88  		Total:              totalAlerts,
    89  		Audited:            audited,
    90  	}
    91  	codeqlScanning := []CodeqlFindings{auditAll}
    92  
    93  	return codeqlScanning, nil
    94  }
    95  
    96  func getApiUrl(serverUrl string) string {
    97  	if serverUrl == "https://github.com" {
    98  		return "https://api.github.com"
    99  	}
   100  
   101  	return (serverUrl + "/api/v3")
   102  }