def transfer_ownership(general_config, actor_options, target_address, gas): """Transfer ownership of contracts to another address.""" emitter = general_config.emitter ADMINISTRATOR, _, _, _ = actor_options.create_actor(emitter) if not target_address: target_address = click.prompt(PROMPT_NEW_OWNER_ADDRESS, type=EIP55_CHECKSUM_ADDRESS) contract_name = actor_options.contract_name if not contract_name: raise click.MissingParameter(param="--contract-name", message="You need to specify an ownable contract") try: contract_deployer_class = ADMINISTRATOR.deployers[contract_name] except KeyError: message = UNKNOWN_CONTRACT_NAME.format(contract_name=contract_name, contracts=ADMINISTRATOR.ownable_deployer_classes.keys()) emitter.echo(message, color='red', bold=True) raise click.Abort() if contract_deployer_class not in ADMINISTRATOR.ownable_deployer_classes: message = CONTRACT_IS_NOT_OWNABLE.format(contract_name=contract_name) emitter.echo(message, color='red', bold=True) raise click.Abort() contract_deployer = contract_deployer_class(registry=ADMINISTRATOR.registry, deployer_address=ADMINISTRATOR.deployer_address) receipt = contract_deployer.transfer_ownership(new_owner=target_address, transaction_gas_limit=gas) paint_receipt_summary(emitter=emitter, receipt=receipt)
def contracts(general_config, actor_options, mode, activate, gas, ignore_deployed, confirmations, parameters): """Compile and deploy contracts.""" emitter = general_config.emitter ADMINISTRATOR, _, deployer_interface, local_registry = actor_options.create_actor(emitter) chain_name = deployer_interface.client.chain_name deployment_parameters = {} if parameters: with open(parameters) as json_file: deployment_parameters = json.load(json_file) contract_name = actor_options.contract_name deployment_mode = constants.__getattr__(mode.upper()) # TODO: constant sorrow try: contract_deployer_class = ADMINISTRATOR.deployers[contract_name] except KeyError: message = UNKNOWN_CONTRACT_NAME.format(contract_name=contract_name, constants=ADMINISTRATOR.deployers.keys()) emitter.echo(message, color='red', bold=True) raise click.Abort() if activate: # For the moment, only StakingEscrow can be activated staking_escrow_deployer = contract_deployer_class(registry=ADMINISTRATOR.registry, deployer_address=ADMINISTRATOR.deployer_address) if contract_name != STAKING_ESCROW_CONTRACT_NAME or not staking_escrow_deployer.ready_to_activate: raise click.BadOptionUsage(option_name="--activate", message=f"You can only activate an idle instance of {STAKING_ESCROW_CONTRACT_NAME}") escrow_address = staking_escrow_deployer._get_deployed_contract().address prompt = CONFIRM_NETWORK_ACTIVATION.format(staking_escrow_name=STAKING_ESCROW_CONTRACT_NAME, staking_escrow_address=escrow_address) click.confirm(prompt, abort=True) receipts = staking_escrow_deployer.activate(gas_limit=gas, confirmations=confirmations) for tx_name, receipt in receipts.items(): paint_receipt_summary(emitter=emitter, receipt=receipt, chain_name=chain_name, transaction_type=tx_name) return # Exit # Stage Deployment paint_staged_deployment(deployer_interface=deployer_interface, administrator=ADMINISTRATOR, emitter=emitter) # Confirm Trigger Deployment if not confirm_deployment(emitter=emitter, deployer_interface=deployer_interface): raise click.Abort() # Deploy emitter.echo(CONTRACT_DEPLOYMENT_SERIES_BEGIN_ADVISORY.format(contract_name=contract_name)) receipts, agent = ADMINISTRATOR.deploy_contract(contract_name=contract_name, gas_limit=gas, deployment_mode=deployment_mode, ignore_deployed=ignore_deployed, confirmations=confirmations, deployment_parameters=deployment_parameters) # Report paint_contract_deployment(contract_name=contract_name, contract_address=agent.contract_address, receipts=receipts, emitter=emitter, chain_name=chain_name, open_in_browser=actor_options.etherscan) # Success registry_outfile = local_registry.filepath emitter.echo(SUCCESSFUL_REGISTRY_CREATION.format(registry_outfile=registry_outfile), bold=True, color='blue')
def contracts(general_config, actor_options, mode, activate, gas, ignore_deployed, confirmations, parameters): """Compile and deploy contracts.""" emitter = general_config.emitter ADMINISTRATOR, _, deployer_interface, local_registry = actor_options.create_actor( emitter) chain_name = deployer_interface.client.chain_name deployment_parameters = {} if parameters: with open(parameters) as json_file: deployment_parameters = json.load(json_file) # # Deploy Single Contract (Amend Registry) # contract_name = actor_options.contract_name deployment_mode = constants.__getattr__( mode.upper()) # TODO: constant sorrow if contract_name: # TODO: Remove this conditional, make it the default try: contract_deployer_class = ADMINISTRATOR.deployers[contract_name] except KeyError: message = UNKNOWN_CONTRACT_NAME.format( contract_name=contract_name, constants=ADMINISTRATOR.deployers.keys()) emitter.echo(message, color='red', bold=True) raise click.Abort() if activate: # For the moment, only StakingEscrow can be activated staking_escrow_deployer = contract_deployer_class( registry=ADMINISTRATOR.registry, deployer_address=ADMINISTRATOR.deployer_address) if contract_name != STAKING_ESCROW_CONTRACT_NAME or not staking_escrow_deployer.ready_to_activate: raise click.BadOptionUsage( option_name="--activate", message= f"You can only activate an idle instance of {STAKING_ESCROW_CONTRACT_NAME}" ) escrow_address = staking_escrow_deployer._get_deployed_contract( ).address prompt = CONFIRM_NETWORK_ACTIVATION.format( staking_escrow_name=STAKING_ESCROW_CONTRACT_NAME, staking_escrow_address=escrow_address) click.confirm(prompt, abort=True) receipts = staking_escrow_deployer.activate( gas_limit=gas, confirmations=confirmations) for tx_name, receipt in receipts.items(): paint_receipt_summary(emitter=emitter, receipt=receipt, chain_name=chain_name, transaction_type=tx_name) return # Exit # Deploy emitter.echo( CONTRACT_DEPLOYMENT_SERIES_BEGIN_ADVISORY.format( contract_name=contract_name)) receipts, agent = ADMINISTRATOR.deploy_contract( contract_name=contract_name, gas_limit=gas, deployment_mode=deployment_mode, ignore_deployed=ignore_deployed, confirmations=confirmations, deployment_parameters=deployment_parameters) # Report paint_contract_deployment(contract_name=contract_name, contract_address=agent.contract_address, receipts=receipts, emitter=emitter, chain_name=chain_name, open_in_browser=actor_options.etherscan) return # Exit # # Deploy Automated Series (Create Registry) # if deployment_mode is not FULL: raise click.BadOptionUsage( option_name='--mode', message= "Only 'full' mode is supported when deploying all network contracts" ) # Confirm filesystem registry writes. if os.path.isfile(local_registry.filepath): emitter.echo(EXISTING_REGISTRY_FOR_DOMAIN.format( registry_filepath=local_registry.filepath), color='yellow') click.confirm(CONFIRM_LOCAL_REGISTRY_DESTRUCTION, abort=True) os.remove(local_registry.filepath) # Stage Deployment paint_staged_deployment(deployer_interface=deployer_interface, administrator=ADMINISTRATOR, emitter=emitter) # Confirm Trigger Deployment if not confirm_deployment(emitter=emitter, deployer_interface=deployer_interface): raise click.Abort() # Delay - Last chance to abort via KeyboardInterrupt paint_deployment_delay(emitter=emitter) # Execute Deployment deployment_receipts = ADMINISTRATOR.deploy_network_contracts( emitter=emitter, interactive=not actor_options.force, etherscan=actor_options.etherscan, ignore_deployed=ignore_deployed) # Paint outfile paths registry_outfile = local_registry.filepath emitter.echo( SUCCESSFUL_REGISTRY_CREATION.format(registry_outfile=registry_outfile), bold=True, color='blue') # Save transaction metadata receipts_filepath = ADMINISTRATOR.save_deployment_receipts( receipts=deployment_receipts) emitter.echo(SUCCESSFUL_SAVE_DEPLOY_RECEIPTS.format( receipts_filepath=receipts_filepath), color='blue', bold=True)
def upgrade(general_config, actor_options, retarget, target_address, ignore_deployed, multisig, confirmations): """Upgrade NuCypher existing proxy contract deployments.""" # # Setup # emitter = general_config.emitter ADMINISTRATOR, deployer_address, blockchain, local_registry = actor_options.create_actor(emitter, is_multisig=bool(multisig)) # FIXME: Workaround for building MultiSig TXs | NRN # # Pre-flight # contract_name = actor_options.contract_name if not contract_name: raise click.BadArgumentUsage(message="--contract-name is required when using --upgrade") try: # Check contract name exists Deployer = ADMINISTRATOR.deployers[contract_name] except KeyError: message = UNKNOWN_CONTRACT_NAME.format(contract_name=contract_name, constants=ADMINISTRATOR.deployers.keys()) emitter.echo(message, color='red', bold=True) raise click.Abort() deployer = Deployer(registry=local_registry) # Check deployer address is owner if Deployer._ownable and deployer_address != deployer.owner: # blockchain read emitter.echo(DEPLOYER_IS_NOT_OWNER.format(deployer_address=deployer_address, contract_name=contract_name, agent=deployer.make_agent())) raise click.Abort() else: emitter.echo('✓ Verified deployer address as contract owner', color='green') # # Business # if multisig: if not target_address: raise click.BadArgumentUsage(message="--multisig requires using --target-address.") if not actor_options.force: click.confirm(CONFIRM_BUILD_RETARGET_TRANSACTION.format(contract_name=contract_name, target_address=target_address), abort=True) transaction = ADMINISTRATOR.retarget_proxy(contract_name=contract_name, target_address=target_address, just_build_transaction=True, confirmations=confirmations) trustee_address = select_client_account(emitter=emitter, prompt="Select trustee address", provider_uri=actor_options.provider_uri, show_eth_balance=False, show_nu_balance=False, show_staking=False) if not actor_options.force: click.confirm(CONFIRM_SELECTED_ACCOUNT.format(address=trustee_address), abort=True) trustee = Trustee(registry=local_registry, checksum_address=trustee_address) transaction_proposal = trustee.create_transaction_proposal(transaction) message = SUCCESSFUL_RETARGET_TX_BUILT.format(contract_name=contract_name, target_address=target_address) emitter.message(message, color='green') paint_multisig_proposed_transaction(emitter, transaction_proposal) # TODO: Show decoded function too filepath = f'proposal-{trustee.multisig_agent.contract_address[:8]}-TX-{transaction_proposal.nonce}.json' transaction_proposal.write(filepath=filepath) emitter.echo(SUCCESSFUL_SAVE_MULTISIG_TX_PROPOSAL.format(filepath=filepath), color='blue', bold=True) return # Exit elif retarget: if not target_address: raise click.BadArgumentUsage(message="--target-address is required when using --retarget") if not actor_options.force: click.confirm(CONFIRM_RETARGET.format(contract_name=contract_name, target_address=target_address), abort=True) receipt = ADMINISTRATOR.retarget_proxy(contract_name=contract_name,target_address=target_address, confirmations=confirmations) message = SUCCESSFUL_RETARGET.format(contract_name=contract_name, target_address=target_address) emitter.message(message, color='green') paint_receipt_summary(emitter=emitter, receipt=receipt) return # Exit else: github_registry = establish_deployer_registry(emitter=emitter, download_registry=True, network=actor_options.network) if not actor_options.force: # Check for human verification of versioned upgrade details click.confirm(CONFIRM_BEGIN_UPGRADE.format(contract_name=contract_name), abort=True) if deployer._ownable: # Only ownable + upgradeable contracts apply verify_upgrade_details(blockchain=blockchain, registry=github_registry, deployer=deployer) # Success receipts = ADMINISTRATOR.upgrade_contract(contract_name=contract_name, ignore_deployed=ignore_deployed, confirmations=confirmations) emitter.message(SUCCESSFUL_UPGRADE.format(contract_name=contract_name), color='green') for name, receipt in receipts.items(): paint_receipt_summary(emitter=emitter, receipt=receipt) emitter.echo(REGISTRY_PUBLICATION_HINT.format(contract_name=contract_name, local_registry=local_registry, network=actor_options.network), color='blue') emitter.echo(ETHERSCAN_VERIFY_HINT.format(solc_version=SOLIDITY_COMPILER_VERSION), color='blue') return # Exit
def upgrade(general_config, actor_options, retarget, target_address, ignore_deployed, confirmations): """Upgrade NuCypher existing proxy contract deployments.""" # # Setup # emitter = general_config.emitter ADMINISTRATOR, deployer_address, blockchain, local_registry = actor_options.create_actor(emitter) # # Pre-flight # contract_name = actor_options.contract_name if not contract_name: raise click.BadArgumentUsage(message=click.style("--contract-name is required when using --upgrade", fg="red")) try: # Check contract name exists Deployer = ADMINISTRATOR.deployers[contract_name] except KeyError: message = UNKNOWN_CONTRACT_NAME.format(contract_name=contract_name, constants=ADMINISTRATOR.deployers.keys()) emitter.error(message) raise click.Abort() deployer = Deployer(registry=local_registry) # Check deployer address is owner if Deployer._ownable and deployer_address != deployer.owner: # blockchain read emitter.error(DEPLOYER_IS_NOT_OWNER.format(deployer_address=deployer_address, contract_name=contract_name, agent=deployer.make_agent())) raise click.Abort() else: emitter.echo('✓ Verified deployer address as contract owner', color='green') # # Business # if retarget: if not target_address: raise click.BadArgumentUsage(message=click.style("--target-address is required when using --retarget", fg="red")) if not actor_options.force: click.confirm(CONFIRM_RETARGET.format(contract_name=contract_name, target_address=target_address), abort=True) receipt = ADMINISTRATOR.retarget_proxy(contract_name=contract_name,target_address=target_address, confirmations=confirmations) message = SUCCESSFUL_RETARGET.format(contract_name=contract_name, target_address=target_address) emitter.message(message, color='green') paint_receipt_summary(emitter=emitter, receipt=receipt) return # Exit else: github_registry = establish_deployer_registry(emitter=emitter, download_registry=True, network=actor_options.network) if not actor_options.force: # Check for human verification of versioned upgrade details click.confirm(CONFIRM_BEGIN_UPGRADE.format(contract_name=contract_name), abort=True) if deployer._ownable: # Only ownable + upgradeable contracts apply verify_upgrade_details(blockchain=blockchain, registry=github_registry, deployer=deployer) # Success receipts = ADMINISTRATOR.upgrade_contract(contract_name=contract_name, ignore_deployed=ignore_deployed, confirmations=confirmations) emitter.message(SUCCESSFUL_UPGRADE.format(contract_name=contract_name), color='green') for name, receipt in receipts.items(): paint_receipt_summary(emitter=emitter, receipt=receipt) emitter.echo(REGISTRY_PUBLICATION_HINT.format(contract_name=contract_name, local_registry=local_registry, network=actor_options.network), color='blue') emitter.echo(ETHERSCAN_VERIFY_HINT.format(solc_version=SOLIDITY_COMPILER_VERSION), color='blue') return # Exit