mirror of
https://github.com/securego/gosec.git
synced 2024-12-26 12:35:52 +00:00
187 lines
4.7 KiB
Go
187 lines
4.7 KiB
Go
package gas_test
|
|
|
|
import (
|
|
"go/ast"
|
|
|
|
"github.com/GoASTScanner/gas"
|
|
"github.com/GoASTScanner/gas/rules"
|
|
"github.com/GoASTScanner/gas/testutils"
|
|
. "github.com/onsi/ginkgo"
|
|
. "github.com/onsi/gomega"
|
|
)
|
|
|
|
var _ = Describe("Issue", func() {
|
|
|
|
Context("when creating a new issue", func() {
|
|
It("should create a code snippet from the specified ast.Node", func() {
|
|
var target *ast.BasicLit
|
|
source := `package main
|
|
const foo = "bar"
|
|
func main(){
|
|
println(foo)
|
|
}
|
|
`
|
|
pkg := testutils.NewTestPackage()
|
|
defer pkg.Close()
|
|
pkg.AddFile("foo.go", source)
|
|
ctx := pkg.CreateContext("foo.go")
|
|
v := testutils.NewMockVisitor()
|
|
v.Callback = func(n ast.Node, ctx *gas.Context) bool {
|
|
if node, ok := n.(*ast.BasicLit); ok {
|
|
target = node
|
|
return false
|
|
}
|
|
return true
|
|
}
|
|
v.Context = ctx
|
|
ast.Walk(v, ctx.Root)
|
|
Expect(target).ShouldNot(BeNil())
|
|
|
|
issue := gas.NewIssue(ctx, target, "", gas.High, gas.High)
|
|
Expect(issue).ShouldNot(BeNil())
|
|
Expect(issue.Code).Should(MatchRegexp(`"bar"`))
|
|
Expect(issue.Line).Should(Equal("2"))
|
|
|
|
})
|
|
|
|
It("should return an error if specific context is not able to be obtained", func() {
|
|
Fail("Not implemented")
|
|
})
|
|
|
|
It("should provide accurate line and file information", func() {
|
|
var target *ast.BasicLit
|
|
source := `package main
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
)
|
|
func main(){
|
|
q := fmt.Sprintf("SELECT * FROM table WHERE %s = ?", os.Args[1]) // nolint: gas
|
|
println(q)
|
|
}
|
|
`
|
|
pkg := testutils.NewTestPackage()
|
|
defer pkg.Close()
|
|
pkg.AddFile("foo.go", source)
|
|
ctx := pkg.CreateContext("foo.go")
|
|
v := testutils.NewMockVisitor()
|
|
v.Callback = func(n ast.Node, ctx *gas.Context) bool {
|
|
if node, ok := n.(*ast.BasicLit); ok {
|
|
target = node
|
|
return false
|
|
}
|
|
return true
|
|
}
|
|
v.Context = ctx
|
|
ast.Walk(v, ctx.Root)
|
|
Expect(target).ShouldNot(BeNil())
|
|
|
|
issue := gas.NewIssue(ctx, target, "", gas.High, gas.High)
|
|
Expect(issue).ShouldNot(BeNil())
|
|
Expect(issue.File).Should(MatchRegexp("foo.go"))
|
|
Expect(issue.Line).Should(Equal("7"))
|
|
})
|
|
|
|
It("should provide accurate line and file information for multi-line statements", func() {
|
|
var target *ast.BinaryExpr
|
|
|
|
source := `package main
|
|
import "os"
|
|
func main(){`
|
|
source += "q := `SELECT * FROM table WHERE` + \n os.Args[1] + `= ?` // nolint: gas\n"
|
|
source += `println(q)}`
|
|
|
|
pkg := testutils.NewTestPackage()
|
|
defer pkg.Close()
|
|
pkg.AddFile("foo.go", source)
|
|
ctx := pkg.CreateContext("foo.go")
|
|
v := testutils.NewMockVisitor()
|
|
v.Callback = func(n ast.Node, ctx *gas.Context) bool {
|
|
if node, ok := n.(*ast.BinaryExpr); ok {
|
|
target = node
|
|
}
|
|
return true
|
|
}
|
|
v.Context = ctx
|
|
ast.Walk(v, ctx.Root)
|
|
Expect(target).ShouldNot(BeNil())
|
|
|
|
// Use SQL rule to check binary expr
|
|
cfg := gas.NewConfig()
|
|
rule, _ := rules.NewSqlStrConcat(cfg)
|
|
issue, err := rule.Match(target, ctx)
|
|
Expect(err).ShouldNot(HaveOccurred())
|
|
Expect(issue).ShouldNot(BeNil())
|
|
Expect(issue.File).Should(MatchRegexp("foo.go"))
|
|
Expect(issue.Line).Should(MatchRegexp("3-4"))
|
|
})
|
|
|
|
It("should maintain the provided severity score", func() {
|
|
var target *ast.BasicLit
|
|
source := `package main
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
)
|
|
func main(){
|
|
q := fmt.Sprintf("SELECT * FROM table WHERE %s = ?", os.Args[1]) // nolint: gas
|
|
println(q)
|
|
}
|
|
`
|
|
pkg := testutils.NewTestPackage()
|
|
defer pkg.Close()
|
|
pkg.AddFile("foo.go", source)
|
|
ctx := pkg.CreateContext("foo.go")
|
|
v := testutils.NewMockVisitor()
|
|
v.Callback = func(n ast.Node, ctx *gas.Context) bool {
|
|
if node, ok := n.(*ast.BasicLit); ok {
|
|
target = node
|
|
return false
|
|
}
|
|
return true
|
|
}
|
|
v.Context = ctx
|
|
ast.Walk(v, ctx.Root)
|
|
Expect(target).ShouldNot(BeNil())
|
|
|
|
issue := gas.NewIssue(ctx, target, "", gas.High, gas.High)
|
|
Expect(issue).ShouldNot(BeNil())
|
|
Expect(issue.Severity).Should(Equal(gas.High))
|
|
})
|
|
|
|
It("should maintain the provided confidence score", func() {
|
|
var target *ast.BasicLit
|
|
source := `package main
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
)
|
|
func main(){
|
|
q := fmt.Sprintf("SELECT * FROM table WHERE %s = ?", os.Args[1]) // nolint: gas
|
|
println(q)
|
|
}
|
|
`
|
|
pkg := testutils.NewTestPackage()
|
|
defer pkg.Close()
|
|
pkg.AddFile("foo.go", source)
|
|
ctx := pkg.CreateContext("foo.go")
|
|
v := testutils.NewMockVisitor()
|
|
v.Callback = func(n ast.Node, ctx *gas.Context) bool {
|
|
if node, ok := n.(*ast.BasicLit); ok {
|
|
target = node
|
|
return false
|
|
}
|
|
return true
|
|
}
|
|
v.Context = ctx
|
|
ast.Walk(v, ctx.Root)
|
|
Expect(target).ShouldNot(BeNil())
|
|
|
|
issue := gas.NewIssue(ctx, target, "", gas.High, gas.High)
|
|
Expect(issue).ShouldNot(BeNil())
|
|
Expect(issue.Confidence).Should(Equal(gas.High))
|
|
})
|
|
|
|
})
|
|
|
|
})
|