Skip to content

Commit

Permalink
Store combat history onchain ⏳
Browse files Browse the repository at this point in the history
  • Loading branch information
Kooshaba committed Jan 31, 2024
1 parent f12ba30 commit 5bdc0ec
Show file tree
Hide file tree
Showing 68 changed files with 2,210 additions and 596 deletions.
1 change: 1 addition & 0 deletions maps/MountainPass.json

Large diffs are not rendered by default.

4 changes: 3 additions & 1 deletion packages/analytics-worker/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,12 @@
"deploy-worker": "pnpm wrangler deploy --config=./wrangler.toml src/index.ts"
},
"dependencies": {
"hono": "^3.7.2"
"hono": "^3.7.2",
"pg": "8.11.3"
},
"devDependencies": {
"@cloudflare/workers-types": "^4.20230914.0",
"@types/pg": "8.10.9",
"wrangler": "^3.9.0"
}
}
148 changes: 38 additions & 110 deletions packages/analytics-worker/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,16 @@
import { Hono } from "hono";
import { Client } from "pg";

// This ensures c.env.DB is correctly typed
type Bindings = {
DB: D1Database;
CLIENT_EVENTS: D1Database;
DB_URL: string;
};

const app = new Hono<{ Bindings: Bindings }>();

app.post("/track-client-event/:chain_id/:world_address", async (c) => {
const client = new Client(c.env.DB_URL);
await client.connect();

const { chain_id, world_address } = c.req.param();
const { event_name, player_address, session_wallet_address, data } = await c.req.json();

Expand All @@ -18,7 +20,7 @@ app.post("/track-client-event/:chain_id/:world_address", async (c) => {
console.log(` data: ${data}`);

try {
await c.env.CLIENT_EVENTS.prepare(
await client.query(
`
INSERT INTO client_events_${chain_id} (
event_name,
Expand All @@ -27,16 +29,14 @@ app.post("/track-client-event/:chain_id/:world_address", async (c) => {
session_wallet_address,
data
) VALUES (
$event_name,
$world_address,
$player_address,
$session_wallet_address,
$data
'${event_name}',
'${world_address}',
'${player_address}',
'${session_wallet_address}',
'${data}'
);
`
)
.bind(event_name, world_address, player_address, session_wallet_address, data)
.run();
);

return c.json({ ok: true, message: `Stored event ${event_name}` });
} catch (e) {
Expand All @@ -46,33 +46,10 @@ app.post("/track-client-event/:chain_id/:world_address", async (c) => {
}
});

app.get(`/client-events/:chain_id/:world_address`, async (c) => {
const { chain_id, world_address } = c.req.param();

try {
const queryParams = c.req.query();
const limit = queryParams["limit"] || 100;
const offset = queryParams["offset"] || 0;

const { results } = await c.env.CLIENT_EVENTS.prepare(
`SELECT
*
FROM client_events_${chain_id}
WHERE world_address = $world_address
ORDER BY id ASC
LIMIT $limit
OFFSET $offset;
`
)
.bind(world_address, limit, offset)
.all();
return c.json(results);
} catch (e) {
return c.json({ err: e }, 500);
}
});

app.post("/track/:chain_id/:world_address", async (c) => {
const client = new Client(c.env.DB_URL);
await client.connect();

const { chain_id, world_address } = c.req.param();
const {
entity,
Expand Down Expand Up @@ -111,9 +88,8 @@ app.post("/track/:chain_id/:world_address", async (c) => {
console.log(` session_wallet_address: ${session_wallet_address}`);

try {
await c.env.DB.prepare(
`
INSERT INTO player_transactions_${chain_id} (
await client.query(
`INSERT INTO player_transactions_${chain_id} (
world_address,
entity,
system_call,
Expand All @@ -132,79 +108,31 @@ app.post("/track/:chain_id/:world_address", async (c) => {
match_entity,
session_wallet_address
) VALUES (
$world_address,
$entity,
$system_call,
$system_id,
$gas_estimate,
$manual_gas_estimate,
$gas_price_gwei,
$status,
$hash,
$error,
$submitted_block,
$completed_block,
$submitted_timestamp,
$completed_timestamp,
$player_address,
$match_entity,
$session_wallet_address
);
`
)
.bind(
world_address,
entity,
system_call,
system_id,
gas_estimate,
manual_gas_estimate === "true" ? "TRUE" : "FALSE",
gas_price_gwei,
status,
hash,
error,
submitted_block,
completed_block,
submitted_timestamp,
completed_timestamp,
player_address,
match_entity,
session_wallet_address
)
.run();
'${world_address}',
'${entity}',
'${system_call}',
'${system_id}',
${gas_estimate},
${manual_gas_estimate === "true" ? "TRUE" : "FALSE"},
${gas_price_gwei},
'${status}',
'${hash}',
'${error}',
${submitted_block},
${completed_block},
${submitted_timestamp},
${completed_timestamp},
'${player_address}',
'${match_entity}',
'${session_wallet_address}'
);`
);

return c.json({ ok: true, message: `Stored tx ${hash}` });
} catch (e) {
return c.json({ err: (e as Error).toString() }, 500);
}
});

// sample post request using curl
// curl -X POST -H "Content-Type: application/json" -d '{"entity":"0x000000","system_call":"charge","gas_estimate":null,"manual_gas_estimate":false,"status":"pending","hash":"0x000001","error":null,"submitted_block": 1,"completed_block": 2,"submitted_timestamp":null,"completed_timestamp":null, "player_address": "0x0004"}' http://localhost:8787/track/1/0x01

app.get("/all/:chain_id", async (c) => {
const { chain_id } = c.req.param();

try {
const { results } = await c.env.DB.prepare(`SELECT * FROM player_transactions_${chain_id};`).all();
return c.json(results);
} catch (e) {
return c.json({ err: e }, 500);
}
});
console.log(e);

app.get("/all/:chain_id/:world_address", async (c) => {
const { chain_id, world_address } = c.req.param();

try {
const { results } = await c.env.DB.prepare(
`SELECT * FROM player_transactions_${chain_id} WHERE world_address = $world_address;`
)
.bind(world_address)
.all();
return c.json(results);
} catch (e) {
return c.json({ err: e }, 500);
return c.json({ err: (e as Error).toString() }, 500);
}
});

Expand Down
6 changes: 3 additions & 3 deletions packages/analytics/src/systems/createUnitKillSystem.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,15 +14,15 @@ export function createUnitKillSystem(layer: AnalyticsLayer) {
const {
world,
networkLayer: {
components: { CombatResult, Match, Position, UnitType, StructureType },
components: { CombatOutcome, Match, Position, UnitType, StructureType },
},
clock,
utils: { getCurrentBlockNumber, storePlayerTotalUnitSnapshot, storePlayerTotalStructureSnapshot, getTurnAtTime },
components: { UnitKill, UnitDeath, StructureCapture, StructureKill, PreviousOwner },
} = layer;

defineSystem(world, [Has(CombatResult)], ({ entity }) => {
const combatResult = getComponentValueStrict(CombatResult, entity);
defineSystem(world, [Has(CombatOutcome)], ({ entity }) => {
const combatResult = getComponentValueStrict(CombatOutcome, entity);
const { attacker: _attacker, defender: _defender, attackerDied, defenderDied, defenderCaptured } = combatResult;

const attacker = _attacker as Entity;
Expand Down
101 changes: 43 additions & 58 deletions packages/art/tiled/maps/MountainPass.tmx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<map version="1.9" tiledversion="1.9.0" orientation="orthogonal" renderorder="right-down" width="18" height="18" tilewidth="16" tileheight="16" infinite="0" nextlayerid="34" nextobjectid="102">
<map version="1.9" tiledversion="1.9.0" orientation="orthogonal" renderorder="right-down" width="22" height="13" tilewidth="16" tileheight="16" infinite="0" nextlayerid="34" nextobjectid="102">
<editorsettings>
<export format="MUD Templates"/>
</editorsettings>
Expand All @@ -8,84 +8,69 @@
<properties>
<property name="entityLayer" type="bool" value="true"/>
</properties>
<layer id="2" name="Tiles" width="18" height="18">
<layer id="2" name="Tiles" width="22" height="13">
<properties>
<property name="prototypeLayer" type="bool" value="true"/>
</properties>
<data encoding="csv">
0,0,0,0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,
0,1,1,1,1,1,0,3,1,1,3,0,2147483649,2147483649,2147483649,2147483649,2147483649,0,
0,1,1,3,1,1,1,0,1,1,0,2147483649,2147483649,2147483649,2147483651,2147483649,2147483649,0,
0,1,3,2,1,2,1,0,2,1,0,2147483649,2147483650,2147483649,2147483650,2147483651,2147483649,0,
0,1,1,1,1,2,1,0,1,2,0,2147483649,2147483650,2147483649,2147483649,2147483649,2147483649,0,
0,1,1,2,2,1,2,0,3,3,0,2147483650,2147483649,2147483650,2147483650,2147483649,2147483649,0,
0,0,1,1,1,2,3,1,1,1,1,2147483651,2147483650,2147483649,2147483649,2147483649,0,0,
1610612737,1610612739,0,0,0,0,1,1,2,2,1,1,0,0,0,0,2684354563,2684354561,
1610612737,1610612737,1610612737,1610612737,1610612738,1610612739,1,2,1,1,2,1,2684354563,2684354561,2684354562,2684354561,2684354561,2684354561,
1610612737,1610612737,1610612737,1610612738,1610612737,1610612739,1,2,1,1,2,1,2684354563,2684354562,2684354561,2684354561,2684354561,2684354561,
1610612737,1610612739,0,0,0,0,1,1,2,2,1,1,0,0,0,0,2684354563,2684354561,
0,0,1073741825,1073741825,1073741825,1073741826,1073741827,1,1,1,1,3221225475,3221225474,3221225473,3221225473,3221225473,0,0,
0,1073741825,1073741825,1073741826,1073741826,1073741825,1073741826,0,3221225475,3221225475,0,3221225474,3221225473,3221225474,3221225474,3221225473,3221225473,0,
0,1073741825,1073741825,1073741825,1073741825,1073741826,1073741825,0,3221225474,3221225473,0,3221225473,3221225474,3221225473,3221225473,3221225473,3221225473,0,
0,1073741825,1073741827,1073741826,1073741825,1073741826,1073741825,0,3221225473,3221225474,0,3221225473,3221225474,3221225473,3221225474,3221225475,3221225473,0,
0,1073741825,1073741825,1073741827,1073741825,1073741825,1073741825,0,3221225473,3221225473,0,3221225473,3221225473,3221225473,3221225475,3221225473,3221225473,0,
0,1073741825,1073741825,1073741825,1073741825,1073741825,0,3221225475,3221225473,3221225473,3221225475,0,3221225473,3221225473,3221225473,3221225473,3221225473,0,
0,0,0,0,0,0,0,3221225473,3221225473,3221225473,3221225473,0,0,0,0,0,0,0
1073741825,2,1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1,1,1,1,3,1,3,1,1,1,1,1,1,1,
1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1073741825,1,1,1,1,2,3,1,1,1,1,1,1,1,1,
1073741827,1073741826,1073741827,1073741827,1073741827,1073741826,2,3,2,3,1,3,2,1,3,1,1,1,1,1,1,1,
1073741826,1073741826,1073741826,1073741826,1073741827,1,1,1,1,2,1,2,2,1,3,1,1,2,1,1,1,1,
2,3,3,2,1,2,2,3,2,3,2,3,2,1,2,1,1,1,1,1,1,1,
2,2,2,2,3,1,1,1,1,2,1,2,2,1,3,1,1,2,1,1,1,1,
3,2,3,3,3,2,2,3,2,3,1,3,2,1,3,1,1,1,1,1,1,1,
1,1,1,1,1,1,1,1,1,1,1,1,2,3,1,1,1,1,1,1,1,1,
1,1,1,1,1,1,1,1,1,1,1,1,3,1,3,1,1,1,1,1,1,1,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1,2,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1
</data>
</layer>
</group>
<group id="15" name="Objects">
<properties>
<property name="entityLayer" type="bool" value="true"/>
</properties>
<layer id="10" name="Objects" width="18" height="18">
<layer id="10" name="Objects" width="22" height="13">
<properties>
<property name="prototypeLayer" type="bool" value="true"/>
</properties>
<data encoding="csv">
0,0,0,0,0,0,0,0,14,9,0,0,0,0,0,0,0,0,
0,0,0,0,0,14,0,0,0,0,0,0,2147483662,0,0,0,0,0,
0,0,10,0,0,0,0,0,0,0,0,0,0,0,0,2147483658,0,0,
0,0,0,0,0,0,0,0,0,14,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,14,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2147483662,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
1610612745,0,0,1610612750,0,0,0,0,0,14,0,0,0,0,0,0,0,2684354574,
1610612750,0,0,0,0,0,0,0,14,0,0,0,0,0,2684354574,0,0,2684354569,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,1073741838,0,0,0,0,0,0,0,0,0,0,0,0,0,0,3221225486,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,3221225486,0,0,0,0,0,0,0,0,0,
0,0,1073741834,0,0,0,0,0,0,0,0,0,0,0,0,3221225482,0,0,
0,0,0,0,0,1073741838,0,0,0,0,0,0,3221225486,0,0,0,0,0,
0,0,0,0,0,0,0,0,3221225481,3221225486,0,0,0,0,0,0,0,0
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,14,0,0,14,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,10,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,14,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,14,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,14,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,14,0,
0,0,0,14,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,10,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,14,0,0,14,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
</data>
</layer>
<layer id="33" name="Metadata" width="18" height="18">
<layer id="33" name="Metadata" width="22" height="13">
<properties>
<property name="prototypeLayer" type="bool" value="true"/>
</properties>
<data encoding="csv">
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,20,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
</data>
</layer>
</group>
Expand Down
Loading

0 comments on commit 5bdc0ec

Please sign in to comment.