Added contributor classes for manga. Implemented MangaDex search.
This commit is contained in:
50
MangaReader.Tests/Search/MangaDex/MangaDexSearchTests.cs
Normal file
50
MangaReader.Tests/Search/MangaDex/MangaDexSearchTests.cs
Normal file
@@ -0,0 +1,50 @@
|
||||
using MangaReader.Core.HttpService;
|
||||
using MangaReader.Core.Search;
|
||||
using MangaReader.Core.Search.MangaDex;
|
||||
using MangaReader.Tests.Utilities;
|
||||
using NSubstitute;
|
||||
using Shouldly;
|
||||
|
||||
namespace MangaReader.Tests.Search.MangaDex;
|
||||
|
||||
public class MangaDexSearchTests
|
||||
{
|
||||
class MangaDexSearchProviderTestWrapper(IHttpService httpService) : MangaDexSearchProvider(httpService)
|
||||
{
|
||||
internal string Test_GetSearchUrl(string keyword) => GetSearchUrl(keyword);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Get_Search_Url()
|
||||
{
|
||||
// Arrange
|
||||
IHttpService httpService = Substitute.For<IHttpService>();
|
||||
MangaDexSearchProviderTestWrapper searchProvider = new(httpService);
|
||||
|
||||
// Act
|
||||
string url = searchProvider.Test_GetSearchUrl("Gal can't be");
|
||||
|
||||
// Assert
|
||||
url.ShouldBe("https://api.mangadex.org/manga?title=gal can't be&limit=5");
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Get_Search_Result()
|
||||
{
|
||||
string resourceName = "MangaReader.Tests.Search.MangaDex.SampleSearchResult.json";
|
||||
string searchResultJson = await ResourceHelper.ReadJsonResourceAsync(resourceName);
|
||||
|
||||
IHttpService httpService = Substitute.For<IHttpService>();
|
||||
|
||||
httpService.GetStringAsync(Arg.Any<string>())
|
||||
.Returns(Task.FromResult(searchResultJson));
|
||||
|
||||
MangaDexSearchProvider searchProvider = new(httpService);
|
||||
MangaSearchResult[] searchResult = await searchProvider.SearchAsync("Gal Can't Be Kind");
|
||||
|
||||
searchResult.Length.ShouldBe(3);
|
||||
searchResult[0].Title.ShouldBe("Gals Can’t Be Kind to Otaku!?");
|
||||
searchResult[0].Url.ShouldBe("https://mangadex.org/title/ee96e2b7-9af2-4864-9656-649f4d3b6fec/gals-can-t-be-kind-to-otaku");
|
||||
searchResult[0].Thumbnail.ShouldBe("https://mangadex.org/covers/ee96e2b7-9af2-4864-9656-649f4d3b6fec/6b3073de-bb65-4723-8113-6068bf8c6eb4.jpg");
|
||||
}
|
||||
}
|
||||
426
MangaReader.Tests/Search/MangaDex/SampleSearchResult.json
Normal file
426
MangaReader.Tests/Search/MangaDex/SampleSearchResult.json
Normal file
@@ -0,0 +1,426 @@
|
||||
{
|
||||
"result": "ok",
|
||||
"response": "collection",
|
||||
"data": [
|
||||
{
|
||||
"id": "ee96e2b7-9af2-4864-9656-649f4d3b6fec",
|
||||
"type": "manga",
|
||||
"attributes": {
|
||||
"title": { "en": "Gals Can\u2019t Be Kind to Otaku!?" },
|
||||
"altTitles": [
|
||||
{ "ja": "\u30aa\u30bf\u30af\u306b\u512a\u3057\u3044\u30ae\u30e3\u30eb\u306f\u3044\u306a\u3044\uff01\uff1f" },
|
||||
{ "ja-ro": "Otaku ni Yasashii Gal wa Inai!?" },
|
||||
{ "ja-ro": "Otaku ni Yasashii Gyaru ha Inai!?" },
|
||||
{ "en": "Gal Can't Be Kind to Otaku!?" },
|
||||
{ "en": "Gals Can't Be Kind To A Geek!?" },
|
||||
{ "zh": "\u6ca1\u6709\u8fa3\u59b9\u4f1a\u5bf9\u963f\u5b85\u6e29\u67d4!?" },
|
||||
{ "pt-br": "Gals N\u00e3o Podem ser Gentis com Otakus!?" },
|
||||
{ "es-la": "\u00bf\u00a1Las Gals no pueden ser amables con los Otakus!?" },
|
||||
{ "vi": "Gyaru kh\u00f4ng th\u1ec3 t\u1eed t\u1ebf v\u1edbi Otaku \u01b0?" }
|
||||
],
|
||||
"description": {
|
||||
"en": "Takuya Seo is an otaku who likes \"anime for girls\" and can't say he likes it out loud. One day, he hooks up with two gals from his class, Amane and Ijichi, but it seems that Amane is also an otaku...",
|
||||
"ja": "\u3042\u307e\u308a\u5927\u304d\u306a\u58f0\u3067\u597d\u304d\u3068\u8a00\u3048\u306a\u3044\u201c\u5973\u5150\u5411\u3051\u30a2\u30cb\u30e1\u201d\u304c\u597d\u304d\u306a\u30aa\u30bf\u30af \u702c\u5c3e\u5353\u4e5f\u3002\u3042\u308b\u65e5\u3001\u30af\u30e9\u30b9\u306e\u30ae\u30e3\u30eb \u5929\u97f3\u3055\u3093\u3068\u4f0a\u5730\u77e5\u3055\u3093\u306b\u7d61\u307e\u308c\u305f\u306e\u3060\u304c\u3001\u4f55\u3084\u3089\u5929\u97f3\u3055\u3093\u3082\u30aa\u30bf\u30af\u306e\u5302\u3044\u304c\u2026\uff1f",
|
||||
"vi": "M\u1ed9t anh b\u1ea1n trung b\u00ecnh Otaku th\u00edch anime d\u00e0nh cho b\u00e9 g\u00e1i, gi\u00e1p m\u1eb7t hai n\u00e0ng Gyaru xinh \u0111\u1eb9p n\u1ed5i ti\u1ebfng nh\u1ea5t tr\u01b0\u1eddng. Nh\u01b0ng kh\u00f4ng ch\u1ec9 c\u00f3 th\u1ebf, m\u1ed9t trong hai n\u1eef nh\u00e2n xinh \u0111\u1eb9p \u1ea5y c\u00f3 g\u00ec \u0111\u00f3...h\u01a1i otaku th\u00ec ph\u1ea3i...?",
|
||||
"es-la": "Takuya Seo es un otaku al que le gusta el \"anime para chicas\" y no puede decir que le guste en voz alta. Un d\u00eda, se junta con dos chicas de su clase, Amane e Ijichi, pero parece que Amane tambi\u00e9n es una otaku...",
|
||||
"pt-br": "Takuya Seo \u00e9 um otaku que gosta de \"animes para garotinhas\" e n\u00e3o pode dizer isso em voz alta. Um dia, ele conversa com duas gals da sua sala, Amane e Ijichi, mas parece que a Amane tamb\u00e9m \u00e9 uma otaku... Uma com\u00e9dia rom\u00e2ntica escolar onde o otaku conhece as gals que ele gosta!"
|
||||
},
|
||||
"isLocked": false,
|
||||
"links": {
|
||||
"al": "138380",
|
||||
"ap": "otaku-ni-yasashii-gal-wa-inai",
|
||||
"bw": "series\/339484",
|
||||
"kt": "69614",
|
||||
"mu": "188325",
|
||||
"amz": "https:\/\/www.amazon.co.jp\/dp\/B0BB2R5WVF",
|
||||
"cdj": "https:\/\/www.cdjapan.co.jp\/searchuni?q=\u30aa\u30bf\u30af\u306b\u512a\u3057\u3044\u30ae\u30e3\u30eb\u306f\u3044\u306a\u3044\uff01\uff1f+(Zenon+Comics)&order=relasc",
|
||||
"ebj": "https:\/\/ebookjapan.yahoo.co.jp\/books\/690493\/",
|
||||
"mal": "144152",
|
||||
"raw": "https:\/\/comic-zenon.com\/episode\/3269754496560134267",
|
||||
"engtl": "https:\/\/x.com\/yenpress\/status\/1913348424826581290"
|
||||
},
|
||||
"originalLanguage": "ja",
|
||||
"lastVolume": "",
|
||||
"lastChapter": "",
|
||||
"publicationDemographic": "seinen",
|
||||
"status": "ongoing",
|
||||
"year": 2021,
|
||||
"contentRating": "safe",
|
||||
"tags": [
|
||||
{
|
||||
"id": "423e2eae-a7a2-4a8b-ac03-a8351462d71d",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Romance" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "4d32cc48-9f00-4cca-9b5a-a839f0764984",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Comedy" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "caaa44eb-cd40-4177-b930-79d3ef2afe87",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "School Life" },
|
||||
"description": {},
|
||||
"group": "theme",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "e5301a23-ebd9-49dd-a0cb-2add944c7fe9",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Slice of Life" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "fad12b5e-68ba-460e-b933-9ae8318f5b65",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Gyaru" },
|
||||
"description": {},
|
||||
"group": "theme",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
}
|
||||
],
|
||||
"state": "published",
|
||||
"chapterNumbersResetOnNewVolume": false,
|
||||
"createdAt": "2022-03-08T07:41:47+00:00",
|
||||
"updatedAt": "2025-04-19T23:05:17+00:00",
|
||||
"version": 44,
|
||||
"availableTranslatedLanguages": [ "it", "es-la", "en", "id", "fr", "vi", "pt-br" ],
|
||||
"latestUploadedChapter": "9e8f9776-a8bf-4118-83df-f0d086479d64"
|
||||
},
|
||||
"relationships": [
|
||||
{
|
||||
"id": "518965e7-c26c-4fd9-881c-f7ce0e78323d",
|
||||
"type": "author"
|
||||
},
|
||||
{
|
||||
"id": "767b8851-6060-478a-a23e-f819fec0fbf2",
|
||||
"type": "artist"
|
||||
},
|
||||
{
|
||||
"id": "a06943fd-6309-49a8-a66a-8df0f6dc41eb",
|
||||
"type": "cover_art",
|
||||
"attributes": {
|
||||
"description": "Volume 9 Cover from BookLive",
|
||||
"volume": "9",
|
||||
"fileName": "6b3073de-bb65-4723-8113-6068bf8c6eb4.jpg",
|
||||
"locale": "ja",
|
||||
"createdAt": "2025-02-20T11:59:45+00:00",
|
||||
"updatedAt": "2025-02-20T11:59:45+00:00",
|
||||
"version": 1
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "6c0a87bf-3adb-4854-a4a6-d5c358b73d21",
|
||||
"type": "creator"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "16c34950-954c-4f0d-808e-d8278a546339",
|
||||
"type": "manga",
|
||||
"attributes": {
|
||||
"title": { "en": "Suufungo no Mirai ga Wakaru You ni Natta Kedo, Onnagokoro wa Wakaranai." },
|
||||
"altTitles": [
|
||||
{ "ja": "\u6570\u5206\u5f8c\u306e\u672a\u6765\u304c\u5206\u304b\u308b\u3088\u3046\u306b\u306a\u3063\u305f\u3051\u3069\u3001\u5973\u5fc3\u306f\u5206\u304b\u3089\u306a\u3044\u3002" },
|
||||
{ "ja-ro": "Suufungo no Mirai ga Wakaru You ni Natta Kedo, Onnagokoro ha Wakaranai." },
|
||||
{ "en": "I Can Now See a Few Minutes Into the Future, but I Still Can't Understand a Woman's Heart." },
|
||||
{ "en": "I Can See a Few Minutes Into the Future, but I Don\u2019t Know What a Woman's Mind Is Like." },
|
||||
{ "id": "Sekarang saya dapat melihat masa depan dalam beberapa menit, tetapi saya tidak dapat memahami hati seorang wanita." },
|
||||
{ "pt-br": "Agora, posso ver alguns minutos no futuro, mas ainda n\u00e3o consigo entender o cora\u00e7\u00e3o de uma mulher." },
|
||||
{ "vi": "T\u00f4i Gi\u1edd C\u00f3 Th\u1ec3 Nh\u00ecn Th\u1ea5y V\u00e0i Kh\u1eafc Trong T\u01b0\u01a1ng Lai, Nh\u01b0ng V\u1eabn Kh\u00f4ng Th\u1ec3 Hi\u1ec3u \u0110\u01b0\u1ee3c Con G\u00e1i Ngh\u0129 G\u00ec" }
|
||||
],
|
||||
"description": {
|
||||
"en": "Arase Itou has the ability to see a few minutes into the future, but the glimpses he sees are always linked to misfortune. With his kind-hearted nature, Arata decides to use this inconvenient power to help girls facing various troubles and prevent their unfortunate futures. However, Arase doesn't realize that, little by little, the girls are growing fond of him. And he remains oblivious to the quiet rivalries forming between them over his attention.",
|
||||
"id": "Arase Itou bisa melihat beberapa menit ke depan. Namun, masa depan yang ia lihat selalu berhubungan dengan masalah. Arase yang baik hati berusaha menghindari masa depan yang tidak menyenangkan ini, namun pada akhirnya masalah tersebut tetap membuatnya membantu berbagai gadis dengan masalah mereka. Tanpa ia sadari, para gadis mulai menyukainya. Arase tidak menyadari bahwa, diam-diam, para gadis bersaing untuk memperebutkannya.",
|
||||
"ja": "\u4f0a\u85e4\u65b0\u4e16\u306f\u6570\u5206\u5f8c\u306e\u672a\u6765\u304c\u5206\u304b\u308b\u3002\u305f\u3060\u3057\u8996\u3048\u308b\u672a\u6765\u306f\u4e0d\u5e78\u306b\u3064\u306a\u304c\u308b\u3082\u306e\u3002\n\u304a\u4eba\u597d\u3057\u306a\u65b0\u4e16\u306f\u305d\u3093\u306a\u4e0d\u90fd\u5408\u306a\u672a\u6765\u3092\u56de\u907f\u3057\u3001\u69d8\u3005\u306a\u60a9\u307f\u3092\u6301\u3064\u5c11\u5973\u3092\u52a9\u3051\u308b\u3053\u3068\u306b\u306a\u308b\u3002\n\u65b0\u4e16\u306f\u77e5\u3089\u306a\u3044\u3002\u3044\u3064\u306e\u9593\u306b\u304b\u3001\u5c11\u5973\u305f\u3061\u306b\u597d\u304b\u308c\u3066\u3044\u308b\u3053\u3068\u306b\u3002\n\u65b0\u4e16\u306f\u6c17\u3065\u304b\u306a\u3044\u3002\u4eba\u77e5\u308c\u305a\u3001\u5c11\u5973\u305f\u3061\u304c\u4e89\u3063\u3066\u3044\u308b\u3053\u3068\u306b\u3002",
|
||||
"vi": "Arata Itou c\u00f3 kh\u1ea3 n\u0103ng nh\u00ecn th\u1ea5y tr\u01b0\u1edbc v\u00e0i ph\u00fat trong t\u01b0\u01a1ng lai, nh\u01b0ng nh\u1eefng h\u00ecnh \u1ea3nh c\u1eadu th\u1ea5y lu\u00f4n g\u1eafn li\u1ec1n v\u1edbi xui x\u1ebbo. L\u00e0 m\u1ed9t ng\u01b0\u1eddi t\u1ed1t b\u1ee5ng, Arata quy\u1ebft \u0111\u1ecbnh t\u1eadn d\u1ee5ng n\u0103ng l\u1ef1c \"b\u1ea5t ti\u1ec7n\" n\u00e0y \u0111\u1ec3 gi\u00fap \u0111\u1ee1 c\u00e1c c\u00f4 g\u00e1i \u0111ang g\u1eb7p kh\u00f3 kh\u0103n v\u00e0 ng\u0103n ch\u1eb7n nh\u1eefng \u0111i\u1ec1u kh\u00f4ng may s\u1ebd x\u1ea3y ra v\u1edbi h\u1ecd. Th\u1ebf nh\u01b0ng, c\u1eadu ho\u00e0n to\u00e0n kh\u00f4ng nh\u1eadn ra r\u1eb1ng c\u00e1c c\u00f4 g\u00e1i ng\u00e0y c\u00e0ng c\u00f3 t\u00ecnh c\u1ea3m v\u1edbi m\u00ecnh. C\u00e0ng kh\u00f4ng hay bi\u1ebft v\u1ec1 nh\u1eefng \"cu\u1ed9c chi\u1ebfn ng\u1ea7m\" gi\u1eefa h\u1ecd \u0111\u1ec3 gi\u00e0nh l\u1ea5y s\u1ef1 ch\u00fa \u00fd c\u1ee7a c\u1eadu.",
|
||||
"pt-br": "Arata Itou tem a habilidade de ver alguns minutos no futuro, mas as vis\u00f5es que ele tem est\u00e3o sempre ligadas a infort\u00fanios. Com seu cora\u00e7\u00e3o bondoso, Arata decide usar esse poder inconveniente para ajudar as garotas que enfrentam diversos problemas e evitar seus futuros infelizes. No entanto, Arata n\u00e3o percebe que, pouco a pouco, as garotas come\u00e7am a se afei\u00e7oar a ele. E ele continua alheio \u00e0s rivalidades silenciosas que est\u00e3o se formando entre elas por causa da sua aten\u00e7\u00e3o."
|
||||
},
|
||||
"isLocked": false,
|
||||
"links": {
|
||||
"al": "184387",
|
||||
"ap": "suufungo-no-mirai-ga-wakaru-you-ni-natta-kedo-onnagokoro-wa-wakaranai",
|
||||
"bw": "series\/501373\/list",
|
||||
"kt": "73470",
|
||||
"mu": "6et7o73",
|
||||
"nu": "i-can-see-a-few-minutes-into-the-future-but-i-dont-know-what-a-womans-mind-is-like",
|
||||
"amz": "https:\/\/www.amazon.co.jp\/dp\/B0DPG735ZF",
|
||||
"cdj": "https:\/\/www.cdjapan.co.jp\/product\/NEOBK-3045342",
|
||||
"ebj": "https:\/\/ebookjapan.yahoo.co.jp\/books\/867769",
|
||||
"mal": "176205",
|
||||
"raw": "https:\/\/comic-walker.com\/detail\/KC_005690_S?episodeType=first"
|
||||
},
|
||||
"originalLanguage": "ja",
|
||||
"lastVolume": "",
|
||||
"lastChapter": "",
|
||||
"publicationDemographic": "shounen",
|
||||
"status": "ongoing",
|
||||
"year": 2024,
|
||||
"contentRating": "safe",
|
||||
"tags": [
|
||||
{
|
||||
"id": "423e2eae-a7a2-4a8b-ac03-a8351462d71d",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Romance" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "4d32cc48-9f00-4cca-9b5a-a839f0764984",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Comedy" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "aafb99c1-7f60-43fa-b75f-fc9502ce29c7",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Harem" },
|
||||
"description": {},
|
||||
"group": "theme",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "caaa44eb-cd40-4177-b930-79d3ef2afe87",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "School Life" },
|
||||
"description": {},
|
||||
"group": "theme",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "eabc5b4c-6aff-42f3-b657-3e90cbd00b75",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Supernatural" },
|
||||
"description": {},
|
||||
"group": "theme",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "f4122d1c-3b44-44d0-9936-ff7502c39ad3",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Adaptation" },
|
||||
"description": {},
|
||||
"group": "format",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
}
|
||||
],
|
||||
"state": "published",
|
||||
"chapterNumbersResetOnNewVolume": false,
|
||||
"createdAt": "2024-11-10T00:54:16+00:00",
|
||||
"updatedAt": "2025-04-16T06:18:51+00:00",
|
||||
"version": 30,
|
||||
"availableTranslatedLanguages": [ "es-la", "id", "pt-br", "en", "ru", "vi" ],
|
||||
"latestUploadedChapter": "f68c92d1-a701-4136-b2bf-7716d581345e"
|
||||
},
|
||||
"relationships": [
|
||||
{
|
||||
"id": "cf0872ad-dcb7-466b-bbf0-d158d454e49c",
|
||||
"type": "author"
|
||||
},
|
||||
{
|
||||
"id": "1459d711-c584-4594-9bb5-bbbe646b69cc",
|
||||
"type": "artist"
|
||||
},
|
||||
{
|
||||
"id": "ee8588b5-145f-4eee-981a-eb604856fbd2",
|
||||
"type": "cover_art",
|
||||
"attributes": {
|
||||
"description": "Volume 1 Cover from BookLive",
|
||||
"volume": "1",
|
||||
"fileName": "7d301e1e-642b-4b7d-b65b-9777b36e80bf.jpg",
|
||||
"locale": "ja",
|
||||
"createdAt": "2024-12-27T20:40:30+00:00",
|
||||
"updatedAt": "2024-12-27T20:40:30+00:00",
|
||||
"version": 1
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "3e37a8a0-2012-4d3d-9495-cbed6d0155d8",
|
||||
"type": "creator"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "f395bfc6-e52f-4f64-9cfb-87037215d214",
|
||||
"type": "manga",
|
||||
"attributes": {
|
||||
"title": { "en": "Ienai Himitsu No Aishikata" },
|
||||
"altTitles": [
|
||||
{ "ja": "\u3044\u3048\u306a\u3044\u79d8\u5bc6\u306e\u611b\u3057\u65b9" },
|
||||
{ "en": "How To Love: A Secret That Cannot Be Told" },
|
||||
{ "zh": "\u65e0\u6cd5\u544a\u4eba\u7684\u79d8\u5bc6\u7231\u597d" },
|
||||
{ "zh-hk": "\u7121\u6cd5\u544a\u4eba\u7684\u79d8\u5bc6\u611b\u597d" },
|
||||
{ "zh-ro": "W\u00faf\u01ce g\u00e0o r\u00e9n de m\u00ecm\u00ec \u00e0ih\u00e0o" },
|
||||
{ "ru": "\u041b\u044e\u0431\u043e\u0432\u043d\u0430\u044f \u0442\u0430\u0439\u043d\u0430, \u043a\u043e\u0442\u043e\u0440\u0443\u044e \u043d\u0435\u043b\u044c\u0437\u044f \u043f\u043e\u0432\u0435\u0434\u0430\u0442\u044c" }
|
||||
],
|
||||
"description": {
|
||||
"en": "High School teacher Saeki Nao is secretly a hardcore otaku who loves yuri manga. One day, at a doujinshi convention they participate in, Nao is eager to convey her feelings to \"Nyapoleon\", an artist she worships. However, it turned out to be a girl from her school, Kurumizawa Haruka, and moreover, she had to help her. After the event, they decided to go out for a meal, at Haruka's suggestion... When she wakes up in the morning, there is Haruka in the bed...?!",
|
||||
"ja": "\u9ad8\u6821\u6559\u5e2b\u30fb\u4f50\u4f2f\u548c\u7dd2\u306f\u5bc6\u304b\u306b\u767e\u5408\u6f2b\u753b\u3092\u611b\u3059\u308b\u30aa\u30bf\u30af\u5973\u5b50\u3002\u3042\u308b\u65e5\u3001\u53c2\u52a0\u3057\u305f\u540c\u4eba\u8a8c\u5373\u58f2\u4f1a\u3067\u3001\u5d07\u62dd\u3059\u308b\u7d75\u5e2b\u300c\u306b\u3083\u30dd\u30ec\u30aa\u30f3\u300d\u306b\u60f3\u3044\u3092\u4f1d\u3048\u3088\u3046\u3068\u610f\u6c17\u8fbc\u3080\u548c\u7dd2\u3002\u3060\u304c\u305d\u3053\u306b\u3044\u305f\u306e\u306f\u2026!?",
|
||||
"pt-br": "Kazuo Saeki, uma professora do ensino m\u00e9dio, \u00e9 uma otaku que ama secretamente produtos yuri.\nUm dia, em um evento de venda doujinshi do qual ela participou, Kazuo estava entusiasmada para transmitir seus pensamentos ao autor \u201cNyapoleon\u201d.\nMas quem ela encontrou l\u00e1 foi\u2026"
|
||||
},
|
||||
"isLocked": false,
|
||||
"links": {
|
||||
"al": "128964",
|
||||
"ap": "ienai-himitsu-no-aishikata",
|
||||
"bw": "series\/299385",
|
||||
"mu": "gmbglvo",
|
||||
"amz": "https:\/\/www.amazon.co.jp\/dp\/B0CR4CG491",
|
||||
"ebj": "https:\/\/ebookjapan.yahoo.co.jp\/books\/636287",
|
||||
"mal": "131861",
|
||||
"raw": "https:\/\/storia.takeshobo.co.jp\/manga\/himitsunoaishikata"
|
||||
},
|
||||
"originalLanguage": "ja",
|
||||
"lastVolume": "2",
|
||||
"lastChapter": "12",
|
||||
"publicationDemographic": "seinen",
|
||||
"status": "completed",
|
||||
"year": 2021,
|
||||
"contentRating": "suggestive",
|
||||
"tags": [
|
||||
{
|
||||
"id": "423e2eae-a7a2-4a8b-ac03-a8351462d71d",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Romance" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "4d32cc48-9f00-4cca-9b5a-a839f0764984",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Comedy" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "a3c67850-4684-404e-9b7f-c69850ee5da6",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Girls' Love" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "b9af3a63-f058-46de-a9a0-e0c13906197a",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "Drama" },
|
||||
"description": {},
|
||||
"group": "genre",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
},
|
||||
{
|
||||
"id": "caaa44eb-cd40-4177-b930-79d3ef2afe87",
|
||||
"type": "tag",
|
||||
"attributes": {
|
||||
"name": { "en": "School Life" },
|
||||
"description": {},
|
||||
"group": "theme",
|
||||
"version": 1
|
||||
},
|
||||
"relationships": []
|
||||
}
|
||||
],
|
||||
"state": "published",
|
||||
"chapterNumbersResetOnNewVolume": false,
|
||||
"createdAt": "2021-11-24T01:19:31+00:00",
|
||||
"updatedAt": "2025-02-24T16:58:42+00:00",
|
||||
"version": 18,
|
||||
"availableTranslatedLanguages": [ "ko", "en", "ga" ],
|
||||
"latestUploadedChapter": "ab661694-2098-46fb-a3f5-bbc1c3e3cd64"
|
||||
},
|
||||
"relationships": [
|
||||
{
|
||||
"id": "a0e14841-b86a-499f-af44-c3fa6f35c424",
|
||||
"type": "author"
|
||||
},
|
||||
{
|
||||
"id": "a0e14841-b86a-499f-af44-c3fa6f35c424",
|
||||
"type": "artist"
|
||||
},
|
||||
{
|
||||
"id": "40df2d2e-b786-4aa9-9218-e3ed168cd96e",
|
||||
"type": "cover_art",
|
||||
"attributes": {
|
||||
"description": "",
|
||||
"volume": "2",
|
||||
"fileName": "c00a33cd-b26b-4554-a9f0-d6885c81eb36.jpg",
|
||||
"locale": "ja",
|
||||
"createdAt": "2024-09-14T22:32:25+00:00",
|
||||
"updatedAt": "2024-09-14T22:32:25+00:00",
|
||||
"version": 1
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "df805b8c-0c05-40f2-8f92-0f096ca346e4",
|
||||
"type": "manga",
|
||||
"related": "preserialization"
|
||||
},
|
||||
{
|
||||
"id": "f8cc4f8a-e596-4618-ab05-ef6572980bbf",
|
||||
"type": "creator"
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
"limit": 5,
|
||||
"offset": 0,
|
||||
"total": 3
|
||||
}
|
||||
@@ -0,0 +1,51 @@
|
||||
using MangaReader.Core.HttpService;
|
||||
using MangaReader.Core.Search;
|
||||
using MangaReader.Core.Search.NatoManga;
|
||||
using MangaReader.Tests.Utilities;
|
||||
using NSubstitute;
|
||||
using Shouldly;
|
||||
|
||||
namespace MangaReader.Tests.Search.NatoManga;
|
||||
|
||||
public class NatoMangaWebSearchTests
|
||||
{
|
||||
[Fact]
|
||||
public void Get_Search_Url()
|
||||
{
|
||||
// Arrange
|
||||
IHttpService httpService = Substitute.For<IHttpService>();
|
||||
NatoMangaSearchProviderTestWrapper searchProvider = new(httpService);
|
||||
|
||||
// Act
|
||||
string url = searchProvider.Test_GetSearchUrl("Gal can't be kind");
|
||||
|
||||
// Assert
|
||||
url.ShouldBe("https://www.natomanga.com/home/search/json?searchword=gal_can_t_be_kind");
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Get_Search_Result()
|
||||
{
|
||||
string resourceName = "MangaReader.Tests.Search.NatoManga.SampleSearchResult.json";
|
||||
string searchResultJson = await ResourceHelper.ReadJsonResourceAsync(resourceName);
|
||||
|
||||
IHttpService httpService = Substitute.For<IHttpService>();
|
||||
|
||||
httpService.GetStringAsync(Arg.Any<string>())
|
||||
.Returns(Task.FromResult(searchResultJson));
|
||||
|
||||
NatoMangaSearchProvider searchProvider = new(httpService);
|
||||
MangaSearchResult[] searchResult = await searchProvider.SearchAsync("Gal Can't Be Kind");
|
||||
|
||||
searchResult.Length.ShouldBe(2);
|
||||
searchResult[0].Title.ShouldBe("Gal Can't Be Kind to Otaku!");
|
||||
searchResult[1].Title.ShouldBe("Gal Can’t Be Kind to Otaku!?");
|
||||
searchResult[0].Url.ShouldBe("https://www.natomanga.com/manga/gal-can-t-be-kind-to-otaku");
|
||||
searchResult[1].Url.ShouldBe("https://www.natomanga.com/manga/gal-cant-be-kind-to-otaku");
|
||||
}
|
||||
}
|
||||
|
||||
internal class NatoMangaSearchProviderTestWrapper(IHttpService httpService) : NatoMangaSearchProvider(httpService)
|
||||
{
|
||||
internal string Test_GetSearchUrl(string keyword) => GetSearchUrl(keyword);
|
||||
}
|
||||
20
MangaReader.Tests/Search/NatoManga/SampleSearchResult.json
Normal file
20
MangaReader.Tests/Search/NatoManga/SampleSearchResult.json
Normal file
@@ -0,0 +1,20 @@
|
||||
[
|
||||
{
|
||||
"id": 51811,
|
||||
"author": "Norishiro-chan, Sakana Uozumi",
|
||||
"name": "Gal Can't Be Kind to Otaku!",
|
||||
"chapterLatest": "Chapter 69",
|
||||
"url": "https:\/\/www.natomanga.com\/manga\/gal-can-t-be-kind-to-otaku",
|
||||
"thumb": "https:\/\/img-r1.2xstorage.com\/thumb\/gal-can-t-be-kind-to-otaku.webp",
|
||||
"slug": "gal-can-t-be-kind-to-otaku"
|
||||
},
|
||||
{
|
||||
"id": 38065,
|
||||
"author": "Norishiro-chan,Sakana Uozimi",
|
||||
"name": "Gal Can\u2019t Be Kind to Otaku!?",
|
||||
"chapterLatest": "Chapter 69",
|
||||
"url": "https:\/\/www.natomanga.com\/manga\/gal-cant-be-kind-to-otaku",
|
||||
"thumb": "https:\/\/img-r1.2xstorage.com\/thumb\/gal-cant-be-kind-to-otaku.webp",
|
||||
"slug": "gal-cant-be-kind-to-otaku"
|
||||
}
|
||||
]
|
||||
Reference in New Issue
Block a user