diff --git a/RMuseum/Controllers/GanjoorController.cs b/RMuseum/Controllers/GanjoorController.cs
index 7d3df737..29436bc9 100644
--- a/RMuseum/Controllers/GanjoorController.cs
+++ b/RMuseum/Controllers/GanjoorController.cs
@@ -1,4 +1,5 @@
-using Microsoft.AspNetCore.Authorization;
+using Audit.WebApi;
+using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Caching.Memory;
@@ -3584,6 +3585,31 @@ namespace RMuseum.Controllers
return Ok(res.Result);
}
+ ///
+ /// synchronize https:://naskban.ir links (logs in and then out to naskban.ir using auth info)
+ ///
+ ///
+ /// number of synched links
+ [HttpPost]
+ [Authorize(Policy = RMuseumSecurableItem.GanjoorEntityShortName + ":" + RMuseumSecurableItem.ModerateOperationShortName)]
+ [Route("naskban")]
+ [ProducesResponseType((int)HttpStatusCode.OK, Type = typeof(int))]
+ [ProducesResponseType((int)HttpStatusCode.BadRequest, Type = typeof(string))]
+ public async Task SynchronizeNaskbanLinksAsync(
+ [AuditIgnore]
+ [FromBody]
+ LoginViewModel loginViewModel
+ )
+ {
+ var userId =
+ new Guid(User.Claims.FirstOrDefault(c => c.Type == "UserId").Value);
+ var res = await _ganjoorService.SynchronizeNaskbanLinksAsync(userId, loginViewModel.Username, loginViewModel.Password);
+
+ if (!string.IsNullOrEmpty(res.ExceptionString))
+ return BadRequest(res.ExceptionString);
+ return Ok(res.Result);
+ }
+
diff --git a/RMuseum/Controllers/PDFLibraryController.cs b/RMuseum/Controllers/PDFLibraryController.cs
index d4cbbd96..f1c5749f 100644
--- a/RMuseum/Controllers/PDFLibraryController.cs
+++ b/RMuseum/Controllers/PDFLibraryController.cs
@@ -1280,7 +1280,7 @@ namespace RMuseum.Controllers
///
[HttpGet]
[Route("ganjoor/unsynched")]
- [AllowAnonymous]
+ [Authorize(Policy = RMuseumSecurableItem.PDFLibraryEntityShortName + ":" + RMuseumSecurableItem.ReviewGanjoorLinksOperationShortName)]
[ProducesResponseType((int)HttpStatusCode.OK, Type = typeof(PDFGanjoorLink[]))]
[ProducesResponseType((int)HttpStatusCode.BadRequest, Type = typeof(string))]
public async Task GetUnsyncedPDFGanjoorLinksAsync()
diff --git a/RMuseum/Models/GanjoorIntegration/PinterestLink.cs b/RMuseum/Models/GanjoorIntegration/PinterestLink.cs
index 39f9b706..f5b7b995 100644
--- a/RMuseum/Models/GanjoorIntegration/PinterestLink.cs
+++ b/RMuseum/Models/GanjoorIntegration/PinterestLink.cs
@@ -129,5 +129,10 @@ namespace RMuseum.Models.GanjoorIntegration
/// page number
///
public int PageNumber { get; set; }
+
+ ///
+ /// naskban link id
+ ///
+ public Guid? NaskbanLinkId { get; set; }
}
}
diff --git a/RMuseum/RMuseum.xml b/RMuseum/RMuseum.xml
index 49ca7047..2a6556ad 100644
--- a/RMuseum/RMuseum.xml
+++ b/RMuseum/RMuseum.xml
@@ -1991,6 +1991,13 @@
+
+
+ synchronize https:://naskban.ir links (logs in and then out to naskban.ir using auth info)
+
+
+ number of synched links
+
readonly mode
@@ -6607,6 +6614,11 @@
page number
+
+
+ naskban link id
+
+
Review Result
@@ -15182,6 +15194,15 @@
+
+
+ synchronize naskban links
+
+
+
+
+ number of synched items
+
translation service implementation
@@ -17869,6 +17890,15 @@
+
+
+ synchronize naskban links
+
+
+
+
+ number of synched items
+
aggressive cache
diff --git a/RMuseum/Services/IGanjoorService.cs b/RMuseum/Services/IGanjoorService.cs
index cba2f300..1be3961f 100644
--- a/RMuseum/Services/IGanjoorService.cs
+++ b/RMuseum/Services/IGanjoorService.cs
@@ -1190,5 +1190,15 @@ namespace RMuseum.Services
///
///
Task> GetCatPoemGeoDateTagsAsync(int catId, bool ignoreSumup = false);
+
+
+ ///
+ /// synchronize naskban links
+ ///
+ ///
+ ///
+ ///
+ /// number of synched items
+ Task> SynchronizeNaskbanLinksAsync(Guid ganjoorUserId, string naskbanUserName, string naskbanPassword);
}
}
diff --git a/RMuseum/Services/Implementation/GanjoorService.cs b/RMuseum/Services/Implementation/GanjoorService.cs
index 84a1b2fc..4b8e56fd 100644
--- a/RMuseum/Services/Implementation/GanjoorService.cs
+++ b/RMuseum/Services/Implementation/GanjoorService.cs
@@ -25,6 +25,15 @@ using System.IO;
using RSecurityBackend.Models.Image;
using FluentFTP;
using System.Drawing;
+using RSecurityBackend.Models.Auth.ViewModels;
+using Newtonsoft.Json;
+using System.Net;
+using System.Text;
+using RMuseum.Models.Auth.ViewModel;
+using System.Net.Http.Headers;
+using RMuseum.Models.GanjoorIntegration.ViewModels;
+using RMuseum.Models.GanjoorIntegration;
+using Microsoft.VisualBasic.ApplicationServices;
namespace RMuseum.Services.Implementation
{
@@ -1569,7 +1578,7 @@ namespace RMuseum.Services.Implementation
where
link.DisplayOnPage == true
&&
- link.ReviewResult == Models.GanjoorIntegration.ReviewResult.Approved
+ link.ReviewResult == ReviewResult.Approved
&&
poem.Id == id
orderby link.IsTextOriginalSource descending, link.ReviewDate
@@ -1588,17 +1597,17 @@ namespace RMuseum.Services.Implementation
join poem in _context.GanjoorPoems
on link.GanjoorPostId equals poem.Id
where
- link.ReviewResult == Models.GanjoorIntegration.ReviewResult.Approved
+ link.ReviewResult == ReviewResult.Approved
&&
poem.Id == id
orderby link.ReviewDate
select new PoemRelatedImage()
{
PoemRelatedImageType = PoemRelatedImageType.ExternalLink,
- ThumbnailImageUrl = link.Item.Images.First().ExternalNormalSizeImageUrl.Replace("/norm/", "/thumb/").Replace("/orig/", "/thumb/"),
+ ThumbnailImageUrl = link.LinkType == LinkType.Naskban ? link.PinterestImageUrl : link.Item.Images.First().ExternalNormalSizeImageUrl.Replace("/norm/", "/thumb/").Replace("/orig/", "/thumb/"),
TargetPageUrl = link.PinterestUrl,
AltText = link.AltText,
- IsTextOriginalSource = false
+ IsTextOriginalSource = link.IsTextOriginalSource
};
museumImages.AddRange(await externalSrc.AsNoTracking().ToListAsync());
@@ -3618,6 +3627,79 @@ namespace RMuseum.Services.Implementation
}
}
+ ///
+ /// synchronize naskban links
+ ///
+ ///
+ ///
+ ///
+ /// number of synched items
+ public async Task> SynchronizeNaskbanLinksAsync(Guid ganjoorUserId, string naskbanUserName, string naskbanPassword)
+ {
+ try
+ {
+ LoginViewModel loginViewModel = new LoginViewModel()
+ {
+ Username = naskbanUserName,
+ Password = naskbanPassword,
+ ClientAppName = "Ganjoor API",
+ Language = "fa-IR"
+ };
+ var loginResponse = await _httpClient.PostAsync("https://api.naskban.ir/api/users/login", new StringContent(JsonConvert.SerializeObject(loginViewModel), Encoding.UTF8, "application/json"));
+
+ if (loginResponse.StatusCode != HttpStatusCode.OK)
+ {
+ return new RServiceResult(0, "login error: " + JsonConvert.DeserializeObject(await loginResponse.Content.ReadAsStringAsync()));
+ }
+ LoggedOnUserModelEx loggedOnUser = JsonConvert.DeserializeObject(await loginResponse.Content.ReadAsStringAsync());
+
+ using (HttpClient secureClient = new HttpClient())
+ {
+ secureClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", loggedOnUser.Token);
+ var unsyncedResponse = await secureClient.GetAsync("https://api.naskban.ir/api/pdf/ganjoor/unsynched");
+ if (!unsyncedResponse.IsSuccessStatusCode)
+ {
+ return new RServiceResult(0, "unsync error: " + JsonConvert.DeserializeObject(await unsyncedResponse.Content.ReadAsStringAsync()));
+ }
+ var unsynchronizeds = JsonConvert.DeserializeObject(await unsyncedResponse.Content.ReadAsStringAsync());
+ foreach (var unsynchronized in unsynchronizeds)
+ {
+ if(false == await _context.PinterestLinks.Where(p => p.NaskbanLinkId == unsynchronized.Id).AnyAsync() )
+ {
+ PinterestLink link = new PinterestLink()
+ {
+ GanjoorPostId = unsynchronized.GanjoorPostId,
+ GanjoorTitle = unsynchronized.GanjoorTitle,
+ GanjoorUrl = unsynchronized.GanjoorUrl,
+ AltText = unsynchronized.PDFPageTitle,
+ LinkType = LinkType.Naskban,
+ PinterestUrl = $"https://naskban.ir/{unsynchronized.PDFBookId}/{unsynchronized.PageNumber}",
+ PinterestImageUrl = unsynchronized.ExternalThumbnailImageUrl,
+ ReviewResult = ReviewResult.Approved,
+ SuggestionDate = DateTime.Now,
+ SuggestedById = ganjoorUserId,
+ Synchronized = true,
+ ReviewerId = ganjoorUserId,
+ IsTextOriginalSource = unsynchronized.IsTextOriginalSource,
+ PDFBookId = unsynchronized.PDFBookId,
+ PageNumber = unsynchronized.PageNumber,
+ NaskbanLinkId = unsynchronized.Id
+ };
+ _context.PinterestLinks.Add(link);
+ }
+ await secureClient.PutAsync($"https://api.naskban.ir/api/pdf/ganjoor/sync/{unsynchronized.Id}", null);
+ }
+ var logoutUrl = $"https://api.naskban.ir/api/users/delsession?userId={loggedOnUser.User.Id}&sessionId={loggedOnUser.SessionId}";
+ await secureClient.DeleteAsync(logoutUrl);
+ return new RServiceResult(unsynchronizeds.Length);
+ }
+ }
+ catch (Exception exp)
+ {
+ return new RServiceResult(0, exp.ToString());
+ }
+ }
+
///
/// aggressive cache
///