github.com/kubeshop/testkube@v1.17.23/contrib/executor/jmeterd/pkg/runner/helpers.go (about)

     1  package runner
     2  
     3  import (
     4  	"os"
     5  	"path/filepath"
     6  	"strings"
     7  
     8  	"github.com/pkg/errors"
     9  
    10  	"github.com/kubeshop/testkube/pkg/api/v1/testkube"
    11  	"github.com/kubeshop/testkube/pkg/executor/content"
    12  	"github.com/kubeshop/testkube/pkg/executor/output"
    13  	"github.com/kubeshop/testkube/pkg/filesystem"
    14  	"github.com/kubeshop/testkube/pkg/ui"
    15  )
    16  
    17  const (
    18  	envVarPrefix = "$"
    19  )
    20  
    21  var (
    22  	ErrParamMissingValue = errors.New("no value found for parameter")
    23  	ErrMissingParam      = errors.New("parameter not found")
    24  )
    25  
    26  func getTestPathAndWorkingDir(fs filesystem.FileSystem, execution *testkube.Execution, dataDir string) (testPath string, workingDir, testFile string, err error) {
    27  	testPath, workingDir, err = content.GetPathAndWorkingDir(execution.Content, dataDir)
    28  	if err != nil {
    29  		output.PrintLogf("%s Failed to resolve absolute directory for %s, using the path directly", ui.IconWarning, dataDir)
    30  	}
    31  
    32  	fileInfo, err := fs.Stat(testPath)
    33  	if err != nil {
    34  		return "", "", "", err
    35  	}
    36  
    37  	testFlag := ""
    38  	for i, arg := range execution.Args {
    39  		if arg == jmeterTestFileFlag {
    40  			if (i + 1) < len(execution.Args) {
    41  				if execution.Args[i+1] != "<runPath>" {
    42  					testFlag = execution.Args[i+1]
    43  					i++
    44  					continue
    45  				}
    46  			}
    47  		}
    48  	}
    49  
    50  	if workingDir == "" {
    51  		workingDir = dataDir
    52  	}
    53  
    54  	sanityCheck := false
    55  	if testFlag != "" {
    56  		if filepath.IsAbs(testFlag) {
    57  			testPath = testFlag
    58  		} else {
    59  			testPath = filepath.Join(workingDir, testFlag)
    60  		}
    61  
    62  		testFile = filepath.Base(testPath)
    63  		sanityCheck = true
    64  	} else if fileInfo.IsDir() {
    65  		testFile, err = findTestFile(fs, execution, testPath, jmxExtension)
    66  		if err != nil {
    67  			return "", "", "", errors.Wrapf(err, "error searching for %s file in test path %s", jmxExtension, testPath)
    68  		}
    69  
    70  		testPath = filepath.Join(testPath, testFile)
    71  		sanityCheck = true
    72  	}
    73  
    74  	if sanityCheck {
    75  		// sanity checking for test script
    76  		fileInfo, err = fs.Stat(testPath)
    77  		if err != nil || fileInfo.IsDir() {
    78  			output.PrintLogf("%s Could not find file %s in the directory, error: %s", ui.IconCross, testFile, err)
    79  			return "", "", "", errors.Wrapf(err, "could not find file %s in the directory", testFile)
    80  		}
    81  	}
    82  
    83  	return
    84  }
    85  
    86  // findTestFile tries to find test file in args or in testPath directory.
    87  func findTestFile(fs filesystem.FileSystem, execution *testkube.Execution, testPath, testExtension string) (testFile string, err error) {
    88  	if len(execution.Args) > 0 {
    89  		testFile = execution.Args[len(execution.Args)-1]
    90  		if strings.HasPrefix(testFile, envVarPrefix) {
    91  			testFile = os.ExpandEnv(testFile)
    92  		}
    93  		if !strings.HasSuffix(testFile, testExtension) {
    94  			testFile = ""
    95  		} else {
    96  			output.PrintLogf("%s %s file provided as last argument: %s", ui.IconWorld, testExtension, testFile)
    97  			execution.Args = execution.Args[:len(execution.Args)-1]
    98  		}
    99  		if testFile == "" {
   100  			testFile, err = searchInDir(fs, testPath, testExtension)
   101  			if err != nil {
   102  				return "", errors.Wrapf(err, "error searching for %s file in test path %s", testExtension, testPath)
   103  			}
   104  			if testFile != "" {
   105  				output.PrintLogf("%s %s file found in test path: %s", ui.IconWorld, testExtension, testFile)
   106  			}
   107  		}
   108  	}
   109  	if testFile == "" {
   110  		output.PrintLogf("%s  %s file not found in args or test path!", ui.IconCross, testExtension)
   111  		return "", errors.Errorf("no %s file found", testExtension)
   112  	}
   113  	return testFile, nil
   114  }
   115  
   116  // searchInDir searches for file with given extension in given directory.
   117  func searchInDir(fs filesystem.FileSystem, dir, extension string) (string, error) {
   118  	files, err := fs.ReadDir(dir)
   119  	if err != nil {
   120  		return "", err
   121  	}
   122  
   123  	for _, file := range files {
   124  		if !file.IsDir() && strings.HasSuffix(file.Name(), "."+extension) {
   125  			return file.Name(), nil
   126  		}
   127  	}
   128  	return "", nil
   129  }
   130  
   131  // injectAndExpandEnvVars injects variables from params into args and expands them if args contains <envVars> placeholder.
   132  // Returns new args with injected and expanded variables.
   133  func injectAndExpandEnvVars(args []string, params []string) []string {
   134  	copied := make([]string, len(args))
   135  	copy(copied, args)
   136  	for i := range copied {
   137  		if copied[i] == "<envVars>" {
   138  			newArgs := make([]string, len(copied)+len(params)-1)
   139  			copy(newArgs, copied[:i])
   140  			copy(newArgs[i:], params)
   141  			copy(newArgs[i+len(params):], copied[i+1:])
   142  			copied = newArgs
   143  			break
   144  		}
   145  	}
   146  
   147  	for i := range copied {
   148  		copied[i] = os.ExpandEnv(copied[i])
   149  	}
   150  
   151  	return copied
   152  }
   153  
   154  // getParamValue searches for a parameter in the args slice and returns its value.
   155  // It returns an error if the parameter is not found or if it does not have an associated value.
   156  func getParamValue(args []string, param string) (string, error) {
   157  	for i, arg := range args {
   158  		if arg == param {
   159  			// Check if the next element exists
   160  			if i+1 < len(args) {
   161  				return args[i+1], nil
   162  			}
   163  			return "", errors.WithStack(ErrParamMissingValue)
   164  		}
   165  	}
   166  	return "", errors.WithStack(ErrMissingParam)
   167  }