template.rs 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384
  1. use crate::config::ProgramWorkspace;
  2. use crate::VERSION;
  3. use anchor_syn::idl::Idl;
  4. use anyhow::Result;
  5. use heck::{CamelCase, MixedCase, SnakeCase};
  6. use solana_sdk::pubkey::Pubkey;
  7. use std::fmt::Write;
  8. pub fn default_program_id() -> Pubkey {
  9. "Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS"
  10. .parse()
  11. .unwrap()
  12. }
  13. pub fn virtual_manifest() -> &'static str {
  14. r#"[workspace]
  15. members = [
  16. "programs/*"
  17. ]
  18. [profile.release]
  19. overflow-checks = true
  20. lto = "fat"
  21. codegen-units = 1
  22. [profile.release.build-override]
  23. opt-level = 3
  24. incremental = false
  25. codegen-units = 1
  26. "#
  27. }
  28. pub fn credentials(token: &str) -> String {
  29. format!(
  30. r#"[registry]
  31. token = "{}"
  32. "#,
  33. token
  34. )
  35. }
  36. pub fn idl_ts(idl: &Idl) -> Result<String> {
  37. let mut idl = idl.clone();
  38. for acc in idl.accounts.iter_mut() {
  39. acc.name = acc.name.to_mixed_case();
  40. }
  41. let idl_json = serde_json::to_string_pretty(&idl)?;
  42. Ok(format!(
  43. r#"export type {} = {};
  44. export const IDL: {} = {};
  45. "#,
  46. idl.name.to_camel_case(),
  47. idl_json,
  48. idl.name.to_camel_case(),
  49. idl_json
  50. ))
  51. }
  52. pub fn cargo_toml(name: &str) -> String {
  53. format!(
  54. r#"[package]
  55. name = "{0}"
  56. version = "0.1.0"
  57. description = "Created with Anchor"
  58. edition = "2021"
  59. [lib]
  60. crate-type = ["cdylib", "lib"]
  61. name = "{1}"
  62. [features]
  63. no-entrypoint = []
  64. no-idl = []
  65. no-log-ix-name = []
  66. cpi = ["no-entrypoint"]
  67. default = []
  68. [dependencies]
  69. anchor-lang = "{2}"
  70. "#,
  71. name,
  72. name.to_snake_case(),
  73. VERSION,
  74. )
  75. }
  76. pub fn deploy_js_script_host(cluster_url: &str, script_path: &str) -> String {
  77. format!(
  78. r#"
  79. const anchor = require('@project-serum/anchor');
  80. // Deploy script defined by the user.
  81. const userScript = require("{0}");
  82. async function main() {{
  83. const url = "{1}";
  84. const preflightCommitment = 'recent';
  85. const connection = new anchor.web3.Connection(url, preflightCommitment);
  86. const wallet = anchor.Wallet.local();
  87. const provider = new anchor.AnchorProvider(connection, wallet, {{
  88. preflightCommitment,
  89. commitment: 'recent',
  90. }});
  91. // Run the user's deploy script.
  92. userScript(provider);
  93. }}
  94. main();
  95. "#,
  96. script_path, cluster_url,
  97. )
  98. }
  99. pub fn deploy_ts_script_host(cluster_url: &str, script_path: &str) -> String {
  100. format!(
  101. r#"import * as anchor from '@project-serum/anchor';
  102. // Deploy script defined by the user.
  103. const userScript = require("{0}");
  104. async function main() {{
  105. const url = "{1}";
  106. const preflightCommitment = 'recent';
  107. const connection = new anchor.web3.Connection(url, preflightCommitment);
  108. const wallet = anchor.Wallet.local();
  109. const provider = new anchor.AnchorProvider(connection, wallet, {{
  110. preflightCommitment,
  111. commitment: 'recent',
  112. }});
  113. // Run the user's deploy script.
  114. userScript(provider);
  115. }}
  116. main();
  117. "#,
  118. script_path, cluster_url,
  119. )
  120. }
  121. pub fn deploy_script() -> &'static str {
  122. r#"// Migrations are an early feature. Currently, they're nothing more than this
  123. // single deploy script that's invoked from the CLI, injecting a provider
  124. // configured from the workspace's Anchor.toml.
  125. const anchor = require("@project-serum/anchor");
  126. module.exports = async function (provider) {
  127. // Configure client to use the provider.
  128. anchor.setProvider(provider);
  129. // Add your deploy script here.
  130. };
  131. "#
  132. }
  133. pub fn ts_deploy_script() -> &'static str {
  134. r#"// Migrations are an early feature. Currently, they're nothing more than this
  135. // single deploy script that's invoked from the CLI, injecting a provider
  136. // configured from the workspace's Anchor.toml.
  137. const anchor = require("@project-serum/anchor");
  138. module.exports = async function (provider) {
  139. // Configure client to use the provider.
  140. anchor.setProvider(provider);
  141. // Add your deploy script here.
  142. };
  143. "#
  144. }
  145. pub fn xargo_toml() -> &'static str {
  146. r#"[target.bpfel-unknown-unknown.dependencies.std]
  147. features = []
  148. "#
  149. }
  150. pub fn lib_rs(name: &str) -> String {
  151. format!(
  152. r#"use anchor_lang::prelude::*;
  153. declare_id!("{}");
  154. #[program]
  155. pub mod {} {{
  156. use super::*;
  157. pub fn initialize(ctx: Context<Initialize>) -> Result<()> {{
  158. Ok(())
  159. }}
  160. }}
  161. #[derive(Accounts)]
  162. pub struct Initialize {{}}
  163. "#,
  164. default_program_id(),
  165. name.to_snake_case(),
  166. )
  167. }
  168. pub fn mocha(name: &str) -> String {
  169. format!(
  170. r#"const anchor = require("@project-serum/anchor");
  171. describe("{}", () => {{
  172. // Configure the client to use the local cluster.
  173. anchor.setProvider(anchor.AnchorProvider.env());
  174. it("Is initialized!", async () => {{
  175. // Add your test here.
  176. const program = anchor.workspace.{};
  177. const tx = await program.methods.initialize().rpc();
  178. console.log("Your transaction signature", tx);
  179. }});
  180. }});
  181. "#,
  182. name,
  183. name.to_camel_case(),
  184. )
  185. }
  186. pub fn package_json() -> String {
  187. format!(
  188. r#"{{
  189. "scripts": {{
  190. "lint:fix": "prettier */*.js \"*/**/*{{.js,.ts}}\" -w",
  191. "lint": "prettier */*.js \"*/**/*{{.js,.ts}}\" --check"
  192. }},
  193. "dependencies": {{
  194. "@project-serum/anchor": "^{0}"
  195. }},
  196. "devDependencies": {{
  197. "chai": "^4.3.4",
  198. "mocha": "^9.0.3",
  199. "prettier": "^2.6.2"
  200. }}
  201. }}
  202. "#,
  203. VERSION
  204. )
  205. }
  206. pub fn ts_package_json() -> String {
  207. format!(
  208. r#"{{
  209. "scripts": {{
  210. "lint:fix": "prettier */*.js \"*/**/*{{.js,.ts}}\" -w",
  211. "lint": "prettier */*.js \"*/**/*{{.js,.ts}}\" --check"
  212. }},
  213. "dependencies": {{
  214. "@project-serum/anchor": "^{0}"
  215. }},
  216. "devDependencies": {{
  217. "chai": "^4.3.4",
  218. "mocha": "^9.0.3",
  219. "ts-mocha": "^10.0.0",
  220. "@types/bn.js": "^5.1.0",
  221. "@types/chai": "^4.3.0",
  222. "@types/mocha": "^9.0.0",
  223. "typescript": "^4.3.5",
  224. "prettier": "^2.6.2"
  225. }}
  226. }}
  227. "#,
  228. VERSION
  229. )
  230. }
  231. pub fn ts_mocha(name: &str) -> String {
  232. format!(
  233. r#"import * as anchor from "@project-serum/anchor";
  234. import {{ Program }} from "@project-serum/anchor";
  235. import {{ {} }} from "../target/types/{}";
  236. describe("{}", () => {{
  237. // Configure the client to use the local cluster.
  238. anchor.setProvider(anchor.AnchorProvider.env());
  239. const program = anchor.workspace.{} as Program<{}>;
  240. it("Is initialized!", async () => {{
  241. // Add your test here.
  242. const tx = await program.methods.initialize().rpc();
  243. console.log("Your transaction signature", tx);
  244. }});
  245. }});
  246. "#,
  247. name.to_camel_case(),
  248. name.to_snake_case(),
  249. name,
  250. name.to_camel_case(),
  251. name.to_camel_case(),
  252. )
  253. }
  254. pub fn ts_config() -> &'static str {
  255. r#"{
  256. "compilerOptions": {
  257. "types": ["mocha", "chai"],
  258. "typeRoots": ["./node_modules/@types"],
  259. "lib": ["es2015"],
  260. "module": "commonjs",
  261. "target": "es6",
  262. "esModuleInterop": true
  263. }
  264. }
  265. "#
  266. }
  267. pub fn git_ignore() -> &'static str {
  268. r#"
  269. .anchor
  270. .DS_Store
  271. target
  272. **/*.rs.bk
  273. node_modules
  274. test-ledger
  275. "#
  276. }
  277. pub fn prettier_ignore() -> &'static str {
  278. r#"
  279. .anchor
  280. .DS_Store
  281. target
  282. node_modules
  283. dist
  284. build
  285. test-ledger
  286. "#
  287. }
  288. pub fn node_shell(
  289. cluster_url: &str,
  290. wallet_path: &str,
  291. programs: Vec<ProgramWorkspace>,
  292. ) -> Result<String> {
  293. let mut eval_string = format!(
  294. r#"
  295. const anchor = require('@project-serum/anchor');
  296. const web3 = anchor.web3;
  297. const PublicKey = anchor.web3.PublicKey;
  298. const Keypair = anchor.web3.Keypair;
  299. const __wallet = new anchor.Wallet(
  300. Keypair.fromSecretKey(
  301. Buffer.from(
  302. JSON.parse(
  303. require('fs').readFileSync(
  304. "{}",
  305. {{
  306. encoding: "utf-8",
  307. }},
  308. ),
  309. ),
  310. ),
  311. ),
  312. );
  313. const __connection = new web3.Connection("{}", "processed");
  314. const provider = new anchor.AnchorProvider(__connection, __wallet, {{
  315. commitment: "processed",
  316. preflightcommitment: "processed",
  317. }});
  318. anchor.setProvider(provider);
  319. "#,
  320. wallet_path, cluster_url,
  321. );
  322. for program in programs {
  323. write!(
  324. &mut eval_string,
  325. r#"
  326. anchor.workspace.{} = new anchor.Program({}, new PublicKey("{}"), provider);
  327. "#,
  328. program.name.to_camel_case(),
  329. serde_json::to_string(&program.idl)?,
  330. program.program_id
  331. )?;
  332. }
  333. Ok(eval_string)
  334. }