feat: Add overlay commit mode.
This commit is contained in:
parent
33d1a4bf49
commit
c0d22d3959
@ -1221,11 +1221,13 @@ public class RepositoryService : BaseService<RepositoryService>
|
|||||||
|
|
||||||
|
|
||||||
var localDb = GetRepositoryLocalDatabase(repo);
|
var localDb = GetRepositoryLocalDatabase(repo);
|
||||||
var manifestList = CreateCommitManifestByCurrentBaselineAndChanges(localDb.LocalAccessor, changes);
|
var (manifestList, miniManifestList) = CreateCommitManifestByCurrentBaselineAndChanges(localDb.LocalAccessor, changes);
|
||||||
|
var snapshot = manifestList.Select(l => $"{l.ModifyTime.ToBinary()}${l.WorkPath}");
|
||||||
|
|
||||||
|
Guid commitId;
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
|
||||||
// Renew for once.
|
// Renew for once.
|
||||||
if (api.RequireRefreshToken() && !(await api.TryRefreshTokenAsync()))
|
if (api.RequireRefreshToken() && !(await api.TryRefreshTokenAsync()))
|
||||||
{
|
{
|
||||||
@ -1234,38 +1236,63 @@ public class RepositoryService : BaseService<RepositoryService>
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Decide create new depot, create full depot or create addon depot.
|
// Decide create new depot, create full depot or create addon depot.
|
||||||
var changesSize = localDb.LocalAccessor.Changes.Values.Sum(x => (long) x.File.Size);
|
|
||||||
var hasAddOrModify = localDb.LocalAccessor.Changes.Any(x =>
|
var hasAddOrModify = localDb.LocalAccessor.Changes.Any(x =>
|
||||||
x.Value.Type == ChangeInfoType.Add || x.Value.Type == ChangeInfoType.Modify);
|
x.Value.Type == ChangeInfoType.Add || x.Value.Type == ChangeInfoType.Modify);
|
||||||
|
var newDepot = forceBaseline || hasAddOrModify || localDb.RepoAccessor == null;
|
||||||
|
|
||||||
|
if (newDepot)
|
||||||
// Generate depot
|
|
||||||
var tempDepotPath = await CreateDepotIntoTempFileAsync(repo, manifestList);
|
|
||||||
if (tempDepotPath == null) return null;
|
|
||||||
|
|
||||||
// Upload and create commit
|
|
||||||
await using var str = File.OpenRead(tempDepotPath);
|
|
||||||
var snapshot = manifestList.Select(l => $"{l.ModifyTime.ToBinary()}${l.WorkPath}");
|
|
||||||
if (api.RequireRefreshToken() && !(await api.TryRefreshTokenAsync()))
|
|
||||||
{
|
{
|
||||||
api.ClearGateway();
|
var changesSize = localDb.LocalAccessor.Changes.Values.Sum(x => (long) x.File.Size);
|
||||||
return null;
|
var baselineSize = localDb.RepoAccessor?.Sum(x => (long) x.Size) ?? 0;
|
||||||
|
var changesRatio = changesSize / (double) baselineSize;
|
||||||
|
var isBaseline = forceBaseline || localDb.CurrentCommit == null || changesRatio > 0.8f;
|
||||||
|
var depotFiles = isBaseline ? manifestList : miniManifestList;
|
||||||
|
|
||||||
|
// Generate depot
|
||||||
|
var tempDepotPath = await CreateDepotIntoTempFileAsync(repo, depotFiles);
|
||||||
|
if (tempDepotPath == null) return null;
|
||||||
|
Console.WriteLine($"Create new {(isBaseline ? "baseline" : "overlay")} depot at \"{tempDepotPath}\"");
|
||||||
|
|
||||||
|
// Upload and create commit
|
||||||
|
await using var str = File.OpenRead(tempDepotPath);
|
||||||
|
if (api.RequireRefreshToken() && !(await api.TryRefreshTokenAsync()))
|
||||||
|
{
|
||||||
|
api.ClearGateway();
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
var requireDepot = isBaseline ? [] : new[] {localDb.CurrentCommit.ToString()!};
|
||||||
|
var rsp = await api.Gateway.CreateCommit(repo.OwnerName, repo.Name,
|
||||||
|
new StreamPart(str, Path.GetFileName(tempDepotPath)), message, snapshot, requireDepot, "");
|
||||||
|
|
||||||
|
commitId = rsp.CommitId;
|
||||||
|
|
||||||
|
// Move depot file to destination
|
||||||
|
var depotsPath = PathUtility.GetWorkspaceDepotCachePath(Api.Current.Username.Value!, repo.OwnerName, repo.Name);
|
||||||
|
var finalPath = Path.Combine(depotsPath, rsp.MainDepotId.ToString());
|
||||||
|
Directory.CreateDirectory(depotsPath);
|
||||||
|
File.Move(tempDepotPath, finalPath, true);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Upload and create commit
|
||||||
|
if (api.RequireRefreshToken() && !(await api.TryRefreshTokenAsync()))
|
||||||
|
{
|
||||||
|
api.ClearGateway();
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
var rsp = await api.Gateway.CreateCommit(repo.OwnerName, repo.Name, null!,
|
||||||
|
message, snapshot, [], localDb.CurrentCommit?.ToString() ?? "");
|
||||||
|
|
||||||
|
commitId = rsp.CommitId;
|
||||||
}
|
}
|
||||||
|
|
||||||
var rsp = await api.Gateway.CreateCommit(repo.OwnerName, repo.Name,
|
|
||||||
new StreamPart(str, Path.GetFileName(tempDepotPath)), message, snapshot, [], string.Empty);
|
|
||||||
|
|
||||||
// Move depot file to destination
|
|
||||||
var depotsPath = PathUtility.GetWorkspaceDepotCachePath(Api.Current.Username.Value!, repo.OwnerName, repo.Name);
|
|
||||||
var finalPath = Path.Combine(depotsPath, rsp.MainDepotId.ToString());
|
|
||||||
Directory.CreateDirectory(depotsPath);
|
|
||||||
File.Move(tempDepotPath, finalPath, true);
|
|
||||||
|
|
||||||
// Fetch mapped manifest
|
// Fetch mapped manifest
|
||||||
var manifest = await DownloadManifestFromServerAsync(repo, rsp.CommitId);
|
var manifest = await DownloadManifestFromServerAsync(repo, commitId);
|
||||||
if (manifest == null) return null;
|
if (manifest == null) return null;
|
||||||
|
|
||||||
var accessor = await DownloadDepotsAndUseLocalCachesToGenerateRepositoryFileTreeAccessorFromServerAsync(repo, rsp.CommitId);
|
var accessor = await DownloadDepotsAndUseLocalCachesToGenerateRepositoryFileTreeAccessorFromServerAsync(repo, commitId);
|
||||||
if (accessor == null) return null; //todo this is a really fatal issue...
|
if (accessor == null) return null; //todo this is a really fatal issue...
|
||||||
if (localDb.RepoAccessor != null)
|
if (localDb.RepoAccessor != null)
|
||||||
{
|
{
|
||||||
@ -1282,10 +1309,11 @@ public class RepositoryService : BaseService<RepositoryService>
|
|||||||
|
|
||||||
// Point to latest state.
|
// Point to latest state.
|
||||||
localDb.RepoAccessor = accessor;
|
localDb.RepoAccessor = accessor;
|
||||||
localDb.CurrentCommit = rsp.CommitId;
|
localDb.CurrentCommit = commitId;
|
||||||
localDb.LocalAccessor.SetBaseline(accessor);
|
localDb.LocalAccessor.SetBaseline(accessor);
|
||||||
SaveRepositoryLocalDatabaseChanges(repo);
|
SaveRepositoryLocalDatabaseChanges(repo);
|
||||||
|
|
||||||
|
Console.WriteLine($"Successful create commit as {commitId}");
|
||||||
return manifest;
|
return manifest;
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
@ -1296,11 +1324,12 @@ public class RepositoryService : BaseService<RepositoryService>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<WorkspaceFile> CreateCommitManifestByCurrentBaselineAndChanges
|
private (List<WorkspaceFile>, List<WorkspaceFile>) CreateCommitManifestByCurrentBaselineAndChanges
|
||||||
(LocalFileTreeAccessor accessor, IEnumerable<ChangeInfo> changes, bool hard = false)
|
(LocalFileTreeAccessor accessor, IEnumerable<ChangeInfo> changes, bool hard = false)
|
||||||
{
|
{
|
||||||
// Create a new depot file manifest.
|
// Create a new depot file manifest.
|
||||||
var files = accessor.BaselineFiles.Values.ToList();
|
var files = accessor.BaselineFiles.Values.ToList();
|
||||||
|
var overlayFsStatus = new List<WorkspaceFile>();
|
||||||
foreach (var c in changes)
|
foreach (var c in changes)
|
||||||
{
|
{
|
||||||
switch (c.Type)
|
switch (c.Type)
|
||||||
@ -1325,6 +1354,7 @@ public class RepositoryService : BaseService<RepositoryService>
|
|||||||
}
|
}
|
||||||
|
|
||||||
files.Add(c.File);
|
files.Add(c.File);
|
||||||
|
overlayFsStatus.Add(c.File);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ChangeInfoType.Remove:
|
case ChangeInfoType.Remove:
|
||||||
@ -1355,12 +1385,13 @@ public class RepositoryService : BaseService<RepositoryService>
|
|||||||
}
|
}
|
||||||
|
|
||||||
files[idx] = c.File;
|
files[idx] = c.File;
|
||||||
|
overlayFsStatus.Add(c.File);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return files;
|
return (files, overlayFsStatus);
|
||||||
}
|
}
|
||||||
|
|
||||||
public async ValueTask<string?> CreateDepotIntoTempFileAsync(RepositoryModel repo, IEnumerable<WorkspaceFile> depotFiles)
|
public async ValueTask<string?> CreateDepotIntoTempFileAsync(RepositoryModel repo, IEnumerable<WorkspaceFile> depotFiles)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user