Docs Update label improvements

pull/3079/head
Yunus Emre Kalkan 6 years ago
parent 6316f5d6b6
commit 8cdd19b934

@ -96,6 +96,7 @@ namespace Volo.Docs.Documents
{
leaf.CreationTime = documentUpdateInfo.CreationTime;
leaf.LastUpdatedTime = documentUpdateInfo.LastUpdatedTime;
leaf.LastSignificantUpdateTime = documentUpdateInfo.LastSignificantUpdateTime;
}
}
@ -189,12 +190,12 @@ namespace Volo.Docs.Documents
{
version = string.IsNullOrWhiteSpace(version) ? project.LatestVersionBranchName : version;
async Task<DocumentWithDetailsDto> GetDocumentAsync()
async Task<DocumentWithDetailsDto> GetDocumentAsync(Document oldDocument = null)
{
Logger.LogInformation($"Not found in the cache. Requesting {documentName} from the source...");
var source = _documentStoreFactory.Create(project.DocumentStoreType);
var sourceDocument = await source.GetDocumentAsync(project, documentName, languageCode, version);
var sourceDocument = await source.GetDocumentAsync(project, documentName, languageCode, version, oldDocument?.LastSignificantUpdateTime);
await _documentRepository.DeleteAsync(project.Id, sourceDocument.Name, sourceDocument.LanguageCode, sourceDocument.Version);
await _documentRepository.InsertAsync(sourceDocument, true);
@ -206,7 +207,8 @@ namespace Volo.Docs.Documents
{
Name = sourceDocument.Name,
CreationTime = sourceDocument.CreationTime,
LastUpdatedTime = sourceDocument.LastUpdatedTime
LastUpdatedTime = sourceDocument.LastUpdatedTime,
LastSignificantUpdateTime = sourceDocument.LastSignificantUpdateTime
});
return CreateDocumentWithDetailsDto(project, sourceDocument);
@ -229,7 +231,7 @@ namespace Volo.Docs.Documents
//TODO: Configurable cache time?
document.LastCachedTime + TimeSpan.FromHours(2) < DateTime.Now)
{
return await GetDocumentAsync();
return await GetDocumentAsync(document);
}
var cacheKey = $"DocumentUpdateInfo{document.ProjectId}#{document.Name}#{document.LanguageCode}#{document.Version}";
@ -238,11 +240,17 @@ namespace Volo.Docs.Documents
Name = document.Name,
CreationTime = document.CreationTime,
LastUpdatedTime = document.LastUpdatedTime,
LastSignificantUpdateTime = document.LastSignificantUpdateTime
});
return CreateDocumentWithDetailsDto(project, document);
}
private bool DoesDocuemntHasSignificantUpdates(Document sourceDocument, Document oldDocument)
{
throw new NotImplementedException();
}
protected virtual DocumentWithDetailsDto CreateDocumentWithDetailsDto(Project project, Document document)
{
var documentDto = ObjectMapper.Map<Document, DocumentWithDetailsDto>(document);

@ -10,5 +10,9 @@ namespace Volo.Docs.Documents
public virtual DateTime CreationTime { get; set; }
public virtual DateTime LastUpdatedTime { get; set; }
public virtual bool HasSignificantUpdates { get; set; }
public DateTime? LastSignificantUpdateTime { get; set; }
}
}

@ -26,6 +26,8 @@ namespace Volo.Docs.Documents
public virtual DateTime? LastUpdatedTime { get; set; }
public DateTime? LastSignificantUpdateTime { get; set; }
public bool IsSelected(string documentName)
{
if (documentName == null)

@ -34,6 +34,8 @@ namespace Volo.Docs.Documents
public virtual DateTime CreationTime { get; set; }
public virtual DateTime LastUpdatedTime { get; set; }
public virtual DateTime? LastSignificantUpdateTime { get; set; }
public virtual DateTime LastCachedTime { get; set; }
@ -60,7 +62,8 @@ namespace Volo.Docs.Documents
[NotNull] string localDirectory,
DateTime creationTime,
DateTime lastUpdatedTime,
DateTime lastCachedTime
DateTime lastCachedTime,
DateTime? lastSignificantUpdateTime = null
)
{
Id = id;
@ -80,6 +83,7 @@ namespace Volo.Docs.Documents
CreationTime = creationTime;
LastUpdatedTime = lastUpdatedTime;
LastCachedTime = lastCachedTime;
LastSignificantUpdateTime = lastSignificantUpdateTime;
Contributors = new List<DocumentContributor>();
ExtraProperties = new Dictionary<string, object>();

@ -1,3 +1,4 @@
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Volo.Abp.Domain.Services;
@ -8,7 +9,7 @@ namespace Volo.Docs.Documents
{
public interface IDocumentSource : IDomainService
{
Task<Document> GetDocumentAsync(Project project, string documentName, string languageCode, string version);
Task<Document> GetDocumentAsync(Project project, string documentName, string languageCode, string version, DateTime? lastKnownSignificantUpdateTime = null);
Task<List<VersionInfo>> GetVersionsAsync(Project project);

@ -16,7 +16,7 @@ namespace Volo.Docs.FileSystem.Documents
{
public const string Type = "FileSystem";
public async Task<Document> GetDocumentAsync(Project project, string documentName, string languageCode, string version)
public async Task<Document> GetDocumentAsync(Project project, string documentName, string languageCode, string version, DateTime? lastKnownSignificantUpdateTime = null)
{
var projectFolder = project.GetFileSystemPath();
var path = Path.Combine(projectFolder, languageCode, documentName);

@ -21,13 +21,15 @@ namespace Volo.Docs.GitHub.Documents
public const string Type = "GitHub";
private readonly IGithubRepositoryManager _githubRepositoryManager;
private readonly IGithubPatchAnalyzer _githubPatchAnalyzer;
public GithubDocumentSource(IGithubRepositoryManager githubRepositoryManager)
public GithubDocumentSource(IGithubRepositoryManager githubRepositoryManager, IGithubPatchAnalyzer githubPatchAnalyzer)
{
_githubRepositoryManager = githubRepositoryManager;
_githubPatchAnalyzer = githubPatchAnalyzer;
}
public virtual async Task<Document> GetDocumentAsync(Project project, string documentName, string languageCode, string version)
public virtual async Task<Document> GetDocumentAsync(Project project, string documentName, string languageCode, string version, DateTime? lastKnownSignificantUpdateTime = null)
{
var token = project.GetGitHubAccessTokenOrNull();
var rootUrl = project.GetGitHubUrl(version);
@ -46,7 +48,9 @@ namespace Volo.Docs.GitHub.Documents
fileName = documentName.Substring(documentName.LastIndexOf('/') + 1);
}
var fileCommits = await GetFileCommitsAsync(project, version, $"docs/{languageCode}/{documentName}");
var fileCommits = await GetFileCommitsAsync(project, version, project.GetGitHubInnerUrl(languageCode, documentName));
var documentCreationTime = fileCommits.LastOrDefault()?.Commit.Author.Date.DateTime ?? DateTime.MinValue;
var document= new Document(GuidGenerator.Create(),
project.Id,
@ -60,9 +64,10 @@ namespace Volo.Docs.GitHub.Documents
rootUrl,
rawRootUrl,
localDirectory,
fileCommits.LastOrDefault()?.Commit.Author.Date.DateTime ?? DateTime.MinValue,
documentCreationTime,
fileCommits.FirstOrDefault()?.Commit.Author.Date.DateTime ?? DateTime.MinValue,
DateTime.Now);
DateTime.Now,
GetLastSignificantUpdateTime(fileCommits, project.GetGitHubInnerUrl(languageCode, documentName), lastKnownSignificantUpdateTime, documentCreationTime) ?? lastKnownSignificantUpdateTime);
var authors = fileCommits
.Where(x => x.Author != null)
@ -82,6 +87,24 @@ namespace Volo.Docs.GitHub.Documents
return document;
}
private DateTime? GetLastSignificantUpdateTime(IReadOnlyList<GitHubCommit> fileCommits, string fileName,
DateTime? lastKnownSignificantUpdateTime, DateTime documentCreationTime)
{
var commitsToEvaluate = (lastKnownSignificantUpdateTime != null
? fileCommits.Where(c => c.Commit.Author.Date.DateTime > lastKnownSignificantUpdateTime)
:fileCommits).Where(c=>c.Commit.Author.Date.DateTime > DateTime.Now.AddDays(-14) && c.Commit.Author.Date.DateTime > documentCreationTime);
foreach (var gitHubCommit in commitsToEvaluate)
{
if (_githubPatchAnalyzer.HasPatchSignificantChanges(gitHubCommit.Files.First(f=>f.Filename == fileName).Patch))
{
return gitHubCommit.Commit.Author.Date.DateTime;
}
}
return null;
}
public async Task<List<VersionInfo>> GetVersionsAsync(Project project)
{
List<VersionInfo> versions;

@ -0,0 +1,68 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Volo.Abp.Domain.Services;
namespace Volo.Docs.GitHub.Documents
{
public class GithubPatchAnalyzer : DomainService, IGithubPatchAnalyzer
{
private const string OldChangeStart = "\\n-";
private const string NewChangeStart = "\\n+";
public bool HasPatchSignificantChanges(string patch)
{
var changes = GetChanges(patch);
foreach (var change in changes)
{
var isSignificant = IsChangeSignificant(change);
if (isSignificant)
{
return true;
}
}
return false;
}
private bool IsChangeSignificant(CommitChanges change)
{
throw new NotImplementedException();
}
private List<CommitChanges> GetChanges(string patch)
{
var changes = new List<CommitChanges>();
var changeList = patch.Split("@@").Where(s => !string.IsNullOrWhiteSpace(s)).Where((c, i) => i % 2 == 0).ToList();
foreach (var change in changeList)
{
var commitChange = new CommitChanges();
var lines = change.Split("\\n");
commitChange.OldLines.AddRange(lines.Where(l => l.StartsWith("-")).Select(l => l.Substring(1)).Where(l => !string.IsNullOrWhiteSpace(l)));
commitChange.NewLines.AddRange(lines.Where(l => l.StartsWith("+")).Select(l => l.Substring(1)).Where(l=>!string.IsNullOrWhiteSpace(l)));
changes.Add(commitChange);
}
return changes;
}
private class CommitChanges
{
public List<string> OldLines { get; set; }
public List<string> NewLines { get; set; }
public CommitChanges()
{
OldLines = new List<string>();
NewLines= new List<string>();
}
}
}
}

@ -0,0 +1,12 @@
using System;
using System.Collections.Generic;
using System.Text;
using Volo.Abp.Domain.Services;
namespace Volo.Docs.GitHub.Documents
{
public interface IGithubPatchAnalyzer : IDomainService
{
bool HasPatchSignificantChanges(string patch);
}
}

@ -14,6 +14,12 @@ namespace Volo.Docs.GitHub.Projects
return project.ExtraProperties["GitHubRootUrl"] as string;
}
public static string GetGitHubInnerUrl([NotNull] this Project project, string languageCode, string documentName)
{
return project
.GetGitHubUrl().Split("{version}")[1].EnsureEndsWith('/').TrimStart('/') + languageCode + '/' + documentName;
}
public static string GetGitHubUrl([NotNull] this Project project, string version)
{
return project

@ -127,16 +127,16 @@ namespace Volo.Docs.Areas.Documents.TagHelpers
if (!node.Path.IsNullOrWhiteSpace() && node.CreationTime.HasValue && node.LastUpdatedTime.HasValue)
{
var newBadge = "<span class='badge badge-primary ml-2' title=\"" + _localizer["NewExplanation"] + "\">" + _localizer["New"] + "</span>";
var updBadge = "<span class='badge badge-light ml-2' title=\"" + _localizer["UpdatedExplanation"] + "\">" + _localizer["Upd"] + "</span>";
if(node.CreationTime + TimeSpan.FromDays(14) > DateTime.Now)
{
badge = newBadge;
var newBadge = "<span class='badge badge-primary ml-2' title=\"" + _localizer["NewExplanation"] + "\">" + _localizer["New"] + "</span>";
badge += newBadge;
}
else if (node.LastUpdatedTime + TimeSpan.FromDays(14) > DateTime.Now)
if (node.LastSignificantUpdateTime != null && node.LastSignificantUpdateTime + TimeSpan.FromDays(14) > DateTime.Now)
{
badge = updBadge;
var updBadge = "<span class='badge badge-light ml-2' title=\"" + _localizer["UpdatedExplanation"] + "\">" + _localizer["Upd"] + "</span>";
badge += updBadge;
}
}

Loading…
Cancel
Save