github.com/helmwave/helmwave@v0.36.4-0.20240509190856-b35563eba4c6/pkg/release/dependency/node.go (about) 1 package dependency 2 3 import "sync" 4 5 const ( 6 // NodePending is a NodeStatus for pending node. 7 NodePending NodeStatus = iota 8 9 // NodeSuccess is a NodeStatus for success node. 10 NodeSuccess 11 12 // NodeFailed is a NodeStatus for failed node. 13 NodeFailed 14 ) 15 16 // NodeStatus is used to code release status - success or failed. 17 // Please use ReleaseSuccess and ReleaseFailed contants. 18 type NodeStatus int 19 20 // Node is graph node. N stands for data type. 21 type Node[N any] struct { 22 Data N 23 dependencies []*Node[N] 24 lock sync.RWMutex 25 status NodeStatus 26 } 27 28 func newNode[N any](data N) *Node[N] { 29 return &Node[N]{ 30 Data: data, 31 status: NodePending, 32 dependencies: make([]*Node[N], 0), 33 } 34 } 35 36 func (node *Node[N]) SetSucceeded() { 37 node.lock.Lock() 38 defer node.lock.Unlock() 39 40 node.status = NodeSuccess 41 } 42 43 func (node *Node[N]) SetFailed() { 44 node.lock.Lock() 45 defer node.lock.Unlock() 46 47 node.status = NodeFailed 48 } 49 50 func (node *Node[N]) IsDone() bool { 51 node.lock.RLock() 52 defer node.lock.RUnlock() 53 54 return node.status != NodePending 55 } 56 57 func (node *Node[N]) IsFailed() bool { 58 node.lock.RLock() 59 defer node.lock.RUnlock() 60 61 return node.status == NodeFailed 62 } 63 64 func (node *Node[N]) IsReady() bool { 65 node.lock.RLock() 66 deps := node.dependencies 67 node.lock.RUnlock() 68 69 for _, dependency := range deps { 70 if !dependency.IsDone() { 71 return false 72 } 73 74 if dependency.IsFailed() { 75 node.SetFailed() 76 77 return false 78 } 79 } 80 81 return true 82 } 83 84 func (node *Node[N]) addDependency(dependency *Node[N]) { 85 node.lock.Lock() 86 defer node.lock.Unlock() 87 88 node.dependencies = append(node.dependencies, dependency) 89 }