Move PRE examples to their own subfolder.

Update .gitignore appropriately.
pull/3258/head
derekpierre 2023-09-28 11:48:51 -04:00
parent 99d2bd86ae
commit 8ac2af0272
10 changed files with 67 additions and 64 deletions

8
.gitignore vendored
View File

@ -27,10 +27,10 @@ chains
.ethash
nucypher_cli/examples/examples-runtime-cruft/*
nucypher_cli/examples/finnegans-wake.txt
examples/heartbeat_demo/*.json
examples/heartbeat_demo/*.msgpack
examples/heartbeat_demo/doctor-files/
examples/heartbeat_demo/alicia-files/
examples/pre/heartbeat_demo/*.json
examples/pre/heartbeat_demo/*.msgpack
examples/pre/heartbeat_demo/doctor-files/
examples/pre/heartbeat_demo/alicia-files/
mypy_reports/
reports/
test-*

View File

@ -17,27 +17,26 @@ from nucypher.utilities.logging import GlobalLoggerSettings
# Boring setup stuff #
######################
LOG_LEVEL = 'info'
LOG_LEVEL = "info"
GlobalLoggerSettings.set_log_level(log_level_name=LOG_LEVEL)
GlobalLoggerSettings.start_console_logging()
BOOK_PATH = Path('finnegans-wake-excerpt.txt')
BOOK_PATH = Path("finnegans-wake-excerpt.txt")
try:
# Replace with ethereum RPC endpoint
L1_PROVIDER = os.environ['DEMO_L1_PROVIDER_URI']
L2_PROVIDER = os.environ['DEMO_L2_PROVIDER_URI']
L1_PROVIDER = os.environ["DEMO_L1_PROVIDER_URI"]
L2_PROVIDER = os.environ["DEMO_L2_PROVIDER_URI"]
# Replace with wallet filepath.
WALLET_FILEPATH = os.environ['DEMO_L2_WALLET_FILEPATH']
SIGNER_URI = f'keystore://{WALLET_FILEPATH}'
WALLET_FILEPATH = os.environ["DEMO_L2_WALLET_FILEPATH"]
SIGNER_URI = f"keystore://{WALLET_FILEPATH}"
# Replace with alice's ethereum address
ALICE_ADDRESS = os.environ['DEMO_ALICE_ADDRESS']
ALICE_ADDRESS = os.environ["DEMO_ALICE_ADDRESS"]
except KeyError:
raise RuntimeError('Missing environment variables to run demo.')
raise RuntimeError("Missing environment variables to run demo.")
print("\n************** Setup **************\n")
@ -76,13 +75,14 @@ connect_web3_provider(eth_provider_uri=L2_PROVIDER)
# WARNING: Never give your mainnet password or mnemonic phrase to anyone.
# Do not use mainnet keys, create a dedicated software wallet to use for this demo.
wallet = Signer.from_signer_uri(SIGNER_URI)
password = os.environ.get('DEMO_ALICE_PASSWORD') or getpass(f"Enter password to unlock Alice's wallet ({ALICE_ADDRESS[:8]}): ")
password = os.environ.get("DEMO_ALICE_PASSWORD") or getpass(
f"Enter password to unlock Alice's wallet ({ALICE_ADDRESS[:8]}): "
)
wallet.unlock_account(account=ALICE_ADDRESS, password=password)
# This is Alice's PRE payment method.
pre_payment_method = SubscriptionManagerPayment(
network=L2_NETWORK,
eth_provider=L2_PROVIDER
network=L2_NETWORK, eth_provider=L2_PROVIDER
)
# This is Alice.
@ -121,7 +121,8 @@ price = alice.pre_payment_method.quote(expiration=expiration.epoch, shares=share
# Alice grants access to Bob...
policy = alice.grant(
remote_bob, label,
remote_bob,
label,
threshold=threshold,
shares=shares,
value=price,
@ -142,13 +143,12 @@ del alice
# Now that Bob has access to the policy, let's show how Enrico the Encryptor
# can share data with the members of this Policy and then how Bob retrieves it.
with open(BOOK_PATH, 'rb') as file:
with open(BOOK_PATH, "rb") as file:
finnegans_wake = file.readlines()
print("\n************** Encrypt and Retrieve **************\n")
for counter, plaintext in enumerate(finnegans_wake):
# Enrico knows the policy's public key from a side-channel.
# In this demo a new enrico is being constructed for each line of text.
# This demonstrates how many individual encryptors may encrypt for a single policy.
@ -166,9 +166,11 @@ for counter, plaintext in enumerate(finnegans_wake):
###############
# Now Bob can retrieve the original message by requesting re-encryption from nodes.
cleartexts = bob.retrieve_and_decrypt([message_kit],
alice_verifying_key=alice_verifying_key,
encrypted_treasure_map=policy.treasure_map)
cleartexts = bob.retrieve_and_decrypt(
[message_kit],
alice_verifying_key=alice_verifying_key,
encrypted_treasure_map=policy.treasure_map,
)
# We show that indeed this is the passage originally encrypted by Enrico.
assert plaintext == cleartexts[0]

View File

@ -34,29 +34,28 @@ from nucypher.utilities.logging import GlobalLoggerSettings
# Boring setup stuff #
######################
LOG_LEVEL = 'info'
LOG_LEVEL = "info"
GlobalLoggerSettings.set_log_level(log_level_name=LOG_LEVEL)
GlobalLoggerSettings.start_console_logging()
TEMP_ALICE_DIR = Path('/', 'tmp', 'heartbeat-demo-alice')
TEMP_ALICE_DIR = Path("/", "tmp", "heartbeat-demo-alice")
POLICY_FILENAME = "policy-metadata.json"
shutil.rmtree(TEMP_ALICE_DIR, ignore_errors=True)
try:
# Replace with ethereum RPC endpoint
L1_PROVIDER = os.environ['DEMO_L1_PROVIDER_URI']
L2_PROVIDER = os.environ['DEMO_L2_PROVIDER_URI']
L1_PROVIDER = os.environ["DEMO_L1_PROVIDER_URI"]
L2_PROVIDER = os.environ["DEMO_L2_PROVIDER_URI"]
# Replace with wallet filepath.
WALLET_FILEPATH = os.environ['DEMO_L2_WALLET_FILEPATH']
SIGNER_URI = f'keystore://{WALLET_FILEPATH}'
WALLET_FILEPATH = os.environ["DEMO_L2_WALLET_FILEPATH"]
SIGNER_URI = f"keystore://{WALLET_FILEPATH}"
# Replace with alice's ethereum address
ALICE_ADDRESS = os.environ['DEMO_ALICE_ADDRESS']
ALICE_ADDRESS = os.environ["DEMO_ALICE_ADDRESS"]
except KeyError:
raise RuntimeError('Missing environment variables to run demo.')
raise RuntimeError("Missing environment variables to run demo.")
L1_NETWORK = "lynx"
L2_NETWORK = "mumbai"
@ -74,13 +73,14 @@ connect_web3_provider(eth_provider_uri=L2_PROVIDER) # Connect to the layer 2 pr
# WARNING: Never give your mainnet password or mnemonic phrase to anyone.
# Do not use mainnet keys, create a dedicated software wallet to use for this demo.
wallet = Signer.from_signer_uri(SIGNER_URI)
password = os.environ.get('DEMO_ALICE_PASSWORD') or getpass(f"Enter password to unlock Alice's wallet ({ALICE_ADDRESS[:8]}): ")
password = os.environ.get("DEMO_ALICE_PASSWORD") or getpass(
f"Enter password to unlock Alice's wallet ({ALICE_ADDRESS[:8]}): "
)
wallet.unlock_account(account=ALICE_ADDRESS, password=password)
# This is Alice's PRE payment method.
pre_payment_method = SubscriptionManagerPayment(
network=L2_NETWORK,
eth_provider=L2_PROVIDER
network=L2_NETWORK, eth_provider=L2_PROVIDER
)
# This is Alicia.
@ -101,7 +101,7 @@ alicia.start_learning_loop(now=True)
# At this point, Alicia is fully operational and can create policies.
# The Policy Label is a bytestring that categorizes the data that Alicia wants to share.
# Note: we add some random chars to create different policies, only for demonstration purposes
label = "heart-data-❤️-"+os.urandom(4).hex()
label = "heart-data-❤️-" + os.urandom(4).hex()
label = label.encode()
# Alicia can create the public key associated to the policy label,
@ -121,9 +121,7 @@ print(
# heart rate measurements from a heart monitor
import heart_monitor # noqa: E402
heart_monitor.generate_heart_rate_samples(policy_pubkey,
samples=50,
save_as_file=True)
heart_monitor.generate_heart_rate_samples(policy_pubkey, samples=50, save_as_file=True)
# Alicia now wants to share data associated with this label.
@ -149,11 +147,13 @@ threshold, shares = 2, 3
# With this information, Alicia creates a policy granting access to Bob.
# The policy is sent to the TACo Application on the Threshold Network.
print("Creating access policy for the Doctor...")
policy = alicia.grant(bob=doctor_strange,
label=label,
threshold=threshold,
shares=shares,
expiration=policy_end_datetime)
policy = alicia.grant(
bob=doctor_strange,
label=label,
threshold=threshold,
shares=shares,
expiration=policy_end_datetime,
)
print("Done!")
# For the demo, we need a way to share with Bob some additional info
@ -162,9 +162,9 @@ policy_info = {
"policy_pubkey": policy.public_key.to_compressed_bytes().hex(),
"alice_sig_pubkey": bytes(alicia.stamp).hex(),
"label": label.decode("utf-8"),
"treasure_map": base64.b64encode(bytes(policy.treasure_map)).decode()
"treasure_map": base64.b64encode(bytes(policy.treasure_map)).decode(),
}
filename = POLICY_FILENAME
with open(filename, 'w') as f:
with open(filename, "w") as f:
json.dump(policy_info, f)

View File

@ -51,7 +51,7 @@ doctor = Bob(
print("Doctor = ", doctor)
# Let's join the policy generated by Alicia. We just need some info about it.
with open("policy-metadata.json", 'r') as f:
with open("policy-metadata.json", "r") as f:
policy_data = json.load(f)
policy_pubkey = PublicKey.from_compressed_bytes(
@ -61,14 +61,16 @@ alices_sig_pubkey = PublicKey.from_compressed_bytes(
bytes.fromhex(policy_data["alice_sig_pubkey"])
)
label = policy_data["label"].encode()
treasure_map = EncryptedTreasureMap.from_bytes(base64.b64decode(policy_data["treasure_map"].encode()))
treasure_map = EncryptedTreasureMap.from_bytes(
base64.b64decode(policy_data["treasure_map"].encode())
)
# The Doctor can retrieve encrypted data which he can decrypt with his private key.
# But first we need some encrypted data!
# Let's read the file produced by the heart monitor and unpack the MessageKits,
# which are the individual ciphertexts.
data = msgpack.load(open("heart_data.msgpack", "rb"), raw=False)
message_kits = (MessageKit.from_bytes(k) for k in data['kits'])
message_kits = (MessageKit.from_bytes(k) for k in data["kits"])
# Now he can ask the TACo nodes on the Threshold Network
# to get a re-encrypted version of each MessageKit.
@ -77,7 +79,7 @@ for message_kit in message_kits:
retrieved_plaintexts = doctor.retrieve_and_decrypt(
[message_kit],
alice_verifying_key=alices_sig_pubkey,
encrypted_treasure_map=treasure_map
encrypted_treasure_map=treasure_map,
)
end = timer()
@ -85,8 +87,8 @@ for message_kit in message_kits:
# Now we can get the heart rate and the associated timestamp,
# generated by the heart rate monitor.
heart_rate = plaintext['heart_rate']
timestamp = maya.MayaDT(plaintext['timestamp'])
heart_rate = plaintext["heart_rate"]
timestamp = maya.MayaDT(plaintext["timestamp"])
# This code block simply pretty prints the heart rate info
terminal_size = shutil.get_terminal_size().columns

View File

@ -3,8 +3,8 @@ from pathlib import Path
from nucypher_core.umbral import PublicKey, SecretKey
DOCTOR_PUBLIC_JSON = Path('doctor.public.json')
DOCTOR_PRIVATE_JSON = Path('doctor.private.json')
DOCTOR_PUBLIC_JSON = Path("doctor.public.json")
DOCTOR_PRIVATE_JSON = Path("doctor.private.json")
def generate_doctor_keys():
@ -16,7 +16,7 @@ def generate_doctor_keys():
"sig": sig_privkey.to_be_bytes().hex(),
}
with open(DOCTOR_PRIVATE_JSON, 'w') as f:
with open(DOCTOR_PRIVATE_JSON, "w") as f:
json.dump(doctor_privkeys, f)
enc_pubkey = enc_privkey.public_key()
@ -25,7 +25,7 @@ def generate_doctor_keys():
"enc": enc_pubkey.to_compressed_bytes().hex(),
"sig": sig_pubkey.to_compressed_bytes().hex(),
}
with open(DOCTOR_PUBLIC_JSON, 'w') as f:
with open(DOCTOR_PUBLIC_JSON, "w") as f:
json.dump(doctor_pubkeys, f)

View File

Before

Width:  |  Height:  |  Size: 677 KiB

After

Width:  |  Height:  |  Size: 677 KiB

View File

@ -5,12 +5,12 @@ import msgpack
from nucypher.characters.lawful import Enrico
HEART_DATA_FILENAME = 'heart_data.msgpack'
HEART_DATA_FILENAME = "heart_data.msgpack"
def generate_heart_rate_samples(policy_pubkey,
samples: int = 500,
save_as_file: bool = False):
def generate_heart_rate_samples(
policy_pubkey, samples: int = 500, save_as_file: bool = False
):
data_source = Enrico(encrypting_key=policy_pubkey)
heart_rate = 80
@ -20,13 +20,12 @@ def generate_heart_rate_samples(policy_pubkey,
for _ in range(samples):
# Simulated heart rate data
# Normal resting heart rate for adults: between 60 to 100 BPM
heart_rate = random.randint(max(60, heart_rate-5),
min(100, heart_rate+5))
heart_rate = random.randint(max(60, heart_rate - 5), min(100, heart_rate + 5))
now += 3
heart_rate_data = {
'heart_rate': heart_rate,
'timestamp': now,
"heart_rate": heart_rate,
"timestamp": now,
}
plaintext = msgpack.dumps(heart_rate_data, use_bin_type=True)
@ -36,7 +35,7 @@ def generate_heart_rate_samples(policy_pubkey,
kits.append(kit_bytes)
data = {
'kits': kits,
"kits": kits,
}
if save_as_file: