display stats of visits for categories and poems

#481
This commit is contained in:
Hamid Reza Mohammadi 2025-05-22 09:43:58 +03:30
parent c05783d0c4
commit 6f1328e508
7 changed files with 146 additions and 0 deletions

View File

@ -12,6 +12,7 @@
</ItemGroup>
<ItemGroup>
<Folder Include="Models\Kontor\" />
<Folder Include="wwwroot\json\" />
</ItemGroup>

View File

@ -0,0 +1,18 @@
namespace KontorService.Models.Reporting.ViewModels
{
public class PageVisitsViewModel
{
/// <summary>
/// url
/// </summary>
public string Url { get; set; }
/// <summary>
/// title
/// </summary>
public string? Title { get; set; }
/// <summary>
/// visits
/// </summary>
public int Visits { get; set; }
}
}

View File

@ -1,4 +1,5 @@
using GanjooRazor.Utils;
using KontorService.Models.Reporting.ViewModels;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.ModelBinding;
@ -1597,6 +1598,31 @@ namespace GanjooRazor.Pages
};
}
public async Task<ActionResult> OnGetTopVisitsAsync(string url)
{
url = $"https://ganjoor.net/{url}";
var apiUrl = $"https://track.kntr.ir/api/reporting/toppages/1/ganjoor.net?parentUrl={WebUtility.UrlEncode(url)}&count=20";
var topVisitsResponse = await _httpClient.GetAsync(apiUrl);
if (!topVisitsResponse.IsSuccessStatusCode)
{
return null;
}
var topVisits = JsonConvert.DeserializeObject<PageVisitsViewModel[]>(await topVisitsResponse.Content.ReadAsStringAsync());
return new PartialViewResult()
{
ViewName = "_TopVisitsPartial",
ViewData = new ViewDataDictionary(new EmptyModelMetadataProvider(), new ModelStateDictionary())
{
Model = new _TopVisitsPartialModel()
{
Visits = topVisits
}
}
};
}
}
}

View File

@ -269,6 +269,7 @@
<div class="poemtablinks"><a href="#photos">تصاویر چهره</a></div>
<div class="poemtablinks"><a href="#papersources">منابع کاغذی</a></div>
}
<div class="poemtablinks"><a href="#topvisits" onclick="javascript:loadTopVisits('@Model.GanjoorPage.FullUrl')">پربازدیدها</a></div>
</div>
<div class="related-images-frame poemtabcontent">
@ -300,6 +301,7 @@
<div class="poemtablinks"><a href="#photos">تصاویر چهره</a></div>
<div class="poemtablinks"><a href="#papersources">منابع کاغذی</a></div>
}
<div class="poemtablinks"><a href="#topvisits" onclick="javascript:loadTopVisits('@Model.GanjoorPage.FullUrl')">پربازدیدها</a></div>
</div>
<div class="related-images-frame poemtabcontent">
@ -333,6 +335,7 @@
<div class="poemtablinks active"><a href="#photos">تصاویر چهره</a></div>
<div class="poemtablinks"><a href="#papersources">منابع کاغذی</a></div>
}
<div class="poemtablinks"><a href="#topvisits" onclick="javascript:loadTopVisits('@Model.GanjoorPage.FullUrl')">پربازدیدها</a></div>
</div>
<div class="poemtabcontent">
<div class="related-images-frame">
@ -375,6 +378,7 @@
<div class="poemtablinks"><a href="#photos">تصاویر چهره</a></div>
<div class="poemtablinks active"><a href="#papersources">منابع کاغذی</a></div>
}
<div class="poemtablinks"><a href="#topvisits" onclick="javascript:loadTopVisits('@Model.GanjoorPage.FullUrl')">پربازدیدها</a></div>
</div>
<div class="poemtabcontent related-images-frame">
@ -409,6 +413,32 @@
}
}
<div class="poempretab" id="topvisits"></div>
<div class="poemtab">
<div class="poemtablinks"><a href="#stats">آمار</a></div>
@if (Model.IsPoetPage)
{
<div class="poemtablinks"><a href="#quoteds">مشق شعر</a></div>
}
<div class="poemtablinks active"><a href="#words" onclick="javascript:loadWordCounts(@Model.GanjoorPage.PoetOrCat.Cat.Id, @Model.GanjoorPage.PoetOrCat.Poet.Id, false)">واژگان</a></div>
<div class="poemtablinks"><a href="#recitations" onclick="javascript:loadCatRecitations(@Model.GanjoorPage.PoetOrCat.Cat.Id)">خوانش‌ها</a></div>
@if (Model.IsPoetPage)
{
<div class="poemtablinks"><a href="#photos">تصاویر چهره</a></div>
<div class="poemtablinks"><a href="#papersources">منابع کاغذی</a></div>
}
<div class="poemtablinks"><a href="#topvisits" onclick="javascript:loadTopVisits('@Model.GanjoorPage.FullUrl')">پربازدیدها</a></div>
</div>
<div class="related-images-frame poemtabcontent">
<div class="century cursor-pointer" id="load-topvisits" onclick="loadTopVisits('@Model.GanjoorPage.FullUrl')">
بارگذاری آمار پربازدیدها
</div>
<div id="topvisits-placeholder">
</div>
</div>
@if (
Model.CategoryPoemGeoDateTags != null && Model.CategoryPoemGeoDateTags.Length > 0
)

View File

@ -0,0 +1,36 @@
@using DNTPersianUtils.Core
@model GanjooRazor.Pages._TopVisitsPartialModel
@if (Model.Visits.Length > 0)
{
<table class="stats" id="topvisits">
<thead>
<tr class="h">
<td class="c1">ردیف</td>
<td class="c2">شعر/بخش</td>
<td class="c3">شمار</td>
</tr>
</thead>
<tbody>
@for (int i = 0; i < Model.Visits.Length; i++)
{
@if (i % 2 == 0)
{
<tr class="e">
<td class="c1">@((i + 1).ToPersianNumbers())</td>
<td class="c2"><a href="@Model.Visits[i].Url">@Model.Visits[i].Title</a></td>
<td class="c3">@RMuseum.Services.Implementation.LanguageUtils.FormatMoney(Model.Visits[i].Visits)</td>
</tr>
}
else
{
<tr>
<td class="c1">@((i + 1).ToPersianNumbers())</td>
<td class="c2"><a href="@Model.Visits[i].Url">@Model.Visits[i].Title</a></td>
<td class="c3">@RMuseum.Services.Implementation.LanguageUtils.FormatMoney(Model.Visits[i].Visits)</td>
</tr>
}
}
</tbody>
</table>
}

View File

@ -0,0 +1,10 @@
using KontorService.Models.Reporting.ViewModels;
using Microsoft.AspNetCore.Mvc.RazorPages;
namespace GanjooRazor.Pages
{
public class _TopVisitsPartialModel : PageModel
{
public PageVisitsViewModel[] Visits { get; set; }
}
}

View File

@ -1969,4 +1969,29 @@ function loadContributionsUsers(dataType, pageNumber) {
}
},
});
}
function loadTopVisits(url) {
var divParent = document.getElementById('topvisits-placeholder');
var imgElementId = 'loadingtopvisitsimg';
divParent.innerHTML = divParent.innerHTML + '<div class="bnumdiv" id="remove-this-topvisits"><img id="' + imgElementId + '" src="/image/loading.gif" alt="بارگذاری"/></div>';
$.ajax({
type: "GET",
url: '?Handler=TopVisits&url=' + url,
error: function () {
if (document.getElementById("remove-this-topvisits") != null) {
document.getElementById("remove-this-topvisits").remove();
}
},
success: function (data) {
if (document.getElementById("remove-this-topvisits") != null) {
document.getElementById("remove-this-topvisits").remove();
if (document.getElementById("load-topvisits") != null) {
document.getElementById("load-topvisits").remove();
}
$(data).appendTo(divParent);
plotChart('topvisits');
}
},
});
}