Example #1
0
// editRule edits a rule
func editRule(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	// id
	id, err := strconv.Atoi(ps.ByName("id"))
	if err != nil {
		ResponseError(w, ErrProjectID)
		return
	}

	// Request
	req := &createRuleRequest{}
	if err := RequestBind(r, req); err != nil {
		ResponseError(w, ErrBadRequest)
		return
	}
	// Validate
	if err := models.ValidateRulePattern(req.Pattern); err != nil {
		ResponseError(w, NewValidationWebError(err))
		return
	}
	if err := models.ValidateRuleLevel(req.Level); err != nil {
		ResponseError(w, NewValidationWebError(err))
		return
	}
	if !req.TrendUp && !req.TrendDown && req.ThresholdMax == 0 && req.ThresholdMin == 0 {
		ResponseError(w, ErrRuleNoCondition)
		return
	}

	rule := &models.Rule{}
	if db.Admin.DB().Where("id = ?", id).First(&rule).Error != nil {
		ResponseError(w, ErrRuleNotFound)
		return
	}

	rule.Comment = req.Comment
	rule.Level = req.Level
	rule.Pattern = req.Pattern
	rule.TrendUp = req.TrendUp
	rule.TrendDown = req.TrendDown
	rule.ThresholdMax = req.ThresholdMax
	rule.ThresholdMin = req.ThresholdMin
	rule.Disabled = req.Disabled

	if db.Admin.DB().Save(rule).Error != nil {
		ResponseError(w, ErrRuleUpdateFailed)
		return
	}
	// Cache
	db.Admin.RulesCache.Delete(id)
	db.Admin.RulesCache.Put(rule)
	rule.SetNumMetrics(len(db.Index.Filter(rule.Pattern)))
	ResponseJSONOK(w, rule)
}
Example #2
0
// Migrate projects.
//
//	1. Fetch all projects from belldb.
//	2. Create the project into bansheedb.
//	3. Create the rules for each project.
//
func migrateProjects() {
	var projs []Project
	// Fetch all projects from belldb.
	if err := bellDB.Find(&projs).Error; err != nil {
		log.Fatal("fetch all projects from %s: %v", *bellDBFileName, err)
	}
	for _, proj := range projs {
		// Create banshee project.
		if err := models.ValidateProjectName(proj.Name); err != nil {
			log.Warn("project %s: %v, skipping..", proj.Name, err)
			continue
		}
		p := &models.Project{Name: proj.Name}
		if err := bansheeDB.Create(p).Error; err != nil {
			sqliteErr, ok := err.(sqlite3.Error)
			if ok && sqliteErr.ExtendedCode == sqlite3.ErrConstraintUnique {
				log.Warn("project %s already in %s, skipping..", p.Name, *bansheeDBFileName)
			} else {
				log.Fatal("cannot create project %s: %v", p.Name, err)
			}
		}
		// Fetch its rules from belldb.
		var rules []Rule
		if err := bellDB.Model(proj).Related(&rules).Error; err != nil {
			log.Fatal("cannot fetch rules for %s: %v", p.Name, err)
		}
		for _, rule := range rules {
			// Create banshee rule.
			if err := models.ValidateRulePattern(rule.Pattern); err != nil {
				log.Warn("rule %s: %v, belongs to %s, skippig..", rule.Pattern, err, proj.Name)
				continue
			}
			r := &models.Rule{
				Pattern:   rule.Pattern,
				ProjectID: p.ID,
				TrendUp:   rule.Up,
				TrendDown: rule.Down,
				// Important: max and min for bell is reversed with banshee's.
				ThresholdMax: rule.Min,
				ThresholdMin: rule.Max,
			}
			if err := bansheeDB.Create(r).Error; err != nil {
				sqliteErr, ok := err.(sqlite3.Error)
				if ok && sqliteErr.ExtendedCode == sqlite3.ErrConstraintUnique {
					log.Warn("rule %s already in %s, skipping..", r.Pattern, *bansheeDBFileName)
				} else {
					log.Fatal("cannot create rule %s: %v", r.Pattern, err)
				}
			}
		}
	}
}
Example #3
0
// createRule creates a rule.
func createRule(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	// Params
	projectID, err := strconv.Atoi(ps.ByName("id"))
	if err != nil {
		ResponseError(w, ErrProjectID)
		return
	}
	// Request
	req := &createRuleRequest{
		Level:    models.RuleLevelLow,
		Disabled: false,
	}
	if err := RequestBind(r, req); err != nil {
		ResponseError(w, ErrBadRequest)
		return
	}
	// Validate
	if err := models.ValidateRulePattern(req.Pattern); err != nil {
		ResponseError(w, NewValidationWebError(err))
		return
	}
	if projectID <= 0 {
		// ProjectID is invalid.
		ResponseError(w, ErrProjectID)
		return
	}
	if !req.TrendUp && !req.TrendDown && req.ThresholdMax == 0 && req.ThresholdMin == 0 {
		ResponseError(w, ErrRuleNoCondition)
		return
	}
	if err := models.ValidateRuleLevel(req.Level); err != nil {
		ResponseError(w, NewValidationWebError(err))
		return
	}
	// Find project.
	proj := &models.Project{}
	if err := db.Admin.DB().First(proj, projectID).Error; err != nil {
		switch err {
		case gorm.RecordNotFound:
			ResponseError(w, ErrProjectNotFound)
			return
		default:
			ResponseError(w, NewUnexceptedWebError(err))
			return
		}
	}
	// Create rule.
	rule := &models.Rule{
		ProjectID:    projectID,
		Pattern:      req.Pattern,
		TrendUp:      req.TrendUp,
		TrendDown:    req.TrendDown,
		ThresholdMax: req.ThresholdMax,
		ThresholdMin: req.ThresholdMin,
		Comment:      req.Comment,
		Level:        req.Level,
		Disabled:     req.Disabled,
	}
	if err := db.Admin.DB().Create(rule).Error; err != nil {
		// Write errors.
		sqliteErr, ok := err.(sqlite3.Error)
		if ok {
			switch sqliteErr.ExtendedCode {
			case sqlite3.ErrConstraintNotNull:
				ResponseError(w, ErrNotNull)
				return
			case sqlite3.ErrConstraintPrimaryKey:
				ResponseError(w, ErrPrimaryKey)
				return
			case sqlite3.ErrConstraintUnique:
				ResponseError(w, ErrDuplicateRulePattern)
				return
			}
		}
		// Unexcepted error.
		ResponseError(w, NewUnexceptedWebError(err))
		return
	}
	// Cache
	db.Admin.RulesCache.Put(rule)
	// Response
	rule.SetNumMetrics(len(db.Index.Filter(rule.Pattern)))
	ResponseJSONOK(w, rule)
}