github.com/keybase/client/go@v0.0.0-20241007131713-f10651d043c8/kbfs/libkbfs/ongoing_work_limiter.go (about)

     1  package libkbfs
     2  
     3  import "context"
     4  
     5  // OngoingWorkLimiter limits maximum number of routines that can work on a same
     6  // type of thing at the same time. For example, it can be used for limiting
     7  // number of ongoing rekeys.
     8  type OngoingWorkLimiter struct {
     9  	permits chan struct{}
    10  }
    11  
    12  // NewOngoingWorkLimiter creates a new *OngoingWorkLimiter with capacity of
    13  // maxNumOngoingWorks.
    14  func NewOngoingWorkLimiter(maxNumOngoingWorks int) *OngoingWorkLimiter {
    15  	return &OngoingWorkLimiter{
    16  		permits: make(chan struct{}, maxNumOngoingWorks),
    17  	}
    18  }
    19  
    20  // WaitToStart blocks until the limiter would allow one more routine to start
    21  // working on the thing.
    22  func (owl *OngoingWorkLimiter) WaitToStart(ctx context.Context) error {
    23  	select {
    24  	case owl.permits <- struct{}{}:
    25  		return nil
    26  	case <-ctx.Done():
    27  		return ctx.Err()
    28  	}
    29  }
    30  
    31  // Done tells the limiter that the caller is done working on the thing, and
    32  // somebody else is free to start work.
    33  func (owl *OngoingWorkLimiter) Done() {
    34  	<-owl.permits
    35  }