anchor-client-gen icon indicating copy to clipboard operation
anchor-client-gen copied to clipboard

Pass programID as argument rather than saving it in a file

Open y2kappa opened this issue 2 years ago • 13 comments

some workflows require regenerating diff program ids depending on cluster etc, would be useful to not require it to be hardcoded in a file

y2kappa avatar Jul 10 '22 10:07 y2kappa

You can always load the program ID through an env var for example. Alternatively you can generate multiple clients for different program IDs. I don't think that being able to change the program ID dynamically during the runtime is good enough reason to introduce the programID argument since in large majority of use cases it's fixed.

kklas avatar Jul 11 '22 22:07 kklas

You can always load the program ID through an env var for example

Can this be done after the code is generated? I also find myself needing to use different program ids with the same generated code, and it would be a lot easier if I could set it using the webpack/JS env. For example:

import { setProgramId } from "./codegen/programId";

ronanyeah avatar Jul 18 '22 16:07 ronanyeah

Yes, the env vars are hard-coded into the bundle by the bundler. So if you're using CRA you can do for example:

// programId.ts
...

export const PROGRAM_ID: PublicKey = new PublicKey(process.env.REACT_APP_MY_PROGRAM_ID)

And if you build your app with:

$ REACT_APP_MY_PROGRAM_ID="<...>" npx react-scripts build

the program id you've specified with REACT_APP_MY_PROGRAM_ID will be hard-coded instead of process.env.REACT_APP_MY_PROGRAM_ID.

This way you can create different bundles for mainnet, devnet, etc.

kklas avatar Jul 18 '22 18:07 kklas

Ok thanks, would be good if there was a way to avoid manually editing the file after generation, such as anchor-client-gen --program-id-env MY_PROGRAM_ID ./target/idl/app.json ./codegen, but this will do for now.

ronanyeah avatar Jul 18 '22 18:07 ronanyeah

Could be useful in some cases but I don't think it's super useful. A lot of people will probably do something like:

export const PROGRAM_ID: PublicKey = config.myProgramId

where you will have one config file with the env var logic.

Also, the PROGRAM_ID constant is not overwritten on subsequent generations so you have to edit it only the first time.

kklas avatar Jul 18 '22 18:07 kklas

Won't the importing/setup of that config module get overwritten and need to be added after every gen?

I use webpack.DefinePlugin to inject my variables, so I would have something like this:

import { PublicKey } from "@solana/web3.js";

// @ts-ignore
// eslint-disable-next-line no-undef
const MY_PROGRAM_ID: string = MY_PROGRAM_ID_;

// This constant will not get overwritten on subsequent code generations and it's safe to modify it's value.
export const PROGRAM_ID: PublicKey = new PublicKey(MY_PROGRAM_ID);

The setup lines I have in the middle are getting removed by the generator.

Maybe anchor-client-gen could have a flag to disable any programId.ts changes.

ronanyeah avatar Jul 19 '22 15:07 ronanyeah

Can't you do ''' export const PROGRAM_ID: PublicKey = new PublicKey(MY_PROGRAM_ID_); ''' ?

Either that or define all your constants in a separate ts file and import it here.

kklas avatar Jul 19 '22 16:07 kklas

The generator will strip my linting comments, and I really don't like the idea of having generated code import a project file, but whatever, I'll figure something out.

ronanyeah avatar Jul 19 '22 19:07 ronanyeah

and I really don't like the idea of having generated code import a project file

Why not? I find it quite convenient.

But also making the generator not overwrite the comment could be one thing we could do.

kklas avatar Jul 19 '22 20:07 kklas

I like the idea of generated code being a deterministic dependency of a project. So the generation command is the only thing that is required when onboarding new team members. At the moment I'm gonna have to document the various subtleties of how programId.ts behaves, what it does/doesn't overwrite, and have instructions to git revert / don't commit programId.ts changes etc.

ronanyeah avatar Jul 19 '22 20:07 ronanyeah

we need to change between devnet and mainnet which have diff program ids so this doesn't work for us ..

y2kappa avatar Jul 20 '22 15:07 y2kappa

we need to change this at runtime, so ENV doesn't work either

y2kappa avatar Jul 20 '22 15:07 y2kappa

I prefer it having a function of env which can default to devnet for example

y2kappa avatar Jul 20 '22 15:07 y2kappa

Yeah switching between different PROGRAM_IDs based on different RPCs seems like a pretty normal use case.

ronanyeah avatar Sep 16 '22 15:09 ronanyeah

Having dynamic programIds would be very helpful

JoeHowarth avatar Nov 09 '22 13:11 JoeHowarth

@ronanyeah @y2kappa @JoeHowarth will this work https://github.com/kklas/anchor-client-gen/pull/55 ?

kklas avatar Nov 09 '22 23:11 kklas

I ended up manually implementing the same thing..

y2kappa avatar Nov 28 '22 12:11 y2kappa

can we reopen? we have to maintain a forked programid.ts if we don't merge the above

y2kappa avatar Feb 10 '23 21:02 y2kappa

@y2kappa I argue that:

  1. if you have the same contract that is forked and deployed on another address, they should be treated as two different programs and codegen them separately
  2. if you want to switch between the same program but deployed on mainnet / devnet, there are other ways to work around it like REACT_APP_SOLANA_NETWORK=devnet or REACT_APP_SOLANA_NETWORK=mainnet to differentiate between program ids
  3. having the ability to switch between the program deployed on different networks via e.g. a select on the UI dynamically is not much better than doing 2) and doing npm start:devnet npm start:mainnet anyways

So not sure why there's a need to do this dynamically. It's just more complex for no benefit.

I'm not against it in general but nobody has produced strong enough arguments to convince me that this is necessary considering above points.

kklas avatar Feb 11 '23 15:02 kklas

I've created https://github.com/kklas/anchor-client-gen/pull/62 to address the issues in this PR.

If it is not accepted in this repo, feel free to use the fork at dcaf labs

sol-mocha avatar Jun 17 '23 16:06 sol-mocha

Closed with #62

kklas avatar Jun 17 '23 22:06 kklas