* work on new block system, working on encryption

* added onionrvalues file for onionr requirements
* added invalidmetadata exception
master
Kevin Froman 2018-06-19 02:01:59 -05:00
parent 7864677498
commit 10ebdddb24
No known key found for this signature in database
GPG Key ID: 0D414D0FE405B63B
4 changed files with 71 additions and 38 deletions

View File

@ -28,7 +28,7 @@ class OnionrCommunicatorDaemon:
logger.warn('New (unstable) communicator is being used.') logger.warn('New (unstable) communicator is being used.')
self.timers = [] self.timers = []
self._core = core.Core() self._core = core.Core(torPort=sys.argv[2])
self.nistSaltTimestamp = 0 self.nistSaltTimestamp = 0
self.powSalt = 0 self.powSalt = 0
self.delay = 1 self.delay = 1

View File

@ -20,7 +20,7 @@
import sqlite3, os, sys, time, math, base64, tarfile, getpass, simplecrypt, hashlib, nacl, logger, json, netcontroller, math, config import sqlite3, os, sys, time, math, base64, tarfile, getpass, simplecrypt, hashlib, nacl, logger, json, netcontroller, math, config
from onionrblockapi import Block from onionrblockapi import Block
import onionrutils, onionrcrypto, onionrproofs, onionrevents as events import onionrutils, onionrcrypto, onionrproofs, onionrevents as events, onionrexceptions, onionrvalues
if sys.version_info < (3, 6): if sys.version_info < (3, 6):
try: try:
@ -30,7 +30,7 @@ if sys.version_info < (3, 6):
sys.exit(1) sys.exit(1)
class Core: class Core:
def __init__(self): def __init__(self, torPort=0):
''' '''
Initialize Core Onionr library Initialize Core Onionr library
''' '''
@ -44,6 +44,7 @@ class Core:
self.bootstrapFileLocation = 'static-data/bootstrap-nodes.txt' self.bootstrapFileLocation = 'static-data/bootstrap-nodes.txt'
self.bootstrapList = [] self.bootstrapList = []
self.requirements = onionrvalues.OnionrValues()
if not os.path.exists('data/'): if not os.path.exists('data/'):
os.mkdir('data/') os.mkdir('data/')
@ -659,11 +660,49 @@ class Core:
conn.close() conn.close()
return True return True
def insertBlock(self, data, header='txt', sign=False, metadata = {}): def insertBlock(self, data, header='txt', sign=False, encryptType='', symKey='', asymPeer='', meta = {}):
''' '''
Inserts a block into the network Inserts a block into the network
encryptType must be specified to encrypt a block
''' '''
try:
data.decode()
except AttributeError:
data = data.encode()
retData = ''
signature = ''
signer = ''
# only use header if not set in provided meta
try:
meta['type']
except KeyError:
meta['type'] = header # block type
jsonMeta = json.dumps(meta)
if encryptType in ('asym', 'sym'):
metadata['encryptType'] = encryptType
else:
raise onionrexceptions.InvalidMetadata('encryptType must be asym or sym')
# sign before encrypt, as unauthenticated crypto should not be a problem here
if sign:
signature = self._crypto.edSign(jsonMeta + data, key=self._crypto.privKey, encodeResult=True)
signer = self._crypto.pubKeyHashID()
if len(jsonMeta) > 1000:
raise onionrexceptions.InvalidMetadata('meta in json encoded form must not exceed 1000 bytes')
if encryptType == 'sym':
if len(symKey) < self.requirements.passwordLength:
raise onionrexceptions.SecurityError('Weak encryption key')
jsonMeta = self._crypto.symmetricEncrypt(jsonMeta, key=symKey, returnEncoded=True)
metadata['meta'] = jsonMeta
powProof = onionrproofs.POW(data) powProof = onionrproofs.POW(data)
powToken = '' powToken = ''
# wait for proof to complete # wait for proof to complete
@ -685,41 +724,7 @@ class Core:
powProof.shutdown() powProof.shutdown()
return '' return ''
try:
data.decode()
except AttributeError:
data = data.encode()
retData = ''
metadata['type'] = header
metadata['powRandomToken'] = powToken
sig = {}
metadata = json.dumps(metadata)
metadata = metadata.encode()
signature = ''
if sign:
signature = self._crypto.edSign(metadata + b'\n' + data, self._crypto.privKey, encodeResult=True)
ourID = self._crypto.pubKeyHashID()
# Convert from bytes on some py versions?
try:
ourID = ourID.decode()
except AttributeError:
pass
metadata = {'sig': signature, 'meta': metadata.decode()}
metadata = json.dumps(metadata)
metadata = metadata.encode()
if len(data) == 0:
logger.error('Will not insert empty block')
else:
addedHash = self.setData(metadata + b'\n' + data)
self.addToBlockDB(addedHash, selfInsert=True)
self.setBlockType(addedHash, header)
retData = addedHash
return retData return retData
def introduceNode(self): def introduceNode(self):

View File

@ -26,6 +26,10 @@ class Unknown(Exception):
class Invalid(Exception): class Invalid(Exception):
pass pass
# block exceptions
class InvalidMetadata(Exception):
pass
# network level exceptions # network level exceptions
class MissingPort(Exception): class MissingPort(Exception):
pass pass

24
onionr/onionrvalues.py Normal file
View File

@ -0,0 +1,24 @@
'''
Onionr - P2P Microblogging Platform & Social network
This file defines values and requirements used by Onionr
'''
'''
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
'''
class OnionrValues:
def __init__(self):
self.passwordLength = 20
self.blockMetadataLengths = {'meta': 1000, 'sig': 88, 'signer': 64, 'time': 10, 'powRandomToken': '1000'}