mirror of
https://github.com/MindWorkAI/AI-Studio.git
synced 2026-07-07 08:06:27 +00:00
Improved source links in chats (#827)
Some checks are pending
Build and Release / Determine run mode (push) Waiting to run
Build and Release / Read metadata (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-aarch64-apple-darwin, osx-arm64, macos-latest, aarch64-apple-darwin, dmg,app,updater, dmg) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-aarch64-pc-windows-msvc.exe, win-arm64, windows-latest, aarch64-pc-windows-msvc, nsis,updater, nsis) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-aarch64-unknown-linux-gnu, linux-arm64, ubuntu-22.04-arm, aarch64-unknown-linux-gnu, appimage,updater, appimage) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-x86_64-apple-darwin, osx-x64, macos-latest, x86_64-apple-darwin, dmg,app,updater, dmg) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-x86_64-pc-windows-msvc.exe, win-x64, windows-latest, x86_64-pc-windows-msvc, nsis,updater, nsis) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-x86_64-unknown-linux-gnu, linux-x64, ubuntu-22.04, x86_64-unknown-linux-gnu, appimage,updater, appimage) (push) Blocked by required conditions
Build and Release / Prepare & create release (push) Blocked by required conditions
Build and Release / Publish release (push) Blocked by required conditions
Some checks are pending
Build and Release / Determine run mode (push) Waiting to run
Build and Release / Read metadata (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-aarch64-apple-darwin, osx-arm64, macos-latest, aarch64-apple-darwin, dmg,app,updater, dmg) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-aarch64-pc-windows-msvc.exe, win-arm64, windows-latest, aarch64-pc-windows-msvc, nsis,updater, nsis) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-aarch64-unknown-linux-gnu, linux-arm64, ubuntu-22.04-arm, aarch64-unknown-linux-gnu, appimage,updater, appimage) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-x86_64-apple-darwin, osx-x64, macos-latest, x86_64-apple-darwin, dmg,app,updater, dmg) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-x86_64-pc-windows-msvc.exe, win-x64, windows-latest, x86_64-pc-windows-msvc, nsis,updater, nsis) (push) Blocked by required conditions
Build and Release / Build app (${{ matrix.dotnet_runtime }}) (-x86_64-unknown-linux-gnu, linux-x64, ubuntu-22.04, x86_64-unknown-linux-gnu, appimage,updater, appimage) (push) Blocked by required conditions
Build and Release / Prepare & create release (push) Blocked by required conditions
Build and Release / Publish release (push) Blocked by required conditions
Co-authored-by: Thorsten Sommer <SommerEngineering@users.noreply.github.com>
This commit is contained in:
parent
796855f0ef
commit
dd72fd5f8b
@ -1,12 +1,83 @@
|
|||||||
using System.Text;
|
using System.Text;
|
||||||
|
using System.Text.RegularExpressions;
|
||||||
|
|
||||||
using AIStudio.Tools.PluginSystem;
|
using AIStudio.Tools.PluginSystem;
|
||||||
|
|
||||||
namespace AIStudio.Tools;
|
namespace AIStudio.Tools;
|
||||||
|
|
||||||
public static class SourceExtensions
|
public static partial class SourceExtensions
|
||||||
{
|
{
|
||||||
private static string TB(string fallbackEN) => I18N.I.T(fallbackEN, typeof(SourceExtensions).Namespace, nameof(SourceExtensions));
|
private static string TB(string fallbackEN) => I18N.I.T(fallbackEN, typeof(SourceExtensions).Namespace, nameof(SourceExtensions));
|
||||||
|
|
||||||
|
private static void AppendMarkdownLink(StringBuilder sb, string title, string url)
|
||||||
|
{
|
||||||
|
sb.Append('[');
|
||||||
|
sb.Append(EscapeMarkdownLinkText(title));
|
||||||
|
sb.Append("](<");
|
||||||
|
sb.Append(NormalizeLinkDestination(url));
|
||||||
|
sb.Append(">)");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static string EscapeMarkdownLinkText(string text)
|
||||||
|
{
|
||||||
|
return text
|
||||||
|
.Replace(@"\", @"\\")
|
||||||
|
.Replace("[", @"\[")
|
||||||
|
.Replace("]", @"\]")
|
||||||
|
.Replace("\r", " ")
|
||||||
|
.Replace("\n", " ");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static string NormalizeLinkDestination(string url)
|
||||||
|
{
|
||||||
|
var normalized = url.Trim().Replace("\r", string.Empty).Replace("\n", string.Empty);
|
||||||
|
normalized = TryUnwrapMarkdownLink(normalized);
|
||||||
|
|
||||||
|
if (Uri.TryCreate(normalized, UriKind.Absolute, out var absoluteUri))
|
||||||
|
return absoluteUri.GetComponents(UriComponents.AbsoluteUri, UriFormat.UriEscaped);
|
||||||
|
|
||||||
|
var sb = new StringBuilder(normalized.Length);
|
||||||
|
foreach (var c in normalized)
|
||||||
|
{
|
||||||
|
if (IsSafeUrlCharacter(c))
|
||||||
|
{
|
||||||
|
sb.Append(c);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
sb.Append(Uri.EscapeDataString(c.ToString()));
|
||||||
|
}
|
||||||
|
|
||||||
|
return sb.ToString();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static string TryUnwrapMarkdownLink(string value)
|
||||||
|
{
|
||||||
|
var match = MarkdownLinkWithOptionalSuffix().Match(value);
|
||||||
|
if (!match.Success)
|
||||||
|
return value;
|
||||||
|
|
||||||
|
var label = match.Groups["label"].Value;
|
||||||
|
var url = match.Groups["url"].Value;
|
||||||
|
var suffix = match.Groups["suffix"].Value;
|
||||||
|
if (string.IsNullOrEmpty(suffix))
|
||||||
|
return url;
|
||||||
|
|
||||||
|
if (Uri.TryCreate(label, UriKind.Absolute, out var labelUri) &&
|
||||||
|
Uri.TryCreate(url, UriKind.Absolute, out var urlUri) &&
|
||||||
|
Uri.Compare(labelUri, urlUri, UriComponents.AbsoluteUri, UriFormat.SafeUnescaped, StringComparison.OrdinalIgnoreCase) == 0)
|
||||||
|
return url + suffix;
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static bool IsSafeUrlCharacter(char c)
|
||||||
|
{
|
||||||
|
if (char.IsAsciiLetterOrDigit(c))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
return c is '-' or '.' or '_' or '~' or ':' or '/' or '?' or '#' or '[' or ']' or '@' or '!' or '$' or '&' or '\'' or '(' or ')' or '*' or '+' or ',' or ';' or '=';
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Converts a list of sources to a markdown-formatted string.
|
/// Converts a list of sources to a markdown-formatted string.
|
||||||
@ -36,11 +107,8 @@ public static class SourceExtensions
|
|||||||
}
|
}
|
||||||
|
|
||||||
sb.Append($"- [{++sourceNum}] ");
|
sb.Append($"- [{++sourceNum}] ");
|
||||||
sb.Append('[');
|
AppendMarkdownLink(sb, source.Title, source.URL);
|
||||||
sb.Append(source.Title);
|
sb.AppendLine();
|
||||||
sb.Append("](");
|
|
||||||
sb.Append(source.URL);
|
|
||||||
sb.AppendLine(")");
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -55,11 +123,8 @@ public static class SourceExtensions
|
|||||||
foreach (var source in ragSources)
|
foreach (var source in ragSources)
|
||||||
{
|
{
|
||||||
sb.Append($"- [{++sourceNum}] ");
|
sb.Append($"- [{++sourceNum}] ");
|
||||||
sb.Append('[');
|
AppendMarkdownLink(sb, source.Title, source.URL);
|
||||||
sb.Append(source.Title);
|
sb.AppendLine();
|
||||||
sb.Append("](");
|
|
||||||
sb.Append(source.URL);
|
|
||||||
sb.AppendLine(")");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return sb.ToString();
|
return sb.ToString();
|
||||||
@ -76,4 +141,7 @@ public static class SourceExtensions
|
|||||||
if (sources.All(s => s.URL != addedSource.URL && s.Title != addedSource.Title))
|
if (sources.All(s => s.URL != addedSource.URL && s.Title != addedSource.Title))
|
||||||
sources.Add((Source)addedSource);
|
sources.Add((Source)addedSource);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[GeneratedRegex(@"^\[(?<label>[^\]]+)\]\((?<url>[^)\r\n]+)\)(?<suffix>.*)$")]
|
||||||
|
private static partial Regex MarkdownLinkWithOptionalSuffix();
|
||||||
}
|
}
|
||||||
@ -1,4 +1,5 @@
|
|||||||
# v26.6.3, build 243 (2026-06-xx xx:xx UTC)
|
# v26.6.3, build 243 (2026-06-xx xx:xx UTC)
|
||||||
|
- Improved source links in chat answers when file or document names contained spaces, umlauts, or other special characters. Source entries now open much more reliably for documents with names such as PDFs from shared portals or internal knowledge bases.
|
||||||
- Improved all assistants, so running tasks can continue when you leave the assistant and return later.
|
- Improved all assistants, so running tasks can continue when you leave the assistant and return later.
|
||||||
- Improved the assistant overview so it shows which assistants are still running or have a result ready.
|
- Improved the assistant overview so it shows which assistants are still running or have a result ready.
|
||||||
- Improved the activity indicators for running chats and assistants so they use a consistent blue highlight.
|
- Improved the activity indicators for running chats and assistants so they use a consistent blue highlight.
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user