Skip to content

Commit

Permalink
Merge branch 'master' into feat/fix-wording
Browse files Browse the repository at this point in the history
  • Loading branch information
meelrossi committed Sep 20, 2023
2 parents 3e1fe30 + 43cb07a commit f62fbb1
Show file tree
Hide file tree
Showing 2 changed files with 123 additions and 0 deletions.
71 changes: 71 additions & 0 deletions src/lib/api/ens.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
import { ENSApi } from './ens'

describe('when fetching the ens list for an owner', () => {
let owner: string

beforeEach(() => {
owner = '0x123'
})

describe('when the ens api is instanced with a subgraph url', () => {
let subgraphUrl: string
let ensApi: ENSApi

beforeEach(() => {
subgraphUrl = 'https://ens-subgraph.com'
ensApi = new ENSApi(subgraphUrl)
})

describe('when the fetch request fails', () => {
beforeEach(() => {
jest.spyOn(global, 'fetch').mockRejectedValueOnce(new Error('Some Error'))
})

it('should throw an error containing the error of the fetch request', async () => {
await expect(ensApi.fetchENSList(owner)).rejects.toThrowError('Failed to fetch ENS list - Some Error')
})
})

describe('when the fetch response is not ok', () => {
beforeEach(() => {
jest.spyOn(global, 'fetch').mockResolvedValueOnce({ ok: false, status: 500 } as any)
})

it('should throw an error containing the status code of the failed response', async () => {
await expect(ensApi.fetchENSList(owner)).rejects.toThrowError('Failed to fetch ENS list - 500')
})
})

describe('when the query result has an errors property', () => {
beforeEach(() => {
jest
.spyOn(global, 'fetch')
.mockResolvedValueOnce({ ok: true, json: () => Promise.resolve({ errors: [{ message: 'Some Error' }] }) } as any)
})

it('should throw an error containing the stringified errors property value', async () => {
await expect(ensApi.fetchENSList(owner)).rejects.toThrowError('Failed to fetch ENS list - [{"message":"Some Error"}]')
})
})

describe('when the query result has a data property', () => {
let mockFetch: jest.SpyInstance

beforeEach(() => {
mockFetch = jest
.spyOn(global, 'fetch')
.mockResolvedValueOnce({ ok: true, json: () => Promise.resolve({ data: { domains: [{ name: 'some-name.eth' }] } }) } as any)
})

it('should return an array of ens names', async () => {
await expect(ensApi.fetchENSList(owner)).resolves.toEqual(['some-name.eth'])
})

it('should add the provided owner to the fetch request', async () => {
await ensApi.fetchENSList(owner)

expect(mockFetch).toHaveBeenCalledWith(subgraphUrl, expect.objectContaining({ body: expect.stringContaining(owner) }))
})
})
})
})
52 changes: 52 additions & 0 deletions src/lib/api/ens.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
type Domain = { name: string }

type DomainsQueryResult = { data: { domains: Domain[] } } | { errors: any }

const FAIL_TO_FETCH_ENS_LIST_MESSAGE = 'Failed to fetch ENS list'

export class ENSApi {
constructor(private subgraph: string) {}

/**
* Will fetch all ens domains owned by the given address.
*/
fetchENSList = async (owner: string): Promise<string[]> => {
const lowercasedOwner = owner.toLowerCase()

let response: Response

try {
response = await fetch(this.subgraph, {
method: 'POST',
headers: {
'content-type': 'application/json'
},
body: JSON.stringify({
query: `
{
domains(
where: {or: [{wrappedOwner: "${lowercasedOwner}"}, {registrant: "${lowercasedOwner}"}]}
) {
name
}
}
`
})
})
} catch (e) {
throw new Error(`${FAIL_TO_FETCH_ENS_LIST_MESSAGE} - ${(e as Error).message}`)
}

if (!response.ok) {
throw new Error(`${FAIL_TO_FETCH_ENS_LIST_MESSAGE} - ${response.status}`)
}

const queryResult: DomainsQueryResult = await response.json()

if ('errors' in queryResult) {
throw new Error(`${FAIL_TO_FETCH_ENS_LIST_MESSAGE} - ${JSON.stringify(queryResult.errors)}`)
}

return queryResult.data.domains.map(domain => domain.name)
}
}

0 comments on commit f62fbb1

Please sign in to comment.