def __init__(self, config=None): ApplicationSession.__init__(self, config) # FIXME self._default_gas = 100000 self._chain_id = 4 profile = config.extra['profile'] if 'ethkey' in config.extra and config.extra['ethkey']: self._ethkey_raw = config.extra['ethkey'] else: self._ethkey_raw = profile.ethkey self._ethkey = eth_keys.keys.PrivateKey(self._ethkey_raw) self._ethadr = web3.Web3.toChecksumAddress(self._ethkey.public_key.to_canonical_address()) self._ethadr_raw = binascii.a2b_hex(self._ethadr[2:]) self.log.info('Client Ethereum key loaded, public address is {adr}', func=hltype(self.__init__), adr=hlid(self._ethadr)) if 'cskey' in config.extra and config.extra['cskey']: cskey = config.extra['cskey'] else: cskey = profile.cskey self._key = cryptosign.SigningKey.from_key_bytes(cskey) self.log.info('Client WAMP authentication key loaded, public key is {pubkey}', func=hltype(self.__init__), pubkey=hlid('0x' + self._key.public_key())) self._running = True
def authenticate(realm, authid, details): self.log.info( '{func}(realm="{realm}", authid="{authid}", details=details)', func=authenticate, realm=hlid(realm), authid=hlid(authid), details=details) return 'anonymous'
async def onJoin(self, details): self.log.info( 'Ok, client joined on realm "{realm}" [session={session}, authid="{authid}", authrole="{authrole}"]', realm=hlid(details.realm), session=hlid(details.session), authid=hlid(details.authid), authrole=hlid(details.authrole), details=details) if 'ready' in self.config.extra: txaio.resolve(self.config.extra['ready'], (self, details))
async def _do_get_actor(self, market_oid, actor_adr): is_member = await self.call('network.xbr.console.is_member', actor_adr) if is_member: actor = await self.call('network.xbr.console.get_member_by_wallet', actor_adr) actor_oid = uuid.UUID(bytes=actor['oid']) actor_adr = web3.Web3.toChecksumAddress(actor['address']) actor_level = actor['level'] actor_balance_eth = web3.Web3.fromWei(unpack_uint256(actor['balance']['eth']), 'ether') actor_balance_xbr = web3.Web3.fromWei(unpack_uint256(actor['balance']['xbr']), 'ether') self.log.info('Found member with address {member_adr} (member level {member_level}, balances: {member_balance_eth} ETH, {member_balance_xbr} XBR)', member_adr=hlid(actor_adr), member_level=hlval(actor_level), member_balance_eth=hlval(actor_balance_eth), member_balance_xbr=hlval(actor_balance_xbr)) if market_oid: market_oids = [market_oid.bytes] else: market_oids = await self.call('network.xbr.console.get_markets_by_actor', actor_oid.bytes) if market_oids: for market_oid in market_oids: # market = await self.call('network.xbr.console.get_market', market_oid) result = await self.call('network.xbr.console.get_actor_in_market', market_oid, actor['address']) for actor in result: actor['actor'] = web3.Web3.toChecksumAddress(actor['actor']) actor['timestamp'] = np.datetime64(actor['timestamp'], 'ns') actor['joined'] = unpack_uint256(actor['joined']) if actor['joined'] else None actor['market'] = uuid.UUID(bytes=actor['market']) actor['security'] = web3.Web3.fromWei(unpack_uint256(actor['security']), 'ether') if actor['security'] else None actor['signature'] = '0x' + binascii.b2a_hex(actor['signature']).decode() if actor['signature'] else None actor['tid'] = '0x' + binascii.b2a_hex(actor['tid']).decode() if actor['tid'] else None actor_type = actor['actor_type'] ACTOR_TYPE_TO_STR = { # Actor is a XBR Provider. 1: 'PROVIDER', # Actor is a XBR Consumer. 2: 'CONSUMER', # Actor is both a XBR Provider and XBR Consumer. 3: 'PROVIDER_CONSUMER', } actor['actor_type'] = ACTOR_TYPE_TO_STR.get(actor_type, None) self.log.info('Actor is joined to market {market_oid}:\n\n{actor}\n', market_oid=hlid(uuid.UUID(bytes=market_oid)), actor=pformat(actor)) else: self.log.info('Member is not yet actor in any market!') else: self.log.warn('Address 0x{member_adr} is not a member in the XBR network', member_adr=binascii.b2a_hex(actor_adr).decode())
def onConnect(self): if self.config.realm == 'xbrnetwork': authextra = { 'pubkey': self._key.public_key(), 'trustroot': None, 'challenge': None, 'channel_binding': 'tls-unique' } self.log.info('Client connected, now joining realm "{realm}" with WAMP-cryptosign authentication ..', realm=hlid(self.config.realm)) self.join(self.config.realm, authmethods=['cryptosign'], authextra=authextra) else: self.log.info('Client connected, now joining realm "{realm}" (no authentication) ..', realm=hlid(self.config.realm)) self.join(self.config.realm)
async def onJoin(self, details): self.log.info('Ok, client joined on realm "{realm}" [session={session}, authid="{authid}", authrole="{authrole}"]', realm=hlid(details.realm), session=hlid(details.session), authid=hlid(details.authid), authrole=hlid(details.authrole), details=details) try: if details.realm == 'xbrnetwork': await self._do_xbrnetwork_realm(details) else: await self._do_market_realm(details) except Exception as e: self.log.failure() self.config.extra['error'] = e finally: self.leave()
async def _do_get_market(self, member_oid, market_oid): member_data = await self.call('network.xbr.console.get_member', member_oid.bytes) member_adr = member_data['address'] market = await self.call('network.xbr.console.get_market', market_oid.bytes) if market: if market['owner'] == member_adr: self.log.info('You are market owner (operator)!') else: self.log.info('Marked is owned by {owner}', owner=hlid(web3.Web3.toChecksumAddress(market['owner']))) market['market'] = uuid.UUID(bytes=market['market']) market['owner'] = web3.Web3.toChecksumAddress(market['owner']) market['maker'] = web3.Web3.toChecksumAddress(market['maker']) market['coin'] = web3.Web3.toChecksumAddress(market['coin']) market['timestamp'] = np.datetime64(market['timestamp'], 'ns') self.log.info('Market {market_oid} information:\n\n{market}\n', market_oid=hlid(market_oid), market=pformat(market)) else: self.log.warn('No market {market_oid} found!', market_oid=hlid(market_oid))
def get_member(self, ethadr_raw): if self.is_attached(): is_member = yield self.call('xbr.network.is_member', ethadr_raw) if is_member: member_data = yield self.call( 'xbr.network.get_member_by_wallet', ethadr_raw) member_data['address'] = web3.Web3.toChecksumAddress( member_data['address']) member_data['oid'] = uuid.UUID(bytes=member_data['oid']) member_data['balance']['eth'] = web3.Web3.fromWei( unpack_uint256(member_data['balance']['eth']), 'ether') member_data['balance']['xbr'] = web3.Web3.fromWei( unpack_uint256(member_data['balance']['xbr']), 'ether') member_data['created'] = np.datetime64(member_data['created'], 'ns') member_level = member_data['level'] member_data['level'] = { # Member is active. 1: 'ACTIVE', # Member is active and verified. 2: 'VERIFIED', # Member is retired. 3: 'RETIRED', # Member is subject to a temporary penalty. 4: 'PENALTY', # Member is currently blocked and cannot current actively participate in the market. 5: 'BLOCKED', }.get(member_level, None) self.log.info( 'Member {member_oid} found for address 0x{member_adr} - current member level {member_level}', member_level=hlval(member_data['level']), member_oid=hlid(member_data['oid']), member_adr=hlval(member_data['address'])) return member_data else: self.log.warn( 'Address {output_ethadr} is not a member in the XBR network', output_ethadr=ethadr_raw) else: self.log.warn( 'not connected: could not retrieve member data for address {output_ethadr}', output_ethadr=ethadr_raw)
def _main(): parser = argparse.ArgumentParser() parser.add_argument('command', type=str, choices=_COMMANDS, const='noop', nargs='?', help='Command to run') parser.add_argument('-d', '--debug', action='store_true', help='Enable debug output.') parser.add_argument('--url', dest='url', type=str, default='wss://planet.xbr.network/ws', help='The router URL (default: "wss://planet.xbr.network/ws").') parser.add_argument('--realm', dest='realm', type=str, default='xbrnetwork', help='The realm to join (default: "xbrnetwork").') parser.add_argument('--ethkey', dest='ethkey', type=str, help='Private Ethereum key (32 bytes as HEX encoded string)') parser.add_argument('--cskey', dest='cskey', type=str, help='Private WAMP-cryptosign authentication key (32 bytes as HEX encoded string)') parser.add_argument('--username', dest='username', type=str, default=None, help='For on-boarding, the new member username.') parser.add_argument('--email', dest='email', type=str, default=None, help='For on-boarding, the new member email address.') parser.add_argument('--market', dest='market', type=str, default=None, help='For creating new markets, the market UUID.') parser.add_argument('--market_title', dest='market_title', type=str, default=None, help='For creating new markets, the market title.') parser.add_argument('--market_label', dest='market_label', type=str, default=None, help='For creating new markets, the market label.') parser.add_argument('--market_homepage', dest='market_homepage', type=str, default=None, help='For creating new markets, the market homepage.') parser.add_argument('--provider_security', dest='provider_security', type=int, default=None, help='') parser.add_argument('--consumer_security', dest='consumer_security', type=int, default=None, help='') parser.add_argument('--market_fee', dest='market_fee', type=int, default=None, help='') parser.add_argument('--marketmaker', dest='marketmaker', type=str, default=None, help='For creating new markets, the market maker address.') parser.add_argument('--actor_type', dest='actor_type', type=int, choices=sorted([ActorType.CONSUMER, ActorType.PROVIDER, ActorType.PROVIDER_CONSUMER]), default=None, help='Actor type: PROVIDER = 1, CONSUMER = 2, PROVIDER_CONSUMER (both) = 3') parser.add_argument('--vcode', dest='vcode', type=str, default=None, help='For verifications of actions, the verification UUID.') parser.add_argument('--vaction', dest='vaction', type=str, default=None, help='For verifications of actions (on-board, create-market, ..), the verification code.') parser.add_argument('--channel', dest='channel', type=str, default=None, help='For creating new channel, the channel UUID.') parser.add_argument('--channel_type', dest='channel_type', type=int, choices=sorted([ChannelType.PAYING, ChannelType.PAYMENT]), default=None, help='Channel type: Seller (PAYING) = 1, Buyer (PAYMENT) = 2') parser.add_argument('--delegate', dest='delegate', type=str, default=None, help='For creating new channel, the delegate address.') parser.add_argument('--amount', dest='amount', type=int, default=None, help='Amount to open the channel with. In tokens of the market coin type, used as means of payment in the market of the channel.') args = parser.parse_args() if args.command == 'version': print('') print(' XBR CLI v{}\n'.format(__version__)) print(' XBRToken contract address: {} [source: {}]'.format(hlid(XBR_DEBUG_TOKEN_ADDR), XBR_DEBUG_TOKEN_ADDR_SRC)) print(' XBRNetwork contract address: {} [source: {}]'.format(hlid(XBR_DEBUG_NETWORK_ADDR), XBR_DEBUG_NETWORK_ADDR_SRC)) print(' XBRMarket contract address: {} [source: {}]'.format(hlid(XBR_DEBUG_MARKET_ADDR), XBR_DEBUG_MARKET_ADDR_SRC)) print(' XBRCatalog contract address: {} [source: {}]'.format(hlid(XBR_DEBUG_CATALOG_ADDR), XBR_DEBUG_CATALOG_ADDR_SRC)) print(' XBRChannel contract address: {} [source: {}]'.format(hlid(XBR_DEBUG_CHANNEL_ADDR), XBR_DEBUG_CHANNEL_ADDR_SRC)) print('') else: if args.command is None or args.command == 'noop': print('no command given. select from: {}'.format(', '.join(_COMMANDS))) sys.exit(0) # read or create a user profile profile = load_or_create_profile() # only start txaio logging after above, which runs click (interactively) if args.debug: txaio.start_logging(level='debug') else: txaio.start_logging(level='info') log = txaio.make_logger() log.info('XBR CLI {version}', version=hlid('v' + __version__)) log.info('Profile {profile} loaded from {path}', profile=hlval(profile.name), path=hlval(profile.path)) extra = { # user profile and defaults 'profile': profile, # allow to override, and add more arguments from the command line 'command': args.command, 'ethkey': binascii.a2b_hex(args.ethkey[2:]) if args.ethkey else None, 'cskey': binascii.a2b_hex(args.cskey[2:]) if args.cskey else None, 'username': args.username, 'email': args.email, 'market': uuid.UUID(args.market) if args.market else None, 'market_title': args.market_title, 'market_label': args.market_label, 'market_homepage': args.market_homepage, 'market_provider_security': args.provider_security or 0, 'market_consumer_security': args.consumer_security or 0, 'market_fee': args.market_fee or 0, 'marketmaker': binascii.a2b_hex(args.marketmaker[2:]) if args.marketmaker else None, 'actor_type': args.actor_type, 'vcode': args.vcode, 'vaction': uuid.UUID(args.vaction) if args.vaction else None, 'channel': uuid.UUID(args.channel) if args.channel else None, 'channel_type': args.channel_type, 'delegate': binascii.a2b_hex(args.delegate[2:]) if args.delegate else None, 'amount': args.amount or 0, } runner = ApplicationRunner(url=args.url, realm=args.realm, extra=extra, serializers=[CBORSerializer()]) try: log.info('Connecting to "{url}" {realm} ..', url=hlval(args.url), realm=('at realm "' + hlval(args.realm) + '"' if args.realm else '')) runner.run(Client, auto_reconnect=False) except Exception as e: print(e) sys.exit(1) else: sys.exit(0)