1use solana_program::{
4 instruction::{AccountMeta, Instruction},
5 pubkey::Pubkey,
6};
7use solana_sdk_ids::system_program;
8use spl_associated_token_account::get_associated_token_address;
9
10use crate::{
11 consts::{DOJO_MINT, FEE_COLLECTOR},
12 instruction::*,
13 state::*,
14};
15
16fn program_id() -> Pubkey {
17 crate::ID
18}
19
20pub fn initialize(authority: Pubkey) -> Instruction {
22 let config_address = config_pda(&program_id()).0;
23 let game_address = game_pda(&program_id()).0;
24 let treasury_address = treasury_pda(&program_id()).0;
25 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
26
27 Instruction {
28 program_id: program_id(),
29 accounts: vec![
30 AccountMeta::new(authority, true),
31 AccountMeta::new(config_address, false),
32 AccountMeta::new(game_address, false),
33 AccountMeta::new(treasury_address, false),
34 AccountMeta::new(treasury_ata, false),
35 AccountMeta::new_readonly(DOJO_MINT, false),
36 AccountMeta::new_readonly(spl_token::ID, false),
37 AccountMeta::new_readonly(spl_associated_token_account::ID, false),
38 AccountMeta::new_readonly(system_program::ID, false),
39 ],
40 data: Initialize {}.to_bytes(),
41 }
42}
43
44pub fn buy_starter_pack(
47 signer: Pubkey,
48 referrer: Option<Pubkey>,
49) -> Instruction {
50 let config_address = config_pda(&program_id()).0;
51 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
52 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
53 let (forge_address, _) = forge_pda(&program_id(), &dojo_address);
54 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
55 let treasury_address = treasury_pda(&program_id()).0;
56
57 let referrer_bytes = referrer.map(|p| p.to_bytes()).unwrap_or([0u8; 32]);
58
59 let game_address = game_pda(&program_id()).0;
60 let mut accounts = vec![
61 AccountMeta::new(signer, true),
62 AccountMeta::new(config_address, false),
63 AccountMeta::new(game_address, false),
64 AccountMeta::new(dojo_address, false),
65 AccountMeta::new(barracks_address, false),
66 AccountMeta::new(forge_address, false),
67 AccountMeta::new(tasks_address, false),
68 AccountMeta::new(treasury_address, false),
69 AccountMeta::new(FEE_COLLECTOR, false),
70 AccountMeta::new_readonly(system_program::ID, false),
71 ];
72 if let Some(ref_dojo) = referrer {
73 let (referral_address, _) = referral_pda(&program_id(), &ref_dojo);
74 accounts.push(AccountMeta::new_readonly(ref_dojo, false));
75 accounts.push(AccountMeta::new(referral_address, false));
76 }
77
78 Instruction {
79 program_id: program_id(),
80 accounts,
81 data: BuyStarterPack { referrer: referrer_bytes }.to_bytes(),
82 }
83}
84
85pub fn recruit_shogun_tickets(
89 signer: Pubkey,
90 count: u64,
91 seed: [u8; 32],
92 prestige: Option<Pubkey>,
93) -> Instruction {
94 let config_address = config_pda(&program_id()).0;
95 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
96 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
97
98 let mut accounts = vec![
99 AccountMeta::new(signer, true),
100 AccountMeta::new_readonly(config_address, false),
101 AccountMeta::new(dojo_address, false),
102 AccountMeta::new(tasks_address, false),
103 ];
104 if let Some(addr) = prestige {
105 accounts.push(AccountMeta::new(addr, false));
106 }
107
108 Instruction {
109 program_id: program_id(),
110 accounts,
111 data: RecruitShogunTickets {
112 count: count.to_le_bytes(),
113 seed,
114 }
115 .to_bytes(),
116 }
117}
118
119pub fn recruit_shogun_sol(
123 signer: Pubkey,
124 count: u64,
125 seed: [u8; 32],
126 prestige: Option<Pubkey>,
127) -> Instruction {
128 let config_address = config_pda(&program_id()).0;
129 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
130 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
131
132 let treasury_address = treasury_pda(&program_id()).0;
133 let mut accounts = vec![
134 AccountMeta::new(signer, true),
135 AccountMeta::new_readonly(config_address, false),
136 AccountMeta::new(dojo_address, false),
137 AccountMeta::new(tasks_address, false),
138 AccountMeta::new(treasury_address, false),
139 AccountMeta::new(FEE_COLLECTOR, false),
140 ];
141 if let Some(addr) = prestige {
142 accounts.push(AccountMeta::new(addr, false));
143 }
144
145 Instruction {
146 program_id: program_id(),
147 accounts,
148 data: RecruitShogunSol {
149 count: count.to_le_bytes(),
150 seed,
151 }
152 .to_bytes(),
153 }
154}
155
156pub fn seat_shogun(
159 signer: Pubkey,
160 slot: u64,
161 rarity: u64,
162 element: u64,
163 prestige: Option<Pubkey>,
164) -> Instruction {
165 let config_address = config_pda(&program_id()).0;
166 let game_address = game_pda(&program_id()).0;
167 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
168 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
169
170 let mut accounts = vec![
171 AccountMeta::new(signer, true),
172 AccountMeta::new_readonly(config_address, false),
173 AccountMeta::new(game_address, false),
174 AccountMeta::new(dojo_address, false),
175 AccountMeta::new(barracks_address, false),
176 ];
177 if let Some(addr) = prestige {
178 accounts.push(AccountMeta::new(addr, false));
179 }
180
181 Instruction {
182 program_id: program_id(),
183 accounts,
184 data: SeatShogun {
185 slot: slot.to_le_bytes(),
186 rarity: rarity.to_le_bytes(),
187 element: element.to_le_bytes(),
188 }
189 .to_bytes(),
190 }
191}
192
193pub fn replace_shogun(
196 signer: Pubkey,
197 slot: u64,
198 new_rarity: u64,
199 new_element: u64,
200 prestige: Option<Pubkey>,
201) -> Instruction {
202 let config_address = config_pda(&program_id()).0;
203 let game_address = game_pda(&program_id()).0;
204 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
205 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
206
207 let mut accounts = vec![
208 AccountMeta::new(signer, true),
209 AccountMeta::new_readonly(config_address, false),
210 AccountMeta::new(game_address, false),
211 AccountMeta::new(dojo_address, false),
212 AccountMeta::new(barracks_address, false),
213 ];
214 if let Some(addr) = prestige {
215 accounts.push(AccountMeta::new(addr, false));
216 }
217
218 Instruction {
219 program_id: program_id(),
220 accounts,
221 data: ReplaceShogun {
222 slot: slot.to_le_bytes(),
223 new_rarity: new_rarity.to_le_bytes(),
224 new_element: new_element.to_le_bytes(),
225 }
226 .to_bytes(),
227 }
228}
229
230pub fn seat_shogun_fill_all(
233 signer: Pubkey,
234 entries: impl IntoIterator<Item = (u64, u64)>,
235 prestige: Option<Pubkey>,
236) -> Instruction {
237 let config_address = config_pda(&program_id()).0;
238 let game_address = game_pda(&program_id()).0;
239 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
240 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
241
242 let mut arr: [SeatShogunFillAllEntry; 12] = [SeatShogunFillAllEntry {
243 rarity: [0; 8],
244 element: [0; 8],
245 }; 12];
246 let mut count = 0u8;
247 for (i, (rarity, element)) in entries.into_iter().take(12).enumerate() {
248 arr[i] = SeatShogunFillAllEntry {
249 rarity: rarity.to_le_bytes(),
250 element: element.to_le_bytes(),
251 };
252 count += 1;
253 }
254
255 let mut accounts = vec![
256 AccountMeta::new(signer, true),
257 AccountMeta::new_readonly(config_address, false),
258 AccountMeta::new(game_address, false),
259 AccountMeta::new(dojo_address, false),
260 AccountMeta::new(barracks_address, false),
261 ];
262 if let Some(addr) = prestige {
263 accounts.push(AccountMeta::new(addr, false));
264 }
265
266 Instruction {
267 program_id: program_id(),
268 accounts,
269 data: SeatShogunFillAll {
270 count,
271 _pad: [0; 7],
272 entries: arr,
273 }
274 .to_bytes(),
275 }
276}
277
278pub fn dine(signer: Pubkey, slot: u64, tier: u64) -> Instruction {
280 let config_address = config_pda(&program_id()).0;
281 let game_address = game_pda(&program_id()).0;
282 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
283 let treasury_address = treasury_pda(&program_id()).0;
284 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
285 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
286 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
287
288 Instruction {
289 program_id: program_id(),
290 accounts: vec![
291 AccountMeta::new(signer, true),
292 AccountMeta::new_readonly(config_address, false),
293 AccountMeta::new(game_address, false),
294 AccountMeta::new(dojo_address, false),
295 AccountMeta::new(barracks_address, false),
296 AccountMeta::new(user_ata, false),
297 AccountMeta::new(treasury_ata, false),
298 AccountMeta::new(DOJO_MINT, false),
299 AccountMeta::new(treasury_address, false),
300 AccountMeta::new_readonly(spl_token::ID, false),
301 ],
302 data: Dine {
303 tier: tier.to_le_bytes(),
304 slot: slot.to_le_bytes(),
305 }
306 .to_bytes(),
307 }
308}
309
310pub fn upgrade_barracks_shards(signer: Pubkey) -> Instruction {
312 let config_address = config_pda(&program_id()).0;
313 let game_address = game_pda(&program_id()).0;
314 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
315 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
316 let treasury_address = treasury_pda(&program_id()).0;
317 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
318 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
319
320 Instruction {
321 program_id: program_id(),
322 accounts: vec![
323 AccountMeta::new(signer, true),
324 AccountMeta::new_readonly(config_address, false),
325 AccountMeta::new(game_address, false),
326 AccountMeta::new(dojo_address, false),
327 AccountMeta::new(barracks_address, false),
328 AccountMeta::new(user_ata, false),
329 AccountMeta::new(treasury_ata, false),
330 AccountMeta::new(DOJO_MINT, false),
331 AccountMeta::new(treasury_address, false),
332 AccountMeta::new_readonly(spl_token::ID, false),
333 ],
334 data: UpgradeBarracksShards {}.to_bytes(),
335 }
336}
337
338pub fn upgrade_barracks_sol(signer: Pubkey) -> Instruction {
340 let config_address = config_pda(&program_id()).0;
341 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
342 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
343 let treasury_address = treasury_pda(&program_id()).0;
344
345 Instruction {
346 program_id: program_id(),
347 accounts: vec![
348 AccountMeta::new(signer, true),
349 AccountMeta::new_readonly(config_address, false),
350 AccountMeta::new(dojo_address, false),
351 AccountMeta::new(barracks_address, false),
352 AccountMeta::new(treasury_address, false),
353 AccountMeta::new(FEE_COLLECTOR, false),
354 AccountMeta::new_readonly(system_program::ID, false),
355 ],
356 data: UpgradeBarracksSol {}.to_bytes(),
357 }
358}
359
360pub fn upgrade_forge(signer: Pubkey) -> Instruction {
362 let config_address = config_pda(&program_id()).0;
363 let game_address = game_pda(&program_id()).0;
364 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
365 let (forge_address, _) = forge_pda(&program_id(), &dojo_address);
366 let treasury_address = treasury_pda(&program_id()).0;
367 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
368 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
369
370 Instruction {
371 program_id: program_id(),
372 accounts: vec![
373 AccountMeta::new(signer, true),
374 AccountMeta::new_readonly(config_address, false),
375 AccountMeta::new(game_address, false),
376 AccountMeta::new(dojo_address, false),
377 AccountMeta::new(forge_address, false),
378 AccountMeta::new(FEE_COLLECTOR, false),
379 AccountMeta::new_readonly(system_program::ID, false),
380 AccountMeta::new(user_ata, false),
381 AccountMeta::new(treasury_ata, false),
382 AccountMeta::new(DOJO_MINT, false),
383 AccountMeta::new(treasury_address, false),
384 AccountMeta::new_readonly(spl_token::ID, false),
385 ],
386 data: UpgradeForge {}.to_bytes(),
387 }
388}
389
390pub fn merge_shogun(
394 signer: Pubkey,
395 merge_type: u64,
396 seed: [u8; 32],
397 prestige: Option<Pubkey>,
398) -> Instruction {
399 let config_address = config_pda(&program_id()).0;
400 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
401 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
402
403 let mut accounts = vec![
404 AccountMeta::new(signer, true),
405 AccountMeta::new_readonly(config_address, false),
406 AccountMeta::new(dojo_address, false),
407 AccountMeta::new(tasks_address, false),
408 ];
409 if let Some(addr) = prestige {
410 accounts.push(AccountMeta::new(addr, false));
411 }
412
413 Instruction {
414 program_id: program_id(),
415 accounts,
416 data: MergeShogun {
417 merge_type: merge_type.to_le_bytes(),
418 seed,
419 }
420 .to_bytes(),
421 }
422}
423
424pub fn prestige_upgrade(signer: Pubkey, slot: u64, prestige: Option<Pubkey>) -> Instruction {
427 let config_address = config_pda(&program_id()).0;
428 let game_address = game_pda(&program_id()).0;
429 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
430 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
431 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
432
433 let mut accounts = vec![
434 AccountMeta::new(signer, true),
435 AccountMeta::new_readonly(config_address, false),
436 AccountMeta::new(game_address, false),
437 AccountMeta::new(dojo_address, false),
438 AccountMeta::new(barracks_address, false),
439 AccountMeta::new(tasks_address, false),
440 ];
441 if let Some(addr) = prestige {
442 accounts.push(AccountMeta::new(addr, false));
443 }
444
445 Instruction {
446 program_id: program_id(),
447 accounts,
448 data: PrestigeUpgrade {
449 slot: slot.to_le_bytes(),
450 }
451 .to_bytes(),
452 }
453}
454
455pub fn prestige_fodder_shogun(
458 signer: Pubkey,
459 collection_index: u8,
460 from_prestige: u64,
461) -> Instruction {
462 let config_address = config_pda(&program_id()).0;
463 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
464 let (prestige_address, _) = prestige_pda(&program_id(), &dojo_address);
465 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
466
467 Instruction {
468 program_id: program_id(),
469 accounts: vec![
470 AccountMeta::new(signer, true),
471 AccountMeta::new_readonly(config_address, false),
472 AccountMeta::new(dojo_address, false),
473 AccountMeta::new(prestige_address, false),
474 AccountMeta::new(tasks_address, false),
475 AccountMeta::new_readonly(system_program::ID, false),
476 ],
477 data: PrestigeFodderShogun {
478 collection_index,
479 _pad: [0; 7],
480 from_prestige: from_prestige.to_le_bytes(),
481 }
482 .to_bytes(),
483 }
484}
485
486pub fn level_up_shogun(signer: Pubkey, slot: u64) -> Instruction {
488 let config_address = config_pda(&program_id()).0;
489 let game_address = game_pda(&program_id()).0;
490 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
491 let treasury_address = treasury_pda(&program_id()).0;
492 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
493 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
494 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
495
496 Instruction {
497 program_id: program_id(),
498 accounts: vec![
499 AccountMeta::new(signer, true),
500 AccountMeta::new_readonly(config_address, false),
501 AccountMeta::new(game_address, false),
502 AccountMeta::new(dojo_address, false),
503 AccountMeta::new(barracks_address, false),
504 AccountMeta::new(user_ata, false),
505 AccountMeta::new(treasury_ata, false),
506 AccountMeta::new(DOJO_MINT, false),
507 AccountMeta::new(treasury_address, false),
508 AccountMeta::new_readonly(spl_token::ID, false),
509 ],
510 data: LevelUpShogun {
511 slot: slot.to_le_bytes(),
512 }
513 .to_bytes(),
514 }
515}
516
517pub fn claim_shards(signer: Pubkey) -> Instruction {
520 let config_address = config_pda(&program_id()).0;
521 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
522 let (forge_address, _) = forge_pda(&program_id(), &dojo_address);
523 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
524 let game_address = game_pda(&program_id()).0;
525 let treasury_address = treasury_pda(&program_id()).0;
526 let dojo_ata = get_associated_token_address(&signer, &DOJO_MINT);
527
528 Instruction {
529 program_id: program_id(),
530 accounts: vec![
531 AccountMeta::new(signer, true),
532 AccountMeta::new_readonly(config_address, false),
533 AccountMeta::new(dojo_address, false),
534 AccountMeta::new(forge_address, false),
535 AccountMeta::new(barracks_address, false),
536 AccountMeta::new_readonly(game_address, false),
537 AccountMeta::new(dojo_ata, false),
538 AccountMeta::new(DOJO_MINT, false),
539 AccountMeta::new(treasury_address, false),
540 AccountMeta::new_readonly(spl_token::ID, false),
541 ],
542 data: ClaimShards {}.to_bytes(),
543 }
544}
545
546pub fn claim_referral_reward(signer: Pubkey, referrer_dojo: Pubkey) -> Instruction {
548 let (referral_address, _) = referral_pda(&program_id(), &referrer_dojo);
549 let treasury_address = treasury_pda(&program_id()).0;
550
551 Instruction {
552 program_id: program_id(),
553 accounts: vec![
554 AccountMeta::new(signer, true),
555 AccountMeta::new(referrer_dojo, false),
556 AccountMeta::new(referral_address, false),
557 AccountMeta::new(treasury_address, false),
558 AccountMeta::new_readonly(system_program::ID, false),
559 ],
560 data: ClaimReferralReward {}.to_bytes(),
561 }
562}
563
564pub fn claim_recruit_reward(signer: Pubkey) -> Instruction {
566 let config_address = config_pda(&program_id()).0;
567 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
568 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
569
570 Instruction {
571 program_id: program_id(),
572 accounts: vec![
573 AccountMeta::new(signer, true),
574 AccountMeta::new_readonly(config_address, false),
575 AccountMeta::new(dojo_address, false),
576 AccountMeta::new(tasks_address, false),
577 ],
578 data: ClaimRecruitReward {}.to_bytes(),
579 }
580}
581
582pub fn claim_forge_reward(signer: Pubkey) -> Instruction {
584 let config_address = config_pda(&program_id()).0;
585 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
586 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
587
588 Instruction {
589 program_id: program_id(),
590 accounts: vec![
591 AccountMeta::new(signer, true),
592 AccountMeta::new_readonly(config_address, false),
593 AccountMeta::new(dojo_address, false),
594 AccountMeta::new(tasks_address, false),
595 ],
596 data: ClaimForgeReward {}.to_bytes(),
597 }
598}
599
600pub fn claim_dine_reward(signer: Pubkey) -> Instruction {
602 let config_address = config_pda(&program_id()).0;
603 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
604 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
605
606 Instruction {
607 program_id: program_id(),
608 accounts: vec![
609 AccountMeta::new(signer, true),
610 AccountMeta::new_readonly(config_address, false),
611 AccountMeta::new(dojo_address, false),
612 AccountMeta::new(tasks_address, false),
613 ],
614 data: ClaimDineReward {}.to_bytes(),
615 }
616}
617
618pub fn ed25519_verify_instruction_for_daily_claim(
621 dojo_pda: Pubkey,
622 signature: [u8; 64],
623) -> Instruction {
624 use crate::consts::{CLAIM_TASK_PREFIX, DAILY_TASK_START, TASK_VERIFIER};
625 let mut message = Vec::with_capacity(CLAIM_TASK_PREFIX.len() + 32 + 8);
626 message.extend_from_slice(CLAIM_TASK_PREFIX);
627 message.extend_from_slice(dojo_pda.as_ref());
628 message.extend_from_slice(&DAILY_TASK_START.to_le_bytes());
629 let verifier_bytes: [u8; 32] = TASK_VERIFIER.to_bytes();
630 crate::utils::new_ed25519_instruction_with_signature(&message, &signature, &verifier_bytes)
631}
632
633pub fn claim_daily_reward(signer: Pubkey, signature: [u8; 64]) -> Instruction {
636 let config_address = config_pda(&program_id()).0;
637 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
638 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
639 let instructions_sysvar = solana_program::sysvar::instructions::ID;
640
641 Instruction {
642 program_id: program_id(),
643 accounts: vec![
644 AccountMeta::new(signer, true),
645 AccountMeta::new_readonly(config_address, false),
646 AccountMeta::new(dojo_address, false),
647 AccountMeta::new(tasks_address, false),
648 AccountMeta::new_readonly(instructions_sysvar, false),
649 ],
650 data: ClaimDailyReward { signature }.to_bytes(),
651 }
652}
653
654pub fn ed25519_verify_instruction_for_off_chain_task(
656 dojo_pda: Pubkey,
657 task_id: u64,
658 signature: [u8; 64],
659) -> Instruction {
660 use crate::consts::{CLAIM_TASK_PREFIX, TASK_VERIFIER};
661 let mut message = Vec::with_capacity(CLAIM_TASK_PREFIX.len() + 32 + 8);
662 message.extend_from_slice(CLAIM_TASK_PREFIX);
663 message.extend_from_slice(dojo_pda.as_ref());
664 message.extend_from_slice(&task_id.to_le_bytes());
665 let verifier_bytes: [u8; 32] = TASK_VERIFIER.to_bytes();
666 crate::utils::new_ed25519_instruction_with_signature(&message, &signature, &verifier_bytes)
667}
668
669pub fn claim_off_chain_task_reward(
672 signer: Pubkey,
673 task_id: u64,
674 signature: [u8; 64],
675) -> Instruction {
676 let config_address = config_pda(&program_id()).0;
677 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
678 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
679 let instructions_sysvar = solana_program::sysvar::instructions::ID;
680
681 Instruction {
682 program_id: program_id(),
683 accounts: vec![
684 AccountMeta::new(signer, true),
685 AccountMeta::new_readonly(config_address, false),
686 AccountMeta::new(dojo_address, false),
687 AccountMeta::new(tasks_address, false),
688 AccountMeta::new_readonly(instructions_sysvar, false),
689 ],
690 data: ClaimOffChainTaskReward {
691 task_id: task_id.to_le_bytes(),
692 signature,
693 }
694 .to_bytes(),
695 }
696}
697
698pub fn claim_seeker_task_reward(
703 signer: Pubkey,
704 signer_sgt_token_account: Pubkey,
705 sgt_mint: Pubkey,
706) -> Instruction {
707 let config_address = config_pda(&program_id()).0;
708 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
709 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
710 let (seeker_address, _) = seeker_pda(&program_id(), &sgt_mint);
711
712 Instruction {
713 program_id: program_id(),
714 accounts: vec![
715 AccountMeta::new(signer, true),
716 AccountMeta::new_readonly(config_address, false),
717 AccountMeta::new(dojo_address, false),
718 AccountMeta::new(tasks_address, false),
719 AccountMeta::new_readonly(signer_sgt_token_account, false),
720 AccountMeta::new_readonly(sgt_mint, false),
721 AccountMeta::new_readonly(spl_token_2022::ID, false),
722 AccountMeta::new(seeker_address, false),
723 AccountMeta::new_readonly(system_program::ID, false),
724 ],
725 data: ClaimSeekerTaskReward {}.to_bytes(),
726 }
727}
728
729pub fn mint_soulbound(
732 signer: Pubkey,
733 signer_sgt_token_account: Pubkey,
734 sgt_mint: Pubkey,
735 soulbound_mint: Pubkey,
736) -> Instruction {
737 let config_address = config_pda(&program_id()).0;
738 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
739 let (seeker_address, _) = seeker_pda(&program_id(), &sgt_mint);
740 let (treasury_address, _) = treasury_pda(&program_id());
741 let soulbound_token = get_associated_token_address(&signer, &soulbound_mint);
742
743 Instruction {
744 program_id: program_id(),
745 accounts: vec![
746 AccountMeta::new(signer, true),
747 AccountMeta::new_readonly(config_address, false),
748 AccountMeta::new(dojo_address, false),
749 AccountMeta::new(seeker_address, false),
750 AccountMeta::new_readonly(signer_sgt_token_account, false),
751 AccountMeta::new_readonly(sgt_mint, false),
752 AccountMeta::new(soulbound_mint, false),
753 AccountMeta::new_readonly(treasury_address, false),
754 AccountMeta::new(soulbound_token, false),
755 AccountMeta::new_readonly(spl_token_2022::ID, false),
756 AccountMeta::new_readonly(system_program::ID, false),
757 AccountMeta::new_readonly(spl_associated_token_account::ID, false),
758 ],
759 data: MintSoulbound {}.to_bytes(),
760 }
761}
762
763pub fn claim_collection_reward(signer: Pubkey, collection_index: u8) -> Instruction {
766 let config_address = config_pda(&program_id()).0;
767 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
768 let (tasks_address, _) = tasks_pda(&program_id(), &dojo_address);
769
770 Instruction {
771 program_id: program_id(),
772 accounts: vec![
773 AccountMeta::new(signer, true),
774 AccountMeta::new_readonly(config_address, false),
775 AccountMeta::new(dojo_address, false),
776 AccountMeta::new(tasks_address, false),
777 ],
778 data: ClaimCollectionReward { collection_index }.to_bytes(),
779 }
780}
781
782pub fn buy_flash_sale(signer: Pubkey) -> Instruction {
784 let config_address = config_pda(&program_id()).0;
785 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
786 let treasury_address = treasury_pda(&program_id()).0;
787 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
788 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
789
790 Instruction {
791 program_id: program_id(),
792 accounts: vec![
793 AccountMeta::new(signer, true),
794 AccountMeta::new_readonly(config_address, false),
795 AccountMeta::new(dojo_address, false),
796 AccountMeta::new(user_ata, false),
797 AccountMeta::new_readonly(treasury_address, false),
798 AccountMeta::new(treasury_ata, false),
799 AccountMeta::new_readonly(spl_token::ID, false),
800 ],
801 data: BuyFlashSale {}.to_bytes(),
802 }
803}
804
805pub fn buy_tickets_with_shards(signer: Pubkey) -> Instruction {
807 let config_address = config_pda(&program_id()).0;
808 let game_address = game_pda(&program_id()).0;
809 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
810 let treasury_address = treasury_pda(&program_id()).0;
811 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
812 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
813
814 Instruction {
815 program_id: program_id(),
816 accounts: vec![
817 AccountMeta::new(signer, true),
818 AccountMeta::new_readonly(config_address, false),
819 AccountMeta::new(game_address, false),
820 AccountMeta::new(dojo_address, false),
821 AccountMeta::new(user_ata, false),
822 AccountMeta::new(treasury_ata, false),
823 AccountMeta::new(DOJO_MINT, false),
824 AccountMeta::new(treasury_address, false),
825 AccountMeta::new_readonly(spl_token::ID, false),
826 ],
827 data: BuyTicketsWithShards {}.to_bytes(),
828 }
829}
830
831pub fn buy_bundle(signer: Pubkey) -> Instruction {
833 let config_address = config_pda(&program_id()).0;
834 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
835 let treasury_address = treasury_pda(&program_id()).0;
836
837 Instruction {
838 program_id: program_id(),
839 accounts: vec![
840 AccountMeta::new(signer, true),
841 AccountMeta::new_readonly(config_address, false),
842 AccountMeta::new(dojo_address, false),
843 AccountMeta::new(treasury_address, false),
844 AccountMeta::new(FEE_COLLECTOR, false),
845 AccountMeta::new_readonly(system_program::ID, false),
846 ],
847 data: BuyBundle {}.to_bytes(),
848 }
849}
850
851pub fn clear_forge_cooldown(signer: Pubkey) -> Instruction {
853 let config_address = config_pda(&program_id()).0;
854 let game_address = game_pda(&program_id()).0;
855 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
856 let (forge_address, _) = forge_pda(&program_id(), &dojo_address);
857 let treasury_address = treasury_pda(&program_id()).0;
858 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
859 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
860
861 Instruction {
862 program_id: program_id(),
863 accounts: vec![
864 AccountMeta::new(signer, true),
865 AccountMeta::new_readonly(config_address, false),
866 AccountMeta::new(game_address, false),
867 AccountMeta::new(dojo_address, false),
868 AccountMeta::new(forge_address, false),
869 AccountMeta::new(user_ata, false),
870 AccountMeta::new(treasury_ata, false),
871 AccountMeta::new(DOJO_MINT, false),
872 AccountMeta::new(treasury_address, false),
873 AccountMeta::new_readonly(spl_token::ID, false),
874 ],
875 data: ClearForgeCooldown {}.to_bytes(),
876 }
877}
878
879pub fn set_genesis_slot(authority: Pubkey, genesis_slot: u64, halving_period_slots: u64) -> Instruction {
881 let config_address = config_pda(&program_id()).0;
882 let game_address = game_pda(&program_id()).0;
883
884 Instruction {
885 program_id: program_id(),
886 accounts: vec![
887 AccountMeta::new(authority, true),
888 AccountMeta::new(config_address, false),
889 AccountMeta::new(game_address, false),
890 ],
891 data: SetGenesisSlot {
892 genesis_slot: genesis_slot.to_le_bytes(),
893 halving_period_slots: halving_period_slots.to_le_bytes(),
894 }
895 .to_bytes(),
896 }
897}
898
899pub fn roll_scene_section_amethyst(signer: Pubkey, count: u64, seed: [u8; 32]) -> Instruction {
902 let config_address = config_pda(&program_id()).0;
903 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
904 let (scenes_address, _) = scenes_pda(&program_id(), &dojo_address);
905
906 Instruction {
907 program_id: program_id(),
908 accounts: vec![
909 AccountMeta::new(signer, true),
910 AccountMeta::new_readonly(config_address, false),
911 AccountMeta::new(dojo_address, false),
912 AccountMeta::new(scenes_address, false),
913 AccountMeta::new_readonly(system_program::ID, false),
914 ],
915 data: RollSceneSectionAmethyst {
916 count: count.to_le_bytes(),
917 seed,
918 }
919 .to_bytes(),
920 }
921}
922
923pub fn roll_scene_section_shards(signer: Pubkey, count: u64, seed: [u8; 32]) -> Instruction {
926 let config_address = config_pda(&program_id()).0;
927 let game_address = game_pda(&program_id()).0;
928 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
929 let (scenes_address, _) = scenes_pda(&program_id(), &dojo_address);
930 let treasury_address = treasury_pda(&program_id()).0;
931 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
932 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
933
934 Instruction {
935 program_id: program_id(),
936 accounts: vec![
937 AccountMeta::new(signer, true),
938 AccountMeta::new_readonly(config_address, false),
939 AccountMeta::new(game_address, false),
940 AccountMeta::new(dojo_address, false),
941 AccountMeta::new(scenes_address, false),
942 AccountMeta::new(user_ata, false),
943 AccountMeta::new(treasury_ata, false),
944 AccountMeta::new(DOJO_MINT, false),
945 AccountMeta::new(treasury_address, false),
946 AccountMeta::new_readonly(spl_token::ID, false),
947 AccountMeta::new_readonly(system_program::ID, false),
948 ],
949 data: RollSceneSectionShards {
950 count: count.to_le_bytes(),
951 seed,
952 }
953 .to_bytes(),
954 }
955}
956
957pub fn salvage_scene_section(signer: Pubkey) -> Instruction {
959 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
960 let (scenes_address, _) = scenes_pda(&program_id(), &dojo_address);
961
962 Instruction {
963 program_id: program_id(),
964 accounts: vec![
965 AccountMeta::new(signer, true),
966 AccountMeta::new(dojo_address, false),
967 AccountMeta::new(scenes_address, false),
968 ],
969 data: SalvageSceneSection {}.to_bytes(),
970 }
971}
972
973pub fn update_active_scene(signer: Pubkey, scene_id: u64) -> Instruction {
976 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
977 let (scenes_address, _) = scenes_pda(&program_id(), &dojo_address);
978 let game_address = game_pda(&program_id()).0;
979 let (barracks_address, _) = barracks_pda(&program_id(), &dojo_address);
980
981 Instruction {
982 program_id: program_id(),
983 accounts: vec![
984 AccountMeta::new(signer, true),
985 AccountMeta::new(dojo_address, false),
986 AccountMeta::new(scenes_address, false),
987 AccountMeta::new(game_address, false),
988 AccountMeta::new(barracks_address, false),
989 ],
990 data: UpdateActiveScene {
991 scene_id: scene_id.to_le_bytes(),
992 }
993 .to_bytes(),
994 }
995}
996
997pub fn buy_chest(signer: Pubkey) -> Instruction {
999 let config_address = config_pda(&program_id()).0;
1000 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
1001 let treasury_address = treasury_pda(&program_id()).0;
1002
1003 Instruction {
1004 program_id: program_id(),
1005 accounts: vec![
1006 AccountMeta::new(signer, true),
1007 AccountMeta::new_readonly(config_address, false),
1008 AccountMeta::new(dojo_address, false),
1009 AccountMeta::new(treasury_address, false),
1010 AccountMeta::new(FEE_COLLECTOR, false),
1011 AccountMeta::new_readonly(system_program::ID, false),
1012 ],
1013 data: BuyChest {}.to_bytes(),
1014 }
1015}
1016
1017pub fn buy_scene(signer: Pubkey, scene_id: u64) -> Instruction {
1019 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
1020 let (scenes_address, _) = scenes_pda(&program_id(), &dojo_address);
1021
1022 Instruction {
1023 program_id: program_id(),
1024 accounts: vec![
1025 AccountMeta::new(signer, true),
1026 AccountMeta::new(dojo_address, false),
1027 AccountMeta::new(scenes_address, false),
1028 AccountMeta::new_readonly(system_program::ID, false),
1029 ],
1030 data: BuyScene {
1031 scene_id: scene_id.to_le_bytes(),
1032 }
1033 .to_bytes(),
1034 }
1035}
1036
1037pub fn buy_scene_dojo(signer: Pubkey, scene_id: u64) -> Instruction {
1039 let config_address = config_pda(&program_id()).0;
1040 let (game_address, _) = game_pda(&program_id());
1041 let (dojo_address, _) = dojo_pda(&program_id(), &signer);
1042 let (scenes_address, _) = scenes_pda(&program_id(), &dojo_address);
1043 let treasury_address = treasury_pda(&program_id()).0;
1044 let user_ata = get_associated_token_address(&signer, &DOJO_MINT);
1045 let treasury_ata = get_associated_token_address(&treasury_address, &DOJO_MINT);
1046
1047 Instruction {
1048 program_id: program_id(),
1049 accounts: vec![
1050 AccountMeta::new(signer, true),
1051 AccountMeta::new_readonly(config_address, false),
1052 AccountMeta::new(game_address, false),
1053 AccountMeta::new(dojo_address, false),
1054 AccountMeta::new(scenes_address, false),
1055 AccountMeta::new(user_ata, false),
1056 AccountMeta::new(treasury_ata, false),
1057 AccountMeta::new(DOJO_MINT, false),
1058 AccountMeta::new(treasury_address, false),
1059 AccountMeta::new_readonly(spl_token::ID, false),
1060 AccountMeta::new_readonly(system_program::ID, false),
1061 ],
1062 data: BuySceneDojo {
1063 scene_id: scene_id.to_le_bytes(),
1064 }
1065 .to_bytes(),
1066 }
1067}
1068
1069pub fn log(config: Pubkey, msg: &[u8]) -> Instruction {
1071 let mut data = Log {
1072 _reserved: [0u8; 8],
1073 }
1074 .to_bytes();
1075 data.extend_from_slice(msg);
1076 Instruction {
1077 program_id: program_id(),
1078 accounts: vec![AccountMeta::new(config, true)],
1079 data,
1080 }
1081}