lock method
Locks the semaphore. The Future completes as soon as the semaphore is released and can be locked again.
Most of the time runLocked, debounce or throttle should be preferred.
Implementation
Future lock() async {
if (completer != null) {
await completer!.future;
await lock();
return;
}
completer = Completer();
}