@conquest-eth/tools 0.0.0

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.
Files changed (143) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +259 -0
  3. package/dist/cli-tool-generator.d.ts +22 -0
  4. package/dist/cli-tool-generator.d.ts.map +1 -0
  5. package/dist/cli-tool-generator.js +217 -0
  6. package/dist/cli-tool-generator.js.map +1 -0
  7. package/dist/cli.d.ts +3 -0
  8. package/dist/cli.d.ts.map +1 -0
  9. package/dist/cli.js +76 -0
  10. package/dist/cli.js.map +1 -0
  11. package/dist/contracts/space-info.d.ts +7 -0
  12. package/dist/contracts/space-info.d.ts.map +1 -0
  13. package/dist/contracts/space-info.js +34 -0
  14. package/dist/contracts/space-info.js.map +1 -0
  15. package/dist/fleet/index.d.ts +4 -0
  16. package/dist/fleet/index.d.ts.map +1 -0
  17. package/dist/fleet/index.js +7 -0
  18. package/dist/fleet/index.js.map +1 -0
  19. package/dist/fleet/manager.d.ts +70 -0
  20. package/dist/fleet/manager.d.ts.map +1 -0
  21. package/dist/fleet/manager.js +92 -0
  22. package/dist/fleet/manager.js.map +1 -0
  23. package/dist/fleet/resolve.d.ts +51 -0
  24. package/dist/fleet/resolve.d.ts.map +1 -0
  25. package/dist/fleet/resolve.js +140 -0
  26. package/dist/fleet/resolve.js.map +1 -0
  27. package/dist/fleet/send.d.ts +29 -0
  28. package/dist/fleet/send.d.ts.map +1 -0
  29. package/dist/fleet/send.js +81 -0
  30. package/dist/fleet/send.js.map +1 -0
  31. package/dist/helpers/index.d.ts +14 -0
  32. package/dist/helpers/index.d.ts.map +1 -0
  33. package/dist/helpers/index.js +28 -0
  34. package/dist/helpers/index.js.map +1 -0
  35. package/dist/index.d.ts +36 -0
  36. package/dist/index.d.ts.map +1 -0
  37. package/dist/index.js +143 -0
  38. package/dist/index.js.map +1 -0
  39. package/dist/planet/acquire.d.ts +16 -0
  40. package/dist/planet/acquire.d.ts.map +1 -0
  41. package/dist/planet/acquire.js +27 -0
  42. package/dist/planet/acquire.js.map +1 -0
  43. package/dist/planet/exit.d.ts +17 -0
  44. package/dist/planet/exit.d.ts.map +1 -0
  45. package/dist/planet/exit.js +56 -0
  46. package/dist/planet/exit.js.map +1 -0
  47. package/dist/planet/index.d.ts +4 -0
  48. package/dist/planet/index.d.ts.map +1 -0
  49. package/dist/planet/index.js +6 -0
  50. package/dist/planet/index.js.map +1 -0
  51. package/dist/planet/manager.d.ts +106 -0
  52. package/dist/planet/manager.d.ts.map +1 -0
  53. package/dist/planet/manager.js +253 -0
  54. package/dist/planet/manager.js.map +1 -0
  55. package/dist/storage/interface.d.ts +93 -0
  56. package/dist/storage/interface.d.ts.map +1 -0
  57. package/dist/storage/interface.js +2 -0
  58. package/dist/storage/interface.js.map +1 -0
  59. package/dist/storage/json-storage.d.ts +28 -0
  60. package/dist/storage/json-storage.d.ts.map +1 -0
  61. package/dist/storage/json-storage.js +148 -0
  62. package/dist/storage/json-storage.js.map +1 -0
  63. package/dist/tools/acquire_planets.d.ts +7 -0
  64. package/dist/tools/acquire_planets.d.ts.map +1 -0
  65. package/dist/tools/acquire_planets.js +63 -0
  66. package/dist/tools/acquire_planets.js.map +1 -0
  67. package/dist/tools/exit_planets.d.ts +5 -0
  68. package/dist/tools/exit_planets.d.ts.map +1 -0
  69. package/dist/tools/exit_planets.js +31 -0
  70. package/dist/tools/exit_planets.js.map +1 -0
  71. package/dist/tools/get_my_planets.d.ts +5 -0
  72. package/dist/tools/get_my_planets.d.ts.map +1 -0
  73. package/dist/tools/get_my_planets.js +30 -0
  74. package/dist/tools/get_my_planets.js.map +1 -0
  75. package/dist/tools/get_pending_exits.d.ts +3 -0
  76. package/dist/tools/get_pending_exits.d.ts.map +1 -0
  77. package/dist/tools/get_pending_exits.js +37 -0
  78. package/dist/tools/get_pending_exits.js.map +1 -0
  79. package/dist/tools/get_pending_fleets.d.ts +3 -0
  80. package/dist/tools/get_pending_fleets.d.ts.map +1 -0
  81. package/dist/tools/get_pending_fleets.js +41 -0
  82. package/dist/tools/get_pending_fleets.js.map +1 -0
  83. package/dist/tools/get_planets_around.d.ts +7 -0
  84. package/dist/tools/get_planets_around.d.ts.map +1 -0
  85. package/dist/tools/get_planets_around.js +41 -0
  86. package/dist/tools/get_planets_around.js.map +1 -0
  87. package/dist/tools/index.d.ts +10 -0
  88. package/dist/tools/index.d.ts.map +1 -0
  89. package/dist/tools/index.js +11 -0
  90. package/dist/tools/index.js.map +1 -0
  91. package/dist/tools/resolve_fleet.d.ts +5 -0
  92. package/dist/tools/resolve_fleet.d.ts.map +1 -0
  93. package/dist/tools/resolve_fleet.js +37 -0
  94. package/dist/tools/resolve_fleet.js.map +1 -0
  95. package/dist/tools/send_fleet.d.ts +16 -0
  96. package/dist/tools/send_fleet.d.ts.map +1 -0
  97. package/dist/tools/send_fleet.js +62 -0
  98. package/dist/tools/send_fleet.js.map +1 -0
  99. package/dist/tools/verify_exit_status.d.ts +5 -0
  100. package/dist/tools/verify_exit_status.d.ts.map +1 -0
  101. package/dist/tools/verify_exit_status.js +39 -0
  102. package/dist/tools/verify_exit_status.js.map +1 -0
  103. package/dist/types.d.ts +126 -0
  104. package/dist/types.d.ts.map +1 -0
  105. package/dist/types.js +34 -0
  106. package/dist/types.js.map +1 -0
  107. package/dist/util/hashing.d.ts +33 -0
  108. package/dist/util/hashing.d.ts.map +1 -0
  109. package/dist/util/hashing.js +38 -0
  110. package/dist/util/hashing.js.map +1 -0
  111. package/dist/util/time.d.ts +43 -0
  112. package/dist/util/time.d.ts.map +1 -0
  113. package/dist/util/time.js +55 -0
  114. package/dist/util/time.js.map +1 -0
  115. package/package.json +78 -0
  116. package/src/cli-tool-generator.ts +287 -0
  117. package/src/cli.ts +109 -0
  118. package/src/contracts/space-info.ts +41 -0
  119. package/src/fleet/index.ts +8 -0
  120. package/src/fleet/manager.ts +140 -0
  121. package/src/fleet/resolve.ts +187 -0
  122. package/src/fleet/send.ts +112 -0
  123. package/src/helpers/index.ts +59 -0
  124. package/src/index.ts +181 -0
  125. package/src/planet/acquire.ts +41 -0
  126. package/src/planet/exit.ts +71 -0
  127. package/src/planet/index.ts +6 -0
  128. package/src/planet/manager.ts +335 -0
  129. package/src/storage/interface.ts +111 -0
  130. package/src/storage/json-storage.ts +184 -0
  131. package/src/tools/acquire_planets.ts +81 -0
  132. package/src/tools/exit_planets.ts +35 -0
  133. package/src/tools/get_my_planets.ts +30 -0
  134. package/src/tools/get_pending_exits.ts +37 -0
  135. package/src/tools/get_pending_fleets.ts +41 -0
  136. package/src/tools/get_planets_around.ts +44 -0
  137. package/src/tools/index.ts +10 -0
  138. package/src/tools/resolve_fleet.ts +37 -0
  139. package/src/tools/send_fleet.ts +68 -0
  140. package/src/tools/verify_exit_status.ts +43 -0
  141. package/src/types.ts +178 -0
  142. package/src/util/hashing.ts +60 -0
  143. package/src/util/time.ts +66 -0
@@ -0,0 +1,43 @@
1
+ import {z} from 'zod';
2
+ import {createTool} from '../types.js';
3
+
4
+ export const verify_exit_status = createTool({
5
+ description:
6
+ "Check and update the status of a planet's exit operation. Verifies if the exit has completed or been interrupted.",
7
+ schema: z.object({
8
+ planetId: z
9
+ .union([z.string(), z.number()])
10
+ .describe('Planet location ID to verify (as hex string or number)'),
11
+ }),
12
+ execute: async (env, {planetId}) => {
13
+ try {
14
+ const result = await env.planetManager.verifyExitStatus(
15
+ typeof planetId === 'string' ? BigInt(planetId) : BigInt(planetId),
16
+ );
17
+
18
+ // Calculate status based on exit state
19
+ const currentTime = Math.floor(Date.now() / 1000);
20
+ const completed = currentTime >= result.exit.exitCompleteTime;
21
+ const status = result.interrupted ? 'interrupted' : completed ? 'completed' : 'in_progress';
22
+ const owner = result.newOwner || result.exit.player;
23
+
24
+ return {
25
+ success: true,
26
+ result: {
27
+ planetId: result.exit.planetId,
28
+ status,
29
+ completed,
30
+ interrupted: result.interrupted,
31
+ owner,
32
+ exitStartTime: result.exit.exitStartTime,
33
+ exitCompleteTime: result.exit.exitCompleteTime,
34
+ },
35
+ };
36
+ } catch (error) {
37
+ return {
38
+ success: false,
39
+ error: error instanceof Error ? error.message : String(error),
40
+ };
41
+ }
42
+ },
43
+ });
package/src/types.ts ADDED
@@ -0,0 +1,178 @@
1
+ import type {Address, PublicClient, WalletClient} from 'viem';
2
+ import type {PlanetInfo} from 'conquest-eth-v0-contracts';
3
+ import type {Abi_IOuterSpace} from 'conquest-eth-v0-contracts/abis/IOuterSpace.js';
4
+ import type {CallToolResult} from '@modelcontextprotocol/sdk/types.js';
5
+ import {z} from 'zod';
6
+ import type {FleetManager} from './fleet/manager.js';
7
+ import type {PlanetManager} from './planet/manager.js';
8
+
9
+ export interface StorageConfig {
10
+ type: 'json' | 'sqlite';
11
+ dataDir?: string; // Default: `${cwd}/data`
12
+ }
13
+
14
+ export type GameContract = {
15
+ address: Address;
16
+ abi: Abi_IOuterSpace;
17
+ };
18
+
19
+ export type ClientsWithOptionalWallet = {
20
+ walletClient?: WalletClient;
21
+ publicClient: PublicClient;
22
+ };
23
+
24
+ export type Clients = {
25
+ walletClient: WalletClient;
26
+ publicClient: PublicClient;
27
+ };
28
+
29
+ export interface ContractConfig {
30
+ genesis: bigint;
31
+ resolveWindow: bigint;
32
+ timePerDistance: bigint;
33
+ exitDuration: bigint;
34
+ acquireNumSpaceships: number;
35
+ [key: string]: bigint | number;
36
+ }
37
+
38
+ export interface ExternalPlanet {
39
+ owner?: `0x${string}`;
40
+ ownerYakuzaSubscriptionEndTime: number;
41
+ lastUpdatedSaved: number;
42
+ startExitTime: number;
43
+ numSpaceships: number;
44
+ flagTime: number;
45
+ travelingUpkeep: number;
46
+ overflow: number;
47
+ active: boolean;
48
+ exiting: boolean;
49
+ exitTimeLeft: number;
50
+ natives: boolean;
51
+ capturing: boolean;
52
+ inReach: boolean;
53
+ rewardGiver: `0x${string}`;
54
+ requireClaimAcknowledgement?: string;
55
+ metadata: Record<string, string | number | boolean>;
56
+ }
57
+
58
+ export interface PendingExit {
59
+ planetId: bigint; // Planet location ID
60
+ player: string; // Player who initiated the exit
61
+ exitStartTime: number; // Timestamp when exit was initiated
62
+ exitDuration: number; // Duration of exit process (typically 7 days)
63
+ exitCompleteTime: number; // When exit will complete
64
+ numSpaceships: number; // Spaceships on planet at exit start
65
+ owner: string; // Current owner (may change due to attacks)
66
+ completed: boolean; // Whether exit has completed
67
+ interrupted: boolean; // Whether exit was interrupted by attack
68
+ lastCheckedAt: number; // Last time status was verified against contract
69
+ }
70
+
71
+ export interface PlanetWithDistance {
72
+ info: PlanetInfo;
73
+ state?: ExternalPlanet;
74
+ distance: number;
75
+ hasPendingExit?: boolean;
76
+ exitInfo?: {
77
+ exitStartTime: number;
78
+ exitCompleteTime: number;
79
+ timeUntilComplete: number;
80
+ };
81
+ }
82
+
83
+ export interface PendingFleet {
84
+ hash?: `0x${string}`; // Hash of the fleet (toHash)
85
+ fleetId: string; // Computed from toHash, from, fleetSender, operator
86
+ fromPlanetId: bigint; // Source planet location
87
+ toPlanetId: bigint; // Destination planet location (hidden during commit)
88
+ quantity: number; // Number of spaceships
89
+ secret: `0x${string}`; // Random secret for hash commitment
90
+ gift: boolean; // Whether this is a gift (no combat)
91
+ specific: `0x${string}`; // Specific target address (advanced feature)
92
+ arrivalTimeWanted: bigint; // Preferred arrival time (advanced feature)
93
+ fleetSender: `0x${string}`; // Address that sent the fleet
94
+ operator: `0x${string}`; // Address that committed the transaction
95
+ committedAt: number; // Timestamp of commit transaction
96
+ estimatedArrivalTime: number; // Estimated arrival time
97
+ resolved: boolean; // Whether fleet has been revealed/resolved
98
+ resolvedAt?: number; // Timestamp of resolution
99
+ }
100
+
101
+ export interface FleetResolution {
102
+ from: bigint; // Source planet location
103
+ to: bigint; // Destination planet location
104
+ distance: bigint; // Distance between planets
105
+ arrivalTimeWanted: bigint; // Preferred arrival time
106
+ gift: boolean; // Whether this is a gift
107
+ specific: `0x${string}`; // Specific target address
108
+ secret: `0x${string}`; // The secret used to generate the hash
109
+ fleetSender: `0x${string}`; // Address that sent the fleet
110
+ operator: `0x${string}`; // Address that committed the transaction
111
+ }
112
+
113
+ // Tool types for MCP server refactoring
114
+ export type ToolEnvironment = {
115
+ // Function to send status updates during tool execution (required)
116
+ sendStatus: (message: string) => Promise<void>;
117
+ // Fleet manager for fleet operations
118
+ fleetManager: FleetManager;
119
+ // Planet manager for planet operations
120
+ planetManager: PlanetManager;
121
+ };
122
+
123
+ // Result returned by tool execute functions
124
+ export type ToolResult =
125
+ | {success: true; result: Record<string, any>}
126
+ | {success: false; error: string; stack?: string};
127
+
128
+ // Tool definition with execute, schema, and description
129
+ export type Tool<S extends z.ZodObject<any> = z.ZodObject<any>> = {
130
+ description: string;
131
+ schema: S;
132
+ execute: (env: ToolEnvironment, params: z.infer<S>) => Promise<ToolResult>;
133
+ };
134
+
135
+ // Helper function to create a tool with automatic type inference
136
+ export function createTool<S extends z.ZodObject<any>>(config: {
137
+ description: string;
138
+ schema: S;
139
+ execute: (env: ToolEnvironment, params: z.infer<S>) => Promise<ToolResult>;
140
+ }): Tool<S> {
141
+ return config;
142
+ }
143
+
144
+ // Convert ToolResult to CallToolResult format
145
+ export function convertToCallToolResult(result: ToolResult): CallToolResult {
146
+ // Import stringifyWithBigInt to handle BigInt serialization
147
+ const stringifyWithBigInt = (obj: any, space?: number): string => {
148
+ return JSON.stringify(
149
+ obj,
150
+ (_key, value) => (typeof value === 'bigint' ? value.toString() : value),
151
+ space,
152
+ );
153
+ };
154
+
155
+ if (result.success === false) {
156
+ return {
157
+ content: [
158
+ {
159
+ type: 'text' as const,
160
+ text: stringifyWithBigInt({
161
+ error: result.error,
162
+ ...(result.stack ? {stack: result.stack} : {}),
163
+ }),
164
+ },
165
+ ],
166
+ isError: true,
167
+ };
168
+ }
169
+
170
+ return {
171
+ content: [
172
+ {
173
+ type: 'text' as const,
174
+ text: stringifyWithBigInt(result.result, 2),
175
+ },
176
+ ],
177
+ };
178
+ }
@@ -0,0 +1,60 @@
1
+ import type {Address} from 'viem';
2
+ import {encodeAbiParameters, encodePacked, keccak256, zeroAddress} from 'viem';
3
+
4
+ /**
5
+ * Compute the toHash used in fleet commit phase
6
+ * This hashes the destination planet and secret together
7
+ *
8
+ * @param toPlanetId - The destination planet location ID
9
+ * @param secret - The secret value to commit to
10
+ * @returns The hash commitment (keccak256 hash)
11
+ */
12
+ export function computeToHash(
13
+ toPlanetId: bigint,
14
+ secret: `0x${string}`,
15
+ options: {gift: boolean; specific: Address; arrivalTimeWanted: bigint},
16
+ ): `0x${string}` {
17
+ const toHash = keccak256(
18
+ encodePacked(
19
+ ['bytes32', 'uint256', 'bool', 'address', 'uint256'],
20
+ [secret, toPlanetId, options.gift, options.specific, options.arrivalTimeWanted],
21
+ ),
22
+ );
23
+ return toHash;
24
+ }
25
+
26
+ /**
27
+ * Compute the fleet ID from send transaction parameters
28
+ * The fleet ID is computed from: toHash, from, fleetSender, operator
29
+ * This matches what the contract emits in the FleetSent event
30
+ *
31
+ * @param toHash - The hash commitment to destination and secret
32
+ * @param fromPlanetId - The source planet location ID
33
+ * @param fleetSender - The address that owns the fleet
34
+ * @param operator - The address that committed the transaction
35
+ * @returns The fleet ID (keccak256 hash)
36
+ */
37
+ export function computeFleetId(
38
+ toHash: `0x${string}`,
39
+ fromPlanetId: bigint,
40
+ fleetSender: Address,
41
+ operator: Address,
42
+ ): `0x${string}` {
43
+ return keccak256(
44
+ encodePacked(
45
+ ['bytes32', 'uint256', 'address', 'address'],
46
+ [toHash, BigInt(fromPlanetId), fleetSender, operator],
47
+ ),
48
+ );
49
+ }
50
+
51
+ /**
52
+ * Generate a random secret for fleet commitment
53
+ *
54
+ * @returns A cryptographically random 32-byte hex string
55
+ */
56
+ export function generateSecret(): `0x${string}` {
57
+ const randomBytes = new Uint8Array(32);
58
+ crypto.getRandomValues(randomBytes);
59
+ return `0x${Buffer.from(randomBytes).toString('hex')}`;
60
+ }
@@ -0,0 +1,66 @@
1
+ /**
2
+ * Get current timestamp in seconds
3
+ */
4
+ export function getCurrentTimestamp(): number {
5
+ return Math.floor(Date.now() / 1000);
6
+ }
7
+
8
+ /**
9
+ * Calculate estimated arrival time based on distance and timePerDistance
10
+ *
11
+ * @param distance - The distance between planets
12
+ * @param timePerDistance - Time multiplier from contract config (seconds per distance unit)
13
+ * @param genesis - Genesis timestamp from contract config
14
+ * @returns Estimated arrival time in seconds
15
+ */
16
+ export function calculateEstimatedArrivalTime(params: {
17
+ startTime: bigint;
18
+ distance: bigint;
19
+ timePerDistance: bigint;
20
+ }): number {
21
+ const {startTime, distance, timePerDistance} = params;
22
+ const travelTime = Number(distance) * Number(timePerDistance);
23
+ return Number(startTime) + travelTime;
24
+ }
25
+
26
+ /**
27
+ * Calculate when the resolve window opens
28
+ * A fleet can be resolved after it arrives and the resolve window has passed
29
+ *
30
+ * @param estimatedArrivalTime - When the fleet is estimated to arrive
31
+ * @param resolveWindow - The resolve window duration in seconds from contract config
32
+ * @returns The timestamp when the fleet can be resolved
33
+ */
34
+ export function calculateResolveWindowOpen(
35
+ estimatedArrivalTime: number,
36
+ resolveWindow: bigint,
37
+ ): number {
38
+ return estimatedArrivalTime + Number(resolveWindow);
39
+ }
40
+
41
+ /**
42
+ * Check if a fleet can be resolved now
43
+ *
44
+ * @param estimatedArrivalTime - When the fleet was estimated to arrive
45
+ * @param resolveWindow - The resolve window duration in seconds
46
+ * @returns True if the fleet can be resolved now
47
+ */
48
+ export function canResolveNow(estimatedArrivalTime: number, resolveWindow: bigint): boolean {
49
+ const currentTime = getCurrentTimestamp();
50
+ const resolveWindowOpen = calculateResolveWindowOpen(estimatedArrivalTime, resolveWindow);
51
+ return currentTime >= resolveWindowOpen;
52
+ }
53
+
54
+ /**
55
+ * Format timestamp as ISO string
56
+ */
57
+ export function formatTimestamp(timestamp: number): string {
58
+ return new Date(timestamp * 1000).toISOString();
59
+ }
60
+
61
+ /**
62
+ * Parse ISO string to timestamp
63
+ */
64
+ export function parseTimestamp(isoString: string): number {
65
+ return Math.floor(new Date(isoString).getTime() / 1000);
66
+ }