fix: close web access to foreign groups and sessions
This commit is contained in:
@@ -0,0 +1,27 @@
|
||||
@page "/access-denied"
|
||||
|
||||
<PageTitle>Доступ запрещен — GM-Relay</PageTitle>
|
||||
|
||||
<div class="page-container">
|
||||
<div class="glass-card" style="max-width: 640px;">
|
||||
<div class="empty-state">
|
||||
<div class="empty-state-icon">⛔</div>
|
||||
<div class="empty-state-title">Доступ запрещен</div>
|
||||
<p class="empty-state-text">Эта группа или сессия недоступна для вашей учётной записи.</p>
|
||||
<a href="/" class="btn-gm btn-gm-primary">← На главную</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@code {
|
||||
[CascadingParameter]
|
||||
private HttpContext? HttpContext { get; set; }
|
||||
|
||||
protected override void OnInitialized()
|
||||
{
|
||||
if (HttpContext is not null && !HttpContext.Response.HasStarted)
|
||||
{
|
||||
HttpContext.Response.StatusCode = StatusCodes.Status403Forbidden;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -2,8 +2,10 @@
|
||||
@using GmRelay.Web.Services
|
||||
@using GmRelay.Shared.Domain
|
||||
@using Microsoft.AspNetCore.Authorization
|
||||
@using Microsoft.AspNetCore.Components.Authorization
|
||||
@attribute [Authorize]
|
||||
@inject SessionService SessionService
|
||||
@inject AuthorizedSessionService SessionService
|
||||
@inject AuthenticationStateProvider AuthStateProvider
|
||||
@inject NavigationManager Navigation
|
||||
|
||||
<PageTitle>Редактирование сессии — GM-Relay</PageTitle>
|
||||
@@ -73,19 +75,28 @@
|
||||
[Parameter] public Guid SessionId { get; set; }
|
||||
private WebSession? session;
|
||||
private SessionEditModel model = new();
|
||||
private bool isSubmitting = false;
|
||||
private bool isSubmitting;
|
||||
private string? errorMessage;
|
||||
|
||||
protected override async Task OnInitializedAsync()
|
||||
{
|
||||
session = await SessionService.GetSessionAsync(SessionId);
|
||||
if (session != null)
|
||||
var authState = await AuthStateProvider.GetAuthenticationStateAsync();
|
||||
if (!authState.User.TryGetTelegramId(out var telegramId))
|
||||
{
|
||||
model.Title = session.Title;
|
||||
// Convert UTC to Moscow for the picker
|
||||
model.ScheduledAtLocal = session.ScheduledAt.ToMoscow();
|
||||
model.JoinLink = session.JoinLink;
|
||||
Navigation.NavigateTo("/access-denied");
|
||||
return;
|
||||
}
|
||||
|
||||
session = await SessionService.GetSessionForGmAsync(SessionId, telegramId);
|
||||
if (session is null)
|
||||
{
|
||||
Navigation.NavigateTo("/access-denied");
|
||||
return;
|
||||
}
|
||||
|
||||
model.Title = session.Title;
|
||||
model.ScheduledAtLocal = session.ScheduledAt.ToMoscow();
|
||||
model.JoinLink = session.JoinLink;
|
||||
}
|
||||
|
||||
private async Task HandleSubmit()
|
||||
@@ -95,13 +106,22 @@
|
||||
|
||||
try
|
||||
{
|
||||
// The value from <input type="datetime-local"> is considered as "unspecified" or local to browser.
|
||||
// We treat it as Moscow time (UTC+3) and convert to UTC.
|
||||
var authState = await AuthStateProvider.GetAuthenticationStateAsync();
|
||||
if (!authState.User.TryGetTelegramId(out var telegramId))
|
||||
{
|
||||
Navigation.NavigateTo("/access-denied");
|
||||
return;
|
||||
}
|
||||
|
||||
var utcTime = new DateTimeOffset(model.ScheduledAtLocal, TimeSpan.FromHours(3)).ToUniversalTime().UtcDateTime;
|
||||
|
||||
await SessionService.UpdateSessionAsync(SessionId, model.Title, utcTime, model.JoinLink);
|
||||
await SessionService.UpdateSessionForGmAsync(SessionId, telegramId, model.Title, utcTime, model.JoinLink);
|
||||
Navigation.NavigateTo($"/group/{session!.GroupId}");
|
||||
}
|
||||
catch (SessionAccessDeniedException)
|
||||
{
|
||||
Navigation.NavigateTo("/access-denied");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
errorMessage = "Не удалось сохранить изменения: " + ex.Message;
|
||||
|
||||
@@ -2,8 +2,11 @@
|
||||
@using GmRelay.Web.Services
|
||||
@using GmRelay.Shared.Domain
|
||||
@using Microsoft.AspNetCore.Authorization
|
||||
@using Microsoft.AspNetCore.Components.Authorization
|
||||
@attribute [Authorize]
|
||||
@inject SessionService SessionService
|
||||
@inject AuthorizedSessionService SessionService
|
||||
@inject AuthenticationStateProvider AuthStateProvider
|
||||
@inject NavigationManager Navigation
|
||||
|
||||
<PageTitle>Сессии группы — GM-Relay</PageTitle>
|
||||
|
||||
@@ -112,7 +115,18 @@
|
||||
|
||||
protected override async Task OnInitializedAsync()
|
||||
{
|
||||
sessions = await SessionService.GetUpcomingSessionsAsync(GroupId);
|
||||
var authState = await AuthStateProvider.GetAuthenticationStateAsync();
|
||||
if (!authState.User.TryGetTelegramId(out var telegramId))
|
||||
{
|
||||
Navigation.NavigateTo("/access-denied");
|
||||
return;
|
||||
}
|
||||
|
||||
sessions = await SessionService.GetUpcomingSessionsForGmAsync(GroupId, telegramId);
|
||||
if (sessions is null)
|
||||
{
|
||||
Navigation.NavigateTo("/access-denied");
|
||||
}
|
||||
}
|
||||
|
||||
private string GetStatusClass(string status) => status switch
|
||||
|
||||
@@ -3,8 +3,9 @@
|
||||
@using Microsoft.AspNetCore.Components.Authorization
|
||||
@using GmRelay.Web.Services
|
||||
@attribute [Authorize]
|
||||
@inject SessionService SessionService
|
||||
@inject AuthorizedSessionService SessionService
|
||||
@inject AuthenticationStateProvider AuthStateProvider
|
||||
@inject NavigationManager Navigation
|
||||
|
||||
<PageTitle>Панель управления — GM-Relay</PageTitle>
|
||||
|
||||
@@ -88,10 +89,12 @@
|
||||
var user = authState.User;
|
||||
userName = user.Identity?.Name ?? "Мастер Игры";
|
||||
|
||||
var telegramIdClaim = user.FindFirst("TelegramId")?.Value;
|
||||
if (long.TryParse(telegramIdClaim, out var telegramId))
|
||||
if (!user.TryGetTelegramId(out var telegramId))
|
||||
{
|
||||
groups = await SessionService.GetGroupsForGmAsync(telegramId);
|
||||
Navigation.NavigateTo("/access-denied");
|
||||
return;
|
||||
}
|
||||
|
||||
groups = await SessionService.GetGroupsForGmAsync(telegramId);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user