code: func (cc *CachingConnector) janitor() {
  	logger.Debug("starting connection janitor")
  	defer cc.waitgroup.Done()
  
  	ticker := time.NewTicker(cc.sweepTime)
  	defer ticker.Stop()
  	for {
  		select {
  		case <-cc.janitorDone:
  			return
  		case <-ticker.C:
  			cc.lock.Lock()
  			cc.sweepAndRemove()
  			numConn := len(cc.index)
  			cc.lock.Unlock()
  			if numConn == 0 {
  				logger.Debug("closing connection janitor")
  				cc.janitorClosed <- true
  				return
  			}
  		}
  	}
  }
docs: // janitor monitors open connections for shutdown state or extended non-usage.
  // This component operates by running a sweep with a period determined by "sweepTime".
  // When a connection returned the GRPC status connectivity.Shutdown or when the connection
  // has its usages closed for longer than "idleTime", the connection is closed and the
  // "connRemove" notifier is called.
  //
  // The caching connector:
  //    notifies the janitor of close by closing the "done" go channel.
  //
  // The janitor:
  //    calls "connRemove" callback when closing a connection.
  //    decrements the "wg" waitgroup when exiting.
  //    writes to the "done" go channel when closing due to becoming empty.