clashofclans.js 3.6.2 → 3.6.3-dev.fb51c0b
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +1 -1
- package/dist/battle-log.spec.d.ts +1 -0
- package/dist/battle-log.spec.js +13 -0
- package/dist/rest/RESTManager.d.ts +6 -1
- package/dist/rest/RESTManager.js +9 -0
- package/dist/struct/Unit.js +2 -0
- package/dist/types/api.d.ts +36 -0
- package/dist/util/Constants.d.ts +2 -32
- package/dist/util/Util.d.ts +1 -0
- package/dist/util/Util.js +38 -0
- package/dist/util/raw.json +1 -1
- package/package.json +1 -1
package/LICENSE
CHANGED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const Client_1 = require("./client/Client");
|
|
4
|
+
const Util_1 = require("./util/Util");
|
|
5
|
+
describe('root', () => {
|
|
6
|
+
const client = new Client_1.Client({ baseURL: process.env.BASE_URL });
|
|
7
|
+
it('should return battle logs', async () => {
|
|
8
|
+
const { body: result } = await client.rest.getBattleLog('#9JPLU2RJ2');
|
|
9
|
+
const legendAttacks = result.items.filter((item) => item.battleType === 'legend').slice(-8);
|
|
10
|
+
console.log(legendAttacks.map((m) => Util_1.Util.calculateTrophies(m.stars, m.destructionPercentage, m.attack, true)));
|
|
11
|
+
expect(result).toHaveProperty('items');
|
|
12
|
+
});
|
|
13
|
+
});
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
2
|
import { EventEmitter } from 'node:events';
|
|
3
|
-
import { APIBuilderBaseLeague, APIBuilderBaseLeagueList, APICapitalLeague, APICapitalLeagueList, APICapitalRaidSeasons, APIClan, APIClanBuilderBaseRankingList, APIClanCapitalRankingList, APIClanList, APIClanMemberList, APIClanRankingList, APIClanWar, APIClanWarLeagueGroup, APIClanWarLogList, APIGoldPassSeason, APILabelList, APILeagueSeasonList, APILeagueTier, APILeagueTierList, APILocation, APILocationList, APIPlayer, APIPlayerBuilderBaseRankingList, APIPlayerRankingList, APIPlayerSeasonRankingList, APIVerifyToken, APIWarLeague, APIWarLeagueList, ClanSearchOptions, LoginOptions, OverrideOptions, RESTOptions, SearchOptions } from '../types';
|
|
3
|
+
import { APIBattleLogEntryList, APIBuilderBaseLeague, APIBuilderBaseLeagueList, APICapitalLeague, APICapitalLeagueList, APICapitalRaidSeasons, APIClan, APIClanBuilderBaseRankingList, APIClanCapitalRankingList, APIClanList, APIClanMemberList, APIClanRankingList, APIClanWar, APIClanWarLeagueGroup, APIClanWarLogList, APIGoldPassSeason, APILabelList, APILeagueGroupList, APILeagueSeasonList, APILeagueSeasonResultList, APILeagueTier, APILeagueTierList, APILocation, APILocationList, APIPlayer, APIPlayerBuilderBaseRankingList, APIPlayerRankingList, APIPlayerSeasonRankingList, APIVerifyToken, APIWarLeague, APIWarLeagueList, ClanSearchOptions, LoginOptions, OverrideOptions, RESTOptions, SearchOptions } from '../types';
|
|
4
4
|
import { RestEvents } from '../util/Constants';
|
|
5
5
|
import { Util } from '../util/Util';
|
|
6
6
|
import { RequestHandler } from './RequestHandler';
|
|
@@ -72,6 +72,11 @@ export declare class RESTManager extends EventEmitter {
|
|
|
72
72
|
getPlayer(playerTag: string, options?: OverrideOptions): Promise<import("../types").Result<APIPlayer>>;
|
|
73
73
|
/** Verify Player API token that can be found from the Game settings. */
|
|
74
74
|
verifyPlayerToken(playerTag: string, token: string, options?: OverrideOptions): Promise<import("../types").Result<APIVerifyToken>>;
|
|
75
|
+
getLeagueHistory(playerTag: string, options?: OverrideOptions): Promise<import("../types").Result<APILeagueSeasonResultList>>;
|
|
76
|
+
getBattleLog(playerTag: string, options?: OverrideOptions): Promise<import("../types").Result<APIBattleLogEntryList>>;
|
|
77
|
+
getLeagueGroup(leagueGroupTag: string, seasonId: string, options?: OverrideOptions & {
|
|
78
|
+
playerTag?: string;
|
|
79
|
+
}): Promise<import("../types").Result<APILeagueGroupList>>;
|
|
75
80
|
/** Get a list of League Tiers. */
|
|
76
81
|
getLeagueTiers(options?: SearchOptions): Promise<import("../types").Result<APILeagueTierList>>;
|
|
77
82
|
/** Get a League tier info. */
|
package/dist/rest/RESTManager.js
CHANGED
|
@@ -81,6 +81,15 @@ class RESTManager extends node_events_1.EventEmitter {
|
|
|
81
81
|
...options
|
|
82
82
|
});
|
|
83
83
|
}
|
|
84
|
+
getLeagueHistory(playerTag, options) {
|
|
85
|
+
return this.requestHandler.request(`/players/${Util_1.Util.encodeURI(playerTag)}/leaguehistory`, options);
|
|
86
|
+
}
|
|
87
|
+
getBattleLog(playerTag, options) {
|
|
88
|
+
return this.requestHandler.request(`/players/${Util_1.Util.encodeURI(playerTag)}/battlelog`, options);
|
|
89
|
+
}
|
|
90
|
+
getLeagueGroup(leagueGroupTag, seasonId, options) {
|
|
91
|
+
return this.requestHandler.request(`/leaguegroup/${leagueGroupTag}/${seasonId}`, options);
|
|
92
|
+
}
|
|
84
93
|
/** Get a list of League Tiers. */
|
|
85
94
|
getLeagueTiers(options) {
|
|
86
95
|
const query = Util_1.Util.queryString(options);
|
package/dist/struct/Unit.js
CHANGED
|
@@ -6,6 +6,8 @@ const Constants_1 = require("../util/Constants");
|
|
|
6
6
|
class Unit {
|
|
7
7
|
// #endregion static
|
|
8
8
|
constructor(data, unit) {
|
|
9
|
+
/** Training time of this unit. */
|
|
10
|
+
this.trainingTime = 0;
|
|
9
11
|
this.name = unit.name;
|
|
10
12
|
this.level = unit.level;
|
|
11
13
|
this.maxLevel = unit.maxLevel;
|
package/dist/types/api.d.ts
CHANGED
|
@@ -317,6 +317,42 @@ export interface APIVerifyToken {
|
|
|
317
317
|
token: string;
|
|
318
318
|
status: 'ok' | 'invalid';
|
|
319
319
|
}
|
|
320
|
+
export interface APIBattleLogEntryList {
|
|
321
|
+
items: APIBattleLogEntry[];
|
|
322
|
+
}
|
|
323
|
+
export interface APILootEntry {
|
|
324
|
+
name: string;
|
|
325
|
+
amount: number;
|
|
326
|
+
}
|
|
327
|
+
export interface APIBattleLogEntry {
|
|
328
|
+
battleType: 'legend' | 'homeVillage' | 'ranked';
|
|
329
|
+
attack: boolean;
|
|
330
|
+
armyShareCode: string;
|
|
331
|
+
opponentPlayerTag: string;
|
|
332
|
+
stars: number;
|
|
333
|
+
destructionPercentage: number;
|
|
334
|
+
lootedResources: APILootEntry[];
|
|
335
|
+
extraLootedResources: APILootEntry[];
|
|
336
|
+
availableLoot: APILootEntry[];
|
|
337
|
+
}
|
|
338
|
+
export interface APILeagueSeasonResult {
|
|
339
|
+
leagueSeasonId: number;
|
|
340
|
+
leagueTrophies: number;
|
|
341
|
+
leagueTierId: number;
|
|
342
|
+
placement: number;
|
|
343
|
+
attackWins: number;
|
|
344
|
+
attackLosses: number;
|
|
345
|
+
attackStars: number;
|
|
346
|
+
defenseWins: number;
|
|
347
|
+
defenseLosses: number;
|
|
348
|
+
defenseStars: number;
|
|
349
|
+
maxBattles: number;
|
|
350
|
+
}
|
|
351
|
+
export interface APILeagueSeasonResultList {
|
|
352
|
+
items: APILeagueSeasonResult[];
|
|
353
|
+
}
|
|
354
|
+
export interface APILeagueGroupList {
|
|
355
|
+
}
|
|
320
356
|
/** /locations */
|
|
321
357
|
export interface APILocationList {
|
|
322
358
|
items: APILocation[];
|
package/dist/util/Constants.d.ts
CHANGED
|
@@ -70,37 +70,6 @@ export declare const RawData: {
|
|
|
70
70
|
building: string;
|
|
71
71
|
buildingLevel: number;
|
|
72
72
|
};
|
|
73
|
-
trainingTime: number;
|
|
74
|
-
regenerationTimes: never[];
|
|
75
|
-
dps: number[];
|
|
76
|
-
upgrade: {
|
|
77
|
-
cost: number[];
|
|
78
|
-
time: number[];
|
|
79
|
-
resource: string;
|
|
80
|
-
resources: never[];
|
|
81
|
-
};
|
|
82
|
-
allowedCharacters: never[];
|
|
83
|
-
minLevel: number;
|
|
84
|
-
seasonal: boolean;
|
|
85
|
-
levels: number[];
|
|
86
|
-
resourceType?: undefined;
|
|
87
|
-
} | {
|
|
88
|
-
tid: string;
|
|
89
|
-
id: number;
|
|
90
|
-
name: string;
|
|
91
|
-
housingSpace: number;
|
|
92
|
-
village: string;
|
|
93
|
-
category: string;
|
|
94
|
-
subCategory: string;
|
|
95
|
-
unlock: {
|
|
96
|
-
hall: number;
|
|
97
|
-
cost: number;
|
|
98
|
-
time: number;
|
|
99
|
-
resource: string;
|
|
100
|
-
building: string;
|
|
101
|
-
buildingLevel: number;
|
|
102
|
-
};
|
|
103
|
-
trainingTime: string;
|
|
104
73
|
regenerationTimes: never[];
|
|
105
74
|
dps: number[];
|
|
106
75
|
upgrade: {
|
|
@@ -114,6 +83,7 @@ export declare const RawData: {
|
|
|
114
83
|
seasonal: boolean;
|
|
115
84
|
levels: number[];
|
|
116
85
|
resourceType?: undefined;
|
|
86
|
+
trainingTime?: undefined;
|
|
117
87
|
} | {
|
|
118
88
|
tid: string;
|
|
119
89
|
id: number;
|
|
@@ -132,7 +102,7 @@ export declare const RawData: {
|
|
|
132
102
|
};
|
|
133
103
|
resourceType: string;
|
|
134
104
|
trainingTime: number;
|
|
135
|
-
regenerationTimes:
|
|
105
|
+
regenerationTimes: null[];
|
|
136
106
|
dps: number[];
|
|
137
107
|
upgrade: {
|
|
138
108
|
cost: number[];
|
package/dist/util/Util.d.ts
CHANGED
|
@@ -65,5 +65,6 @@ export declare class Util extends null {
|
|
|
65
65
|
endTime: Date;
|
|
66
66
|
};
|
|
67
67
|
static allSettled<T>(values: Promise<T>[]): Promise<T[]>;
|
|
68
|
+
static calculateTrophies(stars: number, destruction: number, isAttack: boolean, isLegendLeague: boolean): number;
|
|
68
69
|
static delay(ms: number): Promise<unknown>;
|
|
69
70
|
}
|
package/dist/util/Util.js
CHANGED
|
@@ -226,6 +226,44 @@ class Util extends null {
|
|
|
226
226
|
.filter((res) => res.status === 'fulfilled')
|
|
227
227
|
.map((res) => res.value);
|
|
228
228
|
}
|
|
229
|
+
static calculateTrophies(stars, destruction, isAttack, isLegendLeague) {
|
|
230
|
+
let attackerGain = 0;
|
|
231
|
+
if (stars === 3) {
|
|
232
|
+
// 3 stars always awards the full pool
|
|
233
|
+
attackerGain = 40;
|
|
234
|
+
}
|
|
235
|
+
else if (stars === 2) {
|
|
236
|
+
// 16 base + 1 per 3% over 50%
|
|
237
|
+
attackerGain = 16 + Math.floor((destruction - 50) / 3);
|
|
238
|
+
}
|
|
239
|
+
else if (stars === 1) {
|
|
240
|
+
// 5 base + 1 per 9% destruction
|
|
241
|
+
attackerGain = 5 + Math.floor(destruction / 9);
|
|
242
|
+
}
|
|
243
|
+
else {
|
|
244
|
+
// 0 stars: 1 trophy per 10% destruction (minimum 10% required)
|
|
245
|
+
if (destruction >= 10) {
|
|
246
|
+
attackerGain = Math.floor(destruction / 10);
|
|
247
|
+
}
|
|
248
|
+
}
|
|
249
|
+
// Cap at 40 (standard trophy pool)
|
|
250
|
+
if (attackerGain > 40) {
|
|
251
|
+
attackerGain = 40;
|
|
252
|
+
}
|
|
253
|
+
if (isAttack) {
|
|
254
|
+
return attackerGain;
|
|
255
|
+
}
|
|
256
|
+
// In Legend League, the defender LOSES what the attacker gains
|
|
257
|
+
if (isLegendLeague) {
|
|
258
|
+
return -attackerGain;
|
|
259
|
+
}
|
|
260
|
+
// In Ranked, the defender GAINS the remainder of the 40 pool
|
|
261
|
+
// 0-star defense always gives full 40 to defender
|
|
262
|
+
if (stars === 0) {
|
|
263
|
+
return 40;
|
|
264
|
+
}
|
|
265
|
+
return 40 - attackerGain;
|
|
266
|
+
}
|
|
229
267
|
static async delay(ms) {
|
|
230
268
|
return new Promise((res) => setTimeout(res, ms));
|
|
231
269
|
}
|