Add cli deploy tests (#15116)
This commit is contained in:
parent
f85be6259b
commit
210514b136
|
@ -1554,7 +1554,7 @@ impl fmt::Display for CliUpgradeableProgram {
|
|||
pub struct CliUpgradeableBuffer {
|
||||
pub address: String,
|
||||
pub authority: String,
|
||||
pub program_len: usize,
|
||||
pub data_len: usize,
|
||||
}
|
||||
impl QuietDisplay for CliUpgradeableBuffer {}
|
||||
impl VerboseDisplay for CliUpgradeableBuffer {}
|
||||
|
@ -1565,8 +1565,8 @@ impl fmt::Display for CliUpgradeableBuffer {
|
|||
writeln_name_value(f, "Authority:", &self.authority)?;
|
||||
writeln_name_value(
|
||||
f,
|
||||
"Program Length:",
|
||||
&format!("{:?} ({:#x?}) bytes", self.program_len, self.program_len),
|
||||
"Data Length:",
|
||||
&format!("{:?} ({:#x?}) bytes", self.data_len, self.data_len),
|
||||
)?;
|
||||
Ok(())
|
||||
}
|
||||
|
|
|
@ -973,7 +973,7 @@ fn process_show(
|
|||
authority: authority_address
|
||||
.map(|pubkey| pubkey.to_string())
|
||||
.unwrap_or_else(|| "none".to_string()),
|
||||
program_len: account.data.len()
|
||||
data_len: account.data.len()
|
||||
- UpgradeableLoaderState::buffer_data_offset()?,
|
||||
}))
|
||||
} else {
|
||||
|
|
|
@ -15,7 +15,7 @@ use solana_sdk::{
|
|||
pubkey::Pubkey,
|
||||
signature::{Keypair, Signer},
|
||||
};
|
||||
use std::{fs::File, io::Read, path::PathBuf, str::FromStr};
|
||||
use std::{env, fs::File, io::Read, path::PathBuf, str::FromStr};
|
||||
|
||||
#[test]
|
||||
fn test_cli_program_deploy_non_upgradeable() {
|
||||
|
@ -438,6 +438,25 @@ fn test_cli_program_deploy_with_authority() {
|
|||
program_data[..]
|
||||
);
|
||||
|
||||
// Get upgrade authority
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Show {
|
||||
account_pubkey: Some(program_pubkey),
|
||||
});
|
||||
let response = process_command(&config);
|
||||
let json: Value = serde_json::from_str(&response.unwrap()).unwrap();
|
||||
let authority_pubkey_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("authority")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!(
|
||||
new_upgrade_authority.pubkey(),
|
||||
Pubkey::from_str(&authority_pubkey_str).unwrap()
|
||||
);
|
||||
|
||||
// Set no authority
|
||||
config.signers = vec![&keypair, &new_upgrade_authority];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::SetUpgradeAuthority {
|
||||
|
@ -506,6 +525,22 @@ fn test_cli_program_deploy_with_authority() {
|
|||
} else {
|
||||
panic!("not a buffer account");
|
||||
}
|
||||
|
||||
// Get buffer authority
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Show {
|
||||
account_pubkey: Some(program_pubkey),
|
||||
});
|
||||
let response = process_command(&config);
|
||||
let json: Value = serde_json::from_str(&response.unwrap()).unwrap();
|
||||
let authority_pubkey_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("authority")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!("none", authority_pubkey_str);
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
@ -621,6 +656,25 @@ fn test_cli_program_write_buffer() {
|
|||
program_data[..]
|
||||
);
|
||||
|
||||
// Get buffer authority
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Show {
|
||||
account_pubkey: Some(buffer_keypair.pubkey()),
|
||||
});
|
||||
let response = process_command(&config);
|
||||
let json: Value = serde_json::from_str(&response.unwrap()).unwrap();
|
||||
let authority_pubkey_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("authority")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!(
|
||||
keypair.pubkey(),
|
||||
Pubkey::from_str(&authority_pubkey_str).unwrap()
|
||||
);
|
||||
|
||||
// Specify buffer authority
|
||||
let buffer_keypair = Keypair::new();
|
||||
let authority_keypair = Keypair::new();
|
||||
|
@ -691,6 +745,25 @@ fn test_cli_program_write_buffer() {
|
|||
buffer_account.data[UpgradeableLoaderState::buffer_data_offset().unwrap()..],
|
||||
program_data[..]
|
||||
);
|
||||
|
||||
// Get buffer authority
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Show {
|
||||
account_pubkey: Some(buffer_pubkey),
|
||||
});
|
||||
let response = process_command(&config);
|
||||
let json: Value = serde_json::from_str(&response.unwrap()).unwrap();
|
||||
let authority_pubkey_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("authority")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!(
|
||||
authority_keypair.pubkey(),
|
||||
Pubkey::from_str(&authority_pubkey_str).unwrap()
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
@ -896,3 +969,253 @@ fn test_cli_program_mismatch_buffer_authority() {
|
|||
});
|
||||
process_command(&config).unwrap();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_cli_program_show() {
|
||||
solana_logger::setup();
|
||||
|
||||
let mut pathbuf = PathBuf::from(env!("CARGO_MANIFEST_DIR"));
|
||||
pathbuf.push("tests");
|
||||
pathbuf.push("fixtures");
|
||||
pathbuf.push("noop");
|
||||
pathbuf.set_extension("so");
|
||||
|
||||
let mint_keypair = Keypair::new();
|
||||
let test_validator = TestValidator::with_no_fees(mint_keypair.pubkey());
|
||||
let faucet_addr = run_local_faucet(mint_keypair, None);
|
||||
|
||||
let rpc_client =
|
||||
RpcClient::new_with_commitment(test_validator.rpc_url(), CommitmentConfig::processed());
|
||||
|
||||
let mut file = File::open(pathbuf.to_str().unwrap()).unwrap();
|
||||
let mut program_data = Vec::new();
|
||||
file.read_to_end(&mut program_data).unwrap();
|
||||
let max_len = program_data.len();
|
||||
let minimum_balance_for_buffer = rpc_client
|
||||
.get_minimum_balance_for_rent_exemption(
|
||||
UpgradeableLoaderState::programdata_len(max_len).unwrap(),
|
||||
)
|
||||
.unwrap();
|
||||
|
||||
let mut config = CliConfig::recent_for_tests();
|
||||
let keypair = Keypair::new();
|
||||
config.json_rpc_url = test_validator.rpc_url();
|
||||
config.output_format = OutputFormat::Json;
|
||||
|
||||
// Airdrop
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Airdrop {
|
||||
faucet_host: None,
|
||||
faucet_port: faucet_addr.port(),
|
||||
pubkey: None,
|
||||
lamports: 100 * minimum_balance_for_buffer,
|
||||
};
|
||||
process_command(&config).unwrap();
|
||||
|
||||
// Write a buffer
|
||||
let buffer_keypair = Keypair::new();
|
||||
let authority_keypair = Keypair::new();
|
||||
config.signers = vec![&keypair, &buffer_keypair, &authority_keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::WriteBuffer {
|
||||
program_location: pathbuf.to_str().unwrap().to_string(),
|
||||
buffer_signer_index: Some(1),
|
||||
buffer_pubkey: Some(buffer_keypair.pubkey()),
|
||||
buffer_authority_signer_index: Some(2),
|
||||
max_len: None,
|
||||
});
|
||||
process_command(&config).unwrap();
|
||||
|
||||
// Verify show
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Show {
|
||||
account_pubkey: Some(buffer_keypair.pubkey()),
|
||||
});
|
||||
let response = process_command(&config);
|
||||
let json: Value = serde_json::from_str(&response.unwrap()).unwrap();
|
||||
let address_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("address")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!(
|
||||
buffer_keypair.pubkey(),
|
||||
Pubkey::from_str(&address_str).unwrap()
|
||||
);
|
||||
let authority_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("authority")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!(
|
||||
authority_keypair.pubkey(),
|
||||
Pubkey::from_str(&authority_str).unwrap()
|
||||
);
|
||||
let data_len = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("dataLen")
|
||||
.unwrap()
|
||||
.as_u64()
|
||||
.unwrap();
|
||||
assert_eq!(max_len, data_len as usize);
|
||||
|
||||
// Deploy
|
||||
let program_keypair = Keypair::new();
|
||||
config.signers = vec![&keypair, &authority_keypair, &program_keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Deploy {
|
||||
program_location: Some(pathbuf.to_str().unwrap().to_string()),
|
||||
program_signer_index: Some(2),
|
||||
program_pubkey: Some(program_keypair.pubkey()),
|
||||
buffer_signer_index: None,
|
||||
buffer_pubkey: None,
|
||||
allow_excessive_balance: false,
|
||||
upgrade_authority_signer_index: 1,
|
||||
is_final: false,
|
||||
max_len: Some(max_len),
|
||||
});
|
||||
config.output_format = OutputFormat::JsonCompact;
|
||||
process_command(&config).unwrap();
|
||||
let slot = rpc_client.get_slot().unwrap();
|
||||
|
||||
// Verify show
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Show {
|
||||
account_pubkey: Some(program_keypair.pubkey()),
|
||||
});
|
||||
let response = process_command(&config);
|
||||
let json: Value = serde_json::from_str(&response.unwrap()).unwrap();
|
||||
let address_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("programId")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!(
|
||||
program_keypair.pubkey(),
|
||||
Pubkey::from_str(&address_str).unwrap()
|
||||
);
|
||||
let programdata_address_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("programdataAddress")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
let (programdata_pubkey, _) = Pubkey::find_program_address(
|
||||
&[program_keypair.pubkey().as_ref()],
|
||||
&bpf_loader_upgradeable::id(),
|
||||
);
|
||||
assert_eq!(
|
||||
programdata_pubkey,
|
||||
Pubkey::from_str(&programdata_address_str).unwrap()
|
||||
);
|
||||
let authority_str = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("authority")
|
||||
.unwrap()
|
||||
.as_str()
|
||||
.unwrap();
|
||||
assert_eq!(
|
||||
authority_keypair.pubkey(),
|
||||
Pubkey::from_str(&authority_str).unwrap()
|
||||
);
|
||||
let deployed_slot = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("lastDeploySlot")
|
||||
.unwrap()
|
||||
.as_u64()
|
||||
.unwrap();
|
||||
assert_eq!(slot, deployed_slot);
|
||||
let data_len = json
|
||||
.as_object()
|
||||
.unwrap()
|
||||
.get("dataLen")
|
||||
.unwrap()
|
||||
.as_u64()
|
||||
.unwrap();
|
||||
assert_eq!(max_len, data_len as usize);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_cli_program_dump() {
|
||||
solana_logger::setup();
|
||||
|
||||
let mut pathbuf = PathBuf::from(env!("CARGO_MANIFEST_DIR"));
|
||||
pathbuf.push("tests");
|
||||
pathbuf.push("fixtures");
|
||||
pathbuf.push("noop");
|
||||
pathbuf.set_extension("so");
|
||||
|
||||
let mint_keypair = Keypair::new();
|
||||
let test_validator = TestValidator::with_no_fees(mint_keypair.pubkey());
|
||||
let faucet_addr = run_local_faucet(mint_keypair, None);
|
||||
|
||||
let rpc_client =
|
||||
RpcClient::new_with_commitment(test_validator.rpc_url(), CommitmentConfig::processed());
|
||||
|
||||
let mut file = File::open(pathbuf.to_str().unwrap()).unwrap();
|
||||
let mut program_data = Vec::new();
|
||||
file.read_to_end(&mut program_data).unwrap();
|
||||
let max_len = program_data.len();
|
||||
let minimum_balance_for_buffer = rpc_client
|
||||
.get_minimum_balance_for_rent_exemption(
|
||||
UpgradeableLoaderState::programdata_len(max_len).unwrap(),
|
||||
)
|
||||
.unwrap();
|
||||
|
||||
let mut config = CliConfig::recent_for_tests();
|
||||
let keypair = Keypair::new();
|
||||
config.json_rpc_url = test_validator.rpc_url();
|
||||
config.output_format = OutputFormat::Json;
|
||||
|
||||
// Airdrop
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Airdrop {
|
||||
faucet_host: None,
|
||||
faucet_port: faucet_addr.port(),
|
||||
pubkey: None,
|
||||
lamports: 100 * minimum_balance_for_buffer,
|
||||
};
|
||||
process_command(&config).unwrap();
|
||||
|
||||
// Write a buffer
|
||||
let buffer_keypair = Keypair::new();
|
||||
let authority_keypair = Keypair::new();
|
||||
config.signers = vec![&keypair, &buffer_keypair, &authority_keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::WriteBuffer {
|
||||
program_location: pathbuf.to_str().unwrap().to_string(),
|
||||
buffer_signer_index: Some(1),
|
||||
buffer_pubkey: Some(buffer_keypair.pubkey()),
|
||||
buffer_authority_signer_index: Some(2),
|
||||
max_len: None,
|
||||
});
|
||||
process_command(&config).unwrap();
|
||||
|
||||
// Verify dump
|
||||
let mut out_file = {
|
||||
let current_exe = env::current_exe().unwrap();
|
||||
PathBuf::from(current_exe.parent().unwrap().parent().unwrap())
|
||||
};
|
||||
out_file.set_file_name("out.txt");
|
||||
config.signers = vec![&keypair];
|
||||
config.command = CliCommand::Program(ProgramCliCommand::Dump {
|
||||
account_pubkey: Some(buffer_keypair.pubkey()),
|
||||
output_location: out_file.clone().into_os_string().into_string().unwrap(),
|
||||
});
|
||||
process_command(&config).unwrap();
|
||||
|
||||
let mut file = File::open(out_file).unwrap();
|
||||
let mut out_data = Vec::new();
|
||||
file.read_to_end(&mut out_data).unwrap();
|
||||
assert_eq!(program_data.len(), out_data.len());
|
||||
for i in 0..program_data.len() {
|
||||
assert_eq!(program_data[i], out_data[i]);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue