nothing-unencr
quadrismegistus 4 years ago
parent 616cd9134b
commit 3ba35c8906

@ -11,80 +11,86 @@ class Caller(Operator):
Variant of an Operator which handles local keys and keymaking. Variant of an Operator which handles local keys and keymaking.
""" """
def ring_ring(self,msg):
return super().ring_ring(
msg,
to_whom=self.op,
get_resp_from=self.phone.ring_ring
)
def ring_ring(self,with_msg,to_phone=None): # def ring_ring(self,msg):
# if not to_phone: to_phone=self.phone
# return super().ring_ring(msg,to_phone)
# message should be encrypted caller2caller (by Person.ring) # # message should be encrypted caller2caller (by Person.ring)
msg_encr_caller2caller = with_msg # msg_encr_caller2caller = with_msg
# Caller can only encrypt for Operator (end phone) # # Caller can only encrypt for Operator (end phone)
if not to_phone: to_phone=self.op # if not to_phone: to_phone=self.op
to_whom = to_phone # to_whom = to_phone
# ring 1: encrypt caller2phone # # ring 1: encrypt caller2phone
msg_encr_caller2caller_caller2phone = self.package_msg_to( # msg_encr_caller2caller_caller2phone = self.package_msg_to(
msg_encr_caller2caller, # msg_encr_caller2caller,
to_whom # to_whom
) # )
self.log('msg_encr_caller2caller_caller2phone',msg_encr_caller2caller_caller2phone) # self.log('msg_encr_caller2caller_caller2phone',msg_encr_caller2caller_caller2phone)
# ring 2: dial and get response # # ring 2: dial and get response
resp_msg_encr_caller2caller_caller2phone = self.phone.ring_ring( # resp_msg_encr_caller2caller_caller2phone = self.phone.ring_ring(
msg_encr_caller2caller_caller2phone # msg_encr_caller2caller_caller2phone
) # )
self.log('resp_msg_encr_caller2caller_caller2phone',resp_msg_encr_caller2caller_caller2phone) # self.log('resp_msg_encr_caller2caller_caller2phone',resp_msg_encr_caller2caller_caller2phone)
# ring 3: decrypt and send back # # ring 3: decrypt and send back
resp_msg_encr_caller2caller = self.unpackage_msg_from( # resp_msg_encr_caller2caller = self.unpackage_msg_from(
resp_msg_encr_caller2caller_caller2phone, # resp_msg_encr_caller2caller_caller2phone
to_whom # )
) # self.log('resp_msg_encr_caller2caller',resp_msg_encr_caller2caller)
self.log('resp_msg_encr_caller2caller',resp_msg_encr_caller2caller)
return resp_msg_encr_caller2caller # return resp_msg_encr_caller2caller
def get_new_keys(self, name = None, passphrase = DEBUG_DEFAULT_PASSPHRASE, is_group=None): # def get_new_keys(self, name = None, passphrase = DEBUG_DEFAULT_PASSPHRASE, is_group=None):
# get needed metadata # # get needed metadata
if not name: name=self.name # if not name: name=self.name
if name is None: # if name is None:
name = input('\nWhat is the name for this account? ') # name = input('\nWhat is the name for this account? ')
if passphrase is None: # if passphrase is None:
passphrase = getpass.getpass('\nEnter a memborable password: ') # passphrase = getpass.getpass('\nEnter a memborable password: ')
# if is_group is None: # # if is_group is None:
# is_group = input('\nIs this a group account? [y/N]').strip().lower() == 'y' # # is_group = input('\nIs this a group account? [y/N]').strip().lower() == 'y'
# form request # # form request
msg_to_op = { # msg_to_op = {
'_please':'forge_new_keys', # '_please':'forge_new_keys',
'name':name, # 'name':name,
'passphrase':hashish(passphrase.encode()) # 'passphrase':hashish(passphrase.encode())
} # }
phone_res = self.phone.ring(msg_to_op) # phone_res = self.phone.ring(msg_to_op)
# URI id # # URI id
uri_id = phone_res.get('uri_id') # uri_id = phone_res.get('uri_id')
returned_keys = phone_res.get('_keychain') # returned_keys = phone_res.get('_keychain')
self.log('got URI from Op:',uri_id) # self.log('got URI from Op:',uri_id)
self.log('got returnd keys from Op:',returned_keys) # self.log('got returnd keys from Op:',returned_keys)
stop # stop
# better have the right keys # # better have the right keys
assert set(KEYMAKER_DEFAULT_KEYS_TO_SAVE_ON_CLIENT) == set(returned_keys.keys()) # assert set(KEYMAKER_DEFAULT_KEYS_TO_SAVE_ON_CLIENT) == set(returned_keys.keys())
# now save these keys! # # now save these keys!
saved_keys = self.save_keychain(name,returned_keys,uri_id=uri_id) # saved_keys = self.save_keychain(name,returned_keys,uri_id=uri_id)
self.log('saved keys!',saved_keys) # self.log('saved keys!',saved_keys)
# better have the right keys # # better have the right keys
# assert set(KEYMAKER_DEFAULT_KEYS_TO_SAVE) == set(saved_keys.keys()) # # assert set(KEYMAKER_DEFAULT_KEYS_TO_SAVE) == set(saved_keys.keys())
# success! # # success!
self.log('yay!!!!') # self.log('yay!!!!')
return saved_keys # return saved_keys

@ -91,12 +91,13 @@ class Keymaker(Logger):
self.path_crypt_keys=path_crypt_keys self.path_crypt_keys=path_crypt_keys
self.path_crypt_data=path_crypt_data self.path_crypt_data=path_crypt_data
@property
def pubkey(self): def find_pubkey(self):
global TELEPHONE_KEYCHAIN,OPERATOR_KEYCHAIN
#self.log('keychain?',self.keychain()) #self.log('keychain?',self.keychain())
if 'pubkey' in self._keychain and self._keychain['pubkey']: if 'pubkey' in self._keychain and self._keychain['pubkey']:
return self._keychain['pubkey'] return self._keychain['pubkey']
res = self.crypt_keys.get(self.name, prefix='/pubkey/') res = self.crypt_keys.get(self.name, prefix='/pubkey/')
if res: return res if res: return res
@ -104,28 +105,39 @@ class Keymaker(Logger):
if res: return res if res: return res
self.log('I don\'t know my public key!') self.log('I don\'t know my public key!')
return None raise KomradeException(f'I don\'t know my public key!\n{self}\n{self._keychain}')
#return None
def keychain(self,look_for=KEYMAKER_DEFAULT_ALL_KEY_NAMES): def keychain(self,look_for=KEYMAKER_DEFAULT_ALL_KEY_NAMES):
# load existing keychain
keys = self._keychain #self._keychain = keys = {**self._keychain} keys = self._keychain #self._keychain = keys = {**self._keychain}
uri = self.uri_id
# make sure we have the pubkey
if not 'pubkey' in self._keychain: self._keychain['pubkey']=self.find_pubkey()
pubkey=self._keychain['pubkey']
# get uri
uri = b64encode(pubkey)
# get from cache # get from cache
for keyname in look_for: for keyname in look_for:
if keyname in keys and keys[keyname]: continue if keyname in keys and keys[keyname]: continue
# self.log('??',keyname)
key = self.crypt_keys.get(uri,prefix=f'/{keyname}/') key = self.crypt_keys.get(uri,prefix=f'/{keyname}/')
if key: keys[keyname]=key if key: keys[keyname]=key
# self.log('keys 1!',self._keychain)
# try to assemble # try to assemble
keys = self.assemble(self.assemble(keys)) keys = self.assemble(self.assemble(keys))
# self.log('keys 2!',self._keychain)
#store to existing set
self._keychain = keys
#return
return keys return keys
@property
def pubkey(self): return self.keychain().get('pubkey')
@property @property
def privkey(self): return self.keychain().get('privkey') def privkey(self): return self.keychain().get('privkey')
@property @property
@ -149,8 +161,8 @@ class Keymaker(Logger):
@property @property
def uri_id(self): def uri_id(self):
if not self._uri_id: if not self._uri_id:
if self.pubkey: pubkey = self.find_pubkey()
self._uri_id = b64encode(self.pubkey) self._uri_id = b64encode(pubkey)
return self._uri_id return self._uri_id

@ -15,7 +15,7 @@ def is_valid_msg_d(msg_d):
class Message(Logger): class Message(Logger):
def __init__(self,msg_d,caller=None,callee=None): def __init__(self,msg_d,caller=None,callee=None,messenger=None,embedded_msg=None,is_encrypted=False):
# check input # check input
if not is_valid_msg_d(msg_d): if not is_valid_msg_d(msg_d):
raise KomradeException('This is not a valid msg_d:',msg_d) raise KomradeException('This is not a valid msg_d:',msg_d)
@ -26,33 +26,80 @@ class Message(Logger):
self.from_name=msg_d.get('_from_name') self.from_name=msg_d.get('_from_name')
self.from_pubkey=msg_d.get('_from_pub') self.from_pubkey=msg_d.get('_from_pub')
self.msg=msg_d.get('_msg') self.msg=msg_d.get('_msg')
self.embedded_msg=None # only if this message has an embedded one self.embedded_msg=embedded_msg # only if this message has an embedded one
self._route=msg_d.get(ROUTE_KEYNAME) self._route=msg_d.get(ROUTE_KEYNAME)
self.caller=caller self._caller=caller
self.callee=callee self._callee=callee
self.messenger=None
self.is_encrypted=False
# get operators straight away? # get operators straight away?
if not self.caller or not self.callee: if not self.caller or not self.callee:
self.get_callers() self.get_callers()
def __repr__(self):
return f"""
<MESSAGE>
self.msg_d={self.msg_d}
self.to_name={self.to_name}
self.to_pubkey={self.to_pubkey}
self.from_name={self.from_name}
self.from_pubkey={self.from_pubkey}
self.msg={self.msg}
self.embedded_msg={self.embedded_msg}
self._route={self._route}
self._caller={self.caller}
self._callee={self.callee}
self.messenger={self.messenger}
</MESSAGE>
"""
def get_caller(self,name):
if name == OPERATOR_NAME:
return TheOperator()
if name == TELEPHONE_NAME:
return TheTelephone()
return Caller(name)
@property
def caller(self):
if not self._caller:
self._caller,self._callee = self.get_callers()
return self._caller
@property
def callee(self):
if not self._callee:
self._caller,self._callee = self.get_callers()
return self._callee
## loading messages ## loading messages
def get_callers(self,msg_d): def get_callers(self):
if self.caller is not None and self.callee is not None: if self.caller is not None and self.callee is not None:
return (self.caller,self.callee) return (self.caller,self.callee)
alleged_caller = Operator(alleged_caller_name) alleged_caller = self.get_caller(self.from_name)
alleged_callee = Operator(alleged_callee_name) alleged_callee = self.get_caller(self.to_name)
if not self.caller_records_match(msg_d,alleged_caller,alleged_callee): if not self.caller_records_match(alleged_caller,alleged_callee):
raise KomradeException('Records of callers on The Operator and the Caller do not match. Something fishy going on?') raise KomradeException('Records of callers on The Operator and the Caller do not match. Something fishy going on?')
else: else:
self.caller = alleged_caller self.caller = alleged_caller
self.callee = alleged_callee self.callee = alleged_callee
return (alleged_caller,alleged_caller) return (alleged_caller,alleged_caller)
def caller_records_match(alleged_caller,alleged_callee): def caller_records_match(self,alleged_caller,alleged_callee):
alleged_caller_name = self.from_name alleged_caller_name = self.from_name
alleged_caller_pubkey = self.from_pubkey alleged_caller_pubkey = self.from_pubkey
alleged_callee_name = self.to_name alleged_callee_name = self.to_name
alleged_callee_pubkey = msg_d.get('_to_pub') alleged_callee_pubkey = self.to_pubkey
self.log('caller names:',alleged_caller.name, alleged_caller_name)
self.log('caller pubs:',alleged_caller.pubkey, alleged_caller_pubkey)
self.log('callee names:',alleged_callee.name, alleged_callee_name)
self.log('callee pubs:',alleged_callee.pubkey, alleged_callee_pubkey)
if alleged_callee.name != alleged_callee_name: if alleged_callee.name != alleged_callee_name:
return False return False
if alleged_caller.name != alleged_caller_name: if alleged_caller.name != alleged_caller_name:
@ -63,9 +110,6 @@ class Message(Logger):
return False return False
return True return True
def is_encrypted(self):
return type(self.msg) == bytes
def decrypt(self,recursive=True): def decrypt(self,recursive=True):
# get callers # get callers
caller,callee = self.get_callers() caller,callee = self.get_callers()
@ -87,10 +131,141 @@ class Message(Logger):
return decr_msg return decr_msg
def encrypt(self,recursive=True):
"""
Assuming that a recursive message looks like this:
<MESSAGE>
self.msg_d={'_from_pub': b'UEC2\x00\x00\x00-\x10\xdcu\xc7\x03:\xb6}\xd2\x88\x93E\x88\x00\xed\xda&\x8f\xd0\x1ae\xe1\xa3\x1b=\xd6\xadBB~M\x86\xda\xd57\x8e\xb5', '_from_name': 'TheTelephone', '_to_pub': b'UEC2\x00\x00\x00-W\xbe\xc4\xa2\x02Sm\xe0\xfc\xde\x1c\xbb\xa2E\x8fy \xc7~+\xff\xd7p\xc6s\xab\xe5\xb29M/\xf24\x92\x91n0', '_to_name': 'TheOperator', '_msg': b' \'\x04&h\x00\x00\x00\x00\x01\x01@\x0c\x00\x00\x00\x10\x00\x00\x004\x00\x00\x00\x90\x1a\x88\x89\x93-\x10\xfb\x14\x10\x08M\xc0\xf2_i\x842\xa8k\xcc\xff"c\x0e"x\\"\xaf\x9c\x91>\x87\x9f|~PP\xb5\x02\x91q\\X\xd2\xbdQu\xcc\xd0A\x0b7zL)\x80\x94[\xe7+I\xf1m\x0f\xb4\x80\xc7;\x8fO7\x99\x90d_\xb2y\xc4'}
self.to_name=TheOperator
self.to_pubkey=b'UEC2\x00\x00\x00-W\xbe\xc4\xa2\x02Sm\xe0\xfc\xde\x1c\xbb\xa2E\x8fy \xc7~+\xff\xd7p\xc6s\xab\xe5\xb29M/\xf24\x92\x91n0'
self.from_name=Caller
self.from_pubkey=b'UEC2\x00\x00\x00-\x10\xdcu\xc7\x03:\xb6}\xd2\x88\x93E\x88\x00\xed\xda&\x8f\xd0\x1ae\xe1\xa3\x1b=\xd6\xadBB~M\x86\xda\xd57\x8e\xb5'
self.msg=
<MESSAGE>
self.msg_d={'_from_pub': b'UEC2\x00\x00\x00-\x10\xdcu\xc7\x03:\xb6}\xd2\x88\x93E\x88\x00\xed\xda&\x8f\xd0\x1ae\xe1\xa3\x1b=\xd6\xadBB~M\x86\xda\xd57\x8e\xb5', '_from_name': 'TheTelephone', '_to_pub': b'UEC2\x00\x00\x00-W\xbe\xc4\xa2\x02Sm\xe0\xfc\xde\x1c\xbb\xa2E\x8fy \xc7~+\xff\xd7p\xc6s\xab\xe5\xb29M/\xf24\x92\x91n0', '_to_name': 'TheOperator', '_msg': b' \'\x04&h\x00\x00\x00\x00\x01\x01@\x0c\x00\x00\x00\x10\x00\x00\x004\x00\x00\x00\x90\x1a\x88\x89\x93-\x10\xfb\x14\x10\x08M\xc0\xf2_i\x842\xa8k\xcc\xff"c\x0e"x\\"\xaf\x9c\x91>\x87\x9f|~PP\xb5\x02\x91q\\X\xd2\xbdQu\xcc\xd0A\x0b7zL)\x80\x94[\xe7+I\xf1m\x0f\xb4\x80\xc7;\x8fO7\x99\x90d_\xb2y\xc4'}
self.to_name=TheOperator
self.to_pubkey=b'UEC2\x00\x00\x00-W\xbe\xc4\xa2\x02Sm\xe0\xfc\xde\x1c\xbb\xa2E\x8fy \xc7~+\xff\xd7p\xc6s\xab\xe5\xb29M/\xf24\x92\x91n0'
self.from_name=TheTelephone
self.from_pubkey=b'UEC2\x00\x00\x00-\x10\xdcu\xc7\x03:\xb6}\xd2\x88\x93E\x88\x00\xed\xda&\x8f\xd0\x1ae\xe1\xa3\x1b=\xd6\xadBB~M\x86\xda\xd57\x8e\xb5'
self.msg=b' \'\x04&h\x00\x00\x00\x00\x01\x01@\x0c\x00\x00\x00\x10\x00\x00\x004\x00\x00\x00\x90\x1a\x88\x89\x93-\x10\xfb\x14\x10\x08M\xc0\xf2_i\x842\xa8k\xcc\xff"c\x0e"x\\"\xaf\x9c\x91>\x87\x9f|~PP\xb5\x02\x91q\\X\xd2\xbdQu\xcc\xd0A\x0b7zL)\x80\x94[\xe7+I\xf1m\x0f\xb4\x80\xc7;\x8fO7\x99\x90d_\xb2y\xc4'
self._route=None
self.caller=<komrade.backend.the_telephone.TheTelephone object at 0x7f0acfbf7e80>
self.callee=<komrade.backend.the_operator.TheOperator object at 0x7f0ac868a3c8>
self.messenger=None
</MESSAGE>
self._route=None
self.caller=<komrade.backend.the_telephone.TheTelephone object at 0x7f0acfbf7e80>
self.callee=<komrade.backend.the_operator.TheOperator object at 0x7f0ac868a3c8>
self.messenger=None
</MESSAGE>
"""
if self.is_encrypted: return
self.log(f'attempting to encrypt msg {self.msg} from {self.caller} to {self.callee}')
self.log(f'I now look like v1: {self}')
if not self.has_embedded_msg:
msg_to_encrypt = self.msg
elif recursive:
# first encrypt that message
self.msg.encrypt()
# then encrypt *that* msg's entire msg_d
msg_to_encrypt = self.msg.msg_d
# in both cases, overwrite msg
encr_msg = self.encrypt_to_send(
self.msg,
self.caller.privkey,
self.callee.pubkey
)
self.log('created an encrypted msg:',encr_msg)
self.msg_decr = self.msg
self.msg = encr_msg
self.msg_d['_msg'] = encr_msg
self.log(f'I now look like v2: {self}')
self.is_encrypted = False
## creating/encrypting/rolling up messages
def encrypt_to_send(self,msg_json,from_privkey,to_pubkey):
self.log('msg_json',msg_json)
self.log('from_privkey',from_privkey)
self.log('to_pubkey',to_pubkey)
if not msg_json or not from_privkey or not to_pubkey:
self.log('not enough info!',msg_json,from_privkey,to_pubkey)
whattttttt
return b''
self.log('packing for transmission: msg_json',type(msg_json),msg_json)
msg_b = package_for_transmission(msg_json)
self.log('packing for transmission: msg_b',type(msg_b),msg_b)
# try:
self.log('from privkey =',from_privkey)
self.log('to pubkey =',to_pubkey)
msg_encr = SMessage(
from_privkey,
to_pubkey,
).wrap(msg_b)
self.log('msg_encr',msg_encr)
# stop
return msg_encr
# except ThemisError as e:
# self.log('unable to encrypt to send!',e)
# return b''
def decrypt_from_send(self,msg_encr,from_pubkey,to_privkey):
if not msg_encr or not from_pubkey or not to_privkey:
self.log('not enough info!',msg_encr,from_pubkey,to_privkey)
return {}
try:
# decrypt
msg_b = SMessage(
to_privkey,
from_pubkey,
).unwrap(msg_encr)
# decode
self.log('msg_b??',msg_b)
msg_json = unpackage_from_transmission(msg_b)
self.log('msg_json??',msg_json)
# return
return msg_json
except ThemisError as e:
self.log('unable to decrypt from send!',e)
return {}
def package_msg_to(self,msg,another):
# otherwise send msg
msg_encr = self.encrypt_to_send(msg, self.privkey, another.pubkey)
msg_d = {
'_from_pub':self.pubkey,
'_from_name':self.name,
'_to_pub':another.pubkey,
'_to_name':another.name,
'_msg':msg_encr,
}
self.log(f'I am a {type(self)} packaging a message to {another}')
return msg_d
def unpackage_msg_from(self,msg_encr_b,another):
return self.decrypt_from_send(
msg_encr_b,
from_pubkey=another.pubkey,
to_privkey=self.privkey
)
## msg properties ## msg properties
@property
def has_embedded_msg(self): def has_embedded_msg(self):
return self.embedded_msg is not None return type(self.msg) == Message
@property @property
def messages(self): def messages(self):
@ -102,3 +277,37 @@ class Message(Logger):
def route(self): def route(self):
for msg in self.messages: for msg in self.messages:
if msg._route: return msg._route if msg._route: return msg._route
def test_msg():
phone = TheTelephone()
op = TheOperator()
pprint(op.pubkey)
print('?keychains?')
pprint(phone.pubkey)
msg={'_please':'hello_world'}
msg_d = {
'_from_pub':phone.pubkey,
'_from_name':phone.name,
'_to_pub':op.pubkey,
'_to_name':op.name,
'_msg':msg,
}
# msg_obj = Message(msg_d,caller=phone,callee=op)
# msg_obj.encrypt()
# print(msg_obj)
# print('\n\n',msg_obj.sealed)
resp_msp_obj = phone.ring_ring(msg)
print(resp_msp_obj)

@ -1,11 +1,11 @@
# internal imports # internal imports
import os,sys; sys.path.append(os.path.abspath(os.path.join(os.path.abspath(os.path.join(os.path.dirname(__file__),'..')),'..'))) import os,sys; sys.path.append(os.path.abspath(os.path.join(os.path.abspath(os.path.join(os.path.dirname(__file__),'..')),'..')))
from komrade import * from komrade import *
from komrade.backend.crypt import * # from komrade.backend.crypt import *
from komrade.backend.keymaker import * # from komrade.backend.keymaker import *
from komrade.backend.mazes import * # from komrade.backend.mazes import *
from komrade.backend.switchboard import * # from komrade.backend.switchboard import *
from komrade.backend import *
@ -16,6 +16,10 @@ class Operator(Keymaker):
path_crypt_keys=path_crypt_keys, path_crypt_data=path_crypt_data) path_crypt_keys=path_crypt_keys, path_crypt_data=path_crypt_data)
self.boot(create=False) self.boot(create=False)
# connect phonelines?
from komrade.backend.phonelines import connect_phonelines
self.operator_keychain,self.telephone_keychain,self.omega_key = connect_phonelines()
def boot(self,create=False): def boot(self,create=False):
# Do I have my keys? # Do I have my keys?
have_keys = self.exists() have_keys = self.exists()
@ -53,105 +57,67 @@ class Operator(Keymaker):
return OPERATOR return OPERATOR
def encrypt_to_send(self,msg_json,from_privkey,to_pubkey):
self.log('msg_json',msg_json) def compose_msg_to(self,msg,another):
self.log('from_privkey',from_privkey)
self.log('to_pubkey',to_pubkey)
if not msg_json or not from_privkey or not to_pubkey:
self.log('not enough info!',msg_json,from_privkey,to_pubkey)
whattttttt
return b''
self.log('packing for transmission: msg_json',type(msg_json),msg_json)
msg_b = package_for_transmission(msg_json)
self.log('packing for transmission: msg_b',type(msg_b),msg_b)
# try:
self.log('from privkey =',from_privkey)
self.log('to pubkey =',to_pubkey)
msg_encr = SMessage(
from_privkey,
to_pubkey,
).wrap(msg_b)
self.log('msg_encr',msg_encr)
# stop
return msg_encr
# except ThemisError as e:
# self.log('unable to encrypt to send!',e)
# return b''
def decrypt_from_send(self,msg_encr,from_pubkey,to_privkey):
if not msg_encr or not from_pubkey or not to_privkey:
self.log('not enough info!',msg_encr,from_pubkey,to_privkey)
return {}
try:
# decrypt
msg_b = SMessage(
to_privkey,
from_pubkey,
).unwrap(msg_encr)
# decode
self.log('msg_b??',msg_b)
msg_json = unpackage_from_transmission(msg_b)
self.log('msg_json??',msg_json)
# return
return msg_json
except ThemisError as e:
self.log('unable to decrypt from send!',e)
return {}
def package_msg_to(self,msg,another):
self.log('KEYCHAINNN ',self.keychain())
self.log('my privkey',self.privkey)
self.log('my pubkey',self.pubkey,self.keychain().get('pubkey','!!!?!!?!?!?!?'))
if not self.privkey or not self.pubkey: if not self.privkey or not self.pubkey:
self.log('why do I have no pub/privkey pair!?',self.privkey,self,self.name) raise KomradeException('why do I have no pub/privkey pair!?',self,self.name)
return b''
if not another.name or not another.pubkey: if not another.name or not another.pubkey:
self.log('why do I not know whom I\'m writing to?') raise KomradeException('why do I not know whom I\'m writing to?')
return b''
# otherwise send msg # otherwise create msg
msg_encr = self.encrypt_to_send(msg, self.privkey, another.pubkey)
msg_d = { msg_d = {
'_from_pub':self.pubkey, '_from_pub':self.pubkey,
'_from_name':self.name, '_from_name':self.name,
'_to_pub':another.pubkey, '_to_pub':another.pubkey,
'_to_name':another.name, '_to_name':another.name,
'_msg':msg_encr, '_msg':msg,
} }
self.log(f'I am a {type(self)} packaging a message to {another}') self.log(f'I am a {type(self)} packaging a message to {another}: {msg_d}')
return msg_d
from komrade.backend.messages import Message
msg_obj = Message(msg_d,caller=self,callee=another)
self.log('created msg obj:',msg_obj)
return msg_obj
def seal_msg(self,msg_obj):
# make sure encrypted
msg_obj.encrypt()
# return pure binary version of self's entire msg_d
msg_b = package_for_transmission(msg_obj.msg_d)
# encrypte by omega key
msg_b_encr = self.omega_key.encrypt(msg_b)
return msg_b_encr
def unseal_msg(self,msg_b_encr):
# decrypt by omega
msg_b = self.omega_key.decrypt(msg_b_encr)
# unpackage from transmission
msg_d = unpackage_from_transmission(msg_b)
# get message obj
msg_obj = Message(msg_d)
# decrypt msg
msg_obj.decrypt()
return msg_obj
def unpackage_msg_from(self,msg_encr_b,another): # self = caller
return self.decrypt_from_send( # towhom = phone
msg_encr_b, # bywayof = op
from_pubkey=another.pubkey, def ring_ring(self,msg,to_whom,get_resp_from=None):
to_privkey=self.privkey # get encr msg obj
) msg_obj = self.compose_msg_to(msg, to_whom)
# pass onto next person
# def ring(self,with_msg,to_whom=None,by_way_of=None):
# # ring 1: encrypt from me to 'whom' # get pure encrypted binary, sealed
# msg_encr = self.package_msg_to( msg_sealed = self.seal_msg(msg_obj)
# with_msg,
# whom # pass onto next person...
# ) if not get_resp_from: get_resp_from=to_whom.ring_ring
# self.log(f'msg_encr --> {whom} layer 1',msg_encr) resp_msg_b = get_resp_from(msg_sealed)
# # ring 2: keep ringing via mediator # unseal msg
# resp_msg_encr = by_way_of.ring( resp_msg_obj = self.unseal_msg(resp_msg_b)
# msg_encr
# ) return resp_msg_obj
# self.log('resp_msg_encr',resp_msg_encr)
# # ring 3: decrypt and send back
# resp_msg = self.unpackage_msg_from(
# resp_msg_encr,
# whom
# )
# self.log('resp_msg',resp_msg)
# return resp_msg

@ -5,39 +5,71 @@ from komrade.backend import *
class Person(Caller): class Person(Caller):
# def ring_ring(self,msg,to_whom = None):
# # if no one intended, call the operator
# #return super().ring_ring(with_msg,to_phone=self.op)
# if not to_whom: to_whom = self.op
def ring_ring(self,with_msg,to_whom = None): # # create a message, caller 2 caller
# if no one intended, call the operator # msg_obj = self.compose_msg_to(msg, to_whom)
#return super().ring_ring(with_msg,to_phone=self.op)
if not to_whom: to_whom = self.op # # ring 2: use 'Caller' class to dial and get response
# resp_msg_obj = super().ring_ring(
# msg should be unencrypted # msg_obj
msg_unencr = with_msg # )
self.log('msg_unencr',msg_unencr) # self.log('resp_msg_encr_caller2caller',resp_msg_encr_caller2caller)
# ring 1: encrypt caller2phone # # ring 3: decrypt and send back
msg_encr_caller2caller = self.package_msg_to( # resp_msg_unencr = self.unpackage_msg_from(
msg_unencr, # msg_encr_caller2caller,
to_whom # to_whom
) # )
self.log('msg_encr_caller2caller!',msg_encr_caller2caller) # self.log('resp_msg_unencr',resp_msg_encr_caller2caller)
# ring 2: use 'Caller' class to dial and get response # return resp_msg_unencr
resp_msg_encr_caller2caller = super().ring_ring(
msg_encr_caller2caller # def ring_ring(self,with_msg,to_whom = None):
) # # if no one intended, call the operator
self.log('resp_msg_encr_caller2caller',resp_msg_encr_caller2caller) # #return super().ring_ring(with_msg,to_phone=self.op)
# if not to_whom: to_whom = self.op
# ring 3: decrypt and send back
resp_msg_unencr = self.unpackage_msg_from( # # msg should be unencrypted
msg_encr_caller2caller, # msg_unencr = with_msg
to_whom # self.log('msg_unencr',msg_unencr)
# # ring 1: encrypt caller2phone
# msg_encr_caller2caller = self.package_msg_to(
# msg_unencr,
# to_whom
# )
# self.log('msg_encr_caller2caller!',msg_encr_caller2caller)
# # ring 2: use 'Caller' class to dial and get response
# resp_msg_encr_caller2caller = super().ring_ring(
# msg_encr_caller2caller
# )
# self.log('resp_msg_encr_caller2caller',resp_msg_encr_caller2caller)
# # ring 3: decrypt and send back
# resp_msg_unencr = self.unpackage_msg_from(
# msg_encr_caller2caller,
# to_whom
# )
# self.log('resp_msg_unencr',resp_msg_encr_caller2caller)
# return resp_msg_unencr
def send_msg_to(self,msg,to_whom):
return self.ring_ring(msg,to_whom)
def ring_ring(self,msg,to_whom):
return super().super().ring_ring(
msg,
to_whom,
get_resp_from=super().ring_ring
) )
self.log('resp_msg_unencr',resp_msg_encr_caller2caller)
return resp_msg_unencr
def register(self,name=None,passphrase=DEBUG_DEFAULT_PASSPHRASE, is_group=None): def register(self,name=None,passphrase=DEBUG_DEFAULT_PASSPHRASE, is_group=None):
# get needed metadata # get needed metadata
@ -52,6 +84,11 @@ class Person(Caller):
# form request to operator # form request to operator
msg_to_op = {'_please':'forge_new_keys'} msg_to_op = {'_please':'forge_new_keys'}
msg_response = self.phone.ring_ring(
msg_to_op,
self.op
)
# call and ask operator to register us # call and ask operator to register us
# for only this one! we skip straight to phone, # for only this one! we skip straight to phone,

@ -104,7 +104,7 @@ def connect_phonelines():
# globals # globals
global OMEGA_KEY,OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN global OMEGA_KEY,OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN
if OMEGA_KEY and OPERATOR_KEYCHAIN and TELEPHONE_KEYCHAIN: if OMEGA_KEY and OPERATOR_KEYCHAIN and TELEPHONE_KEYCHAIN:
return (OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN) return (OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN,OMEGA_KEY)
print('\n\n\n\nCONNECTING PHONELINES!\n\n\n\n') print('\n\n\n\nCONNECTING PHONELINES!\n\n\n\n')
@ -167,4 +167,4 @@ def connect_phonelines():
print('>>>> loaded OPERATOR_KEYCHAIN',OPERATOR_KEYCHAIN) print('>>>> loaded OPERATOR_KEYCHAIN',OPERATOR_KEYCHAIN)
print('>>>> loaded TELEPHONE_KEYCHAIN',TELEPHONE_KEYCHAIN) print('>>>> loaded TELEPHONE_KEYCHAIN',TELEPHONE_KEYCHAIN)
return (OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN) return (OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN,OMEGA_KEY)

@ -27,20 +27,13 @@ class TheOperator(Operator):
""" """
Boot up the operator. Requires knowing or setting a password of memory. Boot up the operator. Requires knowing or setting a password of memory.
""" """
# init req paths
# if not os.path.exists(PATH_OPERATOR): os.makedirs(PATH_OPERATOR)
global OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN
from komrade.backend.phonelines import connect_phonelines
if not TELEPHONE_KEYCHAIN or not OPERATOR_KEYCHAIN:
OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN = connect_phonelines()
if not passphrase: self.passphrase=passphrase=getpass.getpass('Hello, this is the Operator speaking. What is the passphrase?\n> ')
super().__init__( super().__init__(
name, name,
passphrase, passphrase,
path_crypt_keys=PATH_CRYPT_OP_KEYS, path_crypt_keys=PATH_CRYPT_OP_KEYS,
path_crypt_data=PATH_CRYPT_OP_DATA) path_crypt_data=PATH_CRYPT_OP_DATA
self._keychain = OPERATOR_KEYCHAIN )
self._keychain = self.operator_keychain
def ring(self, def ring(self,
from_caller=None, from_caller=None,
@ -79,7 +72,8 @@ class TheOperator(Operator):
# route msg back to caller # route msg back to caller
return self.route(msg_obj) return self.route(msg_obj)
def find_pubkey(self):
return self.operator_keychain['pubkey']
def send(self,encr_data_b): def send(self,encr_data_b):

@ -10,26 +10,12 @@ class TheTelephone(Operator):
API client class for Caller to interact with The Operator. API client class for Caller to interact with The Operator.
""" """
def __init__(self, caller=None): def __init__(self, caller=None):
global OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN super().__init__(name=TELEPHONE_NAME)
print('OP???',OPERATOR_KEYCHAIN)
print('PH???',TELEPHONE_KEYCHAIN)
super().__init__(
name=TELEPHONE_NAME,
path_crypt_keys=PATH_CRYPT_CA_KEYS,
path_crypt_data=PATH_CRYPT_CA_KEYS
)
if not TELEPHONE_KEYCHAIN or not OPERATOR_KEYCHAIN:
OPERATOR_KEYCHAIN,TELEPHONE_KEYCHAIN = connect_phonelines()
print('OP2???',OPERATOR_KEYCHAIN)
print('PH2???',TELEPHONE_KEYCHAIN)
# stop
self.caller=caller self.caller=caller
self._keychain = TELEPHONE_KEYCHAIN self._keychain = self.telephone_keychain
print(type(self._keychain), self._keychain)
def find_pubkey(self):
return self.telephone_keychain.get('pubkey')
def send_and_receive(self,msg): def send_and_receive(self,msg):
msg_b64_str = b64encode(msg).decode() msg_b64_str = b64encode(msg).decode()
@ -47,35 +33,13 @@ class TheTelephone(Operator):
self.log('!! error in request',ringring.status_code,ringring.text) self.log('!! error in request',ringring.status_code,ringring.text)
return None return None
def ring_ring(self,with_msg,to_whom=None): def ring_ring(self,msg):
# usually, I'm calling the operator return super().ring_ring(
if not to_whom: to_whom=self.op msg,
to_whom=self.op,
# msg usually already encrypted twice get_resp_from=self.send_and_receive
msg_encr_caller2caller_caller2phone = with_msg
# ring 1: encrypt again
msg_encr_caller2caller_caller2phone_phone2phone = self.package_msg_to(
msg_encr_caller2caller_caller2phone,
to_whom
) )
self.log('msg_encr_caller2caller_caller2phone_phone2phone !',msg_encr_caller2caller_caller2phone_phone2phone)
# ring 2: dial and get response
resp_msg_encr_caller2caller_caller2phone_phone2phone = self.send_and_receive(
msg_encr_caller2caller_caller2phone_phone2phone
)
self.log(' got back from Op: resp_msg_encr_caller2caller_caller2phone_phone2phone',resp_msg_encr_caller2caller_caller2phone_phone2phone)
# msg_encr_caller2caller_caller2phone_phone2phone: return
# ring 3: decrypt
resp_msg_encr_caller2caller_caller2phone = self.unpackage_msg_from(
resp_msg_encr_caller2caller_caller2phone_phone2phone,
to_whom
)
return resp_msg_encr_caller2caller_caller2phone
def test_call(): def test_call():
phone = TheTelephone() phone = TheTelephone()

Loading…
Cancel
Save