feat: replace most hand-crafted types with genereated types

This commit is contained in:
DrakeTDL 2023-10-09 15:20:57 -07:00
parent 63bb438d14
commit 65b925f260
No known key found for this signature in database
9 changed files with 2997 additions and 1470 deletions

1
.gitignore vendored Normal file
View File

@ -0,0 +1 @@
**/node_modules

View File

@ -1,5 +1,8 @@
{
"deno.enable": true,
"deno.lint": true,
"deno.unstable": true
}
"deno.unstable": true,
"deno.disablePaths": [
"graphql-codegen"
]
}

View File

@ -2,5 +2,8 @@
"fmt": {
"lineWidth": 100,
"semiColons": false
},
"tasks": {
"graphql-codegen": "cd graphql-codegen; yarn run graphql-codegen --config codegen.ts"
}
}

View File

@ -0,0 +1,32 @@
import type { CodegenConfig } from "@graphql-codegen/cli"
const config: CodegenConfig = {
overwrite: true,
schema: "https://graphql.anilist.co",
verbose: true,
debug: true,
generates: {
"../src/types/generated/graphql.ts": {
plugins: ["typescript"],
config: {
useImplementingTypes: true,
scalars: {
CountryCode: {
input: "string",
output: "string",
},
FuzzyDateInt: {
input: "string",
output: "string",
},
Json: {
input: "Array<Record<string, unknown>>",
output: "Array<Record<string, unknown>>",
},
},
},
},
},
}
export default config

View File

@ -0,0 +1,15 @@
{
"dependencies": {
"graphql": "^16.8.1"
},
"devDependencies": {
"@graphql-codegen/cli": "5.0.0",
"@graphql-codegen/introspection": "4.0.0",
"@graphql-codegen/typescript": "4.0.1",
"@graphql-codegen/typescript-document-nodes": "4.0.1",
"typescript": "^5.2.2"
},
"scripts": {
"codegen": "graphql-codegen --config codegen.ts"
}
}

2832
graphql-codegen/yarn.lock Normal file

File diff suppressed because it is too large Load Diff

View File

@ -1,39 +1,57 @@
import {
ActivityReplyArguments,
AiringScheduleArguments,
CharacterArguments,
CharacterSort,
ExternalLinkSourceCollectionArguments,
Fetch,
Fields,
Fn,
FollowArguments,
LikeArguments,
MediaArguments,
MediaListArguments,
MediaListCollectionArguments,
MediaSort,
MediaTrendArguments,
MediaTrendSort,
RecommendationArguments,
RecommendationSort,
ReviewArguments,
SiteStatisticsArguments,
StaffArguments,
StaffLanguage,
StaffSort,
StudioArguments,
StudioSort,
ThreadArguments,
ThreadCommentSort,
UpdateQuery,
UserArguments,
Variables,
} from "./types/Anilist.ts"
CharacterEdgeVoiceActorRolesArgs,
CharacterEdgeVoiceActorsArgs,
CharacterMediaArgs,
MediaAiringScheduleArgs,
MediaCharactersArgs,
MediaDescriptionArgs,
MediaEdgeRelationTypeArgs,
MediaEdgeVoiceActorRolesArgs,
MediaEdgeVoiceActorsArgs,
MediaRecommendationsArgs,
MediaReviewsArgs,
MediaSourceArgs,
MediaStaffArgs,
MediaStatusArgs,
MediaStudiosArgs,
MediaTrendsArgs,
QueryActivityReplyArgs,
QueryAiringScheduleArgs,
QueryCharacterArgs,
QueryExternalLinkSourceCollectionArgs,
QueryFollowerArgs,
QueryFollowingArgs,
QueryLikeArgs,
QueryMarkdownArgs,
QueryMediaArgs,
QueryMediaListArgs,
QueryMediaListCollectionArgs,
QueryMediaTagCollectionArgs,
QueryMediaTrendArgs,
QueryRecommendationArgs,
QueryReviewArgs,
QueryStaffArgs,
QueryStudioArgs,
QueryThreadArgs,
QueryThreadCommentArgs,
QueryUserArgs,
SiteStatisticsAnimeArgs,
SiteStatisticsCharactersArgs,
SiteStatisticsMangaArgs,
SiteStatisticsReviewsArgs,
SiteStatisticsStaffArgs,
SiteStatisticsStudiosArgs,
SiteStatisticsUsersArgs,
StaffCharacterMediaArgs,
StaffCharactersArgs,
StaffStaffMediaArgs,
StudioMediaArgs,
} from "./types/generated/graphql.ts"
import { Fetch, Fields, Fn, UpdateQuery } from "./types/Anilist.ts"
import type { AtLeastOne } from "./types/AtLeastOne.ts"
const rewriteVarValues = (
variable: string | number | boolean | (string | number)[],
variable: PropertyKey | unknown | (PropertyKey | unknown)[],
) => {
switch (typeof variable) {
case "object":
@ -64,9 +82,7 @@ const updateOperation = (
.replace(
`%${field[level - 1]}`,
`${field[level]}${variables ? ` (${convertedType[0].join(", ")})` : ""}${
hasSubField
? `${` {\n${t(level + 1)}%${field.at(-1)}\n${t(level)}}`}`
: ""
hasSubField ? `${` {\n${t(level + 1)}%${field.at(-1)}\n${t(level)}}`}` : ""
}\n${t(level)}%${field[level - 1]}`,
)
@ -398,49 +414,52 @@ const AniChartUser = ({ query, level }: Fields<typeof updateOperation>) => ({
},
})
const SiteStatistics = ({ query, level }: Fields<typeof updateOperation>) => ({
withUsers(args: AtLeastOne<SiteStatisticsArguments>, fn: Fn<typeof SiteTrendConnection>) {
withUsers(args: AtLeastOne<SiteStatisticsUsersArgs>, fn: Fn<typeof SiteTrendConnection>) {
query[0] = query[0].set({ subField: "users", level, hasSubField: true, variables: args })
let tmpQuery
fn(SiteTrendConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
query[0] = tmpQuery[0]
return this
},
withAnime(args: AtLeastOne<SiteStatisticsArguments>, fn: Fn<typeof SiteTrendConnection>) {
withAnime(args: AtLeastOne<SiteStatisticsAnimeArgs>, fn: Fn<typeof SiteTrendConnection>) {
query[0] = query[0].set({ subField: "anime", level, hasSubField: true, variables: args })
let tmpQuery
fn(SiteTrendConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
query[0] = tmpQuery[0]
return this
},
withManga(args: AtLeastOne<SiteStatisticsArguments>, fn: Fn<typeof SiteTrendConnection>) {
withManga(args: AtLeastOne<SiteStatisticsMangaArgs>, fn: Fn<typeof SiteTrendConnection>) {
query[0] = query[0].set({ subField: "manga", level, hasSubField: true, variables: args })
let tmpQuery
fn(SiteTrendConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
query[0] = tmpQuery[0]
return this
},
withCharacters(args: AtLeastOne<SiteStatisticsArguments>, fn: Fn<typeof SiteTrendConnection>) {
withCharacters(
args: AtLeastOne<SiteStatisticsCharactersArgs>,
fn: Fn<typeof SiteTrendConnection>,
) {
query[0] = query[0].set({ subField: "characters", level, hasSubField: true, variables: args })
let tmpQuery
fn(SiteTrendConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
query[0] = tmpQuery[0]
return this
},
withStaff(args: AtLeastOne<SiteStatisticsArguments>, fn: Fn<typeof SiteTrendConnection>) {
withStaff(args: AtLeastOne<SiteStatisticsStaffArgs>, fn: Fn<typeof SiteTrendConnection>) {
query[0] = query[0].set({ subField: "staff", level, hasSubField: true, variables: args })
let tmpQuery
fn(SiteTrendConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
query[0] = tmpQuery[0]
return this
},
withStudios(args: AtLeastOne<SiteStatisticsArguments>, fn: Fn<typeof SiteTrendConnection>) {
withStudios(args: AtLeastOne<SiteStatisticsStudiosArgs>, fn: Fn<typeof SiteTrendConnection>) {
query[0] = query[0].set({ subField: "studios", level, hasSubField: true, variables: args })
let tmpQuery
fn(SiteTrendConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
query[0] = tmpQuery[0]
return this
},
withReviews(args: AtLeastOne<SiteStatisticsArguments>, fn: Fn<typeof SiteTrendConnection>) {
withReviews(args: AtLeastOne<SiteStatisticsReviewsArgs>, fn: Fn<typeof SiteTrendConnection>) {
query[0] = query[0].set({ subField: "reviews", level, hasSubField: true, variables: args })
let tmpQuery
fn(SiteTrendConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
@ -1162,23 +1181,23 @@ const Media = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** The current releasing status of the media */
withStatus(args?: { version: number }) {
withStatus(args?: MediaStatusArgs) {
query[0] = query[0].set({ subField: "status", level, variables: args })
return this
},
/** Short description of the media's story and characters */
withDescription(args?: { asHtml: boolean }) {
withDescription(args?: MediaDescriptionArgs) {
query[0] = query[0].set({ subField: "description", level, variables: args })
return this
},
/** Source type the media was adapted from. */
withSource(args?: { version: number }) {
withSource(args?: MediaSourceArgs) {
query[0] = query[0].set({ subField: "source", level, variables: args })
return this
},
/** The staff who produced the media */
withStaff(
args: { sort: StaffSort[] } | undefined,
args: MediaStaffArgs | undefined,
fn: (fields: ReturnType<typeof StaffConnection>) => void,
) {
query[0] = query[0].set({ subField: "staff", level, variables: args })
@ -1189,7 +1208,7 @@ const Media = ({ query, level }: Fields<typeof updateOperation>) => ({
},
/** User recommendations for similar media */
withRecommendations(
args: { sort: [RecommendationSort] } | undefined,
args: MediaRecommendationsArgs | undefined,
fn: (fields: ReturnType<typeof RecommendationConnection>) => void,
) {
query[0] = query[0].set({
@ -1204,7 +1223,7 @@ const Media = ({ query, level }: Fields<typeof updateOperation>) => ({
},
/** The characters in the media */
withCharacters(
args: AtLeastOne<{ page: number; sort: [CharacterSort] }> | undefined,
args: AtLeastOne<MediaCharactersArgs> | undefined,
fn: (fields: ReturnType<typeof CharacterConnection>) => void,
) {
query[0] = query[0].set({ subField: "characters", level, variables: args, hasSubField: true })
@ -1217,7 +1236,7 @@ const Media = ({ query, level }: Fields<typeof updateOperation>) => ({
},
/** The companies who produced the media */
withStudios(
args: { sort: [StudioSort] } | undefined,
args: MediaStudiosArgs | undefined,
fn: (fields: ReturnType<typeof StudioConnection>) => void,
) {
query[0] = query[0].set({ subField: "studios", level, variables: args, hasSubField: true })
@ -1228,7 +1247,7 @@ const Media = ({ query, level }: Fields<typeof updateOperation>) => ({
},
/** The media's entire airing schedule */
withAiringSchedule(
args: { notYetAired: boolean } | undefined,
args: MediaAiringScheduleArgs | undefined,
fn: (fields: ReturnType<typeof AiringScheduleConnection>) => void,
) {
query[0] = query[0].set({
@ -1243,7 +1262,7 @@ const Media = ({ query, level }: Fields<typeof updateOperation>) => ({
},
/** The media's daily trend stats */
withTrends(
args: { sort: [MediaTrendSort] } | undefined,
args: MediaTrendsArgs | undefined,
fn: (fields: ReturnType<typeof MediaTrendConnection>) => void,
) {
query[0] = query[0].set({ subField: "trends", level, variables: args, hasSubField: true })
@ -1254,7 +1273,7 @@ const Media = ({ query, level }: Fields<typeof updateOperation>) => ({
},
/** User reviews of the media */
withReviews(
args: { limit: number } | undefined,
args: MediaReviewsArgs | undefined,
fn: (fields: ReturnType<typeof ReviewConnection>) => void,
) {
query[0] = query[0].set({ subField: "reviews", level, variables: args })
@ -1379,7 +1398,7 @@ const MediaEdge = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** The type of relation to the parent model */
withRelationType(args?: { version: number }) {
withRelationType(args?: MediaEdgeRelationTypeArgs) {
query[0] = query[0].set({ subField: "relationType", level, variables: args })
return this
},
@ -1422,7 +1441,7 @@ const MediaEdge = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** The voice actors of the character */
withVoiceActors(args: { language: StaffLanguage } | undefined, fn: Fn<typeof Staff>) {
withVoiceActors(args: MediaEdgeVoiceActorsArgs | undefined, fn: Fn<typeof Staff>) {
query[0] = query[0].set({ subField: "voiceActors", level, variables: args, hasSubField: true })
let tmpQuery
fn(Staff({ query: tmpQuery = [query[0]], level: level + 1 }))
@ -1430,7 +1449,10 @@ const MediaEdge = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** The voice actors of the character with role date */
withVoiceActorRoles(args: { language: StaffLanguage } | undefined, fn: Fn<typeof StaffRoleType>) {
withVoiceActorRoles(
args: MediaEdgeVoiceActorRolesArgs | undefined,
fn: Fn<typeof StaffRoleType>,
) {
query[0] = query[0].set({
subField: "voiceActorRoles",
level,
@ -1684,7 +1706,7 @@ const Staff = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** Media where the staff member has a production role */
withStaffMedia(args: { sort: MediaSort[] } | undefined, fn: Fn<typeof MediaConnection>) {
withStaffMedia(args: StaffStaffMediaArgs | undefined, fn: Fn<typeof MediaConnection>) {
query[0] = query[0].set({ subField: "staffMedia", level, variables: args, hasSubField: true })
let tmpQuery
fn(MediaConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
@ -1692,7 +1714,7 @@ const Staff = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** Characters voiced by the actor */
withCharacters(args: { sort: CharacterSort[] } | undefined, fn: Fn<typeof CharacterConnection>) {
withCharacters(args: StaffCharactersArgs | undefined, fn: Fn<typeof CharacterConnection>) {
query[0] = query[0].set({ subField: "characters", level, variables: args, hasSubField: true })
let tmpQuery
fn(CharacterConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
@ -1700,7 +1722,7 @@ const Staff = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** Media the actor voiced characters in. (Same data as characters with media as node instead of characters) */
withCharacterMedia(args: { sort: MediaSort[] } | undefined, fn: Fn<typeof MediaConnection>) {
withCharacterMedia(args: StaffCharacterMediaArgs | undefined, fn: Fn<typeof MediaConnection>) {
query[0] = query[0].set({
subField: "characterMedia",
level,
@ -1816,7 +1838,7 @@ const Studio = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** The media the studio has worked on */
withMedia(args: { sort: [MediaSort] } | undefined, fn: Fn<typeof MediaConnection>) {
withMedia(args: StudioMediaArgs | undefined, fn: Fn<typeof MediaConnection>) {
query[0] = query[0].set({ subField: "media", level, variables: args, hasSubField: true })
let tmpQuery
fn(MediaConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
@ -2360,7 +2382,7 @@ const Character = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** Media that includes the character */
withMedia(args: { sort: MediaSort[] } | undefined, fn: Fn<typeof MediaConnection>) {
withMedia(args: CharacterMediaArgs | undefined, fn: Fn<typeof MediaConnection>) {
query[0] = query[0].set({ subField: "media", level, variables: args, hasSubField: true })
let tmpQuery
fn(MediaConnection({ query: tmpQuery = [query[0]], level: level + 1 }))
@ -2402,7 +2424,7 @@ const CharacterEdge = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** The voice actors of the character */
withVoiceActors(args: { language: StaffLanguage } | undefined, fn: Fn<typeof Staff>) {
withVoiceActors(args: CharacterEdgeVoiceActorsArgs | undefined, fn: Fn<typeof Staff>) {
query[0] = query[0].set({ subField: "voiceActors", level, variables: args, hasSubField: true })
let tmpQuery
fn(Staff({ query: tmpQuery = [query[0]], level: level + 1 }))
@ -2410,7 +2432,10 @@ const CharacterEdge = ({ query, level }: Fields<typeof updateOperation>) => ({
return this
},
/** The voice actors of the character with role date */
withVoiceActorRoles(args: { language: StaffLanguage } | undefined, fn: Fn<typeof StaffRoleType>) {
withVoiceActorRoles(
args: CharacterEdgeVoiceActorRolesArgs | undefined,
fn: Fn<typeof StaffRoleType>,
) {
query[0] = query[0].set({
subField: "voiceActorRoles",
level,
@ -2755,7 +2780,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Media query */
Media(
args: AtLeastOne<MediaArguments> & Variables,
args: AtLeastOne<QueryMediaArgs>,
fn?: (fields: ReturnType<typeof Media>) => void,
) {
operation = operation.set({
@ -2775,7 +2800,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Media Trend query */
MediaTrend(
args: AtLeastOne<MediaTrendArguments> & Variables,
args: QueryMediaTrendArgs,
fn?: (fields: ReturnType<typeof MediaTrend>) => void,
) {
operation = operation.set({
@ -2794,7 +2819,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Airing schedule query */
AiringSchedule(
args: AtLeastOne<AiringScheduleArguments> & Variables,
args: QueryAiringScheduleArgs,
fn?: (fields: ReturnType<typeof AiringSchedule>) => void,
) {
operation = operation.set({
@ -2813,7 +2838,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Character query */
Character(
args: AtLeastOne<CharacterArguments> & Variables,
args: QueryCharacterArgs,
fn?: (fields: ReturnType<typeof Character>) => void,
) {
operation = operation.set({
@ -2832,7 +2857,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Staff query */
Staff(
args: AtLeastOne<StaffArguments> & Variables,
args: QueryStaffArgs,
fn?: (fields: ReturnType<typeof Staff>) => void,
) {
operation = operation.set({
@ -2851,7 +2876,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Media list query */
MediaList(
args: AtLeastOne<MediaListArguments> & Variables,
args: QueryMediaListArgs,
fn?: (fields: ReturnType<typeof MediaList>) => void,
) {
operation = operation.set({
@ -2870,7 +2895,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Media list collection query, provides list pre-grouped by status & custom lists. User ID and Media Type arguments required. */
MediaListCollection(
args: AtLeastOne<MediaListCollectionArguments> & Variables,
args: QueryMediaListCollectionArgs,
fn?: (fields: ReturnType<typeof MediaListCollection>) => void,
) {
operation = operation.set({
@ -2894,10 +2919,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Collection of all the possible media tags */
MediaTagCollection(
args: {
/** Mod Only */
status: number
} & Variables,
args: QueryMediaTagCollectionArgs,
fn?: (fields: ReturnType<typeof MediaTag>) => void,
) {
operation = operation.set({
@ -2916,7 +2938,7 @@ export const Client = function (auth?: { token: string }) {
},
/** User query */
User(
args: AtLeastOne<UserArguments> & Variables,
args: QueryUserArgs,
fn?: (fields: ReturnType<typeof User>) => void,
) {
operation = operation.set({
@ -2956,7 +2978,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Studio query */
Studio(
args: AtLeastOne<StudioArguments> & Variables,
args: QueryStudioArgs,
fn?: (fields: ReturnType<typeof Studio>) => void,
) {
operation = operation.set({
@ -2975,7 +2997,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Review query */
Review(
args: AtLeastOne<ReviewArguments> & Variables,
args: QueryReviewArgs,
fn?: (fields: ReturnType<typeof Review>) => void,
) {
operation = operation.set({
@ -2998,7 +3020,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Activity reply query */
ActivityReply(
args: AtLeastOne<ActivityReplyArguments> & Variables,
args: QueryActivityReplyArgs,
fn?: (fields: ReturnType<typeof ActivityReply>) => void,
) {
operation = operation.set({
@ -3017,7 +3039,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Follow query */
Following(
args: AtLeastOne<FollowArguments> & Variables,
args: QueryFollowingArgs,
fn?: (fields: ReturnType<typeof User>) => void,
) {
operation = operation.set({
@ -3036,7 +3058,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Follow query */
Follower(
args: AtLeastOne<FollowArguments> & Variables,
args: QueryFollowerArgs,
fn?: (fields: ReturnType<typeof User>) => void,
) {
operation = operation.set({
@ -3055,7 +3077,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Thread query */
Thread(
args: AtLeastOne<ThreadArguments> & Variables,
args: QueryThreadArgs,
fn?: (fields: ReturnType<typeof Thread>) => void,
) {
operation = operation.set({
@ -3074,18 +3096,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Comment query */
ThreadComment(
args: AtLeastOne<
{
/** Filter by the comment id */
id: number
/** Filter by the thread id */
threadId: number
/** Filter by the user id of the comment's creator */
userId: number
/** The order the results will be returned in */
sort: ThreadCommentSort[]
}
>,
args: QueryThreadCommentArgs,
fn?: (fields: ReturnType<typeof ThreadComment>) => void,
) {
operation = operation.set({
@ -3104,7 +3115,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Recommendation query */
Recommendation(
args: AtLeastOne<RecommendationArguments> & Variables,
args: QueryRecommendationArgs,
fn?: (fields: ReturnType<typeof Recommendation>) => void,
) {
operation = operation.set({
@ -3123,7 +3134,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Like query */
Like(
args: AtLeastOne<LikeArguments> & Variables,
args: QueryLikeArgs,
fn?: (fields: ReturnType<typeof User>) => void,
) {
operation = operation.set({
@ -3142,10 +3153,7 @@ export const Client = function (auth?: { token: string }) {
},
/** Provide AniList markdown to be converted to html (Requires auth) */
Markdown(
args: {
/** The markdown to be parsed to html */
markdown: string
},
args: QueryMarkdownArgs,
fn: (fields: ReturnType<typeof Markdown>) => void,
) {
operation = operation.set({
@ -3186,7 +3194,7 @@ export const Client = function (auth?: { token: string }) {
},
/** ExternalLinkSource collection query */
ExternalLinkSourceCollection(
args: AtLeastOne<ExternalLinkSourceCollectionArguments> & Variables,
args: QueryExternalLinkSourceCollectionArgs,
fn?: (fields: ReturnType<typeof ExternalLinkSourceCollection>) => void,
) {
operation = operation.set({

File diff suppressed because it is too large Load Diff

View File

@ -1,5 +1,5 @@
export type AtLeastOne<O> = {
[P in keyof O]:
& { [L in P]: O[L] }
& Required<{ [L in P]: O[L] }>
& { [L in Exclude<keyof O, P>]?: O[L] }
}[keyof O]