-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #11 from pavel-zhur/feature/index
Feature/index
- Loading branch information
Showing
97 changed files
with
2,710 additions
and
441 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
20 changes: 20 additions & 0 deletions
20
HarmonyDB.Common/HarmonyDB.Common.FullTextSearch/FullTextSearchExtensions.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
namespace HarmonyDB.Common.FullTextSearch; | ||
|
||
public static class FullTextSearchExtensions | ||
{ | ||
public static readonly char[] Separators = | ||
{ | ||
'-', | ||
',', | ||
' ', | ||
'\r', | ||
'\n', | ||
'\'', | ||
}; | ||
|
||
public static string ToSearchSyntax(this string text) => text.ToLowerInvariant().Replace("ё", "е"); | ||
|
||
public static string SearchSyntaxRemoveSeparators(this string text) => text.Replace("'", ""); | ||
|
||
public static bool SearchSyntaxAnySeparatorsToRemove(this string text) => text.Contains('\''); | ||
} |
14 changes: 14 additions & 0 deletions
14
HarmonyDB.Common/HarmonyDB.Common.FullTextSearch/HarmonyDB.Common.FullTextSearch.csproj
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
<Project Sdk="Microsoft.NET.Sdk"> | ||
|
||
<PropertyGroup> | ||
<TargetFramework>net8.0</TargetFramework> | ||
<ImplicitUsings>enable</ImplicitUsings> | ||
<Nullable>enable</Nullable> | ||
<PackageReadmeFile>readme.md</PackageReadmeFile> | ||
</PropertyGroup> | ||
|
||
<ItemGroup> | ||
<None Include="..\..\nuget readme.md" Pack="true" Link="readme.md" PackagePath="\readme.md" /> | ||
</ItemGroup> | ||
|
||
</Project> |
83 changes: 83 additions & 0 deletions
83
HarmonyDB.Common/HarmonyDB.Common.FullTextSearch/SearchHighlightingTools.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,83 @@ | ||
namespace HarmonyDB.Common.FullTextSearch; | ||
|
||
public static class SearchHighlightingTools | ||
{ | ||
public static IEnumerable<(string fragment, bool isHighlighted)> GetFragments(string? query, string text) | ||
{ | ||
if (string.IsNullOrWhiteSpace(text)) yield break; | ||
var split = query?.ToLowerInvariant().ToSearchSyntax().Split(FullTextSearchExtensions.Separators, StringSplitOptions.RemoveEmptyEntries | StringSplitOptions.TrimEntries); | ||
if (split?.Length is null or 0) | ||
{ | ||
yield return (text, false); | ||
yield break; | ||
} | ||
|
||
var remaining = text.ToLowerInvariant().ToSearchSyntax().SearchSyntaxRemoveSeparators(); | ||
var rendering = text; | ||
var anyToRemove = rendering.SearchSyntaxAnySeparatorsToRemove(); | ||
|
||
while (true) | ||
{ | ||
var first = split | ||
.Select(x => (x, index: (int?)remaining.IndexOf(x, StringComparison.Ordinal))) | ||
.Where(x => x.index > -1) | ||
.OrderBy(x => x.index) | ||
.FirstOrDefault(); | ||
|
||
var index = first.index; | ||
|
||
if (index == null) | ||
{ | ||
yield return (remaining, false); | ||
yield break; | ||
} | ||
|
||
var updatedIndex = index.Value; | ||
|
||
if (updatedIndex > 0 && anyToRemove) | ||
{ | ||
var expected = remaining.Substring(0, index.Value); | ||
var renderingTests = rendering.ToLowerInvariant().ToSearchSyntax(); | ||
while (true) | ||
{ | ||
var test = renderingTests.Substring(0, updatedIndex).SearchSyntaxRemoveSeparators(); | ||
if (test == expected) break; | ||
|
||
updatedIndex++; | ||
if (updatedIndex > 100) throw new("Protection. Failed."); | ||
} | ||
} | ||
|
||
var matchLength = first.x.Length; | ||
var updatedMatchLength = matchLength; | ||
|
||
if (anyToRemove) | ||
{ | ||
var expected = remaining.Substring(index.Value, matchLength); | ||
var renderingTests = rendering.Substring(updatedIndex).ToLowerInvariant().ToSearchSyntax(); | ||
while (true) | ||
{ | ||
var test = renderingTests.Substring(0, updatedMatchLength).SearchSyntaxRemoveSeparators(); | ||
if (test == expected) break; | ||
|
||
updatedMatchLength++; | ||
if (updatedMatchLength > 100) throw new("Protection. Failed."); | ||
} | ||
} | ||
|
||
if (index == 0) | ||
{ | ||
yield return (rendering.Substring(0, updatedMatchLength), true); | ||
} | ||
else | ||
{ | ||
yield return (rendering.Substring(0, updatedIndex), false); | ||
yield return (rendering.Substring(updatedIndex, updatedMatchLength), true); | ||
} | ||
|
||
remaining = remaining.Substring(index.Value + matchLength); | ||
rendering = rendering.Substring(updatedIndex + updatedMatchLength); | ||
if (remaining == string.Empty) yield break; | ||
} | ||
} | ||
} |
2 changes: 1 addition & 1 deletion
2
...tend.Web/Tools/TranspositionExtensions.cs → .../Transposition/TranspositionExtensions.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
75 changes: 75 additions & 0 deletions
75
HarmonyDB.Index/HarmonyDB.Index.Analysis/Services/ProgressionsVisualizer.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,75 @@ | ||
using HarmonyDB.Index.Analysis.Models; | ||
using OneShelf.Common; | ||
|
||
namespace HarmonyDB.Index.Analysis.Services; | ||
|
||
public class ProgressionsVisualizer | ||
{ | ||
private readonly ProgressionsSearch _progressionsSearch; | ||
|
||
public const string AttributeSearch = "search"; | ||
public const string AttributeSearchFirst = "search-first"; | ||
|
||
public ProgressionsVisualizer(ProgressionsSearch progressionsSearch) | ||
{ | ||
_progressionsSearch = progressionsSearch; | ||
} | ||
|
||
public List<(Loop loop, int id, string title, string chordsTitle, bool isCompound, int length)> BuildLoopTitles(ChordsProgression progression) | ||
{ | ||
var loops = _progressionsSearch.FindAllLoops(progression.Compact().ExtendedHarmonyMovementsSequences); | ||
var loopTitles = new List<(Loop loop, int id, string title, string chordsTitle, bool isCompound, int length)>(); | ||
|
||
foreach (var (loop, id) in loops.WithIndices()) | ||
{ | ||
var length = loop.EndMovement - loop.Start + 1; | ||
var chordsTitle = string.Join(" ", Enumerable.Range(loop.Start, length).Append(loop.Start) | ||
.Select(i => progression.ExtendedHarmonyMovementsSequences[loop.SequenceIndex].FirstMovementFromIndex + i) | ||
.Select(i => progression.HarmonySequence[i].harmonyGroup.HarmonyRepresentation)); | ||
var title = $"{loop.Successions}/{loop.Occurrences}, {loop.Coverage.Sum(h => progression.HarmonySequence[h].harmonyGroup.SelectSingle(x => x.EndChordIndex - x.StartChordIndex + 1)) * 100 / progression.OriginalSequence.Count}%"; | ||
|
||
loopTitles.Add((loop, id, title, chordsTitle, loop.IsCompound, length)); | ||
} | ||
|
||
return loopTitles; | ||
} | ||
|
||
public IReadOnlyDictionary<int, string> BuildCustomAttributesForSearch( | ||
ChordsProgression progression, | ||
(Dictionary<ChordsProgression, float> foundProgressionsWithCoverage, Dictionary<HarmonyGroup, bool> harmonyGroupsWithIsFirst) searchResult) | ||
=> progression.OriginalSequence | ||
.WithIndices() | ||
.Select(x => ( | ||
x.x, | ||
x.i, | ||
isFirst: searchResult.harmonyGroupsWithIsFirst.TryGetValue(x.x.harmonyGroup, out var isFirst) | ||
? x.x.indexInHarmonyGroup == 0 && isFirst | ||
: (bool?)null)) | ||
.Where(x => x.isFirst.HasValue) | ||
.ToDictionary(x => x.i, x => x.isFirst!.Value ? AttributeSearchFirst : AttributeSearch); | ||
|
||
public IReadOnlyDictionary<int, string> BuildCustomAttributesForLoop(IReadOnlyList<(Loop loop, int id, string title, string chordsTitle, bool isCompound, int length)> loops, ChordsProgression progression, int? loopId) | ||
{ | ||
var loopsCustomAttributes = new Dictionary<int, string>(); | ||
|
||
foreach (var x in loops.WithIndices() | ||
.Where(x => x.i == loopId) | ||
.SelectMany(l => l.x.loop.Coverage | ||
.Select(i => progression.HarmonySequence[i].harmonyGroup) | ||
.SelectMany(g => Enumerable.Range(g.StartChordIndex, g.EndChordIndex - g.StartChordIndex + 1)))) | ||
{ | ||
loopsCustomAttributes[x] = AttributeSearch; | ||
} | ||
|
||
foreach (var x in loops.WithIndices() | ||
.Where(x => x.i == loopId) | ||
.SelectMany(l => l.x.loop.FoundFirsts | ||
.Select(i => progression.HarmonySequence[i].harmonyGroup) | ||
.SelectMany(g => Enumerable.Range(g.StartChordIndex, g.EndChordIndex - g.StartChordIndex + 1)))) | ||
{ | ||
loopsCustomAttributes[x] = AttributeSearchFirst; | ||
} | ||
|
||
return loopsCustomAttributes; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
6 changes: 0 additions & 6 deletions
6
HarmonyDB.Index/HarmonyDB.Index.Api.Model/VExternal1/SearchResponse.cs
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
2 changes: 1 addition & 1 deletion
2
...Model/VExternal1/SearchRequestOrdering.cs → ...External1/SongsByChordsRequestOrdering.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
6 changes: 6 additions & 0 deletions
6
HarmonyDB.Index/HarmonyDB.Index.Api.Model/VExternal1/SongsByChordsResponse.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
namespace HarmonyDB.Index.Api.Model.VExternal1; | ||
|
||
public record SongsByChordsResponse : PagedResponseBase | ||
{ | ||
public required List<SongsByChordsResponseSong> Songs { get; init; } | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
10 changes: 10 additions & 0 deletions
10
HarmonyDB.Index/HarmonyDB.Index.Api.Model/VExternal1/SongsByHeaderRequest.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
namespace HarmonyDB.Index.Api.Model.VExternal1; | ||
|
||
public record SongsByHeaderRequest : PagedRequestBase | ||
{ | ||
public required string Query { get; init; } | ||
|
||
public int MinRating { get; init; } = 70; | ||
|
||
public int SongsPerPage { get; init; } = 100; | ||
} |
8 changes: 8 additions & 0 deletions
8
HarmonyDB.Index/HarmonyDB.Index.Api.Model/VExternal1/SongsByHeaderResponse.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
using HarmonyDB.Source.Api.Model.V1; | ||
|
||
namespace HarmonyDB.Index.Api.Model.VExternal1; | ||
|
||
public record SongsByHeaderResponse : PagedResponseBase | ||
{ | ||
public required List<IndexHeader> Songs { get; init; } | ||
} |
Oops, something went wrong.