Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
39 commits
Select commit Hold shift + click to select a range
1a39fc2
Expose read client
redben Aug 15, 2019
8161b7c
Change reader suffix to /eth
redben Aug 15, 2019
1acee64
Forward rpc static calls as is to /eth endpoint
redben Aug 15, 2019
8b9dcd0
format
redben Aug 15, 2019
5183ef4
Fix _ethCallSupportedMethod return type
redben Aug 15, 2019
62c5f31
e2e wip
redben Aug 18, 2019
8d8ce5c
Don't deploy blueprint contract
enlight Aug 19, 2019
b6918fe
Merge branch 'disable-blueprint' into loom-provider-eth-endpoint
redben Aug 19, 2019
80fa6d0
Keep support for old protocol in client and loomProvider
redben Aug 20, 2019
a5192b6
ws-rpc-client id string/number bug workaround
redben Aug 20, 2019
085b054
revert changes to e2e_tests.ts
redben Aug 21, 2019
bffb4c3
format
redben Aug 21, 2019
5dc2706
Fix loomProvider _ethRPCMethods subscribe/unsubscribe
redben Aug 21, 2019
75a68bc
LoomProvider keep support of old protocol in _onWebSocketMessage
redben Aug 21, 2019
7b84d8f
ws-rpc-client._onEventMessage: add back event handling for old endpoint
redben Aug 21, 2019
8719dcc
Address PR comments
redben Aug 21, 2019
2263779
WSRPCClient keep original interface (protected _getNextRequestId)
redben Aug 22, 2019
d68aa3b
LoomProvider: Remove unused imports
redben Aug 22, 2019
291771d
Address comments on PR
redben Aug 22, 2019
0d728a2
Cleanup
enlight Aug 22, 2019
87994b7
Fix the build?
enlight Aug 22, 2019
6df71f8
Run web3 tests against /queryws & /eth endpoints (where it makes sense)
enlight Aug 23, 2019
d7f7685
Fix .number in loomProvider._createBlockInfo
redben Aug 28, 2019
61e0cff
LoomProvider Web3: Fix events
redben Aug 28, 2019
5a22b37
LoomProvider._onWebSocketMessage fix conditional paths
redben Aug 28, 2019
094d2df
Move call _client.addListenerForTopics()) to the right place
redben Aug 28, 2019
5f2d002
Skip BluePrint contract test
redben Aug 28, 2019
f79c244
Bring back BluePrint
enlight Aug 30, 2019
21f7c13
Cleanup
enlight Sep 24, 2019
a8f2fdb
Fix build error
enlight Sep 24, 2019
a36280e
Make WSRPCClient handle all EVM notifications regardless of the endpoint
enlight Sep 24, 2019
2d8bc4b
/eth endpoint supports eth_getBalance
enlight Sep 24, 2019
cebfaa2
The good old change shit until it works approach
enlight Sep 24, 2019
4fee498
Switch on logging
enlight Sep 24, 2019
50201d7
Upgrade to build 1283
enlight Sep 24, 2019
478f32f
Update loom binary download location
enlight Sep 24, 2019
3f0dcf9
Revert "The good old change shit until it works approach"
enlight Sep 24, 2019
b0d6752
Better naming for tests & some more cleanup
enlight Sep 24, 2019
c466082
Switch off logging
enlight Sep 24, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .travis_e2e_test.sh
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ set -euxo pipefail

eval "$(GIMME_GO_VERSION=1.10.2 gimme)"

export BUILD_ID=build-1213
export BUILD_ID=build-1283

bash e2e_tests.sh

Expand Down
30 changes: 23 additions & 7 deletions e2e_support/genesis.json
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
{
"contracts": [
{
"vm": "plugin",
"format": "plugin",
"name": "BluePrint",
"location": "blueprint:0.0.1",
"init": {}
{
"vm": "plugin",
"format": "plugin",
"name": "BluePrint",
"location": "blueprint:0.0.1",
"init": {}
},
{
"vm": "plugin",
Expand Down Expand Up @@ -62,6 +62,22 @@
{
"name": "tg:binance-cm",
"status": "WAITING"
},
{
"name": "receipts:v3",
"status": "WAITING"
},
{
"name": "receipts:v3.1",
"status": "WAITING"
},
{
"name": "receipts:v3.2",
"status": "WAITING"
},
{
"name": "evm:constantinople",
"status": "WAITING"
}
]
}
Expand Down Expand Up @@ -99,4 +115,4 @@
}
}
]
}
}
2 changes: 1 addition & 1 deletion e2e_tests.sh
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ fi

download_dappchain() {
cd $LOOM_DIR
wget -O loom https://private.delegatecall.com/loom/$PLATFORM/$BUILD_ID/loom-gateway
wget -O loom https://downloads.loomx.io/loom/$PLATFORM/$BUILD_ID/loom-gateway
chmod +x loom
LOOM_BIN=`pwd`/loom
}
Expand Down
51 changes: 40 additions & 11 deletions src/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ import {
} from './crypto-utils'
import { Address, LocalAddress } from './address'
import { WSRPCClient, IJSONRPCEvent } from './internal/ws-rpc-client'
import { RPCClientEvent, IJSONRPCClient } from './internal/json-rpc-client'
import { RPCClientEvent, IJSONRPCClient, IJSONRPCResponse } from './internal/json-rpc-client'
import { sleep, parseUrl } from './helpers'

export interface ITxHandlerResult {
Expand Down Expand Up @@ -243,6 +243,13 @@ export class Client extends EventEmitter {
private _writeClient: IJSONRPCClient
private _readClient!: IJSONRPCClient

/**
* Indicates whether the client is configured to use the /eth endpoint on Loom nodes.
* When this is enabled the client can only be used to interact with EVM contracts.
* NOTE: This limitation will be removed in the near future.
*/
readonly isWeb3EndpointEnabled: boolean

/** Broadcaster to use to send txs & receive results. */
txBroadcaster: ITxBroadcaster

Expand Down Expand Up @@ -315,6 +322,8 @@ export class Client extends EventEmitter {
)
}

this.isWeb3EndpointEnabled = true === /eth$/.test(this._readClient.url)

const emitContractEvent = (url: string, event: IJSONRPCEvent) =>
this._emitContractEvent(url, event)

Expand Down Expand Up @@ -442,6 +451,17 @@ export class Client extends EventEmitter {
}
}

/**
* Sends a Web3 JSON-RPC message to the /eth endpoint on a Loom node.
* @param method RPC method name.
* @param params Parameter object or array.
* @returns A promise that will be resolved with the value of the result field (if any) in the
* JSON-RPC response message.
*/
async sendWeb3MsgAsync<T>(method: string, params: object | any[]): Promise<IJSONRPCResponse<T>> {
return this._readClient.sendAsync<IJSONRPCResponse<T>>(method, params)
}

/**
* Queries the receipt corresponding to a transaction hash
*
Expand Down Expand Up @@ -555,7 +575,6 @@ export class Client extends EventEmitter {
const envelope: EthFilterEnvelope = EthFilterEnvelope.deserializeBinary(
bufferToProtobufBytes(result)
)

switch (envelope.getMessageCase()) {
case EthFilterEnvelope.MessageCase.ETH_BLOCK_HASH_LIST:
return envelope.getEthBlockHashList() as EthBlockHashList
Expand Down Expand Up @@ -675,8 +694,12 @@ export class Client extends EventEmitter {
* @param method Method selected to the filter, can be "newHeads" or "logs"
* @param filter JSON string of the filter
*/
evmSubscribeAsync(method: string, filterObject: Object): Promise<string> {
const filter = JSON.stringify(filterObject)
evmSubscribeAsync(method: string, params: Object | any[]): Promise<string> {
if (this.isWeb3EndpointEnabled) {
return this._readClient.sendAsync<string>('eth_subscribe', params)
}

const filter = JSON.stringify(params)
return this._readClient.sendAsync<string>('evmsubscribe', {
method,
filter
Expand All @@ -691,9 +714,11 @@ export class Client extends EventEmitter {
* @return boolean If true the subscription is removed with success
*/
evmUnsubscribeAsync(id: string): Promise<boolean> {
return this._readClient.sendAsync<boolean>('evmunsubscribe', {
id
})
if (this.isWeb3EndpointEnabled) {
return this._readClient.sendAsync<boolean>('eth_unsubscribe', [id])
}

return this._readClient.sendAsync<boolean>('evmunsubscribe', { id })
}

/**
Expand Down Expand Up @@ -748,13 +773,14 @@ export class Client extends EventEmitter {
}

private _emitContractEvent(url: string, event: IJSONRPCEvent, isEVM: boolean = false): void {
debugLog('_emitContractEvent', arguments)
const { error, result } = event
if (error) {
const eventArgs: IClientErrorEventArgs = { kind: ClientEvent.Error, url, error }
this.emit(ClientEvent.Error, eventArgs)
} else if (this.isWeb3EndpointEnabled && isEVM) {
this.emit(ClientEvent.EVMEvent, event)
} else if (result) {
debugLog('Event', event.id, result)

// Ugh, no built-in JSON->Protobuf marshaller apparently
// https://github.com/google/protobuf/issues/1591 so gotta do this manually
const eventArgs: IChainEventArgs = {
Expand All @@ -776,8 +802,11 @@ export class Client extends EventEmitter {
transactionHashBytes: result.tx_hash ? B64ToUint8Array(result.tx_hash) : new Uint8Array([])
}

if (isEVM) this.emit(ClientEvent.EVMEvent, eventArgs)
else this.emit(ClientEvent.Contract, eventArgs)
if (isEVM) {
this.emit(ClientEvent.EVMEvent, eventArgs)
} else {
this.emit(ClientEvent.Contract, eventArgs)
}
}
}

Expand Down
9 changes: 7 additions & 2 deletions src/helpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -127,11 +127,16 @@ export function parseUrl(rawUrl: string): URL {
}

export function setupProtocolsFromEndpoint(
endpoint: string
endpoint: string,
useWeb3Endpoint: boolean = false
): { writer: IJSONRPCClient; reader: IJSONRPCClient } {
const protocol = selectProtocol(endpoint)
const writerSuffix = protocol === JSONRPCProtocol.HTTP ? '/rpc' : '/websocket'
const readerSuffix = protocol === JSONRPCProtocol.HTTP ? '/query' : '/queryws'
const readerSuffix = useWeb3Endpoint
? '/eth'
: protocol === JSONRPCProtocol.HTTP
? '/query'
: '/queryws'

const writer = createJSONRPCClient({
protocols: [{ url: endpoint + writerSuffix }]
Expand Down
2 changes: 1 addition & 1 deletion src/internal/dual-rpc-client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ export class DualRPCClient extends WSRPCClient {
requestTimeout?: number
reconnectInterval?: number
maxReconnects?: number
generateRequestId?: (method: string, params: object | any[]) => string
generateRequestId?: (method: string, params: object | any[]) => string | number
}) {
super(opts.wsUrl, opts)
const {
Expand Down
3 changes: 2 additions & 1 deletion src/internal/http-rpc-client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ export class HTTPRPCClient extends EventEmitter implements IJSONRPCClient {
public url: string,
opts: {
requestTimeout?: number
generateRequestId?: (method: string, params: object | any[]) => string
generateRequestId?: (method: string, params: object | any[]) => string | number
} = {}
) {
super()
Expand All @@ -40,6 +40,7 @@ export class HTTPRPCClient extends EventEmitter implements IJSONRPCClient {
} = opts

this.requestTimeout = requestTimeout
// FIXME: generateRequestId doesn't actually override this._getNextRequestId at the moment
}

disconnect() {
Expand Down
6 changes: 3 additions & 3 deletions src/internal/json-rpc-client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,19 +10,19 @@ export interface IJSONRPCRequest {
jsonrpc: '2.0'
method: string
params?: any
id?: string
id?: string | number
}

export interface IJSONRPCResultResponse<T> {
jsonrpc: '2.0'
result: T
id: string
id: string | number
}

export interface IJSONRPCErrorResponse {
jsonrpc: '2.0'
error: IJSONRPCError
id: string
id: string | number
}

export interface IJSONRPCResponse<T> extends IJSONRPCResultResponse<T>, IJSONRPCErrorResponse {}
Expand Down
34 changes: 24 additions & 10 deletions src/internal/ws-rpc-client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,14 +35,25 @@ export class WSRPCClient extends EventEmitter {
private _isSubcribed: boolean = false

protected _rpcId: number = 0
protected _getNextRequestId = () => (++this._rpcId).toString()

protected _getNextRequestId = () => {
const id = ++this._rpcId
return this.isWeb3EndpointEnabled ? id.toString() : id
}

requestTimeout: number

get isSubscribed(): boolean {
return this._isSubcribed
}

/**
* Indicates whether the client is configured to use the /eth endpoint on Loom nodes.
* When this is enabled the client can only be used to interact with EVM contracts.
* NOTE: This limitation will be removed in the near future.
*/
readonly isWeb3EndpointEnabled: boolean

/**
*
* @param url
Expand All @@ -59,10 +70,13 @@ export class WSRPCClient extends EventEmitter {
requestTimeout?: number
reconnectInterval?: number
maxReconnects?: number
generateRequestId?: (method: string, params: object | any[]) => string
generateRequestId?: (method: string, params: object | any[]) => string | number
} = {}
) {
super()

this.isWeb3EndpointEnabled = true === /eth$/.test(url)

const {
autoConnect = true,
requestTimeout = 15000, // 15s
Expand Down Expand Up @@ -206,15 +220,15 @@ export class WSRPCClient extends EventEmitter {
const msgStr = message instanceof ArrayBuffer ? Buffer.from(message).toString() : message
const msg = JSON.parse(msgStr)

// Events from native loomchain have the id equals 0
if (msg.id === '0') {
log('Loom Event arrived', msg)
if (msg.method === 'eth_subscription') {
log('EVM contract event arrived', msg)
this.emit(RPCClientEvent.EVMMessage, this.url, msg)
} else if (msg.id === '0') {
// Events from native loomchain have id 0
log('Go contract event arrived', msg)
this.emit(RPCClientEvent.Message, this.url, msg)
}

// Events from EVM have the id from the evmsubscribe command
if (/^0x.+$/.test(msg.id)) {
log('EVM Event arrived', msg)
} else if (/^0x.+$/.test(msg.id)) {
// Events from EVM have the id from the evmsubscribe command
this.emit(RPCClientEvent.EVMMessage, this.url, msg)
}
}
Expand Down
Loading