revert: rollback Fluent UI and Blazor homepage to last successful state (3be3794)
This commit is contained in:
@@ -6,53 +6,77 @@
|
||||
@inject BlogService BlogService
|
||||
@inject ICategoryRepository CategoryRepository
|
||||
@inject NavigationManager Navigation
|
||||
@inject IJSRuntime JS
|
||||
@inject ISnackbar Snackbar
|
||||
|
||||
<PageTitle>새 포스트 작성</PageTitle>
|
||||
|
||||
<section class="admin-page-hero">
|
||||
<div>
|
||||
<div class="admin-eyebrow">Content</div>
|
||||
<h1 class="admin-page-title">새 포스트 작성</h1>
|
||||
<p class="admin-page-subtitle">새로운 블로그 포스트를 작성합니다.</p>
|
||||
<MudText Typo="Typo.caption" Class="admin-eyebrow">Content</MudText>
|
||||
<MudText Typo="Typo.h4" Class="admin-page-title">새 포스트 작성</MudText>
|
||||
<MudText Typo="Typo.body2" Class="admin-page-subtitle">새로운 블로그 포스트를 작성합니다.</MudText>
|
||||
</div>
|
||||
<button type="button" class="site-button secondary" @onclick='() => Navigation.NavigateTo("/taxbaik/admin/blog")'>취소</button>
|
||||
<MudButton Variant="Variant.Outlined" StartIcon="@Icons.Material.Filled.Close" @onclick="GoBack">취소</MudButton>
|
||||
</section>
|
||||
|
||||
<div class="admin-surface mt-4">
|
||||
<form class="admin-dialog-card" @onsubmit="SavePost" @onsubmit:preventDefault="true">
|
||||
<label>제목 * <input class="admin-input" @bind="model.Title" /></label>
|
||||
<label>카테고리
|
||||
<select class="admin-input" @bind="CategoryIdText">
|
||||
<option value="">선택하세요</option>
|
||||
@foreach (var category in categories)
|
||||
{
|
||||
<option value="@category.Id.ToString()">@category.Name</option>
|
||||
}
|
||||
</select>
|
||||
</label>
|
||||
<label>본문 * <textarea class="admin-input" rows="10" @bind="model.Content"></textarea></label>
|
||||
<label>태그 (쉼표로 구분) <input class="admin-input" @bind="model.Tags" /></label>
|
||||
<label>SEO 제목 <input class="admin-input" @bind="model.SeoTitle" /></label>
|
||||
<label>SEO 설명 <textarea class="admin-input" rows="3" @bind="model.SeoDescription"></textarea></label>
|
||||
<label><input type="checkbox" @bind="model.IsPublished" /> 즉시 발행</label>
|
||||
<div class="admin-dialog-actions">
|
||||
<button type="submit" class="site-button primary">저장</button>
|
||||
<MudPaper Class="pa-4 mt-4" Elevation="1">
|
||||
<MudForm @ref="form">
|
||||
<MudTextField @bind-Value="model.Title" Label="제목"
|
||||
Variant="Variant.Outlined" Class="mb-4" Required="true" />
|
||||
|
||||
<MudSelect T="int?" @bind-Value="model.CategoryId" Label="카테고리"
|
||||
Variant="Variant.Outlined" Class="mb-4">
|
||||
@foreach (var category in categories)
|
||||
{
|
||||
<MudSelectItem T="int?" Value="@((int?)category.Id)">@category.Name</MudSelectItem>
|
||||
}
|
||||
</MudSelect>
|
||||
|
||||
<MudTextField @bind-Value="model.Content" Label="본문"
|
||||
Variant="Variant.Outlined" Lines="10" Class="mb-4" Required="true" />
|
||||
|
||||
<MudTextField @bind-Value="model.Tags" Label="태그 (쉼표로 구분)"
|
||||
Variant="Variant.Outlined" Class="mb-4" />
|
||||
|
||||
<MudTextField @bind-Value="model.SeoTitle" Label="SEO 제목"
|
||||
Variant="Variant.Outlined" Class="mb-4" />
|
||||
|
||||
<MudTextField @bind-Value="model.SeoDescription" Label="SEO 설명"
|
||||
Variant="Variant.Outlined" Lines="3" Class="mb-4" />
|
||||
|
||||
<MudCheckBox @bind-Checked="model.IsPublished" Label="즉시 발행" Class="mb-4" />
|
||||
|
||||
<div class="d-flex gap-2">
|
||||
<MudButton Variant="Variant.Filled" Color="Color.Primary"
|
||||
@onclick="SavePost">저장</MudButton>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</MudForm>
|
||||
</MudPaper>
|
||||
|
||||
@code {
|
||||
private MudForm? form;
|
||||
private List<Domain.Entities.Category> categories = [];
|
||||
private CreatePostModel model = new();
|
||||
private string CategoryIdText { get => model.CategoryId?.ToString() ?? ""; set => model.CategoryId = int.TryParse(value, out var id) ? id : null; }
|
||||
|
||||
protected override async Task OnInitializedAsync()
|
||||
{
|
||||
categories = (await CategoryRepository.GetAllAsync()).ToList();
|
||||
}
|
||||
|
||||
private void GoBack()
|
||||
{
|
||||
Navigation.NavigateTo("/taxbaik/admin/blog");
|
||||
}
|
||||
|
||||
private async Task SavePost()
|
||||
{
|
||||
if (form == null)
|
||||
return;
|
||||
|
||||
await form.Validate();
|
||||
if (!form.IsValid)
|
||||
return;
|
||||
|
||||
try
|
||||
{
|
||||
await BlogService.CreateAsync(new CreateBlogPostDto
|
||||
@@ -66,12 +90,12 @@
|
||||
IsPublished = model.IsPublished
|
||||
});
|
||||
|
||||
await JS.InvokeVoidAsync("alert", "포스트가 저장되었습니다.");
|
||||
Snackbar.Add("포스트가 저장되었습니다.", Severity.Success);
|
||||
Navigation.NavigateTo("/taxbaik/admin/blog");
|
||||
}
|
||||
catch (ValidationException ex)
|
||||
{
|
||||
await JS.InvokeVoidAsync("alert", ex.Message);
|
||||
Snackbar.Add(ex.Message, Severity.Error);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -6,60 +6,76 @@
|
||||
@inject BlogService BlogService
|
||||
@inject ICategoryRepository CategoryRepository
|
||||
@inject NavigationManager Navigation
|
||||
@inject IJSRuntime JS
|
||||
@inject ISnackbar Snackbar
|
||||
@inject IDialogService DialogService
|
||||
|
||||
<PageTitle>포스트 수정</PageTitle>
|
||||
|
||||
<section class="admin-page-hero">
|
||||
<div>
|
||||
<div class="admin-eyebrow">Content</div>
|
||||
<h1 class="admin-page-title">포스트 수정</h1>
|
||||
<p class="admin-page-subtitle">블로그 포스트를 수정합니다.</p>
|
||||
<MudText Typo="Typo.caption" Class="admin-eyebrow">Content</MudText>
|
||||
<MudText Typo="Typo.h4" Class="admin-page-title">포스트 수정</MudText>
|
||||
<MudText Typo="Typo.body2" Class="admin-page-subtitle">블로그 포스트를 수정합니다.</MudText>
|
||||
</div>
|
||||
<button type="button" class="site-button secondary" @onclick='() => Navigation.NavigateTo("/taxbaik/admin/blog")'>취소</button>
|
||||
<MudButton Variant="Variant.Outlined" StartIcon="@Icons.Material.Filled.Close" @onclick="GoBack">취소</MudButton>
|
||||
</section>
|
||||
|
||||
@if (isLoading)
|
||||
{
|
||||
<div class="admin-surface mt-4"><Skeleton Count="4" CssClass="taxbaik-skeleton-grid" /></div>
|
||||
<MudProgressLinear Color="Color.Primary" Indeterminate="true" Class="mt-4" />
|
||||
}
|
||||
else if (post == null)
|
||||
{
|
||||
<div class="admin-surface mt-4">포스트를 찾을 수 없습니다.</div>
|
||||
<MudAlert Severity="Severity.Error" Class="mt-4">포스트를 찾을 수 없습니다.</MudAlert>
|
||||
}
|
||||
else
|
||||
{
|
||||
<div class="admin-surface mt-4">
|
||||
<form class="admin-dialog-card" @onsubmit="SavePost" @onsubmit:preventDefault="true">
|
||||
<label>제목 * <input class="admin-input" @bind="model.Title" /></label>
|
||||
<label>카테고리
|
||||
<select class="admin-input" @bind="CategoryIdText">
|
||||
<option value="">선택하세요</option>
|
||||
@foreach (var category in categories)
|
||||
{
|
||||
<option value="@category.Id.ToString()">@category.Name</option>
|
||||
}
|
||||
</select>
|
||||
</label>
|
||||
<label>본문 * <textarea class="admin-input" rows="10" @bind="model.Content"></textarea></label>
|
||||
<label>태그 (쉼표로 구분) <input class="admin-input" @bind="model.Tags" /></label>
|
||||
<label>SEO 제목 <input class="admin-input" @bind="model.SeoTitle" /></label>
|
||||
<label>SEO 설명 <textarea class="admin-input" rows="3" @bind="model.SeoDescription"></textarea></label>
|
||||
<label><input type="checkbox" @bind="model.IsPublished" /> 발행</label>
|
||||
<div class="admin-dialog-actions">
|
||||
<button type="submit" class="site-button primary">저장</button>
|
||||
<button type="button" class="site-button secondary" @onclick="DeletePost">삭제</button>
|
||||
<MudPaper Class="pa-4 mt-4" Elevation="1">
|
||||
<MudForm @ref="form">
|
||||
<MudTextField @bind-Value="model.Title" Label="제목"
|
||||
Variant="Variant.Outlined" Class="mb-4" Required="true" />
|
||||
|
||||
<MudSelect T="int?" @bind-Value="model.CategoryId" Label="카테고리"
|
||||
Variant="Variant.Outlined" Class="mb-4">
|
||||
@foreach (var category in categories)
|
||||
{
|
||||
<MudSelectItem T="int?" Value="@((int?)category.Id)">@category.Name</MudSelectItem>
|
||||
}
|
||||
</MudSelect>
|
||||
|
||||
<MudTextField @bind-Value="model.Content" Label="본문"
|
||||
Variant="Variant.Outlined" Lines="10" Class="mb-4" Required="true" />
|
||||
|
||||
<MudTextField @bind-Value="model.Tags" Label="태그 (쉼표로 구분)"
|
||||
Variant="Variant.Outlined" Class="mb-4" />
|
||||
|
||||
<MudTextField @bind-Value="model.SeoTitle" Label="SEO 제목"
|
||||
Variant="Variant.Outlined" Class="mb-4" />
|
||||
|
||||
<MudTextField @bind-Value="model.SeoDescription" Label="SEO 설명"
|
||||
Variant="Variant.Outlined" Lines="3" Class="mb-4" />
|
||||
|
||||
<MudCheckBox @bind-Checked="model.IsPublished" Label="발행" Class="mb-4" />
|
||||
|
||||
<div class="d-flex gap-2">
|
||||
<MudButton Variant="Variant.Filled" Color="Color.Primary"
|
||||
@onclick="SavePost">저장</MudButton>
|
||||
<MudButton Variant="Variant.Outlined" Color="Color.Error"
|
||||
@onclick="DeletePost">삭제</MudButton>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</MudForm>
|
||||
</MudPaper>
|
||||
}
|
||||
|
||||
@code {
|
||||
[Parameter] public int Id { get; set; }
|
||||
[Parameter]
|
||||
public int Id { get; set; }
|
||||
|
||||
private MudForm? form;
|
||||
private Domain.Entities.BlogPost? post;
|
||||
private List<Domain.Entities.Category> categories = [];
|
||||
private EditPostModel model = new();
|
||||
private bool isLoading = true;
|
||||
private string CategoryIdText { get => model.CategoryId?.ToString() ?? ""; set => model.CategoryId = int.TryParse(value, out var id) ? id : null; }
|
||||
|
||||
protected override async Task OnInitializedAsync()
|
||||
{
|
||||
@@ -74,7 +90,7 @@ else
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
await JS.InvokeVoidAsync("alert", $"포스트 로드 실패: {ex.Message}");
|
||||
Snackbar.Add($"포스트 로드 실패: {ex.Message}", Severity.Error);
|
||||
}
|
||||
finally
|
||||
{
|
||||
@@ -93,9 +109,20 @@ else
|
||||
model.IsPublished = post.IsPublished;
|
||||
}
|
||||
|
||||
private void GoBack()
|
||||
{
|
||||
Navigation.NavigateTo("/taxbaik/admin/blog");
|
||||
}
|
||||
|
||||
private async Task SavePost()
|
||||
{
|
||||
if (post == null) return;
|
||||
if (form == null || post == null)
|
||||
return;
|
||||
|
||||
await form.Validate();
|
||||
if (!form.IsValid)
|
||||
return;
|
||||
|
||||
try
|
||||
{
|
||||
await BlogService.UpdateAsync(post.Id, new CreateBlogPostDto
|
||||
@@ -108,22 +135,43 @@ else
|
||||
SeoDescription = model.SeoDescription,
|
||||
IsPublished = model.IsPublished
|
||||
});
|
||||
await JS.InvokeVoidAsync("alert", "포스트가 저장되었습니다.");
|
||||
|
||||
Snackbar.Add("포스트가 저장되었습니다.", Severity.Success);
|
||||
Navigation.NavigateTo("/taxbaik/admin/blog");
|
||||
}
|
||||
catch (ValidationException ex)
|
||||
{
|
||||
await JS.InvokeVoidAsync("alert", ex.Message);
|
||||
Snackbar.Add(ex.Message, Severity.Error);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Snackbar.Add($"저장 실패: {ex.Message}", Severity.Error);
|
||||
}
|
||||
}
|
||||
|
||||
private async Task DeletePost()
|
||||
{
|
||||
if (post == null) return;
|
||||
if (!await JS.InvokeAsync<bool>("confirm", "정말 삭제하시겠습니까? 이 작업은 취소할 수 없습니다.")) return;
|
||||
await BlogService.DeleteAsync(post.Id);
|
||||
await JS.InvokeVoidAsync("alert", "포스트가 삭제되었습니다.");
|
||||
Navigation.NavigateTo("/taxbaik/admin/blog");
|
||||
if (post == null)
|
||||
return;
|
||||
|
||||
var result = await DialogService.ShowMessageBox(
|
||||
"포스트 삭제",
|
||||
"정말 삭제하시겠습니까? 이 작업은 취소할 수 없습니다.",
|
||||
"삭제", "취소");
|
||||
|
||||
if (result != true)
|
||||
return;
|
||||
|
||||
try
|
||||
{
|
||||
await BlogService.DeleteAsync(post.Id);
|
||||
Snackbar.Add("포스트가 삭제되었습니다.", Severity.Success);
|
||||
Navigation.NavigateTo("/taxbaik/admin/blog");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Snackbar.Add($"삭제 실패: {ex.Message}", Severity.Error);
|
||||
}
|
||||
}
|
||||
|
||||
private class EditPostModel
|
||||
|
||||
@@ -1,72 +1,58 @@
|
||||
@page "/admin/blog"
|
||||
@attribute [Authorize]
|
||||
@inject IApiClient ApiClient
|
||||
@inject IJSRuntime JS
|
||||
@inject ISnackbar Snackbar
|
||||
|
||||
<PageTitle>블로그 관리</PageTitle>
|
||||
|
||||
<section class="admin-page-hero">
|
||||
<div>
|
||||
<div class="admin-eyebrow">Content</div>
|
||||
<h1 class="admin-page-title">블로그 관리</h1>
|
||||
<p class="admin-page-subtitle">검색 유입 콘텐츠의 발행 상태와 성과를 관리합니다.</p>
|
||||
<MudText Typo="Typo.caption" Class="admin-eyebrow">Content</MudText>
|
||||
<MudText Typo="Typo.h4" Class="admin-page-title">블로그 관리</MudText>
|
||||
<MudText Typo="Typo.body2" Class="admin-page-subtitle">검색 유입 콘텐츠의 발행 상태와 성과를 관리합니다.</MudText>
|
||||
</div>
|
||||
<button type="button" class="site-button primary" @onclick='() => NavTo("/taxbaik/admin/blog/create")'>새 포스트 작성</button>
|
||||
<MudButton Variant="Variant.Filled" Color="Color.Primary" StartIcon="@Icons.Material.Filled.EditNote"
|
||||
Href="/taxbaik/admin/blog/create">새 포스트 작성</MudButton>
|
||||
</section>
|
||||
|
||||
<div class="admin-surface mb-4">
|
||||
<div class="admin-summary-bar">
|
||||
<span>전체 포스트: @($"{totalPosts}개")</span>
|
||||
<span>페이지 @currentPage / @totalPages</span>
|
||||
</div>
|
||||
</div>
|
||||
<MudPaper Class="admin-surface mb-4" Elevation="0">
|
||||
<MudStack Row="true" AlignItems="AlignItems.Center" Justify="Justify.SpaceBetween">
|
||||
<MudText Typo="Typo.subtitle1">@($"전체 포스트 {totalPosts}개")</MudText>
|
||||
<MudText Typo="Typo.body2">페이지 @currentPage / @totalPages</MudText>
|
||||
</MudStack>
|
||||
</MudPaper>
|
||||
|
||||
<div class="admin-surface">
|
||||
@if (isLoading)
|
||||
{
|
||||
<Skeleton Count="6" CssClass="taxbaik-skeleton-grid" />
|
||||
}
|
||||
else
|
||||
{
|
||||
<div class="admin-table-wrap">
|
||||
<table class="admin-table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>제목</th>
|
||||
<th>발행</th>
|
||||
<th>조회수</th>
|
||||
<th>작성일</th>
|
||||
<th></th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@foreach (var post in posts)
|
||||
{
|
||||
<tr>
|
||||
<td>@post.Title</td>
|
||||
<td><label><input type="checkbox" checked="@post.IsPublished" @onchange="@(async e => await TogglePublish(post, (bool)e.Value!))" /> 발행</label></td>
|
||||
<td>@post.ViewCount</td>
|
||||
<td>@post.CreatedAt.ToString("yyyy-MM-dd")</td>
|
||||
<td>
|
||||
<div class="admin-row-actions">
|
||||
<a class="site-button secondary" href="@($"/taxbaik/admin/blog/{post.Id}/edit")">수정</a>
|
||||
<button type="button" class="admin-icon-button danger" @onclick="@(async () => await DeletePost(post.Id))">✕</button>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
}
|
||||
</div>
|
||||
<MudDataGrid Items="@posts" Striped="true" Hoverable="true" Loading="@isLoading" Class="admin-grid">
|
||||
<Columns>
|
||||
<PropertyColumn Property="x => x.Title" Title="제목" />
|
||||
<PropertyColumn Property="x => x.IsPublished" Title="발행">
|
||||
<CellTemplate Context="cell">
|
||||
<MudCheckBox T="bool" Value="@cell.Item.IsPublished"
|
||||
ValueChanged="@(async (bool value) => await TogglePublish(cell.Item, value))" />
|
||||
</CellTemplate>
|
||||
</PropertyColumn>
|
||||
<PropertyColumn Property="x => x.ViewCount" Title="조회수" />
|
||||
<PropertyColumn Property="x => x.CreatedAt" Title="작성일" Format="yyyy-MM-dd" />
|
||||
<TemplateColumn>
|
||||
<CellTemplate Context="cell">
|
||||
<MudButton Variant="Variant.Outlined" Size="Size.Small" Color="Color.Primary"
|
||||
Href="@($"/taxbaik/admin/blog/{cell.Item.Id}/edit")">수정하기</MudButton>
|
||||
<MudButton Variant="Variant.Text" Size="Size.Small" Color="Color.Error"
|
||||
@onclick="@(async () => await DeletePost(cell.Item.Id))">삭제</MudButton>
|
||||
</CellTemplate>
|
||||
</TemplateColumn>
|
||||
</Columns>
|
||||
</MudDataGrid>
|
||||
|
||||
<div class="admin-pagination">
|
||||
<button type="button" class="site-button secondary" disabled="@(currentPage <= 1 || isLoading)" @onclick="PreviousPage">이전</button>
|
||||
<button type="button" class="site-button secondary" disabled="@(currentPage >= totalPages || isLoading)" @onclick="NextPage">다음</button>
|
||||
</div>
|
||||
<MudStack Row="true" Justify="Justify.Center" Class="mt-4" Spacing="2">
|
||||
<MudButton Variant="Variant.Outlined" Disabled="@(currentPage <= 1 || isLoading)" @onclick="PreviousPage">이전</MudButton>
|
||||
<MudButton Variant="Variant.Outlined" Disabled="@(currentPage >= totalPages || isLoading)" @onclick="NextPage">다음</MudButton>
|
||||
</MudStack>
|
||||
|
||||
@code {
|
||||
[CascadingParameter] private Task<AuthenticationState>? AuthStateTask { get; set; }
|
||||
[CascadingParameter]
|
||||
private Task<AuthenticationState>? AuthStateTask { get; set; }
|
||||
|
||||
private List<TaxBaik.Domain.Entities.BlogPost> posts = [];
|
||||
private bool isLoading = true;
|
||||
private int currentPage = 1;
|
||||
@@ -76,19 +62,20 @@
|
||||
|
||||
protected override async Task OnAfterRenderAsync(bool firstRender)
|
||||
{
|
||||
if (firstRender && AuthStateTask != null)
|
||||
if (firstRender)
|
||||
{
|
||||
var authState = await AuthStateTask;
|
||||
if (authState.User.Identity?.IsAuthenticated == true)
|
||||
if (AuthStateTask != null)
|
||||
{
|
||||
await LoadPosts();
|
||||
StateHasChanged();
|
||||
var authState = await AuthStateTask;
|
||||
if (authState.User.Identity?.IsAuthenticated == true)
|
||||
{
|
||||
await LoadPosts();
|
||||
StateHasChanged();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private string NavTo(string url) => url;
|
||||
|
||||
private async Task LoadPosts()
|
||||
{
|
||||
isLoading = true;
|
||||
@@ -105,33 +92,58 @@
|
||||
totalPosts = 0;
|
||||
totalPages = 1;
|
||||
}
|
||||
finally
|
||||
{
|
||||
isLoading = false;
|
||||
}
|
||||
isLoading = false;
|
||||
}
|
||||
|
||||
private async Task PreviousPage() { if (currentPage > 1) { currentPage--; await LoadPosts(); } }
|
||||
private async Task NextPage() { if (currentPage < totalPages) { currentPage++; await LoadPosts(); } }
|
||||
private async Task PreviousPage()
|
||||
{
|
||||
if (currentPage <= 1)
|
||||
return;
|
||||
|
||||
currentPage--;
|
||||
await LoadPosts();
|
||||
}
|
||||
|
||||
private async Task NextPage()
|
||||
{
|
||||
if (currentPage >= totalPages)
|
||||
return;
|
||||
|
||||
currentPage++;
|
||||
await LoadPosts();
|
||||
}
|
||||
|
||||
private async Task TogglePublish(TaxBaik.Domain.Entities.BlogPost post, bool isPublished)
|
||||
{
|
||||
var previous = post.IsPublished;
|
||||
post.IsPublished = isPublished;
|
||||
var result = await ApiClient.PutAsync<TaxBaik.Domain.Entities.BlogPost>($"blog/{post.Id}", new { post.Title, post.Content, post.CategoryId, post.Tags, post.SeoTitle, post.SeoDescription, post.ThumbnailUrl, IsPublished = isPublished, post.AuthorId });
|
||||
var result = await ApiClient.PutAsync<TaxBaik.Domain.Entities.BlogPost>($"blog/{post.Id}", new
|
||||
{
|
||||
post.Title,
|
||||
post.Content,
|
||||
post.CategoryId,
|
||||
post.Tags,
|
||||
post.SeoTitle,
|
||||
post.SeoDescription,
|
||||
post.ThumbnailUrl,
|
||||
IsPublished = isPublished,
|
||||
post.AuthorId
|
||||
});
|
||||
|
||||
if (result == null)
|
||||
{
|
||||
post.IsPublished = previous;
|
||||
await JS.InvokeVoidAsync("alert", "발행 상태 변경에 실패했습니다.");
|
||||
Snackbar.Add("발행 상태 변경에 실패했습니다.", Severity.Error);
|
||||
return;
|
||||
}
|
||||
await JS.InvokeVoidAsync("alert", "발행 상태가 변경되었습니다.");
|
||||
|
||||
Snackbar.Add("발행 상태가 변경되었습니다.", Severity.Success);
|
||||
}
|
||||
|
||||
private async Task DeletePost(int postId)
|
||||
{
|
||||
await ApiClient.DeleteAsync($"blog/{postId}");
|
||||
await JS.InvokeVoidAsync("alert", "포스트가 삭제되었습니다.");
|
||||
Snackbar.Add("포스트가 삭제되었습니다.", Severity.Success);
|
||||
await LoadPosts();
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user