This is a little convoluted. Why not this:

    Future clone() {
       _stopwatch = new PrintProfiler('clone');
       _clone(_options.repoUrl);
   }

   Future _clone(String url) {
       HttpFetcher fetcher = new HttpFetcher(_options.store, "origin",
           url, _options.username, _options.password);
  
         return fetcher.isValidRepoUrl(_options.repoUrl).then((isValid) {
           if (isValid) {
             return _startClone(fetcher);
           } else if (!url.endsWith('.git')) {
             return _clone(url + '.git');
           } else {
             return new Future.error('...');
           }
         });
    }

One fetcher, one _startClone() call, etc.