Multi-Signature Wallets and Security
Source:vignettes/multi-signature-wallets.Rmd
multi-signature-wallets.RmdIntroduction
In this guide, we will explore how to generate key pairs, create multi-signature addresses, and use digital signatures to verify the authenticity of messages.
library(multichainr)
# Set the path to your MultiChain binaries
mc_set_path(Sys.getenv("MULTICHAIN_PATH"))1. Node Initialization
As with any MultiChain project, we begin by initializing a local node.
chain_name <- "crypto_demo_chain"
# Create and start the node
mc_node_init(chain_name)
mc_node_start(chain_name)
# Wait for the node to initialize
Sys.sleep(3)
# Connect to the local node
config <- mc_get_config(chain_name)
conn <- mc_connect(config)2. Generating Key Pairs
MultiChain allows you to generate public/private key pairs that are not stored in the node’s wallet. These are useful for creating “cold storage” or for participants who manage their own keys externally.
# Generate three unique key pairs
key_set <- mc_create_keypairs(conn, count = 3)
# View the generated keys (address, pubkey, and the secret privkey)
print(key_set)
# For clarity, let's extract the public keys
public_keys <- key_set$pubkey3. Creating a Multi-Signature Address
We will now create a 2-of-3 multi-signature address. This address will be a Pay-to-Script-Hash (P2SH) address that requires two signatures to authorize spending.
# Create the multisig address and add it to the node's wallet
multisig_addr <- mc_add_multisig_address(conn,
n_required = 2,
keys = public_keys)
cat("The new 2-of-3 multisig address is:", multisig_addr, "\n")
# Validate the address to see its properties
info <- mc_validate_address(conn, multisig_addr)
print(info)4. Granting Permissions to Multisig
Even though a multisig address requires multiple signatures, the network treats it as a standard entity for permissions. We can grant it the right to receive and send assets.
# Grant 'receive' and 'send' permissions to the multisig address
mc_grant(conn, multisig_addr, "receive,send")
# Verify the permissions
all_perms <- mc_list_permissions(conn, "*")
multisig_perms <- all_perms[all_perms$address == multisig_addr, ]
print(multisig_perms)5. Cryptographic Message Signing
Digital signatures are used to prove that a specific message was written by the owner of a private key. This is done without revealing the private key itself.
# 1. Pick one of the generated private keys to sign a message
my_privkey <- key_set$privkey[1]
my_address <- key_set$address[1]
message <- "This is a secure contract signed via R."
# 2. Sign the message
signature <- mc_sign_message(conn, my_privkey, message)
cat("Generated Signature:", signature, "\n")
# 3. Verify the message
# Anyone with the public address and the signature can verify the message
is_valid <- mc_verify_message(conn, my_address, signature, message)
if (is_valid) {
print("The signature is authentic and verified!")
} else {
print("Signature verification failed.")
}6. Cleanup
Shut down the node and remove the temporary data.
# Stop the node
mc_node_stop(conn)
Sys.sleep(2)
# Determine data directory
if (.Platform$OS.type == "windows") {
base_dir <- file.path(Sys.getenv("APPDATA"), "MultiChain")
} else if (Sys.info()["sysname"] == "Darwin") {
base_dir <- file.path(Sys.getenv("HOME"), "Library/Application Support/MultiChain")
} else {
base_dir <- file.path(Sys.getenv("HOME"), ".multichain")
}
chain_dir <- file.path(base_dir, chain_name)
if (dir.exists(chain_dir)) {
unlink(chain_dir, recursive = TRUE)
}Summary
In this vignette, we demonstrated how to:
-
Generate Keys: Using
mc_create_keypairsfor external key management. -
Multisig Setup: Creating a 2-of-3 P2SH address with
mc_add_multisig_address. -
Audit and Validate: Inspecting address properties
with
mc_validate_address. -
Cryptography: Proving ownership and agreement
through
mc_sign_messageandmc_verify_message.