Implement meeting assistant v1

This commit is contained in:
2026-05-20 02:06:16 +02:00
parent 90df1edc03
commit 0297bcc0f6
120 changed files with 11883 additions and 180 deletions
@@ -0,0 +1,83 @@
using System.Text;
using MeetingAssistant.MeetingNotes;
using Microsoft.Extensions.Options;
namespace MeetingAssistant.Summary;
public interface IMeetingSummaryFailureWriter
{
Task<MeetingSummaryRunResult> WriteAsync(
MeetingSessionArtifacts artifacts,
Exception exception,
CancellationToken cancellationToken);
}
public sealed class MeetingSummaryFailureWriter : IMeetingSummaryFailureWriter
{
private readonly MeetingAssistantOptions options;
private readonly IMeetingNoteStore meetingNoteStore;
public MeetingSummaryFailureWriter(
IOptions<MeetingAssistantOptions> options,
IMeetingNoteStore meetingNoteStore)
{
this.options = options.Value;
this.meetingNoteStore = meetingNoteStore;
}
public async Task<MeetingSummaryRunResult> WriteAsync(
MeetingSessionArtifacts artifacts,
Exception exception,
CancellationToken cancellationToken)
{
Directory.CreateDirectory(Path.GetDirectoryName(artifacts.SummaryPath)!);
var meetingNote = File.Exists(artifacts.MeetingNotePath)
? await meetingNoteStore.ReadAsync(artifacts.MeetingNotePath, cancellationToken)
: new MeetingNote("", new MeetingNoteFrontmatter(), "");
var frontmatter = MeetingArtifactFrontmatterRenderer.Create(
artifacts,
meetingNote,
MeetingArtifactFrontmatterRenderer.DefaultTitle(meetingNote, "Meeting Summary"),
artifacts.SummaryPath);
await File.WriteAllTextAsync(
artifacts.SummaryPath,
MeetingArtifactFrontmatterRenderer.Render(
frontmatter,
RenderFailureMarkdown(artifacts, exception)),
cancellationToken);
return new MeetingSummaryRunResult(
artifacts.SummaryPath,
"Summary generation failed. See the summary file for error details.",
Succeeded: false,
Error: exception.Message);
}
private string RenderFailureMarkdown(MeetingSessionArtifacts artifacts, Exception exception)
{
var builder = new StringBuilder();
builder.AppendLine("# Meeting Summary");
builder.AppendLine();
builder.AppendLine("## Summary Generation Failed");
builder.AppendLine();
builder.AppendLine($"Summary generation failed at {DateTimeOffset.Now:O}.");
builder.AppendLine();
builder.AppendLine(MeetingNoteActionLinks.CreateSummaryRetryLink(
options.Api.PublicBaseUrl,
artifacts.SummaryPath));
builder.AppendLine();
builder.AppendLine("## Error");
builder.AppendLine();
builder.AppendLine("```text");
builder.AppendLine(exception.ToString().Replace("```", "` ` `", StringComparison.Ordinal));
builder.AppendLine("```");
builder.AppendLine();
builder.AppendLine("## Meeting Artifacts");
builder.AppendLine();
builder.AppendLine($"- Meeting note: `{artifacts.MeetingNotePath}`");
builder.AppendLine($"- Transcript: `{artifacts.TranscriptPath}`");
builder.AppendLine($"- Assistant context: `{artifacts.AssistantContextPath}`");
builder.AppendLine($"- Summary: `{artifacts.SummaryPath}`");
return builder.ToString();
}
}