github.com/jfrog/frogbot@v1.1.1-0.20231221090046-821a26f50338/utils/outputwriter/outputwriter.go (about) 1 package outputwriter 2 3 import ( 4 "fmt" 5 "strings" 6 7 "github.com/jfrog/froggit-go/vcsutils" 8 ) 9 10 const ( 11 SecretsEmailCSS = `body { 12 font-family: Arial, sans-serif; 13 background-color: #f5f5f5; 14 } 15 table { 16 border-collapse: collapse; 17 width: 80%; 18 } 19 th, td { 20 padding: 10px; 21 border: 1px solid #ccc; 22 } 23 th { 24 background-color: #f2f2f2; 25 } 26 tr:nth-child(even) { 27 background-color: #f9f9f9; 28 } 29 tr:hover { 30 background-color: #f5f5f5; 31 } 32 .table-container { 33 max-width: 700px; 34 padding: 20px; 35 box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1); 36 border-radius: 10px; 37 overflow: hidden; 38 background-color: #fff; 39 margin-top: 10px; 40 } 41 .ignore-comments { 42 margin-top: 10px; 43 margin-bottom: 5px; 44 border-radius: 5px; 45 }` 46 //#nosec G101 -- full secrets would not be hard coded 47 SecretsEmailHTMLTemplate = ` 48 <!DOCTYPE html> 49 <html> 50 <head> 51 <title>Frogbot Secret Detection</title> 52 <style> 53 %s 54 </style> 55 </head> 56 <body> 57 <div> 58 The following potential exposed secrets in your <a href="%s">%s</a> have been detected by <a href="https://docs.jfrog-applications.jfrog.io/jfrog-applications/frogbot">Frogbot</a> 59 <br/> 60 <table class="table-container"> 61 <thead> 62 <tr> 63 <th>FILE</th> 64 <th>LINE:COLUMN</th> 65 <th>SECRET</th> 66 </tr> 67 </thead> 68 <tbody> 69 %s 70 </tbody> 71 </table> 72 <div class="ignore-comments"> 73 <b>NOTE:</b> If you'd like Frogbot to ignore the lines with the potential secrets, add a comment that includes the <b>jfrog-ignore</b> keyword above the lines with the secrets. 74 </div> 75 </div> 76 </body> 77 </html>` 78 //#nosec G101 -- full secrets would not be hard coded 79 SecretsEmailTableRow = ` 80 <tr> 81 <td> %s </td> 82 <td> %d:%d </td> 83 <td> %s </td> 84 </tr>` 85 ) 86 87 // The OutputWriter interface allows Frogbot output to be written in an appropriate way for each git provider. 88 // Some git providers support markdown only partially, whereas others support it fully. 89 type OutputWriter interface { 90 // Options 91 SetJasOutputFlags(entitled, showCaColumn bool) 92 IsShowingCaColumn() bool 93 IsEntitledForJas() bool 94 SetAvoidExtraMessages(avoidExtraMessages bool) 95 AvoidExtraMessages() bool 96 SetPullRequestCommentTitle(pullRequestCommentTitle string) 97 PullRequestCommentTitle() string 98 SetHasInternetConnection(connected bool) 99 HasInternetConnection() bool 100 // VCS info 101 VcsProvider() vcsutils.VcsProvider 102 SetVcsProvider(provider vcsutils.VcsProvider) 103 // Markdown interface 104 FormattedSeverity(severity, applicability string) string 105 Separator() string 106 MarkInCenter(content string) string 107 MarkAsDetails(summary string, subTitleDepth int, content string) string 108 MarkAsTitle(title string, subTitleDepth int) string 109 Image(source ImageSource) string 110 } 111 112 type MarkdownOutput struct { 113 pullRequestCommentTitle string 114 avoidExtraMessages bool 115 showCaColumn bool 116 entitledForJas bool 117 hasInternetConnection bool 118 vcsProvider vcsutils.VcsProvider 119 } 120 121 func (mo *MarkdownOutput) SetVcsProvider(provider vcsutils.VcsProvider) { 122 mo.vcsProvider = provider 123 } 124 125 func (mo *MarkdownOutput) VcsProvider() vcsutils.VcsProvider { 126 return mo.vcsProvider 127 } 128 129 func (mo *MarkdownOutput) SetAvoidExtraMessages(avoidExtraMessages bool) { 130 mo.avoidExtraMessages = avoidExtraMessages 131 } 132 133 func (mo *MarkdownOutput) AvoidExtraMessages() bool { 134 return mo.avoidExtraMessages 135 } 136 137 func (mo *MarkdownOutput) SetHasInternetConnection(connected bool) { 138 mo.hasInternetConnection = connected 139 } 140 141 func (mo *MarkdownOutput) HasInternetConnection() bool { 142 return mo.hasInternetConnection 143 } 144 145 func (mo *MarkdownOutput) SetJasOutputFlags(entitled, showCaColumn bool) { 146 mo.entitledForJas = entitled 147 mo.showCaColumn = showCaColumn 148 } 149 150 func (mo *MarkdownOutput) SetPullRequestCommentTitle(pullRequestCommentTitle string) { 151 mo.pullRequestCommentTitle = pullRequestCommentTitle 152 } 153 154 func (mo *MarkdownOutput) IsShowingCaColumn() bool { 155 return mo.showCaColumn 156 } 157 158 func (mo *MarkdownOutput) IsEntitledForJas() bool { 159 return mo.entitledForJas 160 } 161 162 func (mo *MarkdownOutput) PullRequestCommentTitle() string { 163 return mo.pullRequestCommentTitle 164 } 165 166 func GetCompatibleOutputWriter(provider vcsutils.VcsProvider) OutputWriter { 167 switch provider { 168 case vcsutils.BitbucketServer: 169 return &SimplifiedOutput{MarkdownOutput{vcsProvider: provider, hasInternetConnection: true}} 170 default: 171 return &StandardOutput{MarkdownOutput{vcsProvider: provider, hasInternetConnection: true}} 172 } 173 } 174 175 func MarkdownComment(text string) string { 176 return fmt.Sprintf("\n\n[comment]: <> (%s)\n", text) 177 } 178 179 func MarkAsBold(content string) string { 180 return fmt.Sprintf("**%s**", content) 181 } 182 183 func MarkAsQuote(content string) string { 184 return fmt.Sprintf("`%s`", content) 185 } 186 187 func MarkAsLink(content, link string) string { 188 return fmt.Sprintf("[%s](%s)", content, link) 189 } 190 191 func SectionDivider() string { 192 return "\n---" 193 } 194 195 func MarkAsCodeSnippet(snippet string) string { 196 return fmt.Sprintf("```\n%s\n```", snippet) 197 } 198 199 func WriteContent(builder *strings.Builder, contents ...string) { 200 for _, content := range contents { 201 fmt.Fprintf(builder, "\n%s", content) 202 } 203 } 204 205 func WriteNewLine(builder *strings.Builder) { 206 builder.WriteString("\n") 207 }