CircleChain Architecture

CircleChain is an asset management platform based on blockchain technology that originates from Bitcoin. While Bitcoin is a client application based on blockchain and P2P protocol that stores data locally, CircleChain is a cloud-based distributed P2P and blockchain system. It stores data in cloud storage and provides cloud blockchain and wallet services to manage digital assets. CircleChain extends beyond Bitcoin's capabilities with enhanced features and scalability.

Overall Architecture

Frameworks

The complete architecture includes the following components:

  • API Layer - RESTful interfaces for external communication
  • Services and Events Layer - Core business logic and event handling
  • Background Jobs - Scheduled tasks and maintenance operations
  • Configuration Center - System configuration management
  • Storage Layer - Data persistence and cloud storage services

API Layer

The API layer consists of the following interfaces:

  • User APIs - Public user management interfaces for CircleChain
  • Wallet APIs - Public wallet management interfaces for CircleChain
  • Block APIs - Public blockchain data access interfaces
  • Clouder APIs - Internal clouder node communication interfaces
  • Miner APIs - Internal miner node communication interfaces

API Specifications

All CircleChain APIs follow RESTful design principles with data encoded in JSON format. The request and response headers use Content-Type: application/json.

User APIs

These APIs provide public user management functionality.

sendRegisterVerifyCode

Path: /user/v1/node/register/send-verify-code

Method: POST

Request:

name type required description
phone String optional Phone and email should not be empty either.
email String optional Phone and email should not be empty either.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Sends a verification code before creating a user account. If an email is provided, the verification code will be sent via email. If a phone number is provided, the verification code will be sent via SMS.

register

Path: /user/v1/node/register

Method: POST

Request:

name type required description
phone String optional Phone and email should not be empty either.
email String optional Phone and email should not be empty either.
passwordInput1 String required password
passwordInput2 String required password confirmed, should be the same with passwordInput2
verifyCode String required the verify code sent by api sendRegisterVerifyCode

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

User registration API for creating new accounts.

sendVerifyCode

Path: /user/v1/node/send-verify-code

Method: POST

Request:

name type required description
phone String optional Phone and email should not be empty either.
email String optional Phone and email should not be empty either.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Sends a verification code before user login. If an email is provided, the verification code will be sent via email. If a phone number is provided, the verification code will be sent via SMS.

login

Path: /user/v1/node/login

Method: POST

Request:

name type required description
phone String optional Phone and email should not be empty either.
email String optional Phone and email should not be empty either.
verifyCode String optional the verify code sent by api sendVerifyCode, the verifyCode and password you select one to input
password String optional the password for login, the verifyCode and password you select one to input

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data UserLoginResult optional user login result data

UserLoginResult:

name type required description
userId String required user id
sessionKey String required the session key
sex byte optional the sex
success Boolean required success or failure

Description:

User login API. Upon successful authentication, store the sessionKey securely in your local storage. The sessionKey is used to authenticate subsequent API calls as a logged-in user by setting the following header:

{
    "AuthorizationV2": "<sessionKey>"
}

logout

Path: /user/v1/node/logout

Method: POST

Request:

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

User logout API to terminate the current session.

sendPayVerifyCode

Path: /user/v1/node/pay/send-verify-code

Method: POST

Request:

name type required description
phone String optional Phone and email should not be empty either.
email String optional Phone and email should not be empty either.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Sends a verification code before setting a payment password. If an email is provided, the verification code will be sent via email. If a phone number is provided, the verification code will be sent via SMS.

setPayPassword

Path: /user/v1/node/pay/set-password

Method: POST

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
account AccountPO required account
verifyCode String required the verify code sent by sendPayVerifyCode
password String required the new pay password.

AccountPO:

name type required description
phone String optional Phone and email should not be empty either.
email String optional Phone and email should not be empty either.
encryptedPassword String Optional the password encrypted by user public key, it can be empty here.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Sets the user's payment password for transaction authorization.

havePayPassword

Path: /user/v1/node/have-pay-password

Method: GET

Request:

Request header: { AuthorizationV2: "<sessionKey>" }

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional have or not set.

Description:

Checks whether the user has set a payment password.

sendResetPasswordVerifyCode

Path: /user/v1/node/reset-password/send-verify-code

Method: POST

Request:

name type required description
phone String optional Phone and email should not be empty either.
email String optional Phone and email should not be empty either.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Sends a verification code for resetting the login password. If an email is provided, the verification code will be sent via email. If a phone number is provided, the verification code will be sent via SMS.

resetPassword

Path: /user/v1/node/reset-password

Method: POST

Request:

name type required description
account AccountPO required account
verifyCode String required the verify code sent by sendResetPasswordVerifyCode
password1 String required new login password
password2 String required password confirmed

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Resets the user's login password.

saveOrUpdateUserInfo

Path: /user/v1/node/save-or-update-userinfo

Method: POST

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
userId String required user id
name String required user name
phone String optional user phone
sex Byte optional 1: man 0 woman
icon String optional user icon
address String optional user address
motherLang Integer required 0 English 1 Chinese 2 Japanese 3 French 4 German 5 Italian 6 Korea 7 Thai
wechat String optional wechat account
entWechat String optional enterprise WeChat account
dingtalk String optional dingtalk account

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Saves or updates user profile information.

getUserInfoPO

Path: /user/v1/node/get-user-info

Method: GET

Request:

Request header: { AuthorizationV2: "<sessionKey>" }

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data UserInfoPO optional user info data

UserInfoPO:

name type required description
userId String required user id
name String required user name
phone String optional user phone
sex Byte optional 1: man 0 woman
icon String optional user icon
address String optional user address
motherLang Integer required 0 English 1 Chinese 2 Japanese 3 French 4 German 5 Italian 6 Korea 7 Thai
wechat String optional wechat account
entWechat String optional enterprise WeChat account
dingtalk String optional dingtalk account

Description:

Retrieves user information for the currently logged-in user.

addContacts

Path: /user/v1/node/add-contacts

Method: POST

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
name String required user name
phone String required user phone
sex Byte optional 1: man 0 woman
icon String optional user icon
address String required user address
description String optional description

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Adds a contact to the user's contact list. Currently, only phone contacts are supported.

listContacts

Path: /user/v1/node/list-contacts

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional contact data list

ContactPO:

name type required description
name String required user name
phone String required user phone
sex Byte optional 1: man 0 woman
icon String optional user icon
address String required user address
description String optional description

Description:

Lists user contacts. Currently, only phone contacts are supported.

Wallet APIs

These APIs provide wallet management services.

createWallet

Path: /wallet/v1/node/createWallet

Method: POST

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data String optional address of the wallet

Description:

Creates a wallet for the logged-in user. Each user can create up to 3 wallets.

listWallet

Path: /wallet/v1/node/listWallet

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
phone String optional list the phone's address. If not set, list his own address.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional address of the wallet

Description:

Lists wallets by phone number. If a phone number is provided, it lists the wallets of the logged-in user.

getBalanceOfAddress

Path: /wallet/v1/node/getBalanceOfAddress

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
address String required the address

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Long optional The balance value for the address

Description:

Retrieves the balance for the specified address.

getBalanceByAddressList

Path: /wallet/v1/node/getBalanceByAddressList

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
addressList String required the address list join by ","

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional The balance value for the address

BalanceVO:

name type required description
confirmed Long required confirmed balance
unconfirmed Long required unconfirmed balance

Description:

Batch retrieves balances for a list of addresses.

getBalanceOfWallet

Path: /wallet/v1/node/getBalanceOfWallet

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional The balance value for the address

WalletSpentInfo:

name type required description
address String required address
balance Long required the balance
spent Long required the spent balance

Description:

Lists the logged-in user's wallet spending information.

getAssetsOfWallet

Path: /wallet/v1/node/getBalanceOfWallet

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data AssetsInfo optional The balance value for the address

AssetsInfo:

name type required description
balance Long required the total balance of the user
IdentityNum Integer required the count of identity assets
ownershipNum Integer required the count of ownership assets
walletNum Integer required the count of wallets

Description:

Lists the logged-in user's wallet assets (including balance, ownership, and identity information).

getAssetsOfAddress

Path: /wallet/v1/node/getAssetsOfAddress

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
address String required the address
type Integer required the asset type: 1 ownership, 2 identity

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional The balance value for the address

AddressAssetsInfo:

name type required description
address String required the address
type Integer required asset type: 1 ownership, 2 identity
txId String required the transaction id
idx Integer required the output index of the transaction
value String required the asset value, encoding with hex
doubleHashHex String optional the asset data double hash hex data

Description:

Retrieves user asset information by address and asset type.

getPubKeyHashFromAddress

Path: /wallet/v1/node/getPubKeyHashFromAddress

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type requred description
address String required the address

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data String optional public key hash encoding hex string

Description:

Retrieves the public key hash from the specified address.

sendTo

Path: /wallet/v1/node/sendTo

Method: POST

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
from String required the from address
address String required the to address
receivePhone String optional received phone
email String optional received email
transContent TransactionContentPO required the transfer content data
payPassword String required the payment password

TransactionContentPO:

name type required description
type Integer required the transaction type: 1 ownership, 2 identity
valueHex String optional value encoding in hex string, deprecated.
uuid String optional the uuid for the asset
hash String optinal the asset data hash data

note: If the received phone or email not empty, and then make sure the address address belongs to it.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Sends tokens, ownership, or identity assets to another user.

pay

Path: /wallet/v1/node/pay

Method: POST

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
from String required the from address
to String required the to address
receivePhone String optional received phone
email String optional received email
value Long required the balance value
payPassword String required the payment password

note: If the received phone or email not empty, and then make sure the to address belongs to it.

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data Boolean optional success or failure

Description:

Transfers coins to another user.

searchTxByType

Path: /wallet/v1/node/searchTxByType

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
type Integer required 0 balance 1 ownership 2 identity
pageNo Integer optional default 1
pageSize Integer optional default 10

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional transaction info list.

TransactionInfo:

name type required description
fromAddress String required the from address
toAddress String required the to address
txId String required the transaction id
idx Integer required the output index of the transaction
txType Integer required the transactfion type: 0 balance, 1 ownership, 2 identity
inOut String required IN: input, OUT: output
value String required the balance/asset value
timestamp String required the transaction create timestamp in the 'YYYY-mm-dd HH:MM:SS' date format

Description:

Searches for transactions by type.

searchTxByTime

Path: /wallet/v1/node/searchTxByTime

Method: GET

Request header: { AuthorizationV2: "<sessionKey>" }

Request:

name type required description
startTime Long required the stat time in milliseconds
endTime Long required the end time in milliseconds.
pageNo Integer optional default 1
pageSize Integer optional default 10

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional transaction info list.

TransactionInfo details see the above.

Description:

Searches for transactions by time range.

Block APIs

These APIs provide public blockchain data access without requiring user authentication.

getBlockHashList

Path: /block/v1/node/get-block-hashList

Method: GET

Request:

name type required description
baseHeight Long required The start height

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional block hash list

Description:

Retrieves a list of block hashes by base height and remote node IP:port, with batches of 100 items.

getBlock

Path: /block/v1/node/get-block

Method: GET

Request:

name type required description
hash String required the block hash

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data BlockPO optional block hash list

BlockPO:

name type required description
header BlockHeaderPO required block header
dataHexStr String required block data hex string

Description:

Retrieves a block by its hash.

getBlockHeaderList

Path: /block/v1/node/get-block-header-list

Method: GET

Request:

name type required description
baseHeight Long required The start height

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional block header list

BlockHeaderPO:

name type required description
hash String required block hash
minedTimestamp Long required the mined timestamp
version String required the version
height Long required the height of the block
prevBlockHash String required the previous block hash
merkleTreeRoot String required the merkle tree root
minerIpPort String optional the miner ipPort
minerInfo String optional the miner info
timeStamp Long required the block create timestamp
difficulty Long required the difficulty of the block
nonce Long required the nonce.

Description:

Retrieves a list of block headers by blockchain height, with batches of 100 items.

getBlockData

Path: /block/v1/node/get-block-data

Method: GET

Request:

name type required description
hash String required the block hash

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data String optional the block data encoding in hex string

Description:

get block data by block hash

getBlockTailsHashList

Path: /block/v1/node/get-blocktails-hashList

Method: GET

Request:

name type required description
baseHeight Long required the start height to get

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional block tails hash list

Description:

Retrieves block tails hash list by blockchain height, with batches of 100 items.

getBlockTailsPO

Path: /block/v1/node/get-blocktails-po

Method: GET

Request:

name type required description
hash Long required the block hash

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data BlockTailsPO optional block tails data

BlockTailsPO:

name type required description
height Long required the block height
hash String required the block hash
hashCrc32 Integer required the block hash crc32 value
prevHash String required the previous block hash
isMaster Byte required 0 slave 1 master

Description:

Retrieves block tails by block hash.

getTxByTxId

Path: /block/v1/node/gettx-by-txid

Method: GET

Request:

name type required description
txIdStr String required tx id hex string

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data TransactionDetail optional transaction detail.

TransactionDetail:

name type required description
blockHash String required block hash
height Long required the block height
txIdHexStr String required the transaction id
type Integer required the transaction type: 0 balance, 1 ownership, 2 identity
inputs List required inputs of transaction
outputs List required outputs of transaction
createTime Long required the create time for the transaction
minedTimestamp Long required the block mined timestamp
sendersPubKeyHash List required the sender public key hash list
receiversPubKeyHash List required the receiver public key hash list
confirmations Long required the confirmation of the block.

TXInputPO:

name type required description
txIdStr String required tx id hex string
txOutputIndex Integer required the output index for the transaction
unlockScript String required the unlock script encoding hex string
value String required the value
serialNO Integer required the serial NO.
addressList List required the inputs' address list.

TXOutputPO:

name type required description
txIdStr String required tx id hex string
idx Integer required the output index for the transaction
status Integer required Status: 0 unspent, 1 spent
value String required the value
lockScript String required the lock script encoding hex string
addressList List required the outputs' address list.

Description:

Retrieves transaction details by transaction ID.

getTransactionsByTxIdList

Path: /block/v1/node/gettx-by-txid-list

Method: POST

Request:

name type required description
txIdList List required tx id list

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional transaction details

TransactionDetail: more detail see above.

Description:

Batch retrieves transactions by transaction ID list.

searchTxByTxId

Path: /block/v1/node/search-tx-by-txid

Method: GET

Request:

name type required description
txIdStr String required tx id hex string

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional transaction details

Description:

Searches for all transactions related to the specified transaction ID.

searchTxByAddress

Path: /block/v1/node/search-tx-by-address

Method: GET

Request:

name type required description
address String required the address
minOutputKey String optional Default ""
limit Integer optional Default 100

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data AddressTxInfo optional address transaction info data

AddressTxInfo:

name type required description
address String required the address
pubKeyHash String required public key hash
txDetailList List required Transaction detail list
minOutputKey String required the minOutputKey for next query

TransactionDetail: more details see above.

Note: the minOutputKey value should be set after your query in the first time. When you get AddressTxInfo data, you will get the data minOutputKey.

Description:

Searches for transactions by address and minimum output key.

searchUtxos

Path: /block/v1/node/search-utxos

Method: GET

Request:

name type required description
address String required the address
minOutputKey String optional Default ""
limit Integer optional Default 100

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data AddressUTXOInfo optional address transaction info data

AddressUTXOInfo:

name type required description
address String required the address
pubKeyHash String required public key hash
outputs List required the uxto outputs.

TxOutputPO: more detail see above

Note: the minOutputKey value should be set after your query in the first time. When you get AddressUTXOInfo data, you will get the data outputs which is TXOutputPO type. The outputs list is sort by output db id asc. So you will get the minOutputKey for the next query by the following code:

TXOutputPO lastItem = outputs.get(outputs.size() - 1);

String minOutputKey = lastItem.getTxIdStr() + ":" + lastItem.getTxOutputIndex();

Description:

Searches for UTXOs (Unspent Transaction Outputs) by address and minimum output key.

Clouder APIs

These APIs are internal APIs for clouder nodes.

All requests and responses use Content-Type: application/json.

heartbeat

Path: /coulder/v1/node/heartbeat

Method: POST

Request:

name type required description
requestId String optional
version String required such as '1.0.0'
role String required CLOUDER, MINER
protolVersion String required such as '1.0.0'
publicIP String required
localIP String required
port Integer required such as 80
ipPort String required such as '123.23.45.23:80'
heartBeatPO HeartBeatPO required

HeartBeatPO:

name type required description
baseHeight Long required the base height of the node
ipPortList List required the neighbors ipPort list of the node

Response:

name type required description
status Integer required 200 - success, others failure
message String required the mesage
data HeartBeatInfo optional the heartbeat info data

HeartBeatInfo:

name type required description
heartBeatPO HeartBeatPO required heartbeat po
publicIP String required public ip
localIP String required local ip
port Integer required such as 80
publicKey String required public key hex string
heartBeanSign String required the sign data for the hearbeatPO

Description:

This API is deprecated.

getBlockHashList

Path: /coulder/v1/node/getBlockHashList

Mthod: GET

Request:

name type required description
baseHeight Integer required the start height
ipPort String required the remote node ipPort, such as '123.23.45.23:80'

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional the block hash list

Description:

This API retrieves block hash lists in batches of 100 items.

getBlock

Path: /coulder/v1/node/getBlock

Mthod: GET

Request:

name type required description
hash String required the block hash
ipPort String required the remote node ipPort

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data BlockPO optional the block data.

BlockPO:

name type required description
header BlockHeaderPO required block header
dataHexStr String required block data hex string

BlockHeaderPO:

name type required description
hash String required block hash
minedTimestamp Long required the mined timestamp
version String required the version
height Long required the height of the block
prevBlockHash String required the previous block hash
merkleTreeRoot String required the merkle tree root
minerIpPort String optional the miner ipPort
minerInfo String optional the miner info
timeStamp Long required the block create timestamp
difficulty Long required the difficulty of the block
nonce Long required the nonce.

Description:

This API provides functionality for fetching blocks by their hash.

getBlockHeaderList

Path: /coulder/v1/node/getBlockHeaderList

Method: GET

Request:

name type required description
baseHeight Long required the start height to get block header list
ipPort String required the remote node ipPort

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional the list of block headers

Description:

Batch retrieves block header lists by current block height, with batches of 100 items.

getBlockData

Path: /coulder/v1/node/getBlockData

Method: GET

Request:

name type required description
hash String required the block hash
ipPort String required the remote node ipPort

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data String optional the block data encoding in hex string

Description:

get block data by block hash

broadcastMinedBlock

Path: /coulder/v1/node/broadcastMinedBlock

Method: POST

Request:

name type required description
Block BlockPO required the block data
minerPublicKey String required the miner public key
minerPublicIP String required the miner public ip
blockSign String required the block hash signed by the miner private key

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data String optional the result string

Description:

Broadcasts the mined block data across CircleChain clusters.

brandcastTransaction

Path: /coulder/v1/node/broadcastTransaction

Method: POST

Request:

name type required description
transaction TransactionPO required Transaction data

TransactionPO:

name type required description
txIdHexStr String required the transaction id hex string
type Integer required the transaction type: 0 balance, 1 ownership, 2 identity
inputsHexStr String required the inputs hex string
outputsHexStr String required the outputs hex string
createTime Long required the create time of the transaction

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data String optional transaction id hex string

Description:

Broadcasts transaction data across the network.

broadcastTransactionList

Path: /coulder/v1/node/broadcastTransactionList

Method: POST

Request:

name type required description
transactionList List required Transaction list data

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional transaction id hex string list

Description:

Batch broadcasts transaction list across the network.

getBlockTailsHashList

Path: /coulder/v1/node/getBlockTailsHashList

Method: GET

Request:

name type required description
baseHeight Long required the start height to get
ipPort String required the remote node's ipPort

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional block tails hash list

Description:

Retrieves block tails hash list by blockchain height.

getBlockTailsPO

Path: /coulder/v1/node/getBlockTailsPO

Method: GET

Request:

name type required description
hash Long required the block hash
ipPort String required the remote node's ipPort

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data BlockTailsPO optional block tails data

BlockTailsPO:

name type required description
height Long required the block height
hash String required the block hash
hashCrc32 Integer required the block hash crc32 value
prevHash String required the previous block hash
isMaster Byte required 0 slave 1 master

Description:

Retrieves block tails by block hash.

Miner APIs

These are internal miner APIs that provide mining services.

retrieveMinerIpPortList

Path: /miner/v1/node/retrieveMinerIpPortList

Method: POST

Request:

name type required description
version String required 0.0.1
role String required CLOUDER, MINER etc
protolVersion String required 1.0.0
publicIP String required public ip
localIP String required local ip
port Integer required the port
publicKey String optional the node's public key

Response:

name type required description
status Integer required 200 - success, others failure
message String required the message
data List optional the ipPort list

Description:

Retrieves the list of miner IP:port addresses.

Service and Event Layer

The Service and Common Library Layer includes:

  • Clouder Service
  • Provides clouder services: implementation of internal clouder APIs, including block search, heartbeat, transaction and block broadcast services.
  • Miner Service
  • Provides mining services: implementation of internal miner APIs, including miner list search functionality.
  • Wallet Service
  • Provides wallet services: implementation of public wallet APIs, including wallet creation, asset search, payments, and asset transfers.
  • Blocktails Service
  • Provides block tails services: implementation of block tails APIs for fork management.
  • NodeInfo Service
  • Node information service, provides node search and node information storage services.
  • Blockchain Library
  • Core blockchain library that provides fundamental blockchain functions.

Events:

  • BlockEvent
  • Broadcast when a cloud or miner node receives a valid block, or when a miner node successfully mines a block.
  • TransactionEvent
  • Broadcast when a cloud or miner node receives a valid transaction.
  • TransPoolEvent
  • Only miner nodes can create transaction pool events. Broadcast when the transaction pool is full or when the transaction pool waiting time expires.

Background Jobs

Background Jobs:

  • Heartbeat Job
  • Synchronizes node information with neighbor nodes. The next heartbeat starts 10 seconds after the current job completes.
  • MinerTask Job
  • Can only be executed by miner nodes. The next job executes 10 minutes after the current job completes.
  • SyncBlock Task Job
  • Executes 5 minutes after the last task completes. Starts when the node's block height is lower than the maximum height of neighbors.

Configuration Center

The Configuration Center includes:

  • Async Thread Pool Configuration - Default thread pool settings
  • Path Configuration - API endpoint path configuration
  • Block Configuration - Blockchain instance initialization configuration
  • SyncBlock Task Configuration - Determines whether sync tasks should be started
  • BlockStorage Configuration - Block storage instance configuration
  • WalletStorage Configuration - Wallet storage instance configuration
  • MinerTask Configuration - Determines whether the node should start mining tasks
  • Wallet Configuration - Wallet instance initialization configuration
  • Node Configuration - Node configuration including role, mobile, encrypted password, etc.

Storage Layer

The Storage Layer includes:

  • BlockStorage Service
  • Block storage service that supports storing large data in cloud storage.
  • BlockCopyStorage Service
  • Block copy service that provides block replication functionality.
  • WalletStorage Service
  • Wallet storage service that supports cloud wallet functionality.

Service and Event Layer

Clouder Node Services

Clouder node services provide internal services for ClouderController. The class diagram is shown below:

clouder classes

Transaction Broadcasting Mechanism

The process of broadcasting transactions to neighbor nodes:

  1. Search node information from circle_node_info table ordered by ID descending, starting with Long.MAX_VALUE
  2. When the batch is not empty, send valid transaction information to the batch of neighbor nodes
  3. When the current batch is sent, search for the next batch of nodes using the minimum ID from the current batch
  4. If the next batch is not empty, continue with step 2; otherwise, stop broadcasting

Blockchain Broadcasting

The process of broadcasting blockchain data to neighbor nodes:

  1. Search node information from circle_node_info table ordered by ID descending, starting with Long.MAX_VALUE
  2. When the batch is not empty, send valid block information to the batch of neighbor nodes
  3. When the current batch is sent, search for the next batch of nodes using the minimum ID from the current batch
  4. If the next batch is not empty, continue with step 2; otherwise, stop broadcasting

Miner Node Services

Miner node services provide internal services and functions for miner APIs. The class diagram is shown below:

miner class

Wallet Node Services

Wallet services provide internal services and functions for wallet APIs. The class diagram is shown below:

wallet class

Blockchain Libraries

The blockchain library provides common and basic functions:

Transaction Functions

The blockchain library includes four types of transactions:

  1. Coinbase Transaction - Mining rewards and new coin creation
  2. Coin Transaction - Standard cryptocurrency transfers
  3. Ownership Transaction - Digital asset ownership transfers
  4. Identity Transaction - Digital identity management

The coinbase transaction includes coin coinbase, ownership coinbase, and identity coinbase transactions.

Block Functions

Block functions include block and blockchain operations. The following capabilities are provided:

  1. Block Construction - Including genesis block and normal block creation
  2. Block Search - Locating blocks by various criteria
  3. Block Copy - Block replication functionality
  4. Block Serialization/Deserialization - Data format conversion

The block functions include:

  1. Blockchain Initialization - Setting up the blockchain
  2. Genesis Block Creation - Creating the first block
  3. New Block Addition - Adding blocks to the chain
  4. Blockchain Iteration - Traversing the blockchain
  5. UTXO Search - Finding unspent transaction outputs
  6. Spent Assets Search - Locating spent assets
  7. Transaction Search by ID - Finding transactions in the blockchain
  8. Block Search by Hash or Transaction ID - Locating blocks
  9. Transaction Signing - Cryptographic signature generation

Cryptographic Functions

The blockchain's cryptographic functions include:

  • Address Generation: User addresses are globally unique and anonymous. Each wallet generates one unique address. A registered user with a unique mobile phone can generate up to 3 wallets. Each wallet has a public key that is transformed to a public key hash using RIPEMD160 and additional processing, then encoded to an address using Base58 encoding.

  • Block and Transaction IDs: Block and transaction IDs are generated using SHA256 double hashing of their respective data.

  • Output Locking: Transaction outputs include lock scripts generated using the P2PKH (Pay-to-Public-Key-Hash) protocol, which can only be unlocked by the correct user's private key.

  • Input Unlocking: Transaction inputs include unlock scripts generated by signing with the input's key and the user's private key. The unlock script and lock script are combined and executed in the CircleChain script engine.

  • Asset Transaction Processing: All asset transactions are processed using the same algorithm and process as coin transactions.

  • Asset Security: When uploading assets, they are signed with the user's public key and encrypted using RSA with the user's RSA password. When downloading raw assets from the cloud, the system first verifies the signature and then decrypts the data using the RSA password.

Block Mining Functions

The blockchain module includes the miner's block mining function with two mining styles: single-thread and multi-thread.

Single-thread Mining Algorithm:

// Single-thread mining example
for (long i = 0; i < Long.MAX_VALUE; i++) {
    this.getBlock().setNonce(nonce);
    String shaHex = this.getBlock().computeHash();
    BigInteger shaHexValue = new BigInteger(shaHex, 16);
    log.debug("nonce:{}, shaHexValue:{}, target:{}", nonce, shaHexValue, this.target);
    if (shaHexValue.compareTo(this.target) < 0) {
        break;
    }
}
// Block mining successful!

Multi-thread Mining Algorithm:

int mineThreadCount = Runtime.getRuntime().availableProcessors() + 1; // CPU cores + 1
CircleMiner[] array = new CircleMiner[mineThreadCount];
Long span = Long.MAX_VALUE / mineThreadCount;
for (int i = 0; i < mineThreadCount; i++) {
    BigInteger end = BigInteger.valueOf(i + 1L).multiply(BigInteger.valueOf(span));
    if (end.compareTo(BigInteger.valueOf(Long.MAX_VALUE)) > 0) {
        end = BigInteger.valueOf(Long.MAX_VALUE);
    }
    Range<Long> nonceRange = Range.between(i * span, end.longValue());
    array[i] = new CircleMiner(nonceRange, minerAddress, repoType);
}
List<CompletableFuture<Block>> fList = Lists.newArrayListWithExpectedSize(array.length);
for (CircleMiner miner : array) {
    CompletableFuture<Block> bF = CompletableFuture.supplyAsync(() -> {
        try {
            Block copyOfBlock = Block.deepCopy(unminedBlock);
            Block b = miner.mineBlock(copyOfBlock, repoType);
            if (b != null) {
                log.info("mined block:{}", b.toString());
                return b;
            }
        } catch (Exception e) {
            log.error("mineBlock exception", e);
            minedSuccess.compareAndSet(true, false);
        }
        return null;
    }, threadPool);
    fList.add(bF);
}

Wallet Functions

The wallet system includes wallet packages, individual wallets, and address functions and concepts.

Wallet Package: Only one mobile phone can register for one wallet package.

Wallet: A wallet package contains at most 3 wallets. Each wallet includes a public key and private key pair. The public key generates a public address, and the public address generates a public key hash. The public key hash is used to lock transactions, and the private key is used to generate unlock scripts to unlock lock scripts.

Address: Users use addresses to exchange tokens and assets. A public key is used to generate the address.

Wallet Service Functions:

  1. Wallet Assets Query - Query wallet assets and balances
  2. Token Transactions - Handle cryptocurrency transfers
  3. Asset Transactions - Manage digital asset transfers

Blockchain Fork Management Service

The Blocktails Service is designed to resolve blockchain forking issues. When two or more blocks are mined in the same second, the blockchain forks. The miner stores the forked blocks in the circle_block table and records the forking information in circle_block_tails. When multiple blocks are mined in the same second, the system selects the earliest block as the master block by default and stores the master information in circle_block_tails.

The system stores every block in circle_block and must update the circle_block_tails table and master information according to the rules of maximum height and earliest block mining time.

Design Principles

The master block selection algorithm is as follows:

  1. Search for all master blocktails information ordered by height descending, limit 1
  2. When the blocktails is not null, the blocktails' block is the master block

The circle_block_tails table structure:

Fields Type Description
height Long The height in the blockchain
hash String The hash of the current block
hash_crc32 Integer CRC32 value of the block hash
prev_hash String The previous hash of the current block
is_master Boolean Flag indicating if the block is master

The forking information is stored in the circle_block_tails table.

Forking Process Mechanism

When a broadcast block arrives at a miner node, if the broadcast block has the same block height as the top block of the blockchain and its mined block timestamp is equal to or earlier than the top block (in seconds), then the broadcast block cannot be confirmed as invalid and should be added to circle_block. This causes the blockchain to fork. The forking information of the blockchain will be updated in circle_block_tails. To confirm a block, the forking block depth should be at least 6 or more.

The blockchain confirmation depth is 6. When block confirmation reaches 6, the block can become a master block and can never be changed or deleted. If the block confirmation depth is less than 6, there is a possibility that the block is a slave block due to blockchain forking.

Node Information Services

The CircleChain node information service provides neighbor node information storage and data services for heartbeat, block, and transaction broadcasting.

Node Information Table

The circle_node_info table structure:

Fields Type Description
public_ip String Public IP address
local_ip String Internal IP address
version String Node version
role String Role: CLOUDER (clouder node) or MINER (miner node)
protol_version String Protocol version
port Integer Server port
public_key String Node public key that represents the node
base_height Integer The top height of the CircleChain node blockchain
visit_count Integer Node visit count, default 0
create_time Long Creation time in milliseconds
update_time Long Update time in milliseconds

This table provides data services for broadcasting heartbeat, blocks, and transactions, as well as synchronizing CircleChain node information and blocks.

Background Jobs

Heartbeat Task

The node synchronizes node information with up to 100 neighbor nodes every 10 seconds.

Heartbeat Broadcasting Mechanism

Every query searches for up to 100 least-visited miners in the circle_node_info table. After each heartbeat search, the visit count of these least-visited miners is increased. This ensures that the next query for least-visited miners will include other unvisited or less-visited miners.

Broadcast Algorithm:

List<BaseNodeInfo> baseNodeInfoList = nodeInfoService.queryLeastVisitMiners(); // Query least-visited miners
log.info("searched {} miners to heartbeat", baseNodeInfoList.size());
if (CollectionUtils.isNotEmpty(baseNodeInfoList)) {
    syncSendHeartBeat(baseNodeInfoList);
    List<String> publicIpList = baseNodeInfoList.stream().map(BaseNodeInfo::getPublicIP)
                      .collect(Collectors.toList());
    nodeInfoService.addVisitCountOfNeighbors(publicIpList); // Increase visit count of least-visited miners
}

Block Mining Task

The miner's block mining task checks the mining conditions every 10 minutes after the task completes. When the conditions are met, the mining task starts. The conditions include the following criteria:

  1. The time span since the last mined block is greater than MAX_WAIT_TIME (60 seconds)
  2. The number of transactions in the transaction pool is greater than MAX_BLOCK_TX_SIZE (2048)

If either condition is met, the block mining task will be started.

Miner Design

See more details in the Blockchain Library section.

Block Broadcasting Mechanism

The mechanism is the same as the heartbeat broadcasting.

Note: Only miner nodes have the block broadcasting task; clouder nodes and others do not.

Block Synchronization Task

The block synchronization task starts every 5 minutes after the last synchronization task completes.

Block Synchronization Mechanism

The block synchronization mechanism includes the following steps:

  1. Search for the maximum height node information in the circle_node_info table
  2. In a loop, synchronize block data from the maximum height node using public IP and port, starting from the node's own base height in batches of 100 items
  3. When block synchronization is finished, break the loop

Configuration Center

Async Thread Pool Configuration

Default thread pool configuration:

core_pool_size: 5
max_pool_size: 10
queue_capacity: 100

Path Configuration

External API path configuration:

API Path Configuration

## Clouder APIs
path.blockHashListPath=/clouder/v1/node/getBlockHashList
path.blockPath=/clouder/v1/node/getBlock
path.blockHeaderListPath=/clouder/v1/node/getBlockHeaderList
path.blockDataPath=/clouder/v1/node/getBlockData
path.blockTailsHashListPath=/clouder/v1/node/getBlockTailsHashList
path.blockTailsPOPath=/clouder/v1/node/getBlockTailsPO
path.heartbeatPath=/clouder/v1/node/heartbeat
path.broadcastMinedBlock=/clouder/v1/node/broadcastMinedBlock
path.broadcastTransaction=/clouder/v1/node/broadcastTransaction

## Miner APIs
path.minerIpPortList=/miner/v1/node/retrieveMinerIpPortList

## Wallet APIs
path.initWalletPackage=/wallet/v1/node/initWalletPackage
path.createWallet=/wallet/v1/node/createWallet
path.listWallet=/wallet/v1/node/listWallet
path.listPubkey=/wallet/v1/node/listPubkey
path.balanceOfAddress=/wallet/v1/node/getBalanceOfAddress
path.balanceOfWallet=/wallet/v1/node/getBalanceOfWallet
path.pubKeyHashFromAddress=/wallet/v1/node/getPubKeyHashFromAddress
path.sendTo=/wallet/v1/node/sendTo
path.requestCharge=/wallet/v1/node/requestCharge

## Block APIs
path.blockchainHashListPath=/block/v1/node/get-block-hashlist
path.blockchainPath=/block/v1/node/get-block
path.blockchainHeaderListPath=/block/v1/node/get-block-header-list
path.blockchainDataPath=/block/v1/node/get-block-data
path.blockchainTailsHashListPath=/block/v1/node/get-blocktails-hashlist
path.blockchainTailsPOPath=/block/v1/node/get-blocktails-po

Blockchain Configuration

The blockchain initialization code:

public class BlockchainConfig {
    @Bean(name = "blockchain")
    @DependsOn("blockCloudRepository")
    public Blockchain getBlockchain() {
        Blockchain blockchain = null;

        try {
            blockchain = Blockchain.initBlockchain(RepoType.CLOUD_STORE);
        } catch (Exception e) {
            log.error("initBlockchain error!", e);
            blockchain = Blockchain.createGenesisBlockchain(RepoType.CLOUD_STORE);
        }

        return blockchain;
    }
}

Block Synchronization Configuration

Block synchronization configuration includes checking node height with neighbors and configuring synchronization intervals.

In the JUnit profile, the block synchronization task is not started.

Neighbor Node Selection and Block Synchronization Algorithm

The following Java code samples describe how to select neighbor nodes and implement the synchronization algorithm:

Neighbor Node Selection Algorithm:

BaseNodeInfo maxHeightNodeInfo = clouderService.getMaxHeightInNeighbors();
if (Objects.isNull(maxHeightNodeInfo)) {
    log.warn("there is no max height node!");
    return 0;
}
BaseNodeInfo myNodeInfo = clouderService.getMyBaseNodeInfo();
if (myNodeInfo.getBaseHeight() >= maxHeightNodeInfo.getBaseHeight()) {
    log.warn("my node height {} is not less than neighbor {}!", myNodeInfo.getBaseHeight(),
              maxHeightNodeInfo.getBaseHeight());
    return 0;
}
if (!NetworkUtils.isValidPublicIP(maxHeightNodeInfo.getPublicIP())) {
    log.warn("max height node has no public ip, nodeInfo:{}!", JSON.toJSONString(maxHeightNodeInfo));
    return 0;
}

Block Synchronization Algorithm:

BaseResponse<List<String>> result = clouderApiClient.getBlockHashList(baseHeight, ipPort);
List<String> hashList = result.getData();
for (String hash : hashList) {
    BaseResponse<BlockPO> blockResult = clouderApiClient.getBlock(hash, ipPort);
    if (blockResult != null && blockResult.isOk()) {
        BlockPO blockPO = blockResult.getData();
        Block block = blockPO.convert2Block();
        if (!BlockValidator.verifyBlock(blockchain, block, RepoType.CLOUD_STORE)) {
            log.error("block {} is invalid, discard it...", block.getHash());
            continue;
        }
        blockCopyRepository.copyBlock(block);
    } else {
        log.error("cannot get block from ipPort: {}", ipPort);
    }
}

Blockchain Configuration

Blockchain instance configuration settings.

Wallet Storage Configuration

Wallet instance configuration settings.

Miner Task Configuration

Miner task configuration includes checking whether the node is a miner node and starting the mining task when the node is a miner node.

Wallet Configuration

Wallet instance configuration settings.

Node Information Configuration

Node information configuration includes role, mobile, and encrypted password settings.

Storage Layer

Blockchain Storage Service

Blockchain storage service that supports big data storage.

Interfaces

The blockchain storage service includes the following APIs:

Initialization and Cleanup:

  • void init(): Initialize the service

  • void close(): Clean up resources

Block Search:

  • String getFirstBlockHash(): Get the first block hash

  • String getLastBlockHash(): Get the last block hash

  • Block getBlock(): Get a block

  • String getPrevBlockHash(String blockHash): Get the previous block hash

  • boolean blockExists(String blockHash): Check if a block exists

  • Long getHeight(String blockHash): Get block height

  • Long getBlockHeightByTxId(byte[] txId): Get block height by transaction ID

  • Block getBlockByTxId(byte[] txId): Get block by transaction ID

Block Addition:

  • boolean addBlock(Block block): Add a block to the blockchain

UTXO Functions:

  • Map<String, byte[]> getChainstateBucket(): Search local UTXO mapping

  • void cleanChainStateBucket(): Clear local UTXO data

  • void putUTXOs(String txIdHexStr, TXOutput[] utxos): Save UTXOs in local storage

  • TXOutput[] getUserUTXOs(byte[] pubKeyHash): Search UTXOs by public key hash

  • TXOutput[] getUTXOs(String txIdHexStr): Search transaction UTXOs by transaction ID

  • int deleteUTXOs(String txIdHexStr): Delete UTXOs by transaction ID

Transaction Search:

  • Transaction findTransaction(byte[] txId): Find a transaction

  • List<String> transactionFilterByTypeSet(List<String> txIdList, Set<Integer> typeSet): Filter transaction ID list by transaction type set

Blockchain Copy Service

The blockchain copy service provides block replication functionality.

Details

The copy block service does not validate blocks and their transactions, as it assumes that all input data is valid by default.

Interfaces

  • boolean copyBlock(Block block): Copy block data to the database without any validation

  • boolean copyBlockTail(CircleBlockTails circleBlockTails): Copy block tails data to the database without validation

Wallet Storage Service

The wallet storage service provides wallet data storage functionality, supporting both cloud and local wallet storage for big data.

Interfaces

There are unified APIs for local and cloud storage:

Initialization and Cleanup:

  • void init(): Initialize resources

  • void close(): Clean up resources

Wallet Package Management:

  • void initWalletPackage(WalletPackage walletPackage): Initialize wallet package

  • void updateWalletPackage(WalletPackage walletPackage): Update wallet package

Wallet Package Configuration:

  • WalletPackageConfig getWalletPackageConfigByAddress(String address): Get wallet package configuration by address

  • WalletPackageConfig getWalletPackageConfigByPhone(String phone): Get wallet package configuration by phone

  • WalletPackageConfig getWalletPackageConfigByUid(String uid): Get wallet package configuration by UID

  • boolean saveOrUpdatePhone(String phone, WalletPackageConfig config): Save or update wallet package configuration by phone and config

  • boolean saveOrUpdateAddress(String address, WalletPackageConfig config): Save or update wallet package by address and config

  • boolean saveOrUpdateUid(WalletPackageConfig config): Save or update wallet configuration by UID

  • boolean updateWalletPackageConfig(WalletPackageConfig config): Save or update wallet package configuration

Cloud Wallet Service

The cloud wallet service provides cloud-based wallet functionality, storing your personal wallet data including private keys on secure cloud servers. You can access cloud wallet services through H5 pages to query personal tokens and assets, make transactions, etc.

The cloud wallet server is among the most highly secure servers in the world. You don't need to worry about your personal assets being lost or stolen. Even if your valuable data were lost, you would be compensated by our company (SHC Ltd.).

Local Wallet Service

The Local Wallet Service provides local wallet functionality that does not store your private keys in the cloud. You must store and backup your private keys and local wallet data yourself. If your private keys and local wallet data are lost or stolen, you will be responsible for the consequences.