| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123 |
- package shell
- import (
- "context"
- "os"
- "strings"
- "testing"
- )
- func TestCommandBlocking(t *testing.T) {
- tests := []struct {
- name string
- blockFuncs []BlockFunc
- command string
- shouldBlock bool
- }{
- {
- name: "block simple command",
- blockFuncs: []BlockFunc{
- func(args []string) bool {
- return len(args) > 0 && args[0] == "curl"
- },
- },
- command: "curl https://example.com",
- shouldBlock: true,
- },
- {
- name: "allow non-blocked command",
- blockFuncs: []BlockFunc{
- func(args []string) bool {
- return len(args) > 0 && args[0] == "curl"
- },
- },
- command: "echo hello",
- shouldBlock: false,
- },
- {
- name: "block subcommand",
- blockFuncs: []BlockFunc{
- func(args []string) bool {
- return len(args) >= 2 && args[0] == "brew" && args[1] == "install"
- },
- },
- command: "brew install wget",
- shouldBlock: true,
- },
- {
- name: "allow different subcommand",
- blockFuncs: []BlockFunc{
- func(args []string) bool {
- return len(args) >= 2 && args[0] == "brew" && args[1] == "install"
- },
- },
- command: "brew list",
- shouldBlock: false,
- },
- {
- name: "block npm global install with -g",
- blockFuncs: []BlockFunc{
- ArgumentsBlocker([][]string{
- {"npm", "install", "-g"},
- {"npm", "install", "--global"},
- }),
- },
- command: "npm install -g typescript",
- shouldBlock: true,
- },
- {
- name: "block npm global install with --global",
- blockFuncs: []BlockFunc{
- ArgumentsBlocker([][]string{
- {"npm", "install", "-g"},
- {"npm", "install", "--global"},
- }),
- },
- command: "npm install --global typescript",
- shouldBlock: true,
- },
- {
- name: "allow npm local install",
- blockFuncs: []BlockFunc{
- ArgumentsBlocker([][]string{
- {"npm", "install", "-g"},
- {"npm", "install", "--global"},
- }),
- },
- command: "npm install typescript",
- shouldBlock: false,
- },
- }
- for _, tt := range tests {
- t.Run(tt.name, func(t *testing.T) {
- // Create a temporary directory for each test
- tmpDir, err := os.MkdirTemp("", "shell-test-*")
- if err != nil {
- t.Fatalf("Failed to create temp dir: %v", err)
- }
- defer os.RemoveAll(tmpDir)
- shell := NewShell(&Options{
- WorkingDir: tmpDir,
- BlockFuncs: tt.blockFuncs,
- })
- _, _, err = shell.Exec(context.Background(), tt.command)
- if tt.shouldBlock {
- if err == nil {
- t.Errorf("Expected command to be blocked, but it was allowed")
- } else if !strings.Contains(err.Error(), "not allowed for security reasons") {
- t.Errorf("Expected security error, got: %v", err)
- }
- } else {
- // For non-blocked commands, we might get other errors (like command not found)
- // but we shouldn't get the security error
- if err != nil && strings.Contains(err.Error(), "not allowed for security reasons") {
- t.Errorf("Command was unexpectedly blocked: %v", err)
- }
- }
- })
- }
- }
|