// checkContent check rule content for problems func checkContent(r *rules.Rule) []*Problem { var result []*Problem for respId, resp := range r.Responses { sectionId := "@RESPONSE" if respId != rules.DEFAULT { sectionId += ":" + respId } if resp.File != "" && resp.Content != "" { result = append(result, &Problem{ Type: PROBLEM_ERR, Info: "Response body have two sources", Desc: fmtc.Sprintf("You define two different sources for response body (file and content in response section) in section %s. Please use only one source (file OR content in response section).", sectionId), }, ) } if resp.URL != "" && resp.Content != "" { result = append(result, &Problem{ Type: PROBLEM_ERR, Info: "Response body have two sources", Desc: fmtc.Sprintf("You define two different sources for response body (url and content in response section) in section %s. Please use only one source (url OR content in response section).", sectionId), }, ) } if resp.File == "" && resp.Content == "" && resp.URL != "" { if resp.Code == 200 || resp.Code == 0 { result = append(result, &Problem{ Type: PROBLEM_ERR, Info: "Response body is empty", Desc: fmtc.Sprintf("Section %s doesn't contains any response data.", sectionId), }, ) } } if resp.File != "" && !fsutil.IsExist(resp.File) { result = append(result, &Problem{ Type: PROBLEM_ERR, Info: "File with response is not exist", Desc: fmtc.Sprintf("File %s defined in %s section is not exist.", resp.File, sectionId), }, ) } else { if resp.File != "" && !fsutil.IsReadable(resp.File) { result = append(result, &Problem{ Type: PROBLEM_ERR, Info: "File with response is not readable", Desc: fmtc.Sprintf("File %s defined in %s section is not readable.", resp.File, sectionId), }, ) } } } return result }
// findFile try to find log file func findFile(file string) string { if fsutil.IsExist(file) { return file } configPath := fsutil.ProperPath("FRS", confPaths) if configPath == "" { return file } config, err := knf.Read(configPath) logDir := config.GetS("data:log-dir") if err != nil || logDir == "" { return file } if !strings.Contains(file, ".log") { file += ".log" } if fsutil.CheckPerms("FRS", path.Join(logDir, file)) { return path.Join(logDir, file) } return file }
// Check check rule or all rules for some service func Check(target string) error { if target == "" { return errors.New("You must difine mock file or service name") } targetService, targetMock, targetDir := rules.ParsePath(target) serviceDir := path.Join(knf.GetS(DATA_RULE_DIR), targetService) if !fsutil.IsExist(serviceDir) { return fmtc.Errorf("Service %s is not exist", targetService) } var ruleInfoSlice []*RuleInfo if targetMock != "" { ruleInfoSlice = append(ruleInfoSlice, &RuleInfo{targetService, targetMock, targetDir}) } else { mockFiles := fsutil.ListAllFiles(serviceDir, true, &fsutil.ListingFilter{MatchPatterns: []string{"*.mock"}}, ) for _, mockFile := range mockFiles { mockPath := path.Join(targetService, strings.Replace(mockFile, ".mock", "", -1)) _, targetMock, targetDir := rules.ParsePath(mockPath) ruleInfoSlice = append(ruleInfoSlice, &RuleInfo{targetService, targetMock, targetDir}) } } if len(ruleInfoSlice) == 0 { fmtc.Println("\n{y}No mock's were found{!}\n") return nil } var maxProblemType = PROBLEM_NONE for _, rule := range ruleInfoSlice { maxProblemType = mathutil.MaxU8(checkRule(rule), maxProblemType) } if maxProblemType > PROBLEM_NONE { fmtutil.Separator(false) } switch maxProblemType { case PROBLEM_NONE: fmtc.Printf("\n{g}%s{!}\n\n", okMessages[rand.Int(len(okMessages))]) case PROBLEM_WARN: fmtc.Printf("{y}%s{!}\n\n", warnMessages[rand.Int(len(warnMessages))]) case PROBLEM_ERR: fmtc.Printf("{r}%s{!}\n\n", errorMessages[rand.Int(len(errorMessages))]) } return nil }
func Make(name string) error { if !fsutil.IsWritable(knf.GetS(DATA_RULE_DIR)) { return fmt.Errorf("Directory %s must be writable.", knf.GetS(DATA_RULE_DIR)) } if name == "" { return errors.New("You must difine mock file name (service1/mock1 for example)") } if !strings.Contains(name, "/") { return errors.New("You must difine mock file name as <service-id>/<mock-name>.") } template := knf.GetS(TEMPLATE_PATH) ruleDir := knf.GetS(DATA_RULE_DIR) dirName := path.Dir(name) fullPath := path.Join(ruleDir, name) if !strings.Contains(fullPath, ".mock") { fullPath += ".mock" } if fsutil.IsExist(fullPath) { return fmt.Errorf("File %s already exist\n", fullPath) } if template == "" || !fsutil.CheckPerms("FRS", template) { return createMock(MOCK_TEMPLATE, dirName, fullPath) } templData, err := ioutil.ReadFile(template) if err != nil { return fmt.Errorf("Can't read template content from %s: %v", template, err) } return createMock(string(templData), dirName, fullPath) }
// Load load and parse all rules func (obs *Observer) Load() bool { var ok = true for _, r := range obs.uriMap { if !fsutil.IsExist(r.Path) { delete(obs.uriMap, r.Request.URI) delete(obs.wcMap, r.Path) delete(obs.errMap, r.Path) delete(obs.pathMap, r.Path) delete(obs.nameMap[r.Service], r.FullName) // If no one rule found for service, remove it's own map if len(obs.nameMap[r.Service]) == 0 { delete(obs.nameMap, r.Service) } log.Info("Rule %s unloaded (mock file deleted)", r.PrettyPath) continue } mtime, _ := fsutil.GetMTime(r.Path) if r.ModTime.UnixNano() != mtime.UnixNano() { rule, err := Parse(obs.ruleDir, r.Service, r.Dir, r.Name) if err != nil { log.Error(err.Error()) ok = false continue } // URI can be changed, remove rule from uri map anyway delete(obs.uriMap, r.Request.URI) delete(obs.errMap, r.Path) if r.IsWildcard { delete(obs.wcMap, r.Path) } obs.uriMap[rule.Request.URI] = rule obs.pathMap[rule.Path] = rule if rule.IsWildcard { obs.wcMap[rule.Path] = rule } log.Info("Rule %s reloaded", rule.PrettyPath) } } if !fsutil.CheckPerms("DRX", obs.ruleDir) { log.Error("Can't read directory with rules (%s)", obs.ruleDir) return false } rules := fsutil.ListAllFiles( obs.ruleDir, true, &fsutil.ListingFilter{ MatchPatterns: []string{"*.mock"}, }, ) if len(rules) == 0 { return ok } if !obs.checkRules(rules) { ok = false } return ok }