Skip to content
This repository has been archived by the owner on Jan 2, 2024. It is now read-only.

Commit

Permalink
allow file importing via glob notation
Browse files Browse the repository at this point in the history
  • Loading branch information
gesquive committed May 31, 2018
1 parent 473aa90 commit ed03d22
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 32 deletions.
15 changes: 12 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -46,11 +46,20 @@ Optionally, instead of using a config file you can specify config entries as env
`templr` uses the golang [text template engine](https://golang.org/pkg/text/template/) to generate the final ruleset. In addition to the standard [functions](https://golang.org/pkg/text/template/#hdr-Functions), `templr` has a number of helper functions designed to ease the creation of iptable rules. Please refer to the [helper documentation](https://gesquive.github.io/templr/) for a list of helper functions available.

## Imports
Other rulesets can be imported by using the `{@ path @}` brackets, where the `path` can be either a full path or relative to the current ruleset path. A single path can be imported per set of brackets. For example:
Other rulesets can be imported by using the `{@ glob @}` brackets, where the `glob` can be:

- relative path to file (`../../path/to/file`)
- absolute path to file - (`/path/to/file`)
- a glob of files - (`*.tr`)
- a glob of files in a directory - (`path/to/dir/*`)
- a glob of files in multiple directories - (`path/to/dir/*/.tr`)

The specified glob is checked to see if there are file matches under a relative path first, if no relative matches are found the absolute path is checked. When multiple matches are found, they are imported in alphabetical order and delimited by a newline.

A single `glob` can be imported per set of brackets. For example:
```yaml
{@ path/to/file @}
{@ /path/to/file @}
```
This would result in the contents of `path/to/file` being imported inline into the current ruleset. There is a limit of 100 levels of imports allowed to prevent an infinite import loop.

## Variables
In addition, yaml variables can be defined from within a template by using the `{$ $}` brackets. Anything within the brackets will be parsed as yaml and passed to the template as variables. For example:
Expand Down
43 changes: 17 additions & 26 deletions engine/ruleset.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (
"path"
"path/filepath"
"regexp"
"sort"
"text/template"
"time"

Expand Down Expand Up @@ -163,19 +164,19 @@ func (r *RuleSet) expandImports(ruleset []byte, depth uint) ([]byte, error) {
return expandedRules, nil
}

func (r RuleSet) getFilePath(importPath string) (string, error) {
func (r RuleSet) searchForFiles(importPath string) []string {
templateDirPath := path.Dir(r.templatePath)
relativePath := path.Join(templateDirPath, importPath)

// First try a relative path
if _, err := os.Stat(relativePath); err == nil {
return relativePath, nil
if relList, err := filepath.Glob(relativePath); err == nil && len(relList) > 0 {
return relList
}
// Second, try the full path
if _, err := os.Stat(importPath); err == nil {
return importPath, nil
// Second, try the absolute path
if absList, err := filepath.Glob(importPath); err == nil && len(absList) > 0 {
return absList
}
return "", errors.Errorf("Could not find import path '%s'", importPath)
return []string{}
}

func (r RuleSet) isDir(filePath string) bool {
Expand All @@ -187,26 +188,16 @@ func (r RuleSet) isDir(filePath string) bool {
}

func (r RuleSet) getFileList(importPath string) ([]string, error) {
filePath, err := r.getFilePath(importPath)
if err != nil {
return []string{}, err
}
foundFiles := r.searchForFiles(importPath)
sort.Strings(foundFiles)

fileListInfo := []string{}
if info, err := os.Stat(filePath); err == nil && info.IsDir() {
// then we have a directory, get the file list
dirList, err := filepath.Glob(path.Join(filePath, "*"))
if err != nil {
return []string{}, err
}
for _, filePath := range dirList {
if r.isDir(filePath) {
continue
}
fileListInfo = append(fileListInfo, filePath)
fileList := []string{}
for _, filePath := range foundFiles {
if r.isDir(filePath) {
continue
}
} else { // assume its a file, already got stats
fileListInfo = append(fileListInfo, filePath)
fileList = append(fileList, filePath)
}
return fileListInfo, nil

return fileList, nil
}
6 changes: 3 additions & 3 deletions engine/ruleset_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -152,9 +152,9 @@ func TestBadImport(t *testing.T) {
ruleset.SetImportDepth(3)
expandedRules, err := ruleset.expandImports(rules, 0)

assert.Error(t, err, "missing error")
assert.NoError(t, err, "unexpected error")

assert.Equal(t, "", string(expandedRules), "rules do not match")
assert.Equal(t, "No import ", string(expandedRules), "rules do not match")
}

func TestMaxDepthImports(t *testing.T) {
Expand Down Expand Up @@ -236,7 +236,7 @@ func TestDirectoryList(t *testing.T) {

ruleset := new(RuleSet)
ruleset.SetImportDepth(3)
resultFileList, err := ruleset.getFileList(importDirPath)
resultFileList, err := ruleset.getFileList(path.Join(importDirPath, "*"))
assert.NoError(t, err, "unknown")

assert.Equal(t, len(expectedFileList), len(resultFileList))
Expand Down

0 comments on commit ed03d22

Please sign in to comment.