constraint.go raw

   1  package strategy
   2  
   3  import "git.mleku.dev/mleku/dendrite/pkg/axiom"
   4  
   5  // StrategyConstraint defines a lattice site that accepts strategy elements
   6  // of a specific category and minimum granularity level.
   7  // Implements axiom.Constraint and axiom.LayeredConstraint.
   8  type StrategyConstraint struct {
   9  	Cat      Category
  10  	MinLevel Level
  11  }
  12  
  13  // Tag returns "strategy:<category>".
  14  func (c StrategyConstraint) Tag() string {
  15  	return "strategy:" + c.Cat.String()
  16  }
  17  
  18  // Admits returns true for StrategyElements of matching category and
  19  // sufficient granularity.
  20  func (c StrategyConstraint) Admits(e axiom.Element) bool {
  21  	se, ok := e.(StrategyElement)
  22  	if !ok {
  23  		return false
  24  	}
  25  	return se.Cat == c.Cat && se.Lvl >= c.MinLevel
  26  }
  27  
  28  // Layer returns the strategy layer.
  29  func (c StrategyConstraint) Layer() axiom.Layer {
  30  	return axiom.Layer{Name: "strategy", Depth: int(c.MinLevel)}
  31  }
  32  
  33  // Aligns checks that a layered element is in the strategy layer.
  34  func (c StrategyConstraint) Aligns(le axiom.LayeredElement) bool {
  35  	return le.Layer().Name == "strategy"
  36  }
  37  
  38  // CategoryConstraint is a broader constraint accepting any strategy element
  39  // regardless of category. Used for cross-chapter bridge sites.
  40  type CategoryConstraint struct{}
  41  
  42  // Tag returns "strategy".
  43  func (CategoryConstraint) Tag() string { return "strategy" }
  44  
  45  // Admits returns true for any StrategyElement.
  46  func (CategoryConstraint) Admits(e axiom.Element) bool {
  47  	_, ok := e.(StrategyElement)
  48  	return ok
  49  }
  50  
  51  // Verify interface compliance.
  52  var (
  53  	_ axiom.Constraint        = StrategyConstraint{}
  54  	_ axiom.LayeredConstraint = StrategyConstraint{}
  55  	_ axiom.Constraint        = CategoryConstraint{}
  56  )
  57