본문으로 건너뛰기
버전: 3.3.0

IOST Blockchain API

아래 객체들은 컨트랙트 코드 안에서 바로 사용할 수 있습니다.

storage 객체

모든 변수는 런타임에 메모리에 저장됩니다. IOST는 스마트 컨트랙트에서 데이터를 영속화할 수 있도록 storage 객체를 제공합니다. 'global' 접두어가 없는 API는 호출 중인 컨트랙트 자신의 스토리지를 읽고 씁니다. 'global' 접두어가 붙은 API는 다른 컨트랙트의 스토리지를 읽는 데 사용합니다.

Storage API

put(key, value, payer=contractOwner)

key-value 쌍을 스토리지에 저장합니다.

파라미터타입비고
keystring65536 바이트를 넘을 수 없음
valuestring65536 바이트를 넘을 수 없음
payerstring(선택)누가 ram 비용을 지불할지를 결정합니다. 비워두면 컨트랙트 발행자가 ram 비용을 지불합니다.

반환값: 없음

예시:

// k-v 쌍을 스토리지에 저장하고 ram 비용은 컨트랙트 owner가 지불
storage.put("test-key", "test-value");

// k-v 쌍을 스토리지에 저장하고 ram 비용은 트랜잭션 발행자가 지불
storage.put("test-key", "test-value", tx.publisher);

get(key)

key로 스토리지에서 값을 가져옵니다.

파라미터타입비고
keystring

반환값: 존재하면 string, 존재하지 않으면 null

예시:

let v = storage.get("test-key");
if (v !== null) {
...
}

has(key)

해당 key가 스토리지에 존재하는지 확인합니다.

파라미터타입비고
keystring

반환값: bool (true: 존재, false: 없음)

예시:

if (storage.has("test-key")) {
...
}

del(key)

key로 스토리지에서 key-value 쌍을 삭제합니다.

파라미터타입비고
keystring

반환값: 없음

예시:

storage.del("test-key")

mapPut(key, field, value, payer=contractOwner)

(key, field, value) 쌍을 저장합니다. key+field로 value를 찾습니다.

파라미터타입비고
keystring65536 바이트를 넘을 수 없음
fieldstring65536 바이트를 넘을 수 없음
valuestring65536 바이트를 넘을 수 없음
payerstring(선택)누가 ram 비용을 지불할지를 결정합니다. 비워두면 컨트랙트 발행자가 ram 비용을 지불합니다.

반환값: 없음

예시:

// key-field-value 쌍을 저장하고 ram 비용은 컨트랙트 owner가 지불
storage.mapPut("test-key", "test-field", "test-value");

// key-field-value 쌍을 저장하고 ram 비용은 트랜잭션 발행자가 지불
storage.mapPut("test-key", "test-field", "test-value", tx.publisher);

mapGet(key, field)

(key, field) 쌍을 조회합니다. key+field로 value를 찾습니다.

파라미터타입비고
keystring
fieldstring

반환값: 존재하면 string, 존재하지 않으면 null

예시:

let v = storage.mapGet("test-key", "test-field");
if (v !== null) {
...
}

mapHas(key, field)

(key, field) 쌍의 존재 여부를 확인합니다.

파라미터타입비고
keystring
fieldstring

반환값: bool (true: 존재, false: 없음)

예시:

if (storage.mapHas("test-key", "test-field")) {
...
}

mapKeys(key)

해당 key가 가진 field 목록을 가져옵니다.

주의:

1. 이 API는 최대 256개의 field만 저장합니다. 초과하는 field는 저장되지도 반환되지도 않습니다. 2. 맵의 모든 키를 얻을 필요가 있다면 직접 관리하고 이 API를 사용하지 않을 것을 권장합니다.

파라미터타입비고
keystring

반환값: array[string] (field 배열)

mapLen(key)

mapKeys()의 길이를 반환합니다.

mapKeys와 동일한 주의 사항이 적용됩니다.

파라미터타입비고
keystring

반환값: int (field 개수)

mapDel(key, field)

(key, field, value) 쌍을 삭제합니다. key+field로 value를 삭제합니다.

파라미터타입비고
keystring
fieldstring

반환값: 없음

Global Storage API

다른 컨트랙트의 스토리지를 읽는 API들입니다.

globalHas(contract, key)

지정한 컨트랙트의 스토리지에 key가 존재하는지 확인합니다.

파라미터타입비고
contractstring컨트랙트 ID
keystring

반환값: bool (true: 존재, false: 없음)

예시:

if (storage.globalHas("Contractxxxxxx", "test-key")) {
...
}

globalGet(contract, key)

지정한 컨트랙트의 스토리지에서 key로 value를 가져옵니다.

파라미터타입비고
contractstring컨트랙트 ID
keystring

반환값: 존재하면 value string, 없으면 null

예시:

let v = storage.globalGet("Contractxxxxxx", "test-key");
if (v !== null) {
...
}

globalMapHas(contract, key, field)

지정한 컨트랙트의 스토리지에 (key, field) 쌍이 존재하는지 확인합니다.

파라미터타입비고
contractstring컨트랙트 ID
keystring
fieldstring

반환값: bool (true: 존재, false: 없음)

예시:

// auth.iost 컨트랙트의 스토리지를 읽어 계정 존재 여부 확인
accountExists(account) {
return storage.globalMapHas("auth.iost", "auth", account);
}

globalMapGet(contract, key, field)

다른 컨트랙트의 스토리지에서 (key, field) 쌍의 값을 가져옵니다.

파라미터타입비고
contractstring컨트랙트 ID
keystring
fieldstring

반환값: 존재하면 value string, 없으면 null

예시:

let v = storage.globalMapGet("Contractxxxxxx", "test-key", "test-field");
if (v !== null) {
...
}

globalMapLen(contract, key)

다른 컨트랙트의 스토리지에서 특정 key가 가진 field 개수를 셉니다.

mapKeys와 동일한 주의 사항이 적용됩니다.

파라미터타입비고
contractstring컨트랙트 ID
keystring

반환값: int (field 개수)

globalMapKeys(contract, key)

다른 컨트랙트의 스토리지에서 특정 key가 가진 field 목록을 가져옵니다.

mapKeys와 동일한 주의 사항이 적용됩니다.

파라미터타입비고
contractstring컨트랙트 ID
keystring

반환값: array[string] (field 배열)

blockchain 객체

blockchain 객체는 시스템 API를 호출하거나 다른 컨트랙트의 abi를 호출하는 데 사용됩니다.

transfer(from, to, amount, memo)

iost 토큰을 송금합니다.

파라미터타입비고
fromstring토큰을 보내는 계정
tostring토큰을 받는 계정
amountstring송금 수량
memostring부가 정보

반환값: 없음

예시:

// 트랜잭션 발행자의 1.23 iost를 testacc로 송금
blockchain.transfer(tx.publisher, "testacc", "1.23", "this is memo")

withdraw(to, amount, memo)

컨트랙트에서 iost 토큰을 출금합니다. 다음과 동일합니다:

blockchain.transfer(blockchain.contractName(), to, amount, memo)

파라미터타입비고
tostring토큰을 받는 계정
amountstring송금 수량
memostring부가 정보

반환값: 없음

예시:

// 컨트랙트에서 1.23 iost를 testacc로 전송
blockchain.withdraw(tx.publisher, "1.23", "this is memo")

deposit(from, amount, memo)

iost 토큰을 컨트랙트에 입금합니다. 다음과 동일합니다:

blockchain.transfer(from, blockchain.contractName(), amount, memo)

파라미터타입비고
fromstring송금 계정
amountstring송금 수량
memostring부가 정보

반환값: 없음

예시:

// 트랜잭션 발행자에서 1.23 iost를 컨트랙트로 전송
blockchain.deposit(tx.publisher, "1.23", "this is memo")

contractName()

컨트랙트 ID를 반환합니다.

파라미터: 없음

반환값: 컨트랙트 ID 문자열

publisher()

트랜잭션 발행자를 반환합니다.

파라미터: 없음

반환값: tx publisher 문자열

contractOwner()

컨트랙트 owner를 반환합니다.

파라미터: 없음

반환값: 컨트랙트 발행자 문자열

call(contract, abi, args)

다른 컨트랙트의 abi를 args와 함께 호출합니다.

파라미터타입비고
contractstring컨트랙트 ID
abistring
argsarray/string인자 배열, 또는 그 JSON 문자열

반환값: 호출된 컨트랙트의 반환값을 담은 JSON 문자열을 원소로 가지는 배열.

예시:

// token.iost의 balanceOf를 호출하여 admin의 iost 잔액 조회
let ret = blockchain.call("token.iost", "balanceOf", ["iost", "admin"])
console.log(ret[0]) // 주의: ret[0]이 balanceOf의 반환값

// vote.iost의 getResult를 호출하여 투표 결과 조회
let ret = blockchain.call("vote.iost", "getResult", ["1"])
let voteRes = JSON.parse(ret[0]) // vote.iost의 getResult가 배열을 반환하므로 JSON 파싱이 필요

callWithAuth(contract, abi, args)

호출 측 컨트랙트의 권한을 가지고 다른 컨트랙트의 abi를 호출합니다.

파라미터타입비고
contractstring컨트랙트 ID
abistring
argsarray/string인자 배열, 또는 그 JSON 문자열

반환값: 호출된 컨트랙트의 반환값을 담은 JSON 문자열을 원소로 가지는 배열.

예시:

// testacc로 20 iost 송금
blockchain.callWithAuth("token.iost", "transfer", ["iost", blockchain.contractName(), "testacc", "20", ""]);

// call을 사용하면 컨트랙트의 토큰 송금에는 권한이 필요하므로 오류가 발생합니다.
blockchain.call("token.iost", "transfer", ["iost", blockchain.contractName(), "testacc", "20", ""]); // throw error

requireAuth(account, permission)

지정 계정의 지정 권한이 제공되었는지 확인합니다.

파라미터타입비고
accountstring
permissionstring

반환값: bool (true: 권한이 제공됨, false: 아님)

예시:

// testacc의 active 권한이 제공되었는지 확인
// 즉, 트랜잭션에 testacc의 active 키 서명이 포함되어 있는지를 확인
const ret = blockchain.requireAuth('testacc', 'active');
if (ret !== true) {
throw new Error("require auth failed");
}

receipt(data)

영수증을 생성합니다.

파라미터타입비고
datastring

반환값: 없음

예시:

testReceipt() {
blockchain.receipt("some receipt content")
}

이 컨트랙트의 testReceipt를 호출하면 TxReceipt에 다음과 같은 항목이 기록됩니다.

"receipts": [
{
"funcName": "Contractxxxxx/testReceipt",
"content": "some receipt content"
}
]

event(data)

이벤트를 발행합니다.

파라미터타입비고
datastring

반환값: 없음

예시:

testEvent() {
blockchain.event("some event content")
}

이 컨트랙트의 testEvent를 호출한 뒤에는 subscribe를 통해 이벤트를 받을 수 있습니다.

curl -X POST http://127.0.0.1:30001/subscribe -d '{"topics":["CONTRACT_EVENT"], "filter":{"contract_id":"Contractxxxxx"}}'

{"result":{"event":{"topic":"CONTRACT_EVENT","data":"some event content","time":"1557150634515314000"}}}

blockchain.contextInfo()

{"abi_name":"hello","caller":{"name":"admin","is_account":true},"contract_name":"ContractATrHLF6LnpzjwQ1iU4VB38cSCURYzeCSyH8nSFSw8Tnc","publisher":"admin"}

tx 객체와 block 객체

tx 객체에는 현재 트랜잭션의 정보가 담겨 있습니다. 속성은 다음과 같습니다.

{
time: 1541541540000000000, // 나노초
hash: "4mBbjkCYJQZz7hGSdnRKCLgGEkuhen1FCb6YDD7oLmtP",
expiration: 1541541540010000000, // 나노초
gasLimit: 100000,
gasRatio: 100,
authList: {"Gcv8c2tH8qZrUYnKdEEdTtASsxivic2834MQW6mgxqto":2}, // pubkey
publisher: "user0"
}

예시:

console.log(tx.publisher)

block 객체에는 현재 블록의 정보가 담겨 있습니다. 속성은 다음과 같습니다.

{
number: 132,
parentHash: "4mBbjkCYJQZz7hGSdnRKCLgGEkuhen1FCb6YDD7oLmtP", // 부모 블록 해시
witness: "6sNQa7PV2SFzqCBtQUcQYJGGoU7XaB6R4xuCQVXNZe6b", // 블록 생성자 pubkey. Producer 키는 계정 키와 다릅니다.
time: 1541541540000000000 // 나노초
}

예시:

console.log(block.time)

IOSTCrypto 객체

IOSTCrypto는 해시 함수와 서명 검증 함수를 제공합니다.

sha3(data)

sha3-256 해시를 계산합니다.

파라미터타입비고
datastring

반환값: 해시 바이트 배열을 base58로 인코딩한 문자열. (base58_encode(sha3_256(data)))

예시:

IOSTCrypto.sha3("Fule will be expensive. Everyone will have a small car.") // 결과: EBNarfcGkAczpeiSJwtUfH9FEVd1xFhdZis83erU9WNu

반환값: base58_encode(sha3_256(data))

verify(algo, message, signature, pubkey)

서명을 검증합니다. ed25519와 secp256k1 알고리즘을 모두 지원합니다.

파라미터타입비고
algostring"ed25519" 또는 "secp256k1"
messagestringbase58로 인코딩된 서명 대상 원문
signaturestringbase58로 인코딩된 검증할 서명
pubkeystringbase58로 인코딩된 서명에 사용된 개인키에 대응하는 공개키
  • 반환값: int, 1 (성공) 또는 0 (실패)

예시:

// ed25519 알고리즘 사용
// base58 인코딩된 개인키: "4PTQW2hvwZoyuMdgKbo3iQ9mM7DTzxSV54RpeJyycD9b1R1oGgYT9hKoPpAGiLrhYA8sLQ3sAVFoNuMXRsUH7zw6"
// base58 인코딩된 공개키: "2vSjKSXhepo7vmbPQHFcnEvx8mWRFrf46DaTX1Bp3TBi"
// 원문: "hello world"
// "StV1DL6CwTryKyV"는 "hello world"의 base58 인코딩 결과
// "38V8bZC4e78pU7zBN86CF8R8ip76Rhf3vyiwTQR2MVkqHesmUbZJVmN8AE6eWhQg6ekKaa2H4iB4JJibC5stBRrN"는 위 개인키로 서명한 base58 인코딩 결과
// 따라서 검증 결과는 1이어야 합니다.
let v = IOSTCrypto.verify("ed25519", "StV1DL6CwTryKyV", "38V8bZC4e78pU7zBN86CF8R8ip76Rhf3vyiwTQR2MVkqHesmUbZJVmN8AE6eWhQg6ekKaa2H4iB4JJibC5stBRrN", "2vSjKSXhepo7vmbPQHFcnEvx8mWRFrf46DaTX1Bp3TBi"); // v = 1

Float64, Int64, BigNumber 객체

컨트랙트에서는 고정밀 계산을 위해 Float64, Int64, BigNumber를 사용할 수 있습니다. Float64 API는 여기 에서 확인할 수 있습니다. Int64 API는 여기 에서 확인할 수 있습니다. BigNumber API는 여기 에서 확인할 수 있습니다.

예시:

let bonus = new Float64("1.0123456789");
let earning = bonus.div(2).toFixed(8); // earning은 "0.50617283"
blockchain.withdraw("testacc", earning, "");

비활성화된 JavaScript 메서드

보안상의 이유로 일부 JavaScript 기능이 금지되어 있습니다. 이 문서 에서 허용/금지 API 목록을 확인할 수 있습니다.