Skip to content

Instantly share code, notes, and snippets.

@ninetails
Last active January 10, 2024 20:33
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ninetails/cdea2a9d779d00c226f4c3aca8e709e4 to your computer and use it in GitHub Desktop.
Save ninetails/cdea2a9d779d00c226f4c3aca8e709e4 to your computer and use it in GitHub Desktop.
GraphQL: interfaces & resolvers

GraphQL: interfaces & resolvers

It was made based on Deno docs:

How to use Apollo with Deno

How to run

deno run --allow-run --allow-net --allow-read --allow-env main.ts

Owners Query

You can use the standard

owners { ... }

You can query by ID

owners(id: "3") { ... }

You also can find by their name part

owners(id: "Doe") { ... }

query ExampleQuery {
owners {
id
name
pets {
__typename
id
name
... on Dog {
isGoodBoy
}
... on Cat {
lives
}
... on Bird {
canFly
}
}
}
}
import { ApolloServer } from "npm:@apollo/server@^4.10.0";
import { startStandaloneServer } from "npm:@apollo/server@4.10.0/standalone";
import { graphql } from "npm:graphql@16.8.1";
import { typeDefs } from "./schema.ts";
import { resolvers } from "./resolvers.ts";
const server = new ApolloServer({
typeDefs,
resolvers,
});
const { url } = await startStandaloneServer(server, {
listen: { port: 8000 },
});
console.log(`Server running on: ${url}`);
interface Owner {
id: string;
name: string;
}
interface Pet {
id: string;
type?: PetType;
name: string;
ownerId: string;
[key: string]: any;
}
interface Dog extends Pet {
isGoodBoy: boolean;
}
interface Cat extends Pet {
lives: number;
}
interface Bird extends Pet {
canFly: boolean;
}
interface UnknownPet extends Pet {
}
type Pets = Dog | Cat | Bird | UnknownPet;
enum PetType {
DOG = 'DOG',
CAT = 'CAT',
BIRD = 'BIRD',
}
const owners: Owner[] = [
{
id: "1",
name: "John Doe",
},
{
id: "2",
name: "Jane Doe",
},
{
id: "3",
name: "John Smith",
},
{
id: "4",
name: "Jane Smith",
},
]
const pets: Pets[] = [
{
id: "1",
type: PetType.DOG,
name: "Doggo",
ownerId: "1",
isGoodBoy: true,
},
{
id: "2",
type: PetType.CAT,
name: "Catto",
ownerId: "2",
lives: 9,
},
{
id: "3",
type: PetType.BIRD,
name: "Birdo",
ownerId: "3",
canFly: false,
},
{
id: "4",
type: PetType.BIRD,
name: "Penguin",
ownerId: "3",
canFly: false,
},
{
id: "5",
name: "Isneik",
ownerId: "2",
}
]
export const resolvers = {
Owner: {
pets: (owner: Owner) => {
return pets.filter((pet) => pet.ownerId === owner.id)
},
},
Pet: {
__resolveType(pet: Pet, contextValue: any, info: any){
switch (pet.type) {
case PetType.DOG:
return 'Dog';
case PetType.CAT:
return 'Cat';
case PetType.BIRD:
return 'Bird';
default:
return 'UnknownPet';
}
},
},
Query: {
owners: (_: any, { id, name }: { id: string, name: string }) => {
if (id) {
return owners.filter((owner) => owner.id === id);
}
if (name) {
return owners.filter((owner) => owner.name.toLocaleLowerCase().includes(name.toLocaleLowerCase()));
}
return owners;
},
owner: (_: any, { id, name }: { id: string, name: string }) => {
if (id) {
const owner = owners.find((owner) => owner.id === id);
if (!owner) {
throw new Error(`No owner with id: ${id}`);
}
return owner;
}
if (name) {
const owner = owners.find((owner) => owner.name.toLocaleLowerCase().includes(name.toLocaleLowerCase()));
if (!owner) {
throw new Error(`No owner with name or part: ${name}`);
}
return owner;
}
throw new Error('You must provide either an id or a name');
},
pets: () => pets,
},
};
export const typeDefs = `
type Owner {
id: ID!
name: String!
pets: [Pet]
}
interface Pet {
id: ID!
name: String!
owner: Owner!
}
type Dog implements Pet {
id: ID!
name: String!
owner: Owner!
isGoodBoy: Boolean
}
type Cat implements Pet {
id: ID!
name: String!
owner: Owner!
lives: Int
}
type Bird implements Pet {
id: ID!
name: String!
owner: Owner!
canFly: Boolean
}
type UnknownPet implements Pet {
id: ID!
name: String!
owner: Owner!
}
type Query {
owners(id: String, name: String): [Owner]
owner(id: String, name: String): Owner!
pets: [Pet]
}
`;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment