Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
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
3 changes: 3 additions & 0 deletions .dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
.git
node_modules
npm-debug
20 changes: 20 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
FROM nervos/godwoken-prebuilds:v0.2.0-rc2

WORKDIR "/godwoken-web3"

RUN apt-get update \
&& apt-get dist-upgrade -y \
&& apt-get install jq -y \
&& apt-get clean \
&& echo "Finished installing dependencies"

COPY package*.json ./
COPY packages/godwoken/package*.json ./packages/godwoken/
COPY packages/api-server/package*.json ./packages/api-server/
RUN yarn install

COPY --chown=node . ./
EXPOSE 8024

USER node
CMD ["node", "version"]
117 changes: 116 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,90 @@ yarn workspace @godwoken-web3/godwoken tsc
yarn workspace @godwoken-web3/api-server start
```

## Web3 RPC
## Web3 RPC Modules

### net

- net_version
- net_peerCount
- net_listening

### web3

- web3_sha3
- web3_clientVersion

### eth
- eth_chainId
- eth_protocolVersion
- eth_syncing
- eth_coinbase
- eth_mining
- eth_hashrate
- eth_gasPrice
- eth_accounts
- eth_blockNumber
- eth_sign
- eth_signTransaction
- eth_sendTransaction
- eth_getBalance
- eth_getStorageAt
- eth_getTransactionCount
- eth_getCode
- eth_call
- eth_estimateGas
- eth_getBlockByHash
- eth_getBlockByNumber
- eth_getBlockTransactionCountByHash
- eth_getBlockTransactionCountByNumber
- eth_getUncleByBlockHashAndIndex
- eth_getUncleByBlockNumberAndIndex
- eth_getUncleCountByBlockHash
- eth_getCompilers
- eth_getTransactionByHash
- eth_getTransactionByBlockHashAndIndex
- eth_getTransactionByBlockNumberAndIndex
- eth_getTransactionReceipt
- eth_newFilter
- eth_newBlockFilter
- eth_newPendingTransactionFilter
- eth_uninstallFilter
- eth_getFilterLogs
- eth_getFilterChanges
- eth_getLogs
- eth_sendRawTransaction
- eth_getTipNumber
- eth_gw_executeL2Tranaction
- eth_gw_submitL2Transaction
- eth_gw_getAccountIdByScriptHash
- eth_gw_getScriptHashByAccountId
- eth_gw_getNonce
- eth_gw_getTransactionReceipt
-
### gw

- gw_ping
- gw_get_tip_block_hash
- gw_get_block_hash
- gw_get_block
- gw_get_block_by_number
- gw_get_balance
- gw_get_storage_at
- gw_get_account_id_by_script_hash
- gw_get_nonce
- gw_get_script
- gw_get_script_hash
- gw_get_data
- gw_get_transaction_receipt
- gw_execute_l2transaction
- gw_execute_raw_l2transaction
- gw_submit_l2transaction
- gw_submit_withdrawal_request

### poly
- poly_ethAddressToPolyjuiceAddress
- poly_polyjuiceAddressToEthAddress
## Examples
### web3_clientVersion

```
Expand Down Expand Up @@ -208,3 +291,35 @@ curl http://localhost:3000 -X POST -H "Content-Type: application/json" -d '{"jso
// Response
{"jsonrpc":"2.0","id":1,"result":"eth_sign is not supported!"}
```

### gw_get_script_hash

```
// Request
curl http://localhost:3000 -X POST -H "Content-Type: application/json" -d '{"jsonrpc": "2.0", "method":"gw_get_script_hash", "params": ["0x0"], "id": 1}'

// Response
{"jsonrpc":"2.0","id":1,"result":"0xdb5b85ffffb98bb103a8763a6be8c02d8442f232061e1e644b25beba4b1693c1"}

```

### gw_get_script

```
// Request
curl http://localhost:3000 -X POST -H "Content-Type: application/json" -d '{"jsonrpc": "2.0", "method":"gw_get_script", "params": ["0xdb5b85ffffb98bb103a8763a6be8c02d8442f232061e1e644b25beba4b1693c1"], "id": 1}'

// Response
{"jsonrpc":"2.0","id":1,"result":{"code_hash":"0x841f75a94dbac1b2b400f29d55c02e5535e8ccca38e26c4245022f31f3ff2e81","hash_type":"type","args":"0x599950fbd06d2592d2903633c740f2ad9578ab7aee45d6d0d9f0c07f093417a6"}}

```

### gw_get_nonce
```
// Request
curl http://localhost:3000 -X POST -H "Content-Type: application/json" -d '{"jsonrpc": "2.0", "method":"gw_get_nonce", "params": ["0x2"], "id": 1}'

// Response
{"jsonrpc":"2.0","id":1,"result":"0x1"}

```
6 changes: 6 additions & 0 deletions packages/api-server/app.js
Original file line number Diff line number Diff line change
Expand Up @@ -27,11 +27,17 @@ app.use(function (req, res, next) {

// error handler
app.use(function (err, req, res, next) {
console.error(err.stack);

// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};

// render the error page
console.error("err.status:", err.status);
if (res.headersSent) {
return next(err)
}
res.status(err.status || 500);
res.render('error');
});
Expand Down
8 changes: 7 additions & 1 deletion packages/api-server/src/convert-tx.ts
Original file line number Diff line number Diff line change
Expand Up @@ -46,14 +46,20 @@ function debugLogger(...messages: any[]) {
}
}

export function calcEthTxHash(encodedSignedTx: HexString): Hash {
const ethTxHash =
'0x' + keccak256(Buffer.from(encodedSignedTx.slice(2), 'hex')).toString('hex');
return ethTxHash
}

export async function generateRawTransaction(
data: HexString,
rpc: RPC
): Promise<GodwokenL2Transaction> {
debugLogger('origin data:', data);
const polyjuiceTx: PolyjuiceTransaction = decodeRawTransactionData(data);
debugLogger('decoded polyjuice tx:', polyjuiceTx);
const godwokenTx = parseRawTransactionData(polyjuiceTx, rpc);
const godwokenTx = await parseRawTransactionData(polyjuiceTx, rpc);
return godwokenTx;
}

Expand Down
34 changes: 25 additions & 9 deletions packages/api-server/src/methods/modules/eth.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,10 @@ import { camelToSnake, toHex, handleBlockParamter } from '../../util';
import { core, utils, HexNumber, Hash } from '@ckb-lumos/base';
import { normalizers, Reader } from 'ckb-js-toolkit';
import { types, schemas } from '@godwoken-web3/godwoken';
import { generateRawTransaction } from '../../convert-tx';
import { calcEthTxHash, generateRawTransaction } from '../../convert-tx';
import { Script } from '@ckb-lumos/base';
import { INVALID_PARAMS } from '../error-code';

const Config = require('../../../config/eth.json');
const blake2b = require('blake2b');
require('dotenv').config({ path: './.env' });
Expand Down Expand Up @@ -125,6 +127,12 @@ export class Eth {
validators.newFilterParams
]);

this.sendRawTransaction = middleware(
this.sendRawTransaction.bind(this),
1,
[validators.hexString]
);

//
this.syncing = middleware(this.syncing.bind(this), 0);

Expand Down Expand Up @@ -814,14 +822,22 @@ export class Eth {
}

async sendRawTransaction(args: [string], callback: Callback) {
const data = args[0];
const rawTx = await generateRawTransaction(data, this.rpc);
const moleculeTx = new Reader(
schemas.SerializeL2Transaction(types.NormalizeL2Transaction(rawTx))
).serializeJson();
const result = await this.rpc.submit_l2transaction(moleculeTx);
console.log('sendRawTransaction hash:', result);
callback(null, result);
try {
const data = args[0];
const rawTx = await generateRawTransaction(data, this.rpc);
const moleculeTx = new Reader(
schemas.SerializeL2Transaction(types.NormalizeL2Transaction(rawTx))
).serializeJson();
const gwTxHash = await this.rpc.submit_l2transaction(moleculeTx);
console.log('sendRawTransaction gw hash:', gwTxHash);
const ethTxHash = calcEthTxHash(data);
console.log("sendRawTransaction eth hash:", ethTxHash);
callback(null, ethTxHash);
} catch (error) {
console.error(error);
return callback({ code: INVALID_PARAMS, message: error.message });
// https://www.jsonrpc.org/specification | 5.1 Error object
}
}
/* #endregion */

Expand Down
1 change: 1 addition & 0 deletions packages/api-server/src/methods/types.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { HexNumber, HexString } from '@ckb-lumos/base';
export type Error = {
code?: number;
message: string;
} | null;

Expand Down