Skip to content

Commit

Permalink
feat/claim-airdrop(CCS-101)
Browse files Browse the repository at this point in the history
Signed-off-by: Mateusz Marcinkowski <mateusz.marcinkowski@arianelabs.com>
  • Loading branch information
mateuszm-arianelabs committed Jan 31, 2025
1 parent 1d9fce6 commit 0935695
Show file tree
Hide file tree
Showing 6 changed files with 209 additions and 0 deletions.
117 changes: 117 additions & 0 deletions packages/plugin-hedera/src/actions/claim-airdrop/claim-airdrop.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
import {
Action,
composeContext,
elizaLogger,
generateObjectDeprecated,
HandlerCallback,
IAgentRuntime,
Memory,
ModelClass,
State,
} from "@elizaos/core";
import { HederaProvider } from "../../providers/client";
import { claimAirdropTemplate } from "../../templates";
import { claimAirdropParamsSchema } from "./schema.ts";
import { ClaimAirdropService } from "./services/claim-airdrop-service.ts";

export const claimAirdropAction: Action = {
name: "HEDERA_CLAIM_AIRDROP",
description: "Claim available pending token airdrop",
handler: async (
runtime: IAgentRuntime,
_message: Memory,
state: State,
_options: { [key: string]: unknown },
_callback?: HandlerCallback
) => {
console.log("invoke");

const claimAirdropContext = composeContext({
state: state,
template: claimAirdropTemplate,
templatingEngine: "handlebars",
});

console.log("test");

const claimAirdropContent = await generateObjectDeprecated({
runtime: runtime,
context: claimAirdropContext,
modelClass: ModelClass.SMALL,
});

try {
console.log(claimAirdropContent);

const claimAirdropData =
claimAirdropParamsSchema.parse(claimAirdropContent);

console.log(claimAirdropData);

const accountId = runtime.getSetting("HEDERA_ACCOUNT_ID");

const hederaProvider = new HederaProvider(runtime);
const action = new ClaimAirdropService(hederaProvider);

await action.execute(claimAirdropData, accountId);

await _callback({
text: `Successfully claimed airdrop for token ${claimAirdropData.tokenId}`,
});

return true;
} catch (error) {
elizaLogger.error("Error during claiming airdrop:", error);

if (_callback) {
await _callback({
text: `Error during claiming airdrop: ${error.message}`,
content: { error: error.message },
});
}
return false;
}
},
validate: async (runtime: IAgentRuntime) => {
const privateKey = runtime.getSetting("HEDERA_PRIVATE_KEY");
const accountAddress = runtime.getSetting("HEDERA_ACCOUNT_ID");
const selectedNetworkType = runtime.getSetting("HEDERA_NETWORK_TYPE");

return !!(privateKey && accountAddress && selectedNetworkType);
},
examples: [
[
{
user: "{{user1}}",
content: {
text: "Claim airdrop (1) 5 Tokens ({{0.0.5445766}}) from {{0.0.5393076}}",
action: "HEDERA_CLAIM_AIRDROP",
},
},
{
user: "{{user2}}",
content: {
text: "",
action: "HEDERA_CLAIM_AIRDROP",
},
},
],
[
{
user: "{{user1}}",
content: {
text: "Claim airdrop (2) 50 Tokens ({{0.0.5447843}}) from {{0.0.5393076}}",
action: "HEDERA_CLAIM_AIRDROP",
},
},
{
user: "{{user2}}",
content: {
text: "",
action: "HEDERA_CLAIM_AIRDROP",
},
},
],
],
similes: ["CLAIM_AIRDROP", "CLAIM_TOKEN_AIRDROP", "CLAIM_TOKEN"],
};
6 changes: 6 additions & 0 deletions packages/plugin-hedera/src/actions/claim-airdrop/schema.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import { z } from "zod";

export const claimAirdropParamsSchema = z.object({
senderId: z.string(),
tokenId: z.string(),
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import { HederaProvider } from "../../../providers/client";
import { AccountId, PendingAirdropId, TokenId } from "@hashgraph/sdk";
import { ClaimAirdropData } from "../types.ts";

export class ClaimAirdropService {
constructor(private hederaProvider: HederaProvider) {}

async execute(params: ClaimAirdropData, accountId: string): Promise<void> {
if (!params.tokenId) {
throw new Error("No tokenId provided");
}

if (!params.senderId) {
throw new Error("No senderId provided");
}

if (!accountId) {
throw new Error("No accountId provided");
}

const tokenId = TokenId.fromString(params.tokenId);
const senderId = AccountId.fromString(params.senderId);
const receiverId = AccountId.fromString(accountId);

const pendingAirdrop = new PendingAirdropId({
senderId,
tokenId,
receiverId,
});

const agentKit = this.hederaProvider.getHederaAgentKit();

return agentKit.claimAirdrop(pendingAirdrop);
}
}
4 changes: 4 additions & 0 deletions packages/plugin-hedera/src/actions/claim-airdrop/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
import { claimAirdropParamsSchema } from "./schema.ts";
import { z } from "zod";

export type ClaimAirdropData = z.infer<typeof claimAirdropParamsSchema>;
2 changes: 2 additions & 0 deletions packages/plugin-hedera/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { tokenHoldersAction } from "./actions/token-holders/token-holders.ts";
import { airdropTokenAction } from "./actions/airdrop-token/airdrop-token.ts";
import { rejectTokenAction } from "./actions/reject-token/reject-token.ts";
import { pendingAirdropsAction } from "./actions/pending-airdrops/pending-airdrops.ts";
import { claimAirdropAction } from "./actions/claim-airdrop/claim-airdrop.ts";

export const hederaPlugin: Plugin = {
name: "Hedera",
Expand All @@ -28,6 +29,7 @@ export const hederaPlugin: Plugin = {
airdropTokenAction,
rejectTokenAction,
pendingAirdropsAction,
claimAirdropAction,
],
};

Expand Down
45 changes: 45 additions & 0 deletions packages/plugin-hedera/src/templates/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -164,3 +164,48 @@ Example response for the input: "Show me airdrops for 0.0.5422268", the response
Now respond with a JSON markdown block containing only the extracted values.
`;

export const claimAirdropTemplate = `Given the recent messages and wallet information below:
{{recentMessages}}
{{walletInfo}}
Extract data of pending token airdrop from message with following instructions.
1. **Sender Id**
- Sender Id should looks like "0.0.5422268" and should be string.
- Sender Id as string cant have other chars than numbers 0 to 9 and dots.
- Dots cant start accountId string or end, there is always number on start and end.
- Example sender ids are "0.0.5422268", "0.0.4515756"
3. **Token Id**
- Token Id should looks like "0.0.5422268" and should be string.
- Token Id as string cant have other chars than numbers 0 to 9 and dots.
- Dots cant start accountId string or end, there is always number on start and end.
- Example token ids are "0.0.5447843", "0.0.4515756"
Respond with a JSON markdown block containing only the extracted values:
\`\`\`json
{
"senderId": string, // The senderId for example "0.0.4515756"
"tokenId": string // The tokenId for example "0.0.4515756"
}
\`\`\`
The message commonly have structure like "Claim airdrop (1) 5 Tokens (TOKEN_ID) from SENDER_ID" where TOKEN_ID and SENDER_ID are variables to extract.
Example response for the input: "Claim airdrop (1) 5 Tokens (0.0.5445766) from 0.0.5393076", the response should be:
\`\`\`json
{
"senderId": "0.0.5393076",
"tokenId": "0.0.5445766"
}
\`\`\`
Example response for the input: "Claim airdrop (2) 50 Tokens (0.0.5447843) from 0.0.5393076", the response should be:
\`\`\`json
{
"senderId": "0.0.5393076",
"tokenId": "0.0.5447843"
}
\`\`\`
Now respond with a JSON markdown block containing only the extracted values.
`;

0 comments on commit 0935695

Please # to comment.