appsec renaming, part 4

This commit is contained in:
Sebastien Blot 2023-12-04 22:36:25 +01:00
parent 8046690219
commit 2089ad6663
No known key found for this signature in database
GPG key ID: DFC2902F40449F6A
20 changed files with 306 additions and 306 deletions

View file

@ -62,9 +62,9 @@ func NewCmdAppsecRulesInstall() *cobra.Command {
Args: cobra.MinimumNArgs(1),
DisableAutoGenTag: true,
ValidArgsFunction: func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
return compAllItems(cwhub.WAAP_RULES, args, toComplete)
return compAllItems(cwhub.APPSEC_RULES, args, toComplete)
},
RunE: itemsInstallRunner(hubItemTypes[cwhub.WAAP_RULES]),
RunE: itemsInstallRunner(hubItemTypes[cwhub.APPSEC_RULES]),
}
flags := cmdAppsecRulesInstall.Flags()
@ -84,9 +84,9 @@ func NewCmdAppsecRulesRemove() *cobra.Command {
Aliases: []string{"delete"},
DisableAutoGenTag: true,
ValidArgsFunction: func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
return compInstalledItems(cwhub.WAAP_RULES, args, toComplete)
return compInstalledItems(cwhub.APPSEC_RULES, args, toComplete)
},
RunE: itemsRemoveRunner(hubItemTypes[cwhub.WAAP_RULES]),
RunE: itemsRemoveRunner(hubItemTypes[cwhub.APPSEC_RULES]),
}
flags := cmdAppsecRulesRemove.Flags()
@ -105,9 +105,9 @@ func NewCmdAppsecRulesUpgrade() *cobra.Command {
Example: `cscli appsec-rules upgrade crowdsecurity/crs`,
DisableAutoGenTag: true,
ValidArgsFunction: func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
return compInstalledItems(cwhub.WAAP_RULES, args, toComplete)
return compInstalledItems(cwhub.APPSEC_RULES, args, toComplete)
},
RunE: itemsUpgradeRunner(hubItemTypes[cwhub.WAAP_RULES]),
RunE: itemsUpgradeRunner(hubItemTypes[cwhub.APPSEC_RULES]),
}
flags := cmdAppsecRulesUpgrade.Flags()
@ -119,7 +119,7 @@ func NewCmdAppsecRulesUpgrade() *cobra.Command {
func AppsecRulesInspectRunner(itemType hubItemType) func(cmd *cobra.Command, args []string) error {
return func(cmd *cobra.Command, args []string) error {
f := itemsInspectRunner(hubItemTypes[cwhub.WAAP_RULES])
f := itemsInspectRunner(hubItemTypes[cwhub.APPSEC_RULES])
if err := f(cmd, args); err != nil {
return err
}
@ -161,9 +161,9 @@ func NewCmdAppsecRulesInspect() *cobra.Command {
Args: cobra.MinimumNArgs(1),
DisableAutoGenTag: true,
ValidArgsFunction: func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
return compInstalledItems(cwhub.WAAP_RULES, args, toComplete)
return compInstalledItems(cwhub.APPSEC_RULES, args, toComplete)
},
RunE: AppsecRulesInspectRunner(hubItemTypes[cwhub.WAAP_RULES]),
RunE: AppsecRulesInspectRunner(hubItemTypes[cwhub.APPSEC_RULES]),
}
flags := cmdAppsecRulesInspect.Flags()
@ -182,7 +182,7 @@ func NewCmdAppsecRulesList() *cobra.Command {
cscli appsec-rules list -a
cscli appsec-rules list crowdsecurity/crs`,
DisableAutoGenTag: true,
RunE: itemsListRunner(hubItemTypes[cwhub.WAAP_RULES]),
RunE: itemsListRunner(hubItemTypes[cwhub.APPSEC_RULES]),
}
flags := cmdAppsecRulesList.Flags()

View file

@ -19,9 +19,9 @@ import (
)
var HubTest hubtest.HubTest
var HubWaapTests hubtest.HubTest
var HubAppsecTests hubtest.HubTest
var hubPtr *hubtest.HubTest
var isWaapTest bool
var isAppsecTest bool
func NewHubTestCmd() *cobra.Command {
var hubPath string
@ -41,14 +41,14 @@ func NewHubTestCmd() *cobra.Command {
return fmt.Errorf("unable to load hubtest: %+v", err)
}
HubWaapTests, err = hubtest.NewHubTest(hubPath, crowdsecPath, cscliPath, true)
HubAppsecTests, err = hubtest.NewHubTest(hubPath, crowdsecPath, cscliPath, true)
if err != nil {
return fmt.Errorf("unable to load waap specific hubtest: %+v", err)
return fmt.Errorf("unable to load appsec specific hubtest: %+v", err)
}
/*commands will use the hubPtr, will point to the default hubTest object, or the one dedicated to WAAP tests*/
/*commands will use the hubPtr, will point to the default hubTest object, or the one dedicated to appsec tests*/
hubPtr = &HubTest
if isWaapTest {
hubPtr = &HubWaapTests
if isAppsecTest {
hubPtr = &HubAppsecTests
}
return nil
},
@ -57,7 +57,7 @@ func NewHubTestCmd() *cobra.Command {
cmdHubTest.PersistentFlags().StringVar(&hubPath, "hub", ".", "Path to hub folder")
cmdHubTest.PersistentFlags().StringVar(&crowdsecPath, "crowdsec", "crowdsec", "Path to crowdsec")
cmdHubTest.PersistentFlags().StringVar(&cscliPath, "cscli", "cscli", "Path to cscli")
cmdHubTest.PersistentFlags().BoolVar(&isWaapTest, "waap", false, "Command relates to WAAP tests")
cmdHubTest.PersistentFlags().BoolVar(&isAppsecTest, "appsec", false, "Command relates to appsec tests")
cmdHubTest.AddCommand(NewHubTestCreateCmd())
cmdHubTest.AddCommand(NewHubTestRunCmd())
@ -105,7 +105,7 @@ cscli hubtest create my-scenario-test --parsers crowdsecurity/nginx --scenarios
configFilePath := filepath.Join(testPath, "config.yaml")
configFileData := &hubtest.HubTestItemConfig{}
if logType == "waap" {
if logType == "appsec" {
//create empty nuclei template file
nucleiFileName := fmt.Sprintf("%s.yaml", testName)
nucleiFilePath := filepath.Join(testPath, nucleiFileName)
@ -114,7 +114,7 @@ cscli hubtest create my-scenario-test --parsers crowdsecurity/nginx --scenarios
return err
}
nucleiFile.Close()
configFileData.WaapRules = []string{"your_rule_here.yaml"}
configFileData.AppsecRules = []string{"your_rule_here.yaml"}
configFileData.NucleiTemplate = nucleiFileName
fmt.Println()
fmt.Printf(" Test name : %s\n", testName)
@ -246,7 +246,7 @@ func NewHubTestRunCmd() *cobra.Command {
success := true
testResult := make(map[string]bool)
for _, test := range hubPtr.Tests {
if test.AutoGen && !isWaapTest {
if test.AutoGen && !isAppsecTest {
if test.ParserAssert.AutoGenAssert {
log.Warningf("Assert file '%s' is empty, generating assertion:", test.ParserAssert.File)
fmt.Println()
@ -400,9 +400,9 @@ func NewHubTestInfoCmd() *cobra.Command {
fmt.Println()
fmt.Printf(" Test name : %s\n", test.Name)
fmt.Printf(" Test path : %s\n", test.Path)
if isWaapTest {
if isAppsecTest {
fmt.Printf(" Nuclei Template : %s\n", test.Config.NucleiTemplate)
fmt.Printf(" Waap Rules : %s\n", strings.Join(test.Config.WaapRules, ", "))
fmt.Printf(" Appsec Rules : %s\n", strings.Join(test.Config.AppsecRules, ", "))
} else {
fmt.Printf(" Log file : %s\n", filepath.Join(test.Path, test.Config.LogFile))
fmt.Printf(" Parser assertion file : %s\n", filepath.Join(test.Path, hubtest.ParserAssertFileName))
@ -452,27 +452,27 @@ func NewHubTestCoverageCmd() *cobra.Command {
var showParserCov bool
var showScenarioCov bool
var showOnlyPercent bool
var showWaapCov bool
var showAppsecCov bool
var cmdHubTestCoverage = &cobra.Command{
Use: "coverage",
Short: "coverage",
DisableAutoGenTag: true,
RunE: func(cmd *cobra.Command, args []string) error {
//for this one we explictely don't do for Waap
//for this one we explicitly don't do for appsec
if err := HubTest.LoadAllTests(); err != nil {
return fmt.Errorf("unable to load all tests: %+v", err)
}
var err error
scenarioCoverage := []hubtest.Coverage{}
parserCoverage := []hubtest.Coverage{}
waapRuleCoverage := []hubtest.Coverage{}
appsecRuleCoverage := []hubtest.Coverage{}
scenarioCoveragePercent := 0
parserCoveragePercent := 0
waapRuleCoveragePercent := 0
appsecRuleCoveragePercent := 0
// if both are false (flag by default), show both
showAll := !showScenarioCov && !showParserCov && !showWaapCov
showAll := !showScenarioCov && !showParserCov && !showAppsecCov
if showParserCov || showAll {
parserCoverage, err = HubTest.GetParsersCoverage()
@ -504,30 +504,30 @@ func NewHubTestCoverageCmd() *cobra.Command {
scenarioCoveragePercent = int(math.Round((float64(scenarioTested) / float64(len(scenarioCoverage)) * 100)))
}
if showWaapCov || showAll {
waapRuleCoverage, err = HubTest.GetWaapCoverage()
if showAppsecCov || showAll {
appsecRuleCoverage, err = HubTest.GetAppsecCoverage()
if err != nil {
return fmt.Errorf("while getting scenario coverage: %s", err)
}
waapRuleTested := 0
for _, test := range waapRuleCoverage {
appsecRuleTested := 0
for _, test := range appsecRuleCoverage {
if test.TestsCount > 0 {
waapRuleTested++
appsecRuleTested++
}
}
waapRuleCoveragePercent = int(math.Round((float64(waapRuleTested) / float64(len(waapRuleCoverage)) * 100)))
appsecRuleCoveragePercent = int(math.Round((float64(appsecRuleTested) / float64(len(appsecRuleCoverage)) * 100)))
}
if showOnlyPercent {
if showAll {
fmt.Printf("parsers=%d%%\nscenarios=%d%%\nwaap_rules=%d%%", parserCoveragePercent, scenarioCoveragePercent, waapRuleCoveragePercent)
fmt.Printf("parsers=%d%%\nscenarios=%d%%\nappsec_rules=%d%%", parserCoveragePercent, scenarioCoveragePercent, appsecRuleCoveragePercent)
} else if showParserCov {
fmt.Printf("parsers=%d%%", parserCoveragePercent)
} else if showScenarioCov {
fmt.Printf("scenarios=%d%%", scenarioCoveragePercent)
} else if showWaapCov {
fmt.Printf("waap_rules=%d%%", waapRuleCoveragePercent)
} else if showAppsecCov {
fmt.Printf("appsec_rules=%d%%", appsecRuleCoveragePercent)
}
os.Exit(0)
}
@ -542,8 +542,8 @@ func NewHubTestCoverageCmd() *cobra.Command {
hubTestScenarioCoverageTable(color.Output, scenarioCoverage)
}
if showWaapCov || showAll {
hubTestWaapRuleCoverageTable(color.Output, waapRuleCoverage)
if showAppsecCov || showAll {
hubTestAppsecRuleCoverageTable(color.Output, appsecRuleCoverage)
}
fmt.Println()
@ -553,8 +553,8 @@ func NewHubTestCoverageCmd() *cobra.Command {
if showScenarioCov || showAll {
fmt.Printf("SCENARIOS : %d%% of coverage\n", scenarioCoveragePercent)
}
if showWaapCov || showAll {
fmt.Printf("WAAP RULES : %d%% of coverage\n", waapRuleCoveragePercent)
if showAppsecCov || showAll {
fmt.Printf("APPSEC RULES : %d%% of coverage\n", appsecRuleCoveragePercent)
}
case "json":
dump, err := json.MarshalIndent(parserCoverage, "", " ")
@ -567,7 +567,7 @@ func NewHubTestCoverageCmd() *cobra.Command {
return err
}
fmt.Printf("%s", dump)
dump, err = json.MarshalIndent(waapRuleCoverage, "", " ")
dump, err = json.MarshalIndent(appsecRuleCoverage, "", " ")
if err != nil {
return err
}
@ -583,7 +583,7 @@ func NewHubTestCoverageCmd() *cobra.Command {
cmdHubTestCoverage.PersistentFlags().BoolVar(&showOnlyPercent, "percent", false, "Show only percentages of coverage")
cmdHubTestCoverage.PersistentFlags().BoolVar(&showParserCov, "parsers", false, "Show only parsers coverage")
cmdHubTestCoverage.PersistentFlags().BoolVar(&showScenarioCov, "scenarios", false, "Show only scenarios coverage")
cmdHubTestCoverage.PersistentFlags().BoolVar(&showWaapCov, "waap", false, "Show only waap coverage")
cmdHubTestCoverage.PersistentFlags().BoolVar(&showAppsecCov, "appsec", false, "Show only appsec coverage")
return cmdHubTestCoverage
}

View file

@ -61,9 +61,9 @@ func hubTestParserCoverageTable(out io.Writer, coverage []hubtest.Coverage) {
t.Render()
}
func hubTestWaapRuleCoverageTable(out io.Writer, coverage []hubtest.Coverage) {
func hubTestAppsecRuleCoverageTable(out io.Writer, coverage []hubtest.Coverage) {
t := newLightTable(out)
t.SetHeaders("Waap Rule", "Status", "Number of tests")
t.SetHeaders("Appsec Rule", "Status", "Number of tests")
t.SetHeaderAlignment(table.AlignLeft, table.AlignLeft, table.AlignLeft)
t.SetAlignment(table.AlignLeft, table.AlignLeft, table.AlignLeft)

View file

@ -32,7 +32,7 @@ func ShowMetrics(hubItem *cwhub.Item) error {
return err
}
}
case cwhub.WAAP_RULES:
case cwhub.APPSEC_RULES:
log.Error("FIXME: not implemented yet")
default:
// no metrics for this item type

View file

@ -63,8 +63,8 @@ func FormatPrometheusMetrics(out io.Writer, url string, formatType string) error
lapi_machine_stats := map[string]map[string]map[string]int{}
lapi_bouncer_stats := map[string]map[string]map[string]int{}
decisions_stats := map[string]map[string]map[string]int{}
waap_engine_stats := map[string]map[string]int{}
waap_rule_stats := map[string]map[string]map[string]int{}
appsec_engine_stats := map[string]map[string]int{}
appsec_rule_stats := map[string]map[string]map[string]int{}
alerts_stats := map[string]int{}
stash_stats := map[string]struct {
Type string
@ -228,26 +228,26 @@ func FormatPrometheusMetrics(out io.Writer, url string, formatType string) error
Type string
Count int
}{Type: mtype, Count: ival}
case "cs_waf_reqs_total":
if _, ok := waap_engine_stats[metric.Labels["waap_engine"]]; !ok {
waap_engine_stats[metric.Labels["waap_engine"]] = make(map[string]int, 0)
case "cs_appsec_reqs_total":
if _, ok := appsec_engine_stats[metric.Labels["appsec_engine"]]; !ok {
appsec_engine_stats[metric.Labels["appsec_engine"]] = make(map[string]int, 0)
}
waap_engine_stats[metric.Labels["waap_engine"]]["processed"] = ival
case "cs_waf_block_total":
if _, ok := waap_engine_stats[metric.Labels["waap_engine"]]; !ok {
waap_engine_stats[metric.Labels["waap_engine"]] = make(map[string]int, 0)
appsec_engine_stats[metric.Labels["appsec_engine"]]["processed"] = ival
case "cs_appsec_block_total":
if _, ok := appsec_engine_stats[metric.Labels["appsec_engine"]]; !ok {
appsec_engine_stats[metric.Labels["appsec_engine"]] = make(map[string]int, 0)
}
waap_engine_stats[metric.Labels["waap_engine"]]["blocked"] = ival
case "cs_waf_rule_hits":
waapEngine := metric.Labels["waap_engine"]
appsec_engine_stats[metric.Labels["appsec_engine"]]["blocked"] = ival
case "cs_appsec_rule_hits":
appsecEngine := metric.Labels["appsec_engine"]
ruleID := metric.Labels["rule_name"]
if _, ok := waap_rule_stats[waapEngine]; !ok {
waap_rule_stats[waapEngine] = make(map[string]map[string]int, 0)
if _, ok := appsec_rule_stats[appsecEngine]; !ok {
appsec_rule_stats[appsecEngine] = make(map[string]map[string]int, 0)
}
if _, ok := waap_rule_stats[waapEngine][ruleID]; !ok {
waap_rule_stats[waapEngine][ruleID] = make(map[string]int, 0)
if _, ok := appsec_rule_stats[appsecEngine][ruleID]; !ok {
appsec_rule_stats[appsecEngine][ruleID] = make(map[string]int, 0)
}
waap_rule_stats[waapEngine][ruleID]["triggered"] = ival
appsec_rule_stats[appsecEngine][ruleID]["triggered"] = ival
default:
log.Infof("unknown: %+v", fam.Name)
continue
@ -266,8 +266,8 @@ func FormatPrometheusMetrics(out io.Writer, url string, formatType string) error
decisionStatsTable(out, decisions_stats)
alertStatsTable(out, alerts_stats)
stashStatsTable(out, stash_stats)
waapMetricsToTable(out, waap_engine_stats)
waapRulesToTable(out, waap_rule_stats)
appsecMetricsToTable(out, appsec_engine_stats)
appsecRulesToTable(out, appsec_rule_stats)
return nil
}

View file

@ -113,31 +113,31 @@ func acquisStatsTable(out io.Writer, stats map[string]map[string]int) {
}
}
func waapMetricsToTable(out io.Writer, metrics map[string]map[string]int) {
func appsecMetricsToTable(out io.Writer, metrics map[string]map[string]int) {
t := newTable(out)
t.SetRowLines(false)
t.SetHeaders("WAF Engine", "Processed", "Blocked")
t.SetHeaders("Appsec Engine", "Processed", "Blocked")
t.SetAlignment(table.AlignLeft, table.AlignLeft)
keys := []string{"processed", "blocked"}
if numRows, err := metricsToTable(t, metrics, keys); err != nil {
log.Warningf("while collecting waap stats: %s", err)
log.Warningf("while collecting appsec stats: %s", err)
} else if numRows > 0 {
renderTableTitle(out, "\nWaap Metrics:")
renderTableTitle(out, "\nAppsec Metrics:")
t.Render()
}
}
func waapRulesToTable(out io.Writer, metrics map[string]map[string]map[string]int) {
for waapEngine, waapEngineRulesStats := range metrics {
func appsecRulesToTable(out io.Writer, metrics map[string]map[string]map[string]int) {
for appsecEngine, appsecEngineRulesStats := range metrics {
t := newTable(out)
t.SetRowLines(false)
t.SetHeaders("Rule ID", "Triggered")
t.SetAlignment(table.AlignLeft, table.AlignLeft)
keys := []string{"triggered"}
if numRows, err := metricsToTable(t, waapEngineRulesStats, keys); err != nil {
log.Warningf("while collecting waap rules stats: %s", err)
if numRows, err := metricsToTable(t, appsecEngineRulesStats, keys); err != nil {
log.Warningf("while collecting appsec rules stats: %s", err)
} else if numRows > 0 {
renderTableTitle(out, fmt.Sprintf("\nWaap '%s' Rules Metrics:", waapEngine))
renderTableTitle(out, fmt.Sprintf("\nAppsec '%s' Rules Metrics:", appsecEngine))
t.Render()
}
}

View file

@ -22,7 +22,7 @@ LOOP:
if !event.Process {
continue
}
/*Waap is going to generate 2 events:
/*Application security engine is going to generate 2 events:
- one that is treated as a log and can go to scenarios
- another one that will go directly to LAPI*/
if event.Type == types.APPSEC {

View file

@ -31,7 +31,7 @@ var (
DefaultAuthCacheDuration = (1 * time.Minute)
)
// configuration structure of the acquis for the Waap
// configuration structure of the acquis for the application security engine
type AppsecSourceConfig struct {
ListenAddr string `yaml:"listen_addr"`
CertFilePath string `yaml:"cert_file"`
@ -44,7 +44,7 @@ type AppsecSourceConfig struct {
configuration.DataSourceCommonCfg `yaml:",inline"`
}
// runtime structure of WaapSourceConfig
// runtime structure of AppsecSourceConfig
type AppsecSource struct {
config AppsecSourceConfig
logger *log.Entry
@ -210,7 +210,7 @@ func (w *AppsecSource) Configure(yamlConfig []byte, logger *log.Entry) error {
logger: w.logger.WithFields(log.Fields{
"uuid": appsecRunnerUUID,
}),
WaapRuntime: &wrt,
AppsecRuntime: &wrt,
}
err := runner.Init(appsecCfg.GetDataDir())
if err != nil {
@ -345,15 +345,15 @@ func (w *AppsecSource) appsecHandler(rw http.ResponseWriter, r *http.Request) {
rw.WriteHeader(http.StatusInternalServerError)
return
}
parsedRequest.WaapEngine = w.config.Name
parsedRequest.AppsecEngine = w.config.Name
AppsecReqCounter.With(prometheus.Labels{"source": parsedRequest.RemoteAddrNormalized, "appsec_engine": parsedRequest.WaapEngine}).Inc()
AppsecReqCounter.With(prometheus.Labels{"source": parsedRequest.RemoteAddrNormalized, "appsec_engine": parsedRequest.AppsecEngine}).Inc()
w.InChan <- parsedRequest
response := <-parsedRequest.ResponseChannel
if response.InBandInterrupt {
AppsecBlockCounter.With(prometheus.Labels{"source": parsedRequest.RemoteAddrNormalized, "appsec_engine": parsedRequest.WaapEngine}).Inc()
AppsecBlockCounter.With(prometheus.Labels{"source": parsedRequest.RemoteAddrNormalized, "appsec_engine": parsedRequest.AppsecEngine}).Inc()
}
appsecResponse := w.AppsecRuntime.GenerateResponse(response)

View file

@ -15,15 +15,15 @@ import (
"gopkg.in/tomb.v2"
)
// that's the runtime structure of the WAAP as seen from the acquis
// that's the runtime structure of the Application security engine as seen from the acquis
type AppsecRunner struct {
outChan chan types.Event
inChan chan waf.ParsedRequest
UUID string
WaapRuntime *waf.AppsecRuntimeConfig //this holds the actual waap runtime config, rules, remediations, hooks etc.
WaapInbandEngine coraza.WAF
WaapOutbandEngine coraza.WAF
logger *log.Entry
outChan chan types.Event
inChan chan waf.ParsedRequest
UUID string
AppsecRuntime *waf.AppsecRuntimeConfig //this holds the actual appsec runtime config, rules, remediations, hooks etc.
AppsecInbandEngine coraza.WAF
AppsecOutbandEngine coraza.WAF
logger *log.Entry
}
func (r *AppsecRunner) Init(datadir string) error {
@ -33,11 +33,11 @@ func (r *AppsecRunner) Init(datadir string) error {
inBandRules := ""
outOfBandRules := ""
for _, collection := range r.WaapRuntime.InBandRules {
for _, collection := range r.AppsecRuntime.InBandRules {
inBandRules += collection.String()
}
for _, collection := range r.WaapRuntime.OutOfBandRules {
for _, collection := range r.AppsecRuntime.OutOfBandRules {
outOfBandRules += collection.String()
}
inBandLogger := r.logger.Dup().WithField("band", "inband")
@ -45,52 +45,52 @@ func (r *AppsecRunner) Init(datadir string) error {
//setting up inband engine
inbandCfg := coraza.NewWAFConfig().WithDirectives(inBandRules).WithRootFS(fs).WithDebugLogger(waf.NewCrzLogger(inBandLogger))
if !r.WaapRuntime.Config.InbandOptions.DisableBodyInspection {
if !r.AppsecRuntime.Config.InbandOptions.DisableBodyInspection {
inbandCfg = inbandCfg.WithRequestBodyAccess()
} else {
log.Warningf("Disabling body inspection, Inband rules will not be able to match on body's content.")
}
if r.WaapRuntime.Config.InbandOptions.RequestBodyInMemoryLimit != nil {
inbandCfg = inbandCfg.WithRequestBodyInMemoryLimit(*r.WaapRuntime.Config.InbandOptions.RequestBodyInMemoryLimit)
if r.AppsecRuntime.Config.InbandOptions.RequestBodyInMemoryLimit != nil {
inbandCfg = inbandCfg.WithRequestBodyInMemoryLimit(*r.AppsecRuntime.Config.InbandOptions.RequestBodyInMemoryLimit)
}
r.WaapInbandEngine, err = coraza.NewWAF(inbandCfg)
r.AppsecInbandEngine, err = coraza.NewWAF(inbandCfg)
if err != nil {
return fmt.Errorf("unable to initialize inband engine : %w", err)
}
//setting up outband engine
outbandCfg := coraza.NewWAFConfig().WithDirectives(outOfBandRules).WithRootFS(fs).WithDebugLogger(waf.NewCrzLogger(outBandLogger))
if !r.WaapRuntime.Config.OutOfBandOptions.DisableBodyInspection {
if !r.AppsecRuntime.Config.OutOfBandOptions.DisableBodyInspection {
outbandCfg = outbandCfg.WithRequestBodyAccess()
} else {
log.Warningf("Disabling body inspection, Out of band rules will not be able to match on body's content.")
}
if r.WaapRuntime.Config.OutOfBandOptions.RequestBodyInMemoryLimit != nil {
outbandCfg = outbandCfg.WithRequestBodyInMemoryLimit(*r.WaapRuntime.Config.OutOfBandOptions.RequestBodyInMemoryLimit)
if r.AppsecRuntime.Config.OutOfBandOptions.RequestBodyInMemoryLimit != nil {
outbandCfg = outbandCfg.WithRequestBodyInMemoryLimit(*r.AppsecRuntime.Config.OutOfBandOptions.RequestBodyInMemoryLimit)
}
r.WaapOutbandEngine, err = coraza.NewWAF(outbandCfg)
r.AppsecOutbandEngine, err = coraza.NewWAF(outbandCfg)
if r.WaapRuntime.DisabledInBandRulesTags != nil {
for _, tag := range r.WaapRuntime.DisabledInBandRulesTags {
r.WaapInbandEngine.GetRuleGroup().DeleteByTag(tag)
if r.AppsecRuntime.DisabledInBandRulesTags != nil {
for _, tag := range r.AppsecRuntime.DisabledInBandRulesTags {
r.AppsecInbandEngine.GetRuleGroup().DeleteByTag(tag)
}
}
if r.WaapRuntime.DisabledOutOfBandRulesTags != nil {
for _, tag := range r.WaapRuntime.DisabledOutOfBandRulesTags {
r.WaapOutbandEngine.GetRuleGroup().DeleteByTag(tag)
if r.AppsecRuntime.DisabledOutOfBandRulesTags != nil {
for _, tag := range r.AppsecRuntime.DisabledOutOfBandRulesTags {
r.AppsecOutbandEngine.GetRuleGroup().DeleteByTag(tag)
}
}
if r.WaapRuntime.DisabledInBandRuleIds != nil {
for _, id := range r.WaapRuntime.DisabledInBandRuleIds {
r.WaapInbandEngine.GetRuleGroup().DeleteByID(id)
if r.AppsecRuntime.DisabledInBandRuleIds != nil {
for _, id := range r.AppsecRuntime.DisabledInBandRuleIds {
r.AppsecInbandEngine.GetRuleGroup().DeleteByID(id)
}
}
if r.WaapRuntime.DisabledOutOfBandRuleIds != nil {
for _, id := range r.WaapRuntime.DisabledOutOfBandRuleIds {
r.WaapOutbandEngine.GetRuleGroup().DeleteByID(id)
if r.AppsecRuntime.DisabledOutOfBandRuleIds != nil {
for _, id := range r.AppsecRuntime.DisabledOutOfBandRuleIds {
r.AppsecOutbandEngine.GetRuleGroup().DeleteByID(id)
}
}
@ -117,7 +117,7 @@ func (r *AppsecRunner) processRequest(tx waf.ExtendedTransaction, request *waf.P
}()
//pre eval (expr) rules
err = r.WaapRuntime.ProcessPreEvalRules(request)
err = r.AppsecRuntime.ProcessPreEvalRules(request)
if err != nil {
r.logger.Errorf("unable to process PreEval rules: %s", err)
//FIXME: should we abort here ?
@ -177,7 +177,7 @@ func (r *AppsecRunner) processRequest(tx waf.ExtendedTransaction, request *waf.P
r.logger.Debugf("rules matched for body : %d", in.RuleID)
}
err = r.WaapRuntime.ProcessPostEvalRules(request)
err = r.AppsecRuntime.ProcessPostEvalRules(request)
if err != nil {
r.logger.Errorf("unable to process PostEval rules: %s", err)
}
@ -186,15 +186,15 @@ func (r *AppsecRunner) processRequest(tx waf.ExtendedTransaction, request *waf.P
}
func (r *AppsecRunner) ProcessInBandRules(request *waf.ParsedRequest) error {
tx := waf.NewExtendedTransaction(r.WaapInbandEngine, request.UUID)
r.WaapRuntime.InBandTx = tx
tx := waf.NewExtendedTransaction(r.AppsecInbandEngine, request.UUID)
r.AppsecRuntime.InBandTx = tx
err := r.processRequest(tx, request)
return err
}
func (r *AppsecRunner) ProcessOutOfBandRules(request *waf.ParsedRequest) error {
tx := waf.NewExtendedTransaction(r.WaapOutbandEngine, request.UUID)
r.WaapRuntime.OutOfBandTx = tx
tx := waf.NewExtendedTransaction(r.AppsecOutbandEngine, request.UUID)
r.AppsecRuntime.OutOfBandTx = tx
err := r.processRequest(tx, request)
return err
}
@ -212,32 +212,32 @@ func (r *AppsecRunner) handleInBandInterrupt(request *waf.ParsedRequest) {
}
if in := request.Tx.Interruption(); in != nil {
r.logger.Debugf("inband rules matched : %d", in.RuleID)
r.WaapRuntime.Response.InBandInterrupt = true
r.WaapRuntime.Response.HTTPResponseCode = r.WaapRuntime.Config.BlockedHTTPCode
r.WaapRuntime.Response.Action = r.WaapRuntime.DefaultRemediation
r.AppsecRuntime.Response.InBandInterrupt = true
r.AppsecRuntime.Response.HTTPResponseCode = r.AppsecRuntime.Config.BlockedHTTPCode
r.AppsecRuntime.Response.Action = r.AppsecRuntime.DefaultRemediation
if _, ok := r.WaapRuntime.RemediationById[in.RuleID]; ok {
r.WaapRuntime.Response.Action = r.WaapRuntime.RemediationById[in.RuleID]
if _, ok := r.AppsecRuntime.RemediationById[in.RuleID]; ok {
r.AppsecRuntime.Response.Action = r.AppsecRuntime.RemediationById[in.RuleID]
}
for tag, remediation := range r.WaapRuntime.RemediationByTag {
for tag, remediation := range r.AppsecRuntime.RemediationByTag {
if slices.Contains[[]string, string](in.Tags, tag) {
r.WaapRuntime.Response.Action = remediation
r.AppsecRuntime.Response.Action = remediation
}
}
err = r.WaapRuntime.ProcessOnMatchRules(request, evt)
err = r.AppsecRuntime.ProcessOnMatchRules(request, evt)
if err != nil {
r.logger.Errorf("unable to process OnMatch rules: %s", err)
return
}
// Should the in band match trigger an event ?
if r.WaapRuntime.Response.SendEvent {
if r.AppsecRuntime.Response.SendEvent {
r.outChan <- evt
}
// Should the in band match trigger an overflow ?
if r.WaapRuntime.Response.SendAlert {
if r.AppsecRuntime.Response.SendAlert {
appsecOvlfw, err := AppsecEventGeneration(evt)
if err != nil {
r.logger.Errorf("unable to generate appsec event : %s", err)
@ -260,23 +260,23 @@ func (r *AppsecRunner) handleOutBandInterrupt(request *waf.ParsedRequest) {
}
if in := request.Tx.Interruption(); in != nil {
r.logger.Debugf("inband rules matched : %d", in.RuleID)
r.WaapRuntime.Response.OutOfBandInterrupt = true
r.AppsecRuntime.Response.OutOfBandInterrupt = true
err = r.WaapRuntime.ProcessOnMatchRules(request, evt)
err = r.AppsecRuntime.ProcessOnMatchRules(request, evt)
if err != nil {
r.logger.Errorf("unable to process OnMatch rules: %s", err)
return
}
// Should the match trigger an event ?
if r.WaapRuntime.Response.SendEvent {
if r.AppsecRuntime.Response.SendEvent {
r.outChan <- evt
}
// Should the match trigger an overflow ?
if r.WaapRuntime.Response.SendAlert {
if r.AppsecRuntime.Response.SendAlert {
appsecOvlfw, err := AppsecEventGeneration(evt)
if err != nil {
r.logger.Errorf("unable to generate waap event : %s", err)
r.logger.Errorf("unable to generate appsec event : %s", err)
return
}
r.outChan <- *appsecOvlfw
@ -286,7 +286,7 @@ func (r *AppsecRunner) handleOutBandInterrupt(request *waf.ParsedRequest) {
func (r *AppsecRunner) handleRequest(request *waf.ParsedRequest) {
r.logger.Debugf("Requests handled by runner %s", request.UUID)
r.WaapRuntime.ClearResponse()
r.AppsecRuntime.ClearResponse()
request.IsInBand = true
request.IsOutBand = false
@ -294,7 +294,7 @@ func (r *AppsecRunner) handleRequest(request *waf.ParsedRequest) {
//to measure the time spent in the Application Security Engine
startParsing := time.Now()
//inband WAAP rules
//inband appsec rules
err := r.ProcessInBandRules(request)
if err != nil {
r.logger.Errorf("unable to process InBand rules: %s", err)
@ -309,14 +309,14 @@ func (r *AppsecRunner) handleRequest(request *waf.ParsedRequest) {
AppsecInbandParsingHistogram.With(prometheus.Labels{"source": request.RemoteAddr}).Observe(elapsed.Seconds())
// send back the result to the HTTP handler for the InBand part
request.ResponseChannel <- r.WaapRuntime.Response
request.ResponseChannel <- r.AppsecRuntime.Response
//Now let's process the out of band rules
request.IsInBand = false
request.IsOutBand = true
r.WaapRuntime.Response.SendAlert = false
r.WaapRuntime.Response.SendEvent = true
r.AppsecRuntime.Response.SendAlert = false
r.AppsecRuntime.Response.SendEvent = true
err = r.ProcessOutOfBandRules(request)
if err != nil {
@ -330,7 +330,7 @@ func (r *AppsecRunner) handleRequest(request *waf.ParsedRequest) {
}
func (r *AppsecRunner) Run(t *tomb.Tomb) error {
r.logger.Infof("Waap Runner ready to process event")
r.logger.Infof("Appsec Runner ready to process event")
for {
select {
case <-t.Dying():

View file

@ -175,7 +175,7 @@ func (r *AppsecRunner) AccumulateTxToEvent(evt *types.Event, req *waf.ParsedRequ
if variable.Value() == "" {
continue
}
for _, collectionToKeep := range r.WaapRuntime.CompiledVariablesTracking {
for _, collectionToKeep := range r.AppsecRuntime.CompiledVariablesTracking {
match := collectionToKeep.MatchString(key)
if match {
evt.Waap.Vars[key] = variable.Value()
@ -215,7 +215,7 @@ func (r *AppsecRunner) AccumulateTxToEvent(evt *types.Event, req *waf.ParsedRequ
r.logger.Debugf("custom rule for event, setting name: %s, version: %s, hash: %s", name, version, hash)
}
AppsecRuleHits.With(prometheus.Labels{"rule_name": ruleNameProm, "type": kind, "source": req.RemoteAddrNormalized, "appsec_engine": req.WaapEngine}).Inc()
AppsecRuleHits.With(prometheus.Labels{"rule_name": ruleNameProm, "type": kind, "source": req.RemoteAddrNormalized, "appsec_engine": req.AppsecEngine}).Inc()
corazaRule := map[string]interface{}{
"id": rule.Rule().ID(),

View file

@ -12,12 +12,12 @@ import (
const (
// managed item types.
COLLECTIONS = "collections"
PARSERS = "parsers"
POSTOVERFLOWS = "postoverflows"
SCENARIOS = "scenarios"
WAAP_CONFIGS = "waap-configs"
WAAP_RULES = "waap-rules"
COLLECTIONS = "collections"
PARSERS = "parsers"
POSTOVERFLOWS = "postoverflows"
SCENARIOS = "scenarios"
APPSEC_CONFIGS = "appsec-configs"
APPSEC_RULES = "appsec-rules"
)
const (
@ -29,7 +29,7 @@ const (
var (
// The order is important, as it is used to range over sub-items in collections.
ItemTypes = []string{PARSERS, POSTOVERFLOWS, SCENARIOS, WAAP_CONFIGS, WAAP_RULES, COLLECTIONS}
ItemTypes = []string{PARSERS, POSTOVERFLOWS, SCENARIOS, APPSEC_CONFIGS, APPSEC_RULES, COLLECTIONS}
)
type HubItems map[string]map[string]*Item
@ -78,8 +78,8 @@ type Item struct {
PostOverflows []string `json:"postoverflows,omitempty" yaml:"postoverflows,omitempty"`
Scenarios []string `json:"scenarios,omitempty" yaml:"scenarios,omitempty"`
Collections []string `json:"collections,omitempty" yaml:"collections,omitempty"`
WaapConfigs []string `json:"waap-configs,omitempty" yaml:"waap-configs,omitempty"`
WaapRules []string `json:"waap-rules,omitempty" yaml:"waap-rules,omitempty"`
AppsecConfigs []string `json:"appsec-configs,omitempty" yaml:"appsec-configs,omitempty"`
AppsecRules []string `json:"appsec-rules,omitempty" yaml:"appsec-rules,omitempty"`
}
// installPath returns the location of the symlink to the item in the hub, or the path of the item itself if it's local
@ -194,8 +194,8 @@ func (i *Item) SubItems() []*Item {
sub = append(sub, s)
}
for _, name := range i.WaapConfigs {
s := i.hub.GetItem(WAAP_CONFIGS, name)
for _, name := range i.AppsecConfigs {
s := i.hub.GetItem(APPSEC_CONFIGS, name)
if s == nil {
continue
}
@ -203,8 +203,8 @@ func (i *Item) SubItems() []*Item {
sub = append(sub, s)
}
for _, name := range i.WaapRules {
s := i.hub.GetItem(WAAP_RULES, name)
for _, name := range i.AppsecRules {
s := i.hub.GetItem(APPSEC_RULES, name)
if s == nil {
continue
}
@ -247,15 +247,15 @@ func (i *Item) logMissingSubItems() {
}
}
for _, subName := range i.WaapConfigs {
if i.hub.GetItem(WAAP_CONFIGS, subName) == nil {
log.Errorf("can't find %s in %s, required by %s", subName, WAAP_CONFIGS, i.Name)
for _, subName := range i.AppsecConfigs {
if i.hub.GetItem(APPSEC_CONFIGS, subName) == nil {
log.Errorf("can't find %s in %s, required by %s", subName, APPSEC_CONFIGS, i.Name)
}
}
for _, subName := range i.WaapRules {
if i.hub.GetItem(WAAP_RULES, subName) == nil {
log.Errorf("can't find %s in %s, required by %s", subName, WAAP_RULES, i.Name)
for _, subName := range i.AppsecRules {
if i.hub.GetItem(APPSEC_RULES, subName) == nil {
log.Errorf("can't find %s in %s, required by %s", subName, APPSEC_RULES, i.Name)
}
}

View file

@ -118,11 +118,11 @@ func (h *Hub) getItemFileInfo(path string) (*itemFileInfo, error) {
} else if ret.stage == COLLECTIONS {
ret.ftype = COLLECTIONS
ret.stage = ""
} else if ret.stage == WAAP_RULES {
ret.ftype = WAAP_RULES
} else if ret.stage == APPSEC_RULES {
ret.ftype = APPSEC_RULES
ret.stage = ""
} else if ret.stage == WAAP_CONFIGS {
ret.ftype = WAAP_CONFIGS
} else if ret.stage == APPSEC_CONFIGS {
ret.ftype = APPSEC_CONFIGS
ret.stage = ""
} else if ret.ftype != PARSERS && ret.ftype != POSTOVERFLOWS {
// it's a PARSER / POSTOVERFLOW with a stage

View file

@ -19,13 +19,13 @@ type Coverage struct {
PresentIn map[string]bool //poorman's set
}
func (h *HubTest) GetWaapCoverage() ([]Coverage, error) {
if len(h.HubIndex.GetItemMap(cwhub.WAAP_RULES)) == 0 {
return nil, fmt.Errorf("no waap rules in hub index")
func (h *HubTest) GetAppsecCoverage() ([]Coverage, error) {
if len(h.HubIndex.GetItemMap(cwhub.APPSEC_RULES)) == 0 {
return nil, fmt.Errorf("no appsec rules in hub index")
}
// populate from hub, iterate in alphabetical order
pkeys := sortedMapKeys(h.HubIndex.GetItemMap(cwhub.WAAP_RULES))
pkeys := sortedMapKeys(h.HubIndex.GetItemMap(cwhub.APPSEC_RULES))
coverage := make([]Coverage, len(pkeys))
for i, name := range pkeys {
@ -37,16 +37,16 @@ func (h *HubTest) GetWaapCoverage() ([]Coverage, error) {
}
// parser the expressions a-la-oneagain
waapTestConfigs, err := filepath.Glob(".waap-tests/*/config.yaml")
appsecTestConfigs, err := filepath.Glob(".appsec-tests/*/config.yaml")
if err != nil {
return nil, fmt.Errorf("while find waap-tests config: %s", err)
return nil, fmt.Errorf("while find appsec-tests config: %s", err)
}
for _, waapTestConfigPath := range waapTestConfigs {
for _, appsecTestConfigPath := range appsecTestConfigs {
configFileData := &HubTestItemConfig{}
yamlFile, err := os.ReadFile(waapTestConfigPath)
yamlFile, err := os.ReadFile(appsecTestConfigPath)
if err != nil {
log.Printf("unable to open waap test config file '%s': %s", waapTestConfigPath, err)
log.Printf("unable to open appsec test config file '%s': %s", appsecTestConfigPath, err)
continue
}
err = yaml.Unmarshal(yamlFile, configFileData)
@ -54,22 +54,22 @@ func (h *HubTest) GetWaapCoverage() ([]Coverage, error) {
return nil, fmt.Errorf("unmarshal: %v", err)
}
for _, waapRulesFile := range configFileData.WaapRules {
waapRuleData := &waap_rule.CustomRule{}
yamlFile, err := os.ReadFile(waapRulesFile)
for _, appsecRulesFile := range configFileData.AppsecRules {
appsecRuleData := &waap_rule.CustomRule{}
yamlFile, err := os.ReadFile(appsecRulesFile)
if err != nil {
log.Printf("unable to open waap rule '%s': %s", waapRulesFile, err)
log.Printf("unable to open appsec rule '%s': %s", appsecRulesFile, err)
}
err = yaml.Unmarshal(yamlFile, waapRuleData)
err = yaml.Unmarshal(yamlFile, appsecRuleData)
if err != nil {
return nil, fmt.Errorf("unmarshal: %v", err)
}
waapRuleName := waapRuleData.Name
appsecRuleName := appsecRuleData.Name
for idx, cov := range coverage {
if cov.Name == waapRuleName {
if cov.Name == appsecRuleName {
coverage[idx].TestsCount++
coverage[idx].PresentIn[waapTestConfigPath] = true
coverage[idx].PresentIn[appsecTestConfigPath] = true
}
}
}

View file

@ -11,30 +11,30 @@ import (
)
type HubTest struct {
CrowdSecPath string
CscliPath string
HubPath string
HubTestPath string //generic parser/scenario tests .tests
HubWaapTestPath string //dir specific to waap tests .waap-tests
HubIndexFile string
TemplateConfigPath string
TemplateProfilePath string
TemplateSimulationPath string
TemplateAcquisPath string
TemplateWaapProfilePath string
HubIndex *cwhub.Hub
Tests []*HubTestItem
CrowdSecPath string
CscliPath string
HubPath string
HubTestPath string //generic parser/scenario tests .tests
HubAppsecTestPath string //dir specific to appsec tests .appsec-tests
HubIndexFile string
TemplateConfigPath string
TemplateProfilePath string
TemplateSimulationPath string
TemplateAcquisPath string
TemplateAppsecProfilePath string
HubIndex *cwhub.Hub
Tests []*HubTestItem
}
const (
templateConfigFile = "template_config.yaml"
templateSimulationFile = "template_simulation.yaml"
templateProfileFile = "template_profiles.yaml"
templateAcquisFile = "template_acquis.yaml"
templateWaapProfilePath = "template_waap-profile.yaml"
templateConfigFile = "template_config.yaml"
templateSimulationFile = "template_simulation.yaml"
templateProfileFile = "template_profiles.yaml"
templateAcquisFile = "template_acquis.yaml"
templateAppsecProfilePath = "template_appsec-profile.yaml"
)
func NewHubTest(hubPath string, crowdsecPath string, cscliPath string, isWaapTest bool) (HubTest, error) {
func NewHubTest(hubPath string, crowdsecPath string, cscliPath string, isAppsecTest bool) (HubTest, error) {
hubPath, err := filepath.Abs(hubPath)
if err != nil {
return HubTest{}, fmt.Errorf("can't get absolute path of hub: %+v", err)
@ -58,8 +58,8 @@ func NewHubTest(hubPath string, crowdsecPath string, cscliPath string, isWaapTes
}
}
if isWaapTest {
HubTestPath := filepath.Join(hubPath, "./.waap-tests/")
if isAppsecTest {
HubTestPath := filepath.Join(hubPath, "./.appsec-tests/")
hubIndexFile := filepath.Join(hubPath, ".index.json")
local := &csconfig.LocalHubCfg{
@ -75,17 +75,17 @@ func NewHubTest(hubPath string, crowdsecPath string, cscliPath string, isWaapTes
}
return HubTest{
CrowdSecPath: crowdsecPath,
CscliPath: cscliPath,
HubPath: hubPath,
HubTestPath: HubTestPath,
HubIndexFile: hubIndexFile,
TemplateConfigPath: filepath.Join(HubTestPath, templateConfigFile),
TemplateProfilePath: filepath.Join(HubTestPath, templateProfileFile),
TemplateSimulationPath: filepath.Join(HubTestPath, templateSimulationFile),
TemplateWaapProfilePath: filepath.Join(HubTestPath, templateWaapProfilePath),
TemplateAcquisPath: filepath.Join(HubTestPath, templateAcquisFile),
HubIndex: hub,
CrowdSecPath: crowdsecPath,
CscliPath: cscliPath,
HubPath: hubPath,
HubTestPath: HubTestPath,
HubIndexFile: hubIndexFile,
TemplateConfigPath: filepath.Join(HubTestPath, templateConfigFile),
TemplateProfilePath: filepath.Join(HubTestPath, templateProfileFile),
TemplateSimulationPath: filepath.Join(HubTestPath, templateSimulationFile),
TemplateAppsecProfilePath: filepath.Join(HubTestPath, templateAppsecProfilePath),
TemplateAcquisPath: filepath.Join(HubTestPath, templateAcquisFile),
HubIndex: hub,
}, nil
}

View file

@ -21,7 +21,7 @@ type HubTestItemConfig struct {
Parsers []string `yaml:"parsers,omitempty"`
Scenarios []string `yaml:"scenarios,omitempty"`
PostOverflows []string `yaml:"postoverflows,omitempty"`
WaapRules []string `yaml:"waap-rules,omitempty"`
AppsecRules []string `yaml:"appsec-rules,omitempty"`
NucleiTemplate string `yaml:"nuclei_template,omitempty"`
ExpectedNucleiFailure bool `yaml:"expect_failure,omitempty"`
LogFile string `yaml:"log_file,omitempty"`
@ -53,15 +53,15 @@ type HubTestItem struct {
ScenarioResultFile string
BucketPourResultFile string
HubPath string
HubTestPath string
HubIndexFile string
TemplateConfigPath string
TemplateProfilePath string
TemplateSimulationPath string
TemplateAcquisPath string
TemplateWaapProfilePath string
HubIndex *cwhub.Hub
HubPath string
HubTestPath string
HubIndexFile string
TemplateConfigPath string
TemplateProfilePath string
TemplateSimulationPath string
TemplateAcquisPath string
TemplateAppsecProfilePath string
HubIndex *cwhub.Hub
Config *HubTestItemConfig
@ -87,7 +87,7 @@ const (
TestBouncerApiKey = "this_is_a_bad_password"
DefaultNucleiTarget = "http://127.0.0.1:80/"
DefaultWaapHost = "127.0.0.1:4241"
DefaultAppsecHost = "127.0.0.1:4241"
)
func NewTest(name string, hubTest *HubTest) (*HubTestItem, error) {
@ -139,19 +139,19 @@ func NewTest(name string, hubTest *HubTest) (*HubTestItem, error) {
InstallDir: runtimeFolder,
InstallDataDir: filepath.Join(runtimeFolder, "data"),
},
Config: configFileData,
HubPath: hubTest.HubPath,
HubTestPath: hubTest.HubTestPath,
HubIndexFile: hubTest.HubIndexFile,
TemplateConfigPath: hubTest.TemplateConfigPath,
TemplateProfilePath: hubTest.TemplateProfilePath,
TemplateSimulationPath: hubTest.TemplateSimulationPath,
TemplateAcquisPath: hubTest.TemplateAcquisPath,
TemplateWaapProfilePath: hubTest.TemplateWaapProfilePath,
HubIndex: hubTest.HubIndex,
ScenarioAssert: ScenarioAssert,
ParserAssert: ParserAssert,
CustomItemsLocation: []string{hubTest.HubPath, testPath},
Config: configFileData,
HubPath: hubTest.HubPath,
HubTestPath: hubTest.HubTestPath,
HubIndexFile: hubTest.HubIndexFile,
TemplateConfigPath: hubTest.TemplateConfigPath,
TemplateProfilePath: hubTest.TemplateProfilePath,
TemplateSimulationPath: hubTest.TemplateSimulationPath,
TemplateAcquisPath: hubTest.TemplateAcquisPath,
TemplateAppsecProfilePath: hubTest.TemplateAppsecProfilePath,
HubIndex: hubTest.HubIndex,
ScenarioAssert: ScenarioAssert,
ParserAssert: ParserAssert,
CustomItemsLocation: []string{hubTest.HubPath, testPath},
}, nil
}
@ -313,75 +313,75 @@ func (t *HubTestItem) InstallHub() error {
}
}
// install waaprules in runtime environment
for _, waaprule := range t.Config.WaapRules {
log.Infof("adding rule '%s'", waaprule)
if waaprule == "" {
// install appsec-rules in runtime environment
for _, appsecrule := range t.Config.AppsecRules {
log.Infof("adding rule '%s'", appsecrule)
if appsecrule == "" {
continue
}
if hubWaapRule, ok := t.HubIndex.GetItemMap(cwhub.WAAP_RULES)[waaprule]; ok {
waapRuleSource, err := filepath.Abs(filepath.Join(t.HubPath, hubWaapRule.RemotePath))
if hubAppsecRule, ok := t.HubIndex.GetItemMap(cwhub.APPSEC_RULES)[appsecrule]; ok {
appsecRuleSource, err := filepath.Abs(filepath.Join(t.HubPath, hubAppsecRule.RemotePath))
if err != nil {
return fmt.Errorf("can't get absolute path of '%s': %s", waapRuleSource, err)
return fmt.Errorf("can't get absolute path of '%s': %s", appsecRuleSource, err)
}
waapRuleFilename := filepath.Base(waapRuleSource)
appsecRuleFilename := filepath.Base(appsecRuleSource)
// runtime/hub/waap-rules/author/waap-rule
hubDirWaapRuleDest := filepath.Join(t.RuntimeHubPath, filepath.Dir(hubWaapRule.RemotePath))
// runtime/hub/appsec-rules/author/appsec-rule
hubDirAppsecRuleDest := filepath.Join(t.RuntimeHubPath, filepath.Dir(hubAppsecRule.RemotePath))
// runtime/waap-rules/
waapRuleDirDest := fmt.Sprintf("%s/waap-rules/", t.RuntimePath)
// runtime/appsec-rules/
appsecRuleDirDest := fmt.Sprintf("%s/appsec-rules/", t.RuntimePath)
if err := os.MkdirAll(hubDirWaapRuleDest, os.ModePerm); err != nil {
return fmt.Errorf("unable to create folder '%s': %s", hubDirWaapRuleDest, err)
if err := os.MkdirAll(hubDirAppsecRuleDest, os.ModePerm); err != nil {
return fmt.Errorf("unable to create folder '%s': %s", hubDirAppsecRuleDest, err)
}
if err := os.MkdirAll(waapRuleDirDest, os.ModePerm); err != nil {
return fmt.Errorf("unable to create folder '%s': %s", waapRuleDirDest, err)
if err := os.MkdirAll(appsecRuleDirDest, os.ModePerm); err != nil {
return fmt.Errorf("unable to create folder '%s': %s", appsecRuleDirDest, err)
}
// runtime/hub/waap-rules/crowdsecurity/rule.yaml
hubDirWaapRulePath := filepath.Join(waapRuleDirDest, waapRuleFilename)
if err := Copy(waapRuleSource, hubDirWaapRulePath); err != nil {
return fmt.Errorf("unable to copy '%s' to '%s': %s", waapRuleSource, hubDirWaapRulePath, err)
// runtime/hub/appsec-rules/crowdsecurity/rule.yaml
hubDirAppsecRulePath := filepath.Join(appsecRuleDirDest, appsecRuleFilename)
if err := Copy(appsecRuleSource, hubDirAppsecRulePath); err != nil {
return fmt.Errorf("unable to copy '%s' to '%s': %s", appsecRuleSource, hubDirAppsecRulePath, err)
}
// runtime/waap-rules/rule.yaml
waapRulePath := filepath.Join(waapRuleDirDest, waapRuleFilename)
if err := os.Symlink(hubDirWaapRulePath, waapRulePath); err != nil {
// runtime/appsec-rules/rule.yaml
appsecRulePath := filepath.Join(appsecRuleDirDest, appsecRuleFilename)
if err := os.Symlink(hubDirAppsecRulePath, appsecRulePath); err != nil {
if !os.IsExist(err) {
return fmt.Errorf("unable to symlink waap-rule '%s' to '%s': %s", hubDirWaapRulePath, waapRulePath, err)
return fmt.Errorf("unable to symlink appsec-rule '%s' to '%s': %s", hubDirAppsecRulePath, appsecRulePath, err)
}
}
} else {
customWaapRuleExist := false
customAppsecRuleExist := false
for _, customPath := range t.CustomItemsLocation {
// we check if its a custom waap-rule
customWaapRulePath := filepath.Join(customPath, waaprule)
if _, err := os.Stat(customWaapRulePath); os.IsNotExist(err) {
// we check if its a custom appsec-rule
customAppsecRulePath := filepath.Join(customPath, appsecrule)
if _, err := os.Stat(customAppsecRulePath); os.IsNotExist(err) {
continue
}
customWaapRulePathSplit := strings.Split(customWaapRulePath, "/")
customWappRuleName := customWaapRulePathSplit[len(customWaapRulePathSplit)-1]
customAppsecRulePathSplit := strings.Split(customAppsecRulePath, "/")
customAppsecRuleName := customAppsecRulePathSplit[len(customAppsecRulePathSplit)-1]
waapRuleDirDest := fmt.Sprintf("%s/waap-rules/", t.RuntimePath)
if err := os.MkdirAll(waapRuleDirDest, os.ModePerm); err != nil {
return fmt.Errorf("unable to create folder '%s': %s", waapRuleDirDest, err)
appsecRuleDirDest := fmt.Sprintf("%s/appsec-rules/", t.RuntimePath)
if err := os.MkdirAll(appsecRuleDirDest, os.ModePerm); err != nil {
return fmt.Errorf("unable to create folder '%s': %s", appsecRuleDirDest, err)
}
// runtime/waap-rules/
customWaapRuleDest := fmt.Sprintf("%s/waap-rules/%s", t.RuntimePath, customWappRuleName)
// runtime/appsec-rules/
customAppsecRuleDest := fmt.Sprintf("%s/appsec-rules/%s", t.RuntimePath, customAppsecRuleName)
// if path to postoverflow exist, copy it
if err := Copy(customWaapRulePath, customWaapRuleDest); err != nil {
if err := Copy(customAppsecRulePath, customAppsecRuleDest); err != nil {
continue
}
customWaapRuleExist = true
customAppsecRuleExist = true
break
}
if !customWaapRuleExist {
return fmt.Errorf("couldn't find custom waap-rule '%s' in the following location: %+v", waaprule, t.CustomItemsLocation)
if !customAppsecRuleExist {
return fmt.Errorf("couldn't find custom appsec-rule '%s' in the following location: %+v", appsecrule, t.CustomItemsLocation)
}
}
}
@ -562,12 +562,12 @@ func (t *HubTestItem) RunWithNucleiTemplate() error {
}
//hardcode bouncer key
cmdArgs = []string{"-c", t.RuntimeConfigFilePath, "bouncers", "add", "waaptests", "-k", TestBouncerApiKey}
cmdArgs = []string{"-c", t.RuntimeConfigFilePath, "bouncers", "add", "appsectests", "-k", TestBouncerApiKey}
cscliBouncerCmd := exec.Command(t.CscliPath, cmdArgs...)
output, err = cscliBouncerCmd.CombinedOutput()
if err != nil {
if !strings.Contains(string(output), "unable to create bouncer: bouncer waaptests already exists") {
if !strings.Contains(string(output), "unable to create bouncer: bouncer appsectests already exists") {
fmt.Println(string(output))
return fmt.Errorf("fail to run '%s' for test '%s': %v", cscliRegisterCmd.String(), t.Name, err)
}
@ -579,9 +579,9 @@ func (t *HubTestItem) RunWithNucleiTemplate() error {
crowdsecDaemon.Start()
//wait for the waap port to be available
if _, err := IsAlive(DefaultWaapHost); err != nil {
return fmt.Errorf("waap is down: %s", err)
//wait for the appsec port to be available
if _, err := IsAlive(DefaultAppsecHost); err != nil {
return fmt.Errorf("appsec is down: %s", err)
}
// check if the target is available
@ -608,17 +608,17 @@ func (t *HubTestItem) RunWithNucleiTemplate() error {
if t.Config.ExpectedNucleiFailure {
if err != nil && errors.Is(err, NucleiTemplateFail) {
log.Infof("WAAP test %s failed as expected", t.Name)
log.Infof("Appsec test %s failed as expected", t.Name)
t.Success = true
} else {
log.Errorf("WAAP test %s failed: %s", t.Name, err)
log.Errorf("Appsec test %s failed: %s", t.Name, err)
}
} else {
if err == nil {
log.Infof("WAAP test %s succeeded", t.Name)
log.Infof("Appsec test %s succeeded", t.Name)
t.Success = true
} else {
log.Errorf("WAAP test %s failed: %s", t.Name, err)
log.Errorf("Appsec test %s failed: %s", t.Name, err)
}
}
crowdsecDaemon.Process.Kill()
@ -875,23 +875,23 @@ func (t *HubTestItem) Run() error {
return fmt.Errorf("unable to copy 'patterns' from '%s' to '%s': %s", crowdsecPatternsFolder, t.RuntimePatternsPath, err)
}
// create the waap-configs dir
if err = os.MkdirAll(filepath.Join(t.RuntimePath, "waap-configs"), os.ModePerm); err != nil {
// create the appsec-configs dir
if err = os.MkdirAll(filepath.Join(t.RuntimePath, "appsec-configs"), os.ModePerm); err != nil {
return fmt.Errorf("unable to create folder '%s': %+v", t.RuntimePath, err)
}
//if it's a waap rule test, we need acquis and waap profile
if len(t.Config.WaapRules) > 0 {
//if it's an appsec rule test, we need acquis and appsec profile
if len(t.Config.AppsecRules) > 0 {
// copy template acquis file to runtime folder
log.Infof("copying %s to %s", t.TemplateAcquisPath, t.RuntimeAcquisFilePath)
if err = Copy(t.TemplateAcquisPath, t.RuntimeAcquisFilePath); err != nil {
return fmt.Errorf("unable to copy '%s' to '%s': %v", t.TemplateAcquisPath, t.RuntimeAcquisFilePath, err)
}
log.Infof("copying %s to %s", t.TemplateWaapProfilePath, filepath.Join(t.RuntimePath, "waap-configs", "config.yaml"))
// copy template waap-config file to runtime folder
if err = Copy(t.TemplateWaapProfilePath, filepath.Join(t.RuntimePath, "waap-configs", "config.yaml")); err != nil {
return fmt.Errorf("unable to copy '%s' to '%s': %v", t.TemplateWaapProfilePath, filepath.Join(t.RuntimePath, "waap-configs", "config.yaml"), err)
log.Infof("copying %s to %s", t.TemplateAppsecProfilePath, filepath.Join(t.RuntimePath, "appsec-configs", "config.yaml"))
// copy template appsec-config file to runtime folder
if err = Copy(t.TemplateAppsecProfilePath, filepath.Join(t.RuntimePath, "appsec-configs", "config.yaml")); err != nil {
return fmt.Errorf("unable to copy '%s' to '%s': %v", t.TemplateAppsecProfilePath, filepath.Join(t.RuntimePath, "appsec-configs", "config.yaml"), err)
}
} else { //otherwise we drop a blank acquis file
if err = os.WriteFile(t.RuntimeAcquisFilePath, []byte(""), os.ModePerm); err != nil {

View file

@ -116,7 +116,7 @@ func IsAlive(target string) (bool, error) {
for {
conn, err := net.Dial("tcp", target)
if err == nil {
log.Debugf("waap is up after %s", time.Since(start))
log.Debugf("appsec is up after %s", time.Since(start))
conn.Close()
return true, nil
}

View file

@ -16,7 +16,7 @@ func LoadAppsecRules(hubInstance *cwhub.Hub) error {
hub = hubInstance
for _, hubAppsecRuleItem := range hub.GetItemMap(cwhub.WAAP_RULES) {
for _, hubAppsecRuleItem := range hub.GetItemMap(cwhub.APPSEC_RULES) {
//log.Infof("loading %s", hubWafRuleItem.LocalPath)
if !hubAppsecRuleItem.State.Installed {
continue
@ -38,8 +38,8 @@ func LoadAppsecRules(hubInstance *cwhub.Hub) error {
continue
}
if rule.Type != WAAP_RULE {
log.Warnf("unexpected type %s instead of %s for file %s", rule.Type, WAAP_RULE, hubAppsecRuleItem.State.LocalPath)
if rule.Type != cwhub.APPSEC_RULES {
log.Warnf("unexpected type %s instead of %s for file %s", rule.Type, cwhub.APPSEC_RULES, hubAppsecRuleItem.State.LocalPath)
continue
}

View file

@ -15,11 +15,11 @@ import (
)
const (
URIHeaderName = "X-Crowdsec-Waap-Uri"
VerbHeaderName = "X-Crowdsec-Waap-Verb"
HostHeaderName = "X-Crowdsec-Waap-Host"
IPHeaderName = "X-Crowdsec-Waap-Ip"
APIKeyHeaderName = "X-Crowdsec-Waap-Api-Key"
URIHeaderName = "X-Crowdsec-Appsec-Uri"
VerbHeaderName = "X-Crowdsec-Appsec-Verb"
HostHeaderName = "X-Crowdsec-Appsec-Host"
IPHeaderName = "X-Crowdsec-Appsec-Ip"
APIKeyHeaderName = "X-Crowdsec-Appsec-Api-Key"
)
type ParsedRequest struct {
@ -40,7 +40,7 @@ type ParsedRequest struct {
ResponseChannel chan AppsecTempResponse `json:"-"`
IsInBand bool `json:"-"`
IsOutBand bool `json:"-"`
WaapEngine string `json:"waap_engine,omitempty"`
AppsecEngine string `json:"appsec_engine,omitempty"`
RemoteAddrNormalized string `json:"normalized_remote_addr,omitempty"`
}
@ -313,12 +313,12 @@ func NewParsedRequestFromRequest(r *http.Request) (ParsedRequest, error) {
remoteAddrNormalized := ""
host, _, err := net.SplitHostPort(r.RemoteAddr)
if err != nil {
log.Errorf("Invalid waap remote IP source %v: %s", r.RemoteAddr, err.Error())
log.Errorf("Invalid appsec remote IP source %v: %s", r.RemoteAddr, err.Error())
remoteAddrNormalized = r.RemoteAddr
} else {
ip := net.ParseIP(host)
if ip == nil {
log.Errorf("Invalid waap remote IP address source %v: %s", r.RemoteAddr, err.Error())
log.Errorf("Invalid appsec remote IP address source %v: %s", r.RemoteAddr, err.Error())
remoteAddrNormalized = r.RemoteAddr
} else {
remoteAddrNormalized = ip.String()

View file

@ -184,7 +184,7 @@ func (wc *AppsecConfig) LoadByPath(file string) error {
}
func (wc *AppsecConfig) Load(configName string) error {
appsecConfigs := hub.GetItemMap(cwhub.WAAP_CONFIGS)
appsecConfigs := hub.GetItemMap(cwhub.APPSEC_CONFIGS)
for _, hubAppsecConfigItem := range appsecConfigs {
if !hubAppsecConfigItem.State.Installed {

View file

@ -16,7 +16,7 @@ type AppsecCollection struct {
Rules []string
}
var WAAP_RULE = "waap-rule"
var APPSEC_RULE = "appsec-rule"
// to be filled w/ seb update
type AppsecCollectionConfig struct {