Move cloning logic to its own file

This has gotten very complex and needs to be properly tested. It's the
number 1 bug.
This commit is contained in:
Vishesh Handa
2021-01-19 14:05:51 +01:00
parent 9946993364
commit 4c7efdb2dc
5 changed files with 94 additions and 77 deletions

View File

@ -241,20 +241,6 @@ class GitNoteRepository {
} }
} }
Future<String> defaultBranch(String remoteName) async {
try {
return await _gitRepo.defaultBranch(
remote: remoteName,
publicKey: settings.sshPublicKey,
privateKey: settings.sshPrivateKey,
password: settings.sshPassword,
);
} on GitException catch (ex, stackTrace) {
Log.e("GitDefaultBranch Failed", ex: ex, stacktrace: stackTrace);
rethrow;
}
}
Future<int> numChanges() async { Future<int> numChanges() async {
try { try {
var repo = await git.GitRepository.load(gitDirPath); var repo = await git.GitRepository.load(gitDirPath);

View File

@ -403,54 +403,6 @@ class Repository with ChangeNotifier {
_gitRepo = GitNoteRepository(gitDirPath: repoPath, settings: settings); _gitRepo = GitNoteRepository(gitDirPath: repoPath, settings: settings);
var repo = await GitRepository.load(repoPath);
var remote = repo.config.remote(remoteName);
var remoteBranchName = "master";
try {
remoteBranchName = await _gitRepo.defaultBranch(remoteName);
} catch (ex) {
Log.w("Could not get git main branch - assuming master", ex: ex);
}
var remoteBranch = await repo.remoteBranch(remoteName, remoteBranchName);
Log.i("Using remote branch: $remoteBranchName");
var branches = await repo.branches();
if (branches.isEmpty) {
Log.i("Completing - no local branch");
if (remoteBranchName != null &&
remoteBranchName.isNotEmpty &&
remoteBranch != null) {
await repo.checkoutBranch(remoteBranchName, remoteBranch.hash);
}
await repo.setUpstreamTo(remote, remoteBranchName);
} else {
var branch = branches[0];
if (branch == remoteBranchName) {
Log.i("Completing - localBranch: $branch");
await repo.setUpstreamTo(remote, remoteBranchName);
await _gitRepo.merge();
} else {
Log.i(
"Completing - localBranch diff remote: $branch $remoteBranchName");
var headRef = await repo.resolveReference(await repo.head());
await repo.checkoutBranch(remoteBranchName, headRef.hash);
await repo.deleteBranch(branch);
await repo.setUpstreamTo(remote, remoteBranchName);
await _gitRepo.merge();
}
// if more than one branch
// TODO: Check if one of the branches matches the remote branch name
// and use that
// if not, then just create a new branch with the remoteBranchName
// and merge ..
}
await _addFileInRepo(repo: this, settings: settings); await _addFileInRepo(repo: this, settings: settings);
this.repoPath = repoPath; this.repoPath = repoPath;

82
lib/setup/clone.dart Normal file
View File

@ -0,0 +1,82 @@
import 'package:dart_git/dart_git.dart';
import 'package:git_bindings/git_bindings.dart' as git_bindings;
import 'package:meta/meta.dart';
import 'package:gitjournal/utils/logger.dart';
Future<void> cloneRemote({
@required String repoPath,
@required String cloneUrl,
@required String remoteName,
@required String sshPublicKey,
@required String sshPrivateKey,
@required String sshPassword,
}) async {
var repo = await GitRepository.load(repoPath);
// FIXME: In the case of no remotes and no commits, revert to clone?
var remote = await repo.addOrUpdateRemote(remoteName, cloneUrl);
var _gitRepo = git_bindings.GitRepo(folderPath: repoPath);
await _gitRepo.fetch(
remote: remoteName,
publicKey: sshPublicKey,
privateKey: sshPrivateKey,
password: sshPassword,
);
var remoteBranchName = "master";
try {
var branch = await _gitRepo.defaultBranch(
remote: remoteName,
publicKey: sshPublicKey,
privateKey: sshPrivateKey,
password: sshPassword,
);
if (branch != null && branch.isNotEmpty) {
Log.i("Got default branch: $branch");
remoteBranchName = branch;
}
} catch (ex) {
Log.w("Could not get git main branch - assuming master", ex: ex);
}
var remoteBranch = await repo.remoteBranch(remoteName, remoteBranchName);
Log.i("Using remote branch: $remoteBranchName");
var branches = await repo.branches();
if (branches.isEmpty) {
Log.i("Completing - no local branch");
if (remoteBranchName != null &&
remoteBranchName.isNotEmpty &&
remoteBranch != null) {
await repo.checkoutBranch(remoteBranchName, remoteBranch.hash);
}
await repo.setUpstreamTo(remote, remoteBranchName);
} else {
var branch = branches[0];
if (branch == remoteBranchName) {
Log.i("Completing - localBranch: $branch");
await repo.setUpstreamTo(remote, remoteBranchName);
await _gitRepo.merge();
} else {
Log.i("Completing - localBranch diff remote: $branch $remoteBranchName");
var headRef = await repo.resolveReference(await repo.head());
await repo.checkoutBranch(remoteBranchName, headRef.hash);
await repo.deleteBranch(branch);
await repo.setUpstreamTo(remote, remoteBranchName);
await _gitRepo.merge();
}
// if more than one branch
// TODO: Check if one of the branches matches the remote branch name
// and use that
// if not, then just create a new branch with the remoteBranchName
// and merge ..
}
}

View File

@ -20,6 +20,7 @@ import 'package:gitjournal/repository.dart';
import 'package:gitjournal/settings.dart'; import 'package:gitjournal/settings.dart';
import 'package:gitjournal/setup/autoconfigure.dart'; import 'package:gitjournal/setup/autoconfigure.dart';
import 'package:gitjournal/setup/button.dart'; import 'package:gitjournal/setup/button.dart';
import 'package:gitjournal/setup/clone.dart';
import 'package:gitjournal/setup/clone_url.dart'; import 'package:gitjournal/setup/clone_url.dart';
import 'package:gitjournal/setup/loading_error.dart'; import 'package:gitjournal/setup/loading_error.dart';
import 'package:gitjournal/setup/repo_selector.dart'; import 'package:gitjournal/setup/repo_selector.dart';
@ -525,18 +526,16 @@ class GitHostSetupScreenState extends State<GitHostSetupScreen> {
String error; String error;
try { try {
var repo = await GitRepository.load(repoPath); await cloneRemote(
await repo.addOrUpdateRemote(widget.remoteName, _gitCloneUrl); cloneUrl: _gitCloneUrl,
remoteName: widget.remoteName,
var repoN = git_bindings.GitRepo(folderPath: repoPath); repoPath: repoPath,
await repoN.fetch( sshPassword: settings.sshPassword,
remote: widget.remoteName, sshPrivateKey: settings.sshPrivateKey,
publicKey: settings.sshPublicKey, sshPublicKey: settings.sshPublicKey,
privateKey: settings.sshPrivateKey,
password: settings.sshPassword,
); );
} on Exception catch (e, stacktrace) { } on Exception catch (e, stacktrace) {
Log.e("Failed to add remote", ex: e, stacktrace: stacktrace); Log.e("Failed to clone", ex: e, stacktrace: stacktrace);
error = e.toString(); error = e.toString();
} }

View File

@ -477,11 +477,9 @@ packages:
git_bindings: git_bindings:
dependency: "direct main" dependency: "direct main"
description: description:
path: "." path: "/Users/vishesh/src/gitjournal/git_bindings"
ref: HEAD relative: false
resolved-ref: "89c587037dd4d9d9270b09b51df40e537d7263c5" source: path
url: "https://github.com/GitJournal/git_bindings.git"
source: git
version: "0.0.18" version: "0.0.18"
git_url_parse2: git_url_parse2:
dependency: "direct main" dependency: "direct main"