Skip to content

Commit

Permalink
fix(achievements): adds achievements to the API and adds support for …
Browse files Browse the repository at this point in the history
…sanity as a source

tested and working for getting all achievements as well as achievements by player name
  • Loading branch information
KenEucker committed Dec 23, 2023
1 parent e1875ff commit 28631f9
Show file tree
Hide file tree
Showing 19 changed files with 315 additions and 25 deletions.
43 changes: 31 additions & 12 deletions examples/node/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -62,21 +62,21 @@ const log = (message, response, toLog = false) => {
}

const getTag1Async = async (pre, client, out = false, opts = {}) => {
const tag1 = await client.tags(1, opts)
const tag1 = await client.tags(1, opts).catch(console.error)
log(`${pre} :: successfully retrieved tag 1 data by number`, tag1, out)

return tag1
}

const getTodaysTagsAsync = async (pre, client, out = false, opts = {}) => {
const todaysTags = await client.tags({ time :'day', limit: 10 }, opts)
const todaysTags = await client.tags({ time :'day', limit: 10 }, opts).catch(console.error)
log(`${pre} :: successfully todays tags data`, todaysTags, out)

return todaysTags
}

const getQueueAsync = async (pre, client, out = false, opts = {}) => {
const tags = await client.getQueue(undefined, opts)
const tags = await client.getQueue(undefined, opts).catch(console.error)
log(`${pre} :: successfully retrieved queued tag data`, tags, out)
console.log(tags[0])

Expand All @@ -100,58 +100,75 @@ const queueTagAsync = async (pre, client, out = false, opts = {}) => {

const get10TagsAsync = async (pre, client, out = false, opts = {}) => {
opts.limit = opts.limit ? opts.limit : 10
const tags = await client.getTags(undefined, opts)
const tags = await client.getTags(undefined, opts).catch(console.error)
log(`${pre} :: successfully retrieved tags data`, tags, out)
console.log(tags[0])

return tags
}

const getCurrentTagAsync = async (pre, client, out = false, opts = {}) => {
const current = await client.getTag(undefined, opts)
const current = await client.getTag(undefined, opts).catch(console.error)
log(`${pre} :: successfully retrieved current tag data`, current, out)

return current
}

const getGameAsync = async (pre, client, out = false, opts = {}) => {
const testGameData = await client.getGame(undefined, opts)
const testGameData = await client.getGame(undefined, opts).catch(console.error)
log(`${pre} :: success fully retrieved game data`, testGameData, out)

return testGameData
}

const getAllGamesAsync = async (pre, client, out = false, opts = {}) => {
const testGameData = await client.getGame({game: undefined}, opts)
const testGameData = await client.getGame({game: undefined}, opts).catch(console.error)
log(`${pre} :: success fully retrieved game data`, testGameData, out)

return testGameData
}

const get10PlayersAsync = async (pre, client, out = false, opts = {}) => {
opts.limit = opts.limit ? opts.limit : 10
const testPlayerData = await client.getPlayers(undefined, opts)
const testPlayerData = await client.getPlayers(undefined, opts).catch(console.error)
log(`${pre} :: success fully retrieved player data`, testPlayerData, out)

return testPlayerData
}

const get10AmbassadorsAsync = async (pre, client, out = false, opts = {}) => {
opts.limit = opts.limit ? opts.limit : 10
const testAmbassadorData = await client.getAmbassadors(undefined, opts)
const testAmbassadorData = await client.getAmbassadors(undefined, opts).catch(console.error)
log(`${pre} :: success fully retrieved ambassador data`, testAmbassadorData, out)

return testAmbassadorData
}

const get10SettingsAsync = async (pre, client, out = false, opts = {}) => {
opts.limit = opts.limit ? opts.limit : 10
const testSettingData = await client.getSettings(undefined, opts)
const testSettingData = await client.getSettings(undefined, opts).catch(console.error)
log(`${pre} :: success fully retrieved game settings`, testSettingData, out)

return testSettingData
}

const get10AchievementsAsync = async (pre, client, out = false, opts = {}) => {
opts.limit = opts.limit ? opts.limit : 10
const testAchievementData = await client.getAchievements(undefined, opts).catch(console.error)
log(`${pre} :: success fully retrieved game achievements`, testAchievementData, out)

return testAchievementData
}

const getPlayerAchievementsAsync = async (pre, client, out = false, opts = {}) => {
opts.limit = opts.limit ? opts.limit : 10
opts.player = 'Ken'
const testAchievementData = await client.getAchievements(undefined, opts).catch(console.error)
log(`${pre} :: success fully retrieved player achievements for player [${opts.player}]`, testAchievementData, out)

return testAchievementData
}

const runTests = async (out = false) => {
if (false) {
console.log(pretty("Default BikeTag Client Instantiated"), biketagDefaultInstanceOpts)
Expand All @@ -163,7 +180,7 @@ const runTests = async (out = false) => {
await get10PlayersAsync("BikeTag", biketagDefaultInstance, out)
}

if (bikeTagImgurInstance) {
if (false) {
console.log(pretty("Imgur BikeTag Client Instantiated"), imgurInstanceOpts)
await getGameAsync("Imgur", bikeTagImgurInstance, out)
// await getTag1Async("Imgur", bikeTagImgurInstance, out)
Expand All @@ -175,7 +192,7 @@ const runTests = async (out = false) => {
// await get10PlayersAsync("Imgur", bikeTagImgurInstance, out)
}

if (false) {
if (bikeTagSanityInstance) {
console.log(pretty("Sanity BikeTag Client Instantiated"), sanityInstanceOpts)
// await getTag1Async("Sanity", bikeTagSanityInstance, out)
// await get10TagsAsync("Sanity", bikeTagSanityInstance, out)
Expand All @@ -184,6 +201,8 @@ const runTests = async (out = false) => {
// await get10PlayersAsync("Sanity", bikeTagSanityInstance, out)
// await get10AmbassadorsAsync("Sanity", bikeTagSanityInstance, out)
// await get10SettingsAsync("Sanity", bikeTagSanityInstance, out)
// await get10AchievementsAsync("Sanity", bikeTagSanityInstance, out)
await getPlayerAchievementsAsync("Sanity", bikeTagSanityInstance, out)
}
}

Expand Down
4 changes: 2 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "biketag",
"version": "3.2.1",
"version": "3.2.2",
"description": "The Javascript client API for BikeTag Games",
"main": "./biketag.node.js",
"browser": "./biketag.js",
Expand Down
33 changes: 33 additions & 0 deletions src/biketag/getAchievements.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { BikeTagClient } from '../client'
import { ACHIEVEMENTS_ENDPOINT } from '../common/endpoints'
import { AvailableApis, HttpStatusCode } from '../common/enums'
import { getAchievementsPayload } from '../common/payloads'
import { Achievement } from '../common/schema'
import { BikeTagApiResponse } from '../common/types'
import { getApiUrl } from './helpers'

export async function getAchievements(
client: BikeTagClient,
payload: getAchievementsPayload
): Promise<BikeTagApiResponse<Achievement[]>> {
delete payload.source
const opts = {
url: getApiUrl(payload.host, ACHIEVEMENTS_ENDPOINT, payload.game),
data: payload,
}

/// TODO: allow getting achievements by Player
const response = await (payload.cached
? client.cachedRequest(opts)
: client.request(opts))

const success = response.status === 200

return {
data: response.data as unknown as Achievement[],
success,
error: !success ? response.statusText : undefined,
source: AvailableApis[AvailableApis.biketag],
status: success ? HttpStatusCode.Ok : response.status,
}
}
102 changes: 101 additions & 1 deletion src/client.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,11 @@
import { Game, Tag, Player, Ambassador, Setting } from './common/schema'
import {
Game,
Tag,
Player,
Ambassador,
Setting,
Achievement,
} from './common/schema'
import {
Credentials,
BikeTagApiResponse,
Expand Down Expand Up @@ -35,6 +42,7 @@ import {
getQueuePayload,
queueTagPayload,
archiveTagPayload,
getAchievementsPayload,
} from './common/payloads'
import {
constructTagNumberSlug,
Expand Down Expand Up @@ -1304,6 +1312,98 @@ export class BikeTagClient extends EventEmitter {
}
}

/// **************************** Achievement Data Methods ********************************* ///

achievements(
payload?:
| RequireAtLeastOne<getAchievementsPayload>
| RequireAtLeastOne<getAchievementsPayload>
| string
| string[],
opts?: RequireAtLeastOne<Credentials>
): Promise<BikeTagApiResponse<Achievement[]> | Achievement[]> {
const options = this.options(
payload,
DataTypes.game,
opts,
'getAchievements'
)
return this.getAchievements(options as getAchievementsPayload, opts).then(
(r) => (options.concise ? r.data : r)
)
}

getAchievement(
payload: RequireAtLeastOne<getAchievementsPayload> | string,
opts?: RequireAtLeastOne<Credentials>
): Promise<BikeTagApiResponse<Achievement>> {
const { client, options, api } = this.getClientAdapter(
payload,
opts,
DataTypes.setting
)
const clientMethod = api.getAchievement

/// If the client adapter implements a direct way to retrieve a single setting
if (clientMethod) {
return clientMethod(client, options).catch((e) => {
return {
status: HttpStatusCode.InternalServerError,
data: null,
error: e.code ?? e,
success: false,
source: AvailableApis[options.source],
}
})
}

/// Else, use the get all and filter method
return this.getAchievements(
this.getInitialPayload(
payload,
undefined,
'getAchievements'
) as unknown as getAchievementsPayload,
opts
).then((r) => {
return {
data: r.data?.length ? r.data[0] : null,
status: r.status,
source: r.source,
success: r.success,
}
})
}

getAchievements(
payload?: RequireAtLeastOne<getAchievementsPayload> | string[],
opts?: RequireAtLeastOne<Credentials>
): Promise<BikeTagApiResponse<Achievement[]>> {
const { client, options, api, source } = this.getClientAdapter(
payload,
opts,
DataTypes.achievement,
'getAchievements'
)
const clientMethod = api.getAchievements

if (clientMethod) {
return clientMethod(client, options).catch((e) => {
return Promise.resolve({
status: HttpStatusCode.InternalServerError,
data: null,
error: e.code ?? e,
success: false,
source,
})
})
} else {
return Promise.reject(
`getAchievements ${Errors.NotImplemented} ${source}`
)
}
}

/// **************************** Client Instance Methods ****************************** ///

/// Data provided by Gun Client
Expand Down
24 changes: 19 additions & 5 deletions src/common/data.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Tag, Game, Player, Ambassador, Setting } from './schema'
import { Tag, Game, Player, Ambassador, Setting, Achievement } from './schema'

export const cacheKeys = {
sanityUrlText: `sanity::`,
Expand Down Expand Up @@ -109,17 +109,18 @@ export const gameDataObjectFields = {

export const createPlayerObject = (playerData: any = {}): Player => {
return {
tags: playerData.tags ?? [],
games: playerData.games ?? (playerData.game ? [playerData.game] : []),
achievements: playerData.tags ?? [],
bicon: playerData.bicon ?? '',
games: playerData.games ?? (playerData.game ? [playerData.game] : []),
name: playerData.name ?? '',
slug: playerData.slug ?? '',
tags: playerData.tags ?? [],
} as Player
}

export const playerDataFields = Object.keys(createPlayerObject())
export const playerDataReferenceFields = ['games', 'tags']
export const playerDataArrayFields = ['games', 'tags']
export const playerDataReferenceFields = ['games', 'tags', 'achievements']
export const playerDataArrayFields = ['games', 'tags', 'achievements']
export const playerDataAssetFields = ['bicon']
export const playerDataObjectFields = {
bicon: 'asset->_ref',
Expand Down Expand Up @@ -156,3 +157,16 @@ export const createSettingObject = (settingData: any = {}): Setting => {
} as Setting
}
export const settingDataFields = Object.keys(createSettingObject())

export const createAchievementObject = (
achievementData: any = {}
): Achievement => {
return {
slug: achievementData.slug ?? '',
description: achievementData.description ?? '',
name: achievementData.name ?? '',
key: achievementData.key ?? '',
value: achievementData.value ?? '',
} as Achievement
}
export const achievementDataFields = Object.keys(createAchievementObject())
2 changes: 2 additions & 0 deletions src/common/endpoints.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ export const QUEUE_ENDPOINT = `queue`

export const SETTINGS_ENDPOINT = `settings`

export const ACHIEVEMENTS_ENDPOINT = `achievements`

export const UPDATE_ENDPOINT = `update`

export const DELETE_ENDPOINT = `delete`
Expand Down
1 change: 1 addition & 0 deletions src/common/enums.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ export enum DataTypes {
setting,
tag,
queue,
achievement,
}

export enum Errors {
Expand Down
Loading

0 comments on commit 28631f9

Please sign in to comment.