mirror of
https://github.com/Suwayomi/Tachidesk.git
synced 2025-12-10 06:42:07 +01:00
@@ -35,6 +35,24 @@ The GraphQL API can be queried with a POST request to `/api/graphql`. There is a
|
|||||||
|
|
||||||
The REST API can be queried at `/api/v1`. An interactive Swagger API explorer is available at `/api/swagger-ui`.
|
The REST API can be queried at `/api/v1`. An interactive Swagger API explorer is available at `/api/swagger-ui`.
|
||||||
|
|
||||||
|
### Tracker client authorization
|
||||||
|
#### OAuth
|
||||||
|
Since the url of a Suwayomi-Server is not known, it is not possible to redirect directly to the client.<br/>
|
||||||
|
Thus, to provide tracker support via oauth, the tracker clients redirect to the [suwayomi website](https://suwayomi.org/)
|
||||||
|
and there the actual redirection to the client takes place.
|
||||||
|
|
||||||
|
When implementing the login process in your client you have to make sure to follow some preconditions:
|
||||||
|
|
||||||
|
To be able to redirect to the client you have to attach a `state` object to the query of the auth url
|
||||||
|
- this `state` object has to have a `redirectUrl` which points to the client route at which you want to handle the auth result
|
||||||
|
- besides the `redirectUrl` you can pass any information you require to handle the result (e.g. the server `id` of the tracker client)
|
||||||
|
- example URL for AniList: `https://anilist.co/api/v2/oauth/authorize?client_id=ID&response_type=token&state={ redirectUrl: "http://localhost:4567/handle/oauth/result", trackerId: 1, anyOtherInfo: "your client requires" }`
|
||||||
|
|
||||||
|
Once the permission has been granted, you will get redirected to the client at the provided route (`redirectUrl`).<br/>
|
||||||
|
- Example URL (decoded) for AniList: `http://localhost:4567/tracker/login?access_token=TOKEN&token_type=Bearer&expires_in=31622400&state={ redirectUrl: "http://localhost:4567/handle/oauth/result", trackerId: 1, anyOtherInfo: "your client requires" }`).<br/>
|
||||||
|
|
||||||
|
Finally, to finish the login process, you just have to pass this URL to the server as the `callbackUrl`.
|
||||||
|
|
||||||
## Why a web app?
|
## Why a web app?
|
||||||
This structure is chosen to
|
This structure is chosen to
|
||||||
- Achieve the maximum multi-platform-ness
|
- Achieve the maximum multi-platform-ness
|
||||||
|
|||||||
@@ -15,6 +15,7 @@ import suwayomi.tachidesk.graphql.dataLoaders.CategoryMetaDataLoader
|
|||||||
import suwayomi.tachidesk.graphql.dataLoaders.ChapterDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.ChapterDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.ChapterMetaDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.ChapterMetaDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.ChaptersForMangaDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.ChaptersForMangaDataLoader
|
||||||
|
import suwayomi.tachidesk.graphql.dataLoaders.DisplayScoreForTrackRecordDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.DownloadedChapterCountForMangaDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.DownloadedChapterCountForMangaDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.ExtensionDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.ExtensionDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.ExtensionForSourceDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.ExtensionForSourceDataLoader
|
||||||
@@ -30,6 +31,10 @@ import suwayomi.tachidesk.graphql.dataLoaders.MangaForSourceDataLoader
|
|||||||
import suwayomi.tachidesk.graphql.dataLoaders.MangaMetaDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.MangaMetaDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.SourceDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.SourceDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.SourcesForExtensionDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.SourcesForExtensionDataLoader
|
||||||
|
import suwayomi.tachidesk.graphql.dataLoaders.TrackRecordDataLoader
|
||||||
|
import suwayomi.tachidesk.graphql.dataLoaders.TrackRecordsForMangaIdDataLoader
|
||||||
|
import suwayomi.tachidesk.graphql.dataLoaders.TrackRecordsForTrackerIdDataLoader
|
||||||
|
import suwayomi.tachidesk.graphql.dataLoaders.TrackerDataLoader
|
||||||
import suwayomi.tachidesk.graphql.dataLoaders.UnreadChapterCountForMangaDataLoader
|
import suwayomi.tachidesk.graphql.dataLoaders.UnreadChapterCountForMangaDataLoader
|
||||||
|
|
||||||
class TachideskDataLoaderRegistryFactory {
|
class TachideskDataLoaderRegistryFactory {
|
||||||
@@ -59,11 +64,11 @@ class TachideskDataLoaderRegistryFactory {
|
|||||||
SourcesForExtensionDataLoader(),
|
SourcesForExtensionDataLoader(),
|
||||||
ExtensionDataLoader(),
|
ExtensionDataLoader(),
|
||||||
ExtensionForSourceDataLoader(),
|
ExtensionForSourceDataLoader(),
|
||||||
// TrackerDataLoader(),
|
TrackerDataLoader(),
|
||||||
// TrackRecordsForMangaIdDataLoader(),
|
TrackRecordsForMangaIdDataLoader(),
|
||||||
// DisplayScoreForTrackRecordDataLoader(),
|
DisplayScoreForTrackRecordDataLoader(),
|
||||||
// TrackRecordsForTrackerIdDataLoader(),
|
TrackRecordsForTrackerIdDataLoader(),
|
||||||
// TrackRecordDataLoader(),
|
TrackRecordDataLoader(),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ import suwayomi.tachidesk.graphql.mutations.MangaMutation
|
|||||||
import suwayomi.tachidesk.graphql.mutations.MetaMutation
|
import suwayomi.tachidesk.graphql.mutations.MetaMutation
|
||||||
import suwayomi.tachidesk.graphql.mutations.SettingsMutation
|
import suwayomi.tachidesk.graphql.mutations.SettingsMutation
|
||||||
import suwayomi.tachidesk.graphql.mutations.SourceMutation
|
import suwayomi.tachidesk.graphql.mutations.SourceMutation
|
||||||
|
import suwayomi.tachidesk.graphql.mutations.TrackMutation
|
||||||
import suwayomi.tachidesk.graphql.mutations.UpdateMutation
|
import suwayomi.tachidesk.graphql.mutations.UpdateMutation
|
||||||
import suwayomi.tachidesk.graphql.queries.BackupQuery
|
import suwayomi.tachidesk.graphql.queries.BackupQuery
|
||||||
import suwayomi.tachidesk.graphql.queries.CategoryQuery
|
import suwayomi.tachidesk.graphql.queries.CategoryQuery
|
||||||
@@ -35,6 +36,7 @@ import suwayomi.tachidesk.graphql.queries.MangaQuery
|
|||||||
import suwayomi.tachidesk.graphql.queries.MetaQuery
|
import suwayomi.tachidesk.graphql.queries.MetaQuery
|
||||||
import suwayomi.tachidesk.graphql.queries.SettingsQuery
|
import suwayomi.tachidesk.graphql.queries.SettingsQuery
|
||||||
import suwayomi.tachidesk.graphql.queries.SourceQuery
|
import suwayomi.tachidesk.graphql.queries.SourceQuery
|
||||||
|
import suwayomi.tachidesk.graphql.queries.TrackQuery
|
||||||
import suwayomi.tachidesk.graphql.queries.UpdateQuery
|
import suwayomi.tachidesk.graphql.queries.UpdateQuery
|
||||||
import suwayomi.tachidesk.graphql.server.primitives.Cursor
|
import suwayomi.tachidesk.graphql.server.primitives.Cursor
|
||||||
import suwayomi.tachidesk.graphql.server.primitives.GraphQLCursor
|
import suwayomi.tachidesk.graphql.server.primitives.GraphQLCursor
|
||||||
@@ -76,7 +78,7 @@ val schema =
|
|||||||
TopLevelObject(MetaQuery()),
|
TopLevelObject(MetaQuery()),
|
||||||
TopLevelObject(SettingsQuery()),
|
TopLevelObject(SettingsQuery()),
|
||||||
TopLevelObject(SourceQuery()),
|
TopLevelObject(SourceQuery()),
|
||||||
// TopLevelObject(TrackQuery()),
|
TopLevelObject(TrackQuery()),
|
||||||
TopLevelObject(UpdateQuery()),
|
TopLevelObject(UpdateQuery()),
|
||||||
),
|
),
|
||||||
mutations =
|
mutations =
|
||||||
@@ -92,7 +94,7 @@ val schema =
|
|||||||
TopLevelObject(MetaMutation()),
|
TopLevelObject(MetaMutation()),
|
||||||
TopLevelObject(SettingsMutation()),
|
TopLevelObject(SettingsMutation()),
|
||||||
TopLevelObject(SourceMutation()),
|
TopLevelObject(SourceMutation()),
|
||||||
// TopLevelObject(TrackMutation()),
|
TopLevelObject(TrackMutation()),
|
||||||
TopLevelObject(UpdateMutation()),
|
TopLevelObject(UpdateMutation()),
|
||||||
),
|
),
|
||||||
subscriptions =
|
subscriptions =
|
||||||
|
|||||||
@@ -155,9 +155,9 @@ class MangaType(
|
|||||||
return dataFetchingEnvironment.getValueFromDataLoader<Long, SourceType?>("SourceDataLoader", sourceId)
|
return dataFetchingEnvironment.getValueFromDataLoader<Long, SourceType?>("SourceDataLoader", sourceId)
|
||||||
}
|
}
|
||||||
|
|
||||||
// fun trackRecords(dataFetchingEnvironment: DataFetchingEnvironment): CompletableFuture<TrackRecordNodeList> {
|
fun trackRecords(dataFetchingEnvironment: DataFetchingEnvironment): CompletableFuture<TrackRecordNodeList> {
|
||||||
// return dataFetchingEnvironment.getValueFromDataLoader<Int, TrackRecordNodeList>("TrackRecordsForMangaIdDataLoader", id)
|
return dataFetchingEnvironment.getValueFromDataLoader<Int, TrackRecordNodeList>("TrackRecordsForMangaIdDataLoader", id)
|
||||||
// }
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
data class MangaNodeList(
|
data class MangaNodeList(
|
||||||
|
|||||||
@@ -20,6 +20,7 @@ import suwayomi.tachidesk.manga.controller.DownloadController
|
|||||||
import suwayomi.tachidesk.manga.controller.ExtensionController
|
import suwayomi.tachidesk.manga.controller.ExtensionController
|
||||||
import suwayomi.tachidesk.manga.controller.MangaController
|
import suwayomi.tachidesk.manga.controller.MangaController
|
||||||
import suwayomi.tachidesk.manga.controller.SourceController
|
import suwayomi.tachidesk.manga.controller.SourceController
|
||||||
|
import suwayomi.tachidesk.manga.controller.TrackController
|
||||||
import suwayomi.tachidesk.manga.controller.UpdateController
|
import suwayomi.tachidesk.manga.controller.UpdateController
|
||||||
|
|
||||||
object MangaAPI {
|
object MangaAPI {
|
||||||
@@ -133,13 +134,13 @@ object MangaAPI {
|
|||||||
ws("", UpdateController::categoryUpdateWS)
|
ws("", UpdateController::categoryUpdateWS)
|
||||||
}
|
}
|
||||||
|
|
||||||
// path("track") {
|
path("track") {
|
||||||
// get("list", TrackController.list)
|
get("list", TrackController.list)
|
||||||
// post("login", TrackController.login)
|
post("login", TrackController.login)
|
||||||
// post("logout", TrackController.logout)
|
post("logout", TrackController.logout)
|
||||||
// post("search", TrackController.search)
|
post("search", TrackController.search)
|
||||||
// post("bind", TrackController.bind)
|
post("bind", TrackController.bind)
|
||||||
// post("update", TrackController.update)
|
post("update", TrackController.update)
|
||||||
// }
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user