#blockchain

블록체인의 탄생

현대 사회에서 기술의 발전의 가장 큰 흐름은 바로 atom worldbit world 로 옮기려 한다는 것이다.
모든 실제 세계의 정보와 행동 양식 더 넘어서는 시장 그 자체에 이르기 까지 모든 atom world 즉, 실제 세계의 모든 것을 컴퓨터 사이의 네트워크로 구성되는 bit world 에 밀어 넣으려는 다양한 시도들이 계속되었다.

흔히, Database 즉, 데이터를 넣기위한 저장공간은 실제로 현대사회에서 모든 권리를 대변하고 있다.
은행의 돈, 국가에서 개인의 신분 등 모든 중요한 정보들은 database 내에 존재하고 실제가 어떻게 되었든 database 안의 내용이 곧 진리인 사회속에서 우리는 살아가고 있다. 심지어는 database에 명확하게 들어가지 못하는 많은 정보들은 그 가치를 잃어가는 사회이기도 하다.

하지만, 이렇게 모든 현실 세계의 데이터를 database라는 꽉막힌 틀이 쑤셔넣는 것은 상당한 노력을 필요로 하는 일이고, 심지어 이러한 데이터베이스는 단지 하나의 컴퓨터에 존재하는 bit 덩어리에 불과하기 때문에 사람들이 서로가 소통해서 문제를 해결하듯이 database와 database 사이에서 원활하게 정보를 교류하여 문제를 빠르게 처리하는 것은 매우 어렵다.

각 database는 서로 다른 형태로 존재하고 때문에 우리는 유사한 정보를 수도없이 많이 컴퓨터에게 가르쳐 주어야 한다.
흔한 예로 우리는 수많은 사이트에 수도없이 많이 같은 주소를 입력하고, 정부에서 민원을 처리하는 경우 각 부서를 옮겨다니면서 수십번씩 이름과 개인 정보를 입력하는 수고를 들여서 일을 처리해야 한다. 이는 너무나도 비효율적인 시스템이 아닐 수 없다.

시간이 지나고 우리는 이렇게 유연하지 못한 database의 홍수 속에서 어떻게 각각의 database를 통합하여 보다 유연하고 효율적인 데이터의 흐름을 만들어 낼 수 있을지 고민하게 되고 3가지의 해안을 제시하게 되었다.

1.Diverse peers model
첫번째 방법은 단순히 컴퓨터와 컴퓨터를 연결하는 것이다.
흔히 오늘날에는 결제를 하기 위해 쇼핑몰과 통신하고, 쇼핑몰은 은행과 은행은 다시 국세청과 정보를 교환해야 한다.
이렇게 하나의 단순 작업을 처리하기 위해서 각 peer들이 계속해서 통신을 해야하고 매일매일 소프트웨어를 업그레이드해야 할 뿐만 아니라 버그에도 매우 취약하다.

또 하나의 심각한 문제는 무엇이 진짜인지를 알 수 없다는 것이다.
진리는 존재하지 않고 각 peer 들 내부의 database의 수치값만이 존재하기 때문에 정보가 일관되지 않은 경우가 빈번하게 일어난다.
가령 내가 쇼핑몰에서 물건을 주문과 결제를했는데 쇼핑몰 내의 database에서 내가 결제한 정보가 없다고 선언해 버린다면 우리는 대처할 수 있는 방법이 사실상 거의 없다고 보아도 무관하다.
또 A 업체와 B 업체가 거래를 하려고 하는데 서로가 가진 재고량과 주문, 발송량이 일치하지 않는 경우 심각한 문제를 초래하게 된다.

2.Hub and Spoke
두번째 방법은 이렇게 어려움 프로세스를 맡아줄 중앙 허브를 두는 것이다.
많은 peer들이 직접 서로가 1:1 로 수십번 정보의 일관성을 흐리지 않고 정보를 교환하는 것은 매우 어렵기 때문에 이 모든 일을 다 처리해줄 마법같은 서비스들이 등장하게 되었다. 가령 결제사라던가 전자인증정보 시스템, VISA 처럼 수많은 peer들과 올바로 통신하고 데이터의 일관성을 보장해주는 중앙기관이 생기고 나머지 모든 peer는 이러한 중앙기관에 의존해 업무를 처리하는 것이다.

사실상 이러한 시스템은 자연적 독점기업이라고 보아도 무방하다. 이렇게 수많은 peer 들이 정보를 교환하는데 이 중앙 기업은 technical cost 라는 명목으로 막대한 부를 축적하고 당신의 신용과 정보에 대한 완벽한 통제권을 가지고 있다. 이는 전혀 민주적이지 못하며 VISA 사의 경우 전 세계 거래의 1% 라는 천문학적인 수입을 올릴 수 있는 시스템이 완성되는 것이다.

3.Protocol - if you can find them
프로토콜은 궁극의 유니콘 같은 존재이다. 최적의 프로토콜을 찾으면 이러한 database의 완벽한 통합을 할 수 있겠지만, 현실 세계에서는 아무도 그런 프로토콜을 가지고 있지 못하다.
HTTP, HTML, SMTP 등 많은 standard 들이 생겨나게 되었지만 아직 많은 한계들이 보인다.
가령 slack 이나 Gchat의 경우 각 플랫폼 내의 사용자들이 서로간에 소통할 수 있도록 기존의 프로토콜사용하여 훌륭하게 동작시키고 있지만, 각 기업들 사이에 데이터를 교환하는 것은 불가능하다. 왜냐하면 각 기업이 어떤 프로토콜을 사용하는지를 공개하지 않기 때문이다. 때문에, 모든 서비스에 접근하여 중재역할을 하기 위해서는 각 게이트웨이를 해킹하는 수밖에는 없다.

블록체인은 위의 세가지 해안이 극복하지 못하는 많은 부분을 해결해 줄 해안으로 떠올랐고 그것이 블록체인의 시작이다.

참고자료 - Programmable Blockchains in Context: Ethereum’s Future by vinay gupta

블록체인이란 무엇인가요?

블록체인이란 수많은 컴퓨터들을 연결하여 모든 컴퓨터가 동일한 체인 형태의 정보 리스트를 가지도록 하는 분산 컴퓨팅 기반의 데이터 위변조 기술이다.
이 때 저장하고자 하는 데이터는 작은 정보들의 집합인 블록으로 구성되고 각 블록들이 서로 연결고리를 가지게 하여 누구도 중간 블록을 수정할 수 없고, 변경의 결과를 열람할 수 있게된다.

이러한 블록체인의 가장 큰 특징은 바로 분산 노드의 운영자가 임의로 데이터를 조작하지 못한다는 것이다.
가령 기존의 데이터베이스의 경우 데이터베이스의 관리자가 손쉽게 데이터베이스를 조작할 수 있었고, 악한 마음을 가진다면 이를 기정사실화 하여 각종 보안 문제들에 휘말리게 된다. 하지만 블록체인의 경우 각 블록들이 수정되면 전체 연결고리가 깨어지게 되어 근본적으로 기존의 데이터를 수정하지 못하도록 고안되었기에 데이터베이스 관리자가 모든 권한을 가졌던 기존의 중앙집권적 권력체계가 무너지게 된다고 볼 수 있기에 보다 민주적인 형태의 데이터 저장 기술로 칭송받고 있다.

이러한 분산 시스템을 운영함에 있어 가장 큰 문제 중 하나는 비잔틴 장군 문제(Byzantine General Problems) 이다.
여기서는 적군의 도시를 공격하려는 비잔티움 제국군의 여러 부대가 지리적으로 떨어진 상태에서 각 부대의 지휘관들이 (중간에 잡힐지도 모르는) 전령을 통해 교신하면서 공격 계획을 함께 세우는 상황을 가정하고 있습니다. 이 부대의 지휘관 중 일부에는 배신자가 섞여있을 수 있고, 배신자는 규칙을 충실히 따르는 충직한 지휘관들과 달리 규칙에 얽매이지 않고 마음대로 행동할 수 있다. 이 때 배신자의 존재에도 불구하고 충직한 지휘관들이 동일한 공격 계획을 세우기 위해서는 충직한 지휘관들의 수가 얼마나 있어야 하며, 이 지휘관들이 어떤 규칙을 따라 교신해야 하는지에 대한 문제가 비잔티움 장군 문제이다.

블록체인 기술은 이러한 비잔틴 장군 문제를 최초로 해결하였으며 비잔틴 장군 문제에 대한 내성이 있다는 의미로 비잔틴 장애 허용(BFT) 시스템 중의 하나이다.

블록체인 플랫폼 이더리움 백서에 대한 설명

현대 가상화폐의 근간이 되는 블록체인 기술의 핵심은 시간의 흐름에 따른 각 노드의 상태를 저장하는 UTXO(Unspent Transaction Output) 를 모두 저장하는 것이다.
각 트랜잭션은 k개의 input을 가지고 각 입력은 UTXO에 대한 레퍼런스를 가지며 특정 노드의 상태는 이러한 UTXO의 리스트로 구성된다.

블록은 10분 간격으로 생성되며, 각 블록은 timestamp, nonce, hash of previous block, transaction list 로 구성되며 블록을 생성하기 위한 과정을 채굴(mining) 이라고 하며 다음의 단계에 따라 진행된다.

  1. 이전 블록의 해시값 검사
  2. 블록의 timestamp가 이전 블록의 것보다 크고 2시간이 경과하지 않은지 검사
  3. POW
  4. 상태집합 S 의 S[0] 에 이전 블록의 마지막 상태값을 저장
  5. 0 ~ n-1 의 모든 i에 대해 S[i+1] = APPLY(S[i], TX[i]) 를 수행
  6. 마지막 블록에 상태값 S[n] 를 등록

위 과정을 완료한 뒤에 해당 블록의 헤더를 해싱하고 그 해시를 풀기 위한 nonce를 무작위값을 계속 대입하면서 구함. = > mining

블록의 구조

블록은 위에서 언급했듯이 timestamp, nonce, hash of previous block, transaction list 로 구성되는데, 이 중에서 transaction list는 블록 데이터 부분에 저장되고 나머지는 블록 헤더에 저장이된다. 또, 블록 헤더에는 블록데이터에 대한 해시값이 저장되는데, 이 해시값은 머클트리 형태로 저장된 트랜잭션 리스트의 root hash의 값으로 하나의 트랜잭션이라도 조작되면 이 값이 바뀌게 되어 블록이 변질되었음을 알 수 있게 된다.

여기서 머클트리 란, 가령 n 개의 트랜잭션이 있다면 높이가 log(n)인 이진트리 형태로 구성되며, 각 부모는 자식의 해시를 가지게 되어 하나의 트랜잭션만 바뀌어도 수많은 노드의 해시값이 바뀌게 되는 트리이다.

이러한 블록들은 level DB 에 bloack hash 를 키로 블록 데이터를 value로 저장됩니다.
이러한 db의 종류는 block_hash db, block_number db, transaction db 등이 있습니다.

보안의 원리

블록체인은 어떠한 원리로 보안을 유지하는가?

먼저 다음과 같은 경우를 통해 블록체인을 훼손하는 경우를 생각해 보자.
먼저 가장 마지막 블록번호가 270번 블록이라고 하자.

  1. 사용자가 특정 상인에게 100BTC 를 입금한다.
  2. 상인이 사용자에게 디지털 재화를 전송한다(순식간에 전송 가능하다고 전재한다.)
  3. 사용자가 스스로에게 100BTC를 입금한다.

이 경우 블록체인은 3의 트랜잭션을 보 정상적인 state에 있지 않은 utxo라 판단하게 되고 사용자의 블록체인은 따로 분기되게 된다.
만약 그 동안 1시간이 경과하였다면 하지만 그와 동시에 다른 사용자들은 계속해서 블록을 생성하여 271~275까지 많은양의 블록을 생성한 상태이고 그들이 가리키는 해시값은 사용자의 270번 블록이 아닌 블록체인의 270번 블록을 가리키게 되고 사용자의 노드는 기존 블록체인에서 분리되게 된다.

이더리움

이더리움의 기본 단위는 account 이며, EOA(External Owned Account) 와 Contract 두 종류의 account 가 있습니다.

EOA 는 메세지를 보내는 주체이며 message에 의해 contract가 조작됩니다.
여기서 message는 가상의 객체이며 송/수신자 정보와 데이터, eth 양 등의 정보를 담고 있습니다.ㄴ

Contract가 Call 을 수행할때 생성됩니다.

블록체인의 비잔틴 장군 문제 해결

블록체인에서는 모든 정보를 블록이라는 정보 뭉치의 연결로 보고 각 블록에는 암호화된 해시값이 있어 다음 블록을 가리키고 있는 형태로 구성되어 있습니다.
또한 다음 블록이 생성되기 위해서는 참여하는 노드의 절반이상이 해당 노드가 올바른 노드라고 판단해야 다음 블록이 연결될 수 있기 때문에, 악의적인 목적을 가진 노드가 몇 개 존재한다고 하더라도 안정적으로 동작을 함을 말합니다.

합의 알고리즘

POW

새로운 화폐가 생성되는 과정(조폐)에서, 생성자들(채굴자들)에게 “일을 했다는 것을 증명(proof of work)”하는 것을 강제하여 화폐의 가치와 보안을 보장하는 방식이다.

분산 네트워크에서는 조폐 과정에서 누가 얼마의 새 화폐를 받을지를 결정할 중앙 권력이 없기 때문에 모든 참여자들이 자동적으로 동의할 수 있는 방법이 필요하다. 이때 일방향함수인 해시 함수가 계산(검산)하기는 쉽지만 역을 구하는 것(채굴)은 어렵다는 것에 착안하여, 모든 참여자가 해시 함수를 계산해서 가장 먼저 계산한 사람이 새 화폐를 받아가게 하는 것.

최초로 상업적 성공을 거둔 암호화폐 비트코인의 경우, 블록체인의 다음 블록을 캐기 위한 해시 함수의 입력값에 거래내역을 담은 블록체인의 최신값을 연동시켜서, 송금과 조폐 양 기능과 보안을 동시에 해결하였다.

나무 위키 참조

POS

암호화폐에서 proof-of-stake의 이니셜. 가치 증명, 또는 지분 증명으로 번역된다.

POW와는 근본적으로 다른 조폐 개념으로, 신규 코인을 발행할 때 이미 기존에 코인을 가지고 있던 사람들에게 전체 대비 각각의 소지량의 비율만큼을 지급하는 방식이다. 즉 암호화폐하면 으레 생각하는 채굴이 없다! 단, 현실적으로 액수에 관계없이 코인을 보유한 모든 지갑에 일괄적으로 %를 더하는 것은 불가능하므로, 조폐 과정에 참여하고 싶은 사람들이 일정 액수를 걸고(stake), 렌덤하게 추첨하여 참여자들 중 한명에게 다음 블록 보상(신규 코인)이 돌아가는 방식을 쓴다. 당연히 더 많이 걸수록 당첨 확률이 늘어난다. 참여에 필요한 최소 액수가 적어도 한화 수억원 어치이므로, 일반인들은 마이닝 풀과 유사한 개념인 스테이크 풀에 코인을 위탁해서 추첨에 참여한다.

얼핏 들으면 돈놓고 돈먹는 헤괴한 시스템으로 보일 수 있으나, 코인캡의 등락 없이는 신규 코인이 잔뜩 발행돼도 개당 가격이 내려가므로 각 코인 소유자들의 자산 가치는 동일하게 유지됨을 알 수 있다. 특정 집단이 과반수를 차지할 경우 그들의 지분이 계속 늘어나는 폐해가 벌어질 수 있으나, 채굴의 51%공격과 마찬가지로 당사자들의 이해관계 때문에 자정능력을 가진다. 채굴(POW) 대비 가장 큰 장점은 채굴에 들어가는 막대한 양의 에너지 낭비 없이 조폐와 거래를 운용할 수 있다는 점이다. 단점은 탈중앙화된 신규 코인은 이런 식으로 발행하기가 쉽지 않다는 점.

퀀텀(Qtum) 등에서 POS를 채택하고 있다.

POW와 POS 외에 POI라는 기술도 있다.

나무위키 참조

토큰 생성

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
pragma solidity ^0.4.20;

contract MyToken {
event Transfer(address indexed from, address indexed to, uint256 value);
/* This creates an array with all balances */
mapping (address => uint256) public balanceOf;
string public name;
string public symbol;
uint8 public decimals;
/* Initializes contract with initial supply tokens to the creator of the contract */
function MyToken(uint256 initialSupply, string tokenName, string tokenSymbol, uint8 decimalUnits) public {
balanceOf[msg.sender] = initialSupply; // Give the creator all initial tokens
name = tokenName; // Set the name for display purposes
symbol = tokenSymbol; // Set the symbol for display purposes
decimals = decimalUnits; // Amount of decimals for display purposes
}

/* Send coins */
function transfer(address _to, uint256 _value) public {
require(balanceOf[msg.sender] >= _value); // Check if the sender has enough
require(balanceOf[_to] + _value >= balanceOf[_to]); // Check for overflows
balanceOf[msg.sender] -= _value; // Subtract from the sender
balanceOf[_to] += _value; // Add the same to the recipient
/* Notify anyone listening that this transfer took place */
emit Transfer(msg.sender, _to, _value);
}
}

먼저 crowd sale을 진행하기 전에 crowd sale에서 사용할 토큰을 생성하고, crowd sale의 shares address에 등록해 준다.

crowd sale contract

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
pragma solidity ^0.4.16;

interface token {
function transfer(address receiver, uint amount) external;
}

contract Crowdsale {
address public beneficiary;
uint public fundingGoal;
uint public amountRaised;
uint public deadline; //마감 기한
uint public price;
token public tokenReward;
mapping(address => uint256) public balanceOf;
bool fundingGoalReached = false;
bool crowdsaleClosed = false;

event GoalReached(address recipient, uint totalAmountRaised);
event FundTransfer(address backer, uint amount, bool isContribution);

/**
* Constructor function
*
* Setup the owner
*/
function Crowdsale(
address ifSuccessfulSendTo, //
uint fundingGoalInEthers, //이더 단위의 모금 목표액
uint durationInMinutes, //분 단위의 모금 기간
uint etherCostOfEachToken, //각 토큰 당 단위 가격(이더 기준)
address addressOfTokenUsedAsReward //모금의 보상으로 주어질 위에서 만든 토큰의 주소
) public {
beneficiary = ifSuccessfulSendTo;
fundingGoal = fundingGoalInEthers * 1 ether;
deadline = now + durationInMinutes * 1 minutes;
price = etherCostOfEachToken * 1 ether;
tokenReward = token(addressOfTokenUsedAsReward);
}

/**
* Fallback function
*
* The function without name is the default function that is called whenever anyone sends funds to a contract
*/
function () payable public {
require(!crowdsaleClosed);
uint amount = msg.value;
balanceOf[msg.sender] += amount;
amountRaised += amount;
tokenReward.transfer(msg.sender, amount / price);
emit FundTransfer(msg.sender, amount, true);
}

modifier afterDeadline() { if (now >= deadline) _; }

/**
* Check if goal was reached
*
* Checks if the goal or time limit has been reached and ends the campaign
*/
function checkGoalReached() afterDeadline public {
if (amountRaised >= fundingGoal){
fundingGoalReached = true;
emit GoalReached(beneficiary, amountRaised);
}
crowdsaleClosed = true;
}


/**
* Withdraw the funds
*
* Checks to see if goal or time limit has been reached, and if so, and the funding goal was reached,
* sends the entire amount to the beneficiary. If goal was not reached, each contributor can withdraw
* the amount they contributed.
*/
function safeWithdrawal() afterDeadline public {
if (!fundingGoalReached) {
uint amount = balanceOf[msg.sender];
balanceOf[msg.sender] = 0;
if (amount > 0) {
if (msg.sender.send(amount)) {
emit FundTransfer(msg.sender, amount, false);
} else {
balanceOf[msg.sender] = amount;
}
}
}

if (fundingGoalReached && beneficiary == msg.sender) {
if (beneficiary.send(amountRaised)) {
emit FundTransfer(beneficiary, amountRaised, false);
} else {
//If we fail to send the funds to beneficiary, unlock funders balance
fundingGoalReached = false;
}
}
}
}

기본 contract 작성

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
pragma solidity ^0.4.20;

contract MyToken {
event Transfer(address indexed from, address indexed to, uint256 value);
/* This creates an array with all balances */
mapping (address => uint256) public balanceOf;
string public name;
string public symbol;
uint8 public decimals;
/* Initializes contract with initial supply tokens to the creator of the contract */
function MyToken(uint256 initialSupply, string tokenName, string tokenSymbol, uint8 decimalUnits) public {
balanceOf[msg.sender] = initialSupply; // Give the creator all initial tokens
name = tokenName; // Set the name for display purposes
symbol = tokenSymbol; // Set the symbol for display purposes
decimals = decimalUnits; // Amount of decimals for display purposes
}

/* Send coins */
function transfer(address _to, uint256 _value) public {
require(balanceOf[msg.sender] >= _value); // Check if the sender has enough
require(balanceOf[_to] + _value >= balanceOf[_to]); // Check for overflows
balanceOf[msg.sender] -= _value; // Subtract from the sender
balanceOf[_to] += _value; // Add the same to the recipient
/* Notify anyone listening that this transfer took place */
emit Transfer(msg.sender, _to, _value);
}
}

상속을 이용한 보다 심플란 contract 작성하기

is owned를 통해 상속을 하여 owner 변수와 onlyOwner modifier에 접근할 수 있게 되었다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
pragma solidity ^0.4.20;

contract owned {
address public owner;

function owned() {
owner = msg.sender;
}

modifier onlyOwner {
require(msg.sender == owner);
_;
}

function transferOwnership(address newOwner) onlyOwner {
owner = newOwner;
}
}

contract MyToken is owned{
event Transfer(address indexed from, address indexed to, uint256 value);
/* This creates an array with all balances */
mapping (address => uint256) public balanceOf;
string public name;
string public symbol;
uint8 public decimals;
/* Initializes contract with initial supply tokens to the creator of the contract */
function MyToken(
uint256 initialSupply,
string tokenName,
uint8 decimalUnits,
string tokenSymbol,
address centralMinter
) {
if(centralMinter != 0 ) owner = centralMinter;
}

/* Send coins */
function transfer(address _to, uint256 _value) public {
require(balanceOf[msg.sender] >= _value); // Check if the sender has enough
require(balanceOf[_to] + _value >= balanceOf[_to]); // Check for overflows
balanceOf[msg.sender] -= _value; // Subtract from the sender
balanceOf[_to] += _value; // Add the same to the recipient
/* Notify anyone listening that this transfer took place */
emit Transfer(msg.sender, _to, _value);
}
}

#

향상된 최종 코인

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
pragma solidity ^0.4.16;

contract owned {
address public owner;

function owned() public {
owner = msg.sender;
}

modifier onlyOwner {
require(msg.sender == owner);
_;
}

function transferOwnership(address newOwner) onlyOwner public {
owner = newOwner;
}
}

interface tokenRecipient { function receiveApproval(address _from, uint256 _value, address _token, bytes _extraData) external; }

contract TokenERC20 {
// Public variables of the token
string public name;
string public symbol;
uint8 public decimals = 18;
// 18 decimals is the strongly suggested default, avoid changing it
uint256 public totalSupply;

// This creates an array with all balances
mapping (address => uint256) public balanceOf;
mapping (address => mapping (address => uint256)) public allowance;

// This generates a public event on the blockchain that will notify clients
event Transfer(address indexed from, address indexed to, uint256 value);

// This notifies clients about the amount burnt
event Burn(address indexed from, uint256 value);

/**
* Constrctor function
*
* Initializes contract with initial supply tokens to the creator of the contract
*/
function TokenERC20(
uint256 initialSupply,
string tokenName,
string tokenSymbol
) public {
totalSupply = initialSupply * 10 ** uint256(decimals); // Update total supply with the decimal amount
balanceOf[msg.sender] = totalSupply; // Give the creator all initial tokens
name = tokenName; // Set the name for display purposes
symbol = tokenSymbol; // Set the symbol for display purposes
}

/**
* Internal transfer, only can be called by this contract
*/
function _transfer(address _from, address _to, uint _value) internal {
// Prevent transfer to 0x0 address. Use burn() instead
require(_to != 0x0);
// Check if the sender has enough
require(balanceOf[_from] >= _value);
// Check for overflows
require(balanceOf[_to] + _value > balanceOf[_to]);
// Save this for an assertion in the future
uint previousBalances = balanceOf[_from] + balanceOf[_to];
// Subtract from the sender
balanceOf[_from] -= _value;
// Add the same to the recipient
balanceOf[_to] += _value;
emit Transfer(_from, _to, _value);
// Asserts are used to use static analysis to find bugs in your code. They should never fail
assert(balanceOf[_from] + balanceOf[_to] == previousBalances);
}

/**
* Transfer tokens
*
* Send `_value` tokens to `_to` from your account
*
* @param _to The address of the recipient
* @param _value the amount to send
*/
function transfer(address _to, uint256 _value) public {
_transfer(msg.sender, _to, _value);
}

/**
* Transfer tokens from other address
*
* Send `_value` tokens to `_to` in behalf of `_from`
*
* @param _from The address of the sender
* @param _to The address of the recipient
* @param _value the amount to send
*/
function transferFrom(address _from, address _to, uint256 _value) public returns (bool success) {
require(_value <= allowance[_from][msg.sender]); // Check allowance
allowance[_from][msg.sender] -= _value;
_transfer(_from, _to, _value);
return true;
}

/**
* Set allowance for other address
*
* Allows `_spender` to spend no more than `_value` tokens in your behalf
*
* @param _spender The address authorized to spend
* @param _value the max amount they can spend
*/
function approve(address _spender, uint256 _value) public
returns (bool success) {
allowance[msg.sender][_spender] = _value;
return true;
}

/**
* Set allowance for other address and notify
*
* Allows `_spender` to spend no more than `_value` tokens in your behalf, and then ping the contract about it
*
* @param _spender The address authorized to spend
* @param _value the max amount they can spend
* @param _extraData some extra information to send to the approved contract
*/
function approveAndCall(address _spender, uint256 _value, bytes _extraData)
public
returns (bool success) {
tokenRecipient spender = tokenRecipient(_spender);
if (approve(_spender, _value)) {
spender.receiveApproval(msg.sender, _value, this, _extraData);
return true;
}
}

/**
* Destroy tokens
*
* Remove `_value` tokens from the system irreversibly
*
* @param _value the amount of money to burn
*/
function burn(uint256 _value) public returns (bool success) {
require(balanceOf[msg.sender] >= _value); // Check if the sender has enough
balanceOf[msg.sender] -= _value; // Subtract from the sender
totalSupply -= _value; // Updates totalSupply
emit Burn(msg.sender, _value);
return true;
}

/**
* Destroy tokens from other account
*
* Remove `_value` tokens from the system irreversibly on behalf of `_from`.
*
* @param _from the address of the sender
* @param _value the amount of money to burn
*/
function burnFrom(address _from, uint256 _value) public returns (bool success) {
require(balanceOf[_from] >= _value); // Check if the targeted balance is enough
require(_value <= allowance[_from][msg.sender]); // Check allowance
balanceOf[_from] -= _value; // Subtract from the targeted balance
allowance[_from][msg.sender] -= _value; // Subtract from the sender's allowance
totalSupply -= _value; // Update totalSupply
emit Burn(_from, _value);
return true;
}
}

/******************************************/
/* ADVANCED TOKEN STARTS HERE */
/******************************************/

contract MyAdvancedToken is owned, TokenERC20 {

uint256 public sellPrice;
uint256 public buyPrice;

mapping (address => bool) public frozenAccount;

/* This generates a public event on the blockchain that will notify clients */
event FrozenFunds(address target, bool frozen);

/* Initializes contract with initial supply tokens to the creator of the contract */
function MyAdvancedToken(
uint256 initialSupply,
string tokenName,
string tokenSymbol
) TokenERC20(initialSupply, tokenName, tokenSymbol) public {}

/* Internal transfer, only can be called by this contract */
function _transfer(address _from, address _to, uint _value) internal {
require (_to != 0x0); // Prevent transfer to 0x0 address. Use burn() instead
require (balanceOf[_from] >= _value); // Check if the sender has enough
require (balanceOf[_to] + _value >= balanceOf[_to]); // Check for overflows
require(!frozenAccount[_from]); // Check if sender is frozen
require(!frozenAccount[_to]); // Check if recipient is frozen
balanceOf[_from] -= _value; // Subtract from the sender
balanceOf[_to] += _value; // Add the same to the recipient
emit Transfer(_from, _to, _value);
}

/// @notice Create `mintedAmount` tokens and send it to `target`
/// @param target Address to receive the tokens
/// @param mintedAmount the amount of tokens it will receive
function mintToken(address target, uint256 mintedAmount) onlyOwner public {
balanceOf[target] += mintedAmount;
totalSupply += mintedAmount;
emit Transfer(0, this, mintedAmount);
emit Transfer(this, target, mintedAmount);
}

/// @notice `freeze? Prevent | Allow` `target` from sending & receiving tokens
/// @param target Address to be frozen
/// @param freeze either to freeze it or not
function freezeAccount(address target, bool freeze) onlyOwner public {
frozenAccount[target] = freeze;
emit FrozenFunds(target, freeze);
}

/// @notice Allow users to buy tokens for `newBuyPrice` eth and sell tokens for `newSellPrice` eth
/// @param newSellPrice Price the users can sell to the contract
/// @param newBuyPrice Price users can buy from the contract
function setPrices(uint256 newSellPrice, uint256 newBuyPrice) onlyOwner public {
sellPrice = newSellPrice;
buyPrice = newBuyPrice;
}

/// @notice Buy tokens from contract by sending ether
function buy() payable public {
uint amount = msg.value / buyPrice; // calculates the amount
_transfer(this, msg.sender, amount); // makes the transfers
}

/// @notice Sell `amount` tokens to contract
/// @param amount amount of tokens to be sold
function sell(uint256 amount) public {
require(address(this).balance >= amount * sellPrice); // checks if the contract has enough ether to buy
_transfer(msg.sender, this, amount); // makes the transfers
msg.sender.transfer(amount * sellPrice); // sends ether to the seller. It's important to do this last to avoid recursion attacks
}
}

Greeter Contract 만들기

Greeter.sol

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
contract Mortal {
/* Define variable owner of the type address */
address owner;

/* This function is executed at initialization and sets the owner of the contract */
function Mortal() { owner = msg.sender; }

/* Function to recover the funds on the contract */
function kill() { if (msg.sender == owner) selfdestruct(owner); }
}

contract Greeter is Mortal {
/* Define variable greeting of the type string */
string greeting;

/* This runs when the contract is executed */
function Greeter(string _greeting) public {
greeting = _greeting;
}

/* Main function */
function greet() constant returns (string) {
return greeting;
}
}

solidity compiler 설치 및 컴파일 하기

solcjs 설치하기

1
npm install -g solc

컴파일 하기

1
solcjs -o target --bin --abi Greeter.sol

js 스크립트 작성

main.js

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
var greeterFactory = eth.contract(<contents of the file Greeter.abi>)

var greeterCompiled = "0x" + "<contents of the file Greeter.bin>"

var _greeting = "Hello World!"

var greeter = greeterFactory.new(_greeting,{from:eth.accounts[0],data:greeterCompiled,gas:47000000}, function(e, contract){
if(e) {
console.error(e); // If something goes wrong, at least we'll know.
return;
}

if(!contract.address) {
console.log("Contract transaction send: TransactionHash: " + contract.transactionHash + " waiting to be mined...");

} else {
console.log("Contract mined! Address: " + contract.address);
console.log(contract);
}
})

geth console 에서 스크립트 실행

1
loadScript("main.js")

채굴 시작 및 greeter 실행

1
miner.start()

채굴이 완료되면 contract에 address가 부여되고 계약이 발행된다.

이제는 블록체인 상에 greeter라는 봇이 생성되었으므로 다음과 같이 자유롭게 호출하여 사용이 가능하다.

1
greeter.greet();

블록체인이란?

블록체인이란 수정 불가능한 분산형 원장을 의미하며, 특정 정보의 목록이 다수의 컴퓨터에 동시에 저장되고 수정될 수 있는 시스템을 의미합니다.
기존의 시스템은 단일 서버에 모든 정보가 저장되기 때문에 서비스 사용자들이 정보를 알 수 없고, 기업이나 혹은 악한 의도를 가진 사용자에 의해 플랫폼이 훼손될 수 있어 안전하지 못했다면, 블록체인은 수정이 불가능하기 때문에 신뢰할 수 있는 특징이 있습니다.

이러한 블록체인은 반드시 BFT를 가져야 하는데

기본 개념

이더리움에서의 기본 단위는 account 이며 이러한 account는 다음과 같이 두 종류로 나뉘게 됩니다.

  1. EOA(External Owned Account)
  2. Countract Account

여기서 EOA란 계정정보를 포함한 계약을 의미하며 외부 사용자가 private key 를 통해 제어합니다.
이러한 EOA 는 Contract Account의 내부 함수들을 사용할 수 있으며 Contract Account의 내부 함수들은 오직 EOA에 의해서만 호출될 수 있습니다.

Install ethereum command line interface (Ethereum CLI)

  1. 윈도우 go-ethereum(geth) 다운로드
    다운로드

  2. geth 실행

    1
    geth console

테스트 네트워크 구축하기

  1. genesis.json 생성하기

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    {
    "config": {
    "chainId": 15,
    "homesteadBlock": 0,
    "eip155Block": 0,
    "eip158Block": 0
    },
    "difficulty": "20",
    "gasLimit": "2100000",
    "alloc": {
    "7df9a875a174b3bc565e6424a0050ebc1b2d1d82":
    { "balance": "300000" },
    "f41c74c9ae680c1aa78f42e5647a62f353b7bdde":
    { "balance": "400000" }
    }
    }
  2. 블록체인 초기화 하기

    1
    geth init genesis.json --datadir ethereum_private
  3. geth console 로 geth 노드 열기

    1
    geth --networkid 123 --datadir ethereum_private console
  4. account 만들기

    1
    personal.newAccount("testuser1")
  5. mining 시작하기

    1
    miner.start()
  6. 자신이 위치한 노드 확인하기

    1
    admin.nodeInfo.enode
  7. 다른 노드 연결하기
    위에서 받은 nodeurl을 받아 다른 클라이언트에서 다음 명령어를 실행한다.

    1
    admin.addPeer("_nodeurl_")

이를 통해 노드와 노드가 연결될 수 있다.

  1. 다른 클라이언트들의 로그 확인
    1
    geth console 2>>geth.log

참조 블로그

이더리움 공식 가이드

geth 명령어

geth 가동

1
2
3
geth --datadir ~/.ethereum_private init ~/dev/genesis.json

geth --fast --cache 512 --ipcpath ~/Library/Ethereum/geth.ipc --networkid 1234 --datadir ~/.ethereum_private console

계좌 생성

1
2
personal.newAccount("testuser1")
personal.newAccount("testuser2")

계좌 확인

1
eth.accounts

잔고 확인

1
eth.getBalance(eth.accounts[0])

블록 수 확인

1
eth.blockNumber

채굴 시작하기

1
miner.start()

채굴 정지

1
miner.stop()

트랜잭션 발행

1
2
3
4
5
6
7
8
eth.sendTransaction({from: 'id', to:'id', value:web3.toWei(1,"ether")})
please unlocak account id

or

eth.sendTransaction({from:eth.accounts[0], to:eth.accounts[1], value:web3.toWei(1,"ether")})

트랜잭션 발행하는 계좌의 암호를 입력

geth 기동

1
2
mkdir eth_data
geth --networkid "123" --rpc --rpcaddr "222.239.251.75" --rpcport 8545 --rpccorsdomain "*" --rpcapi "net,eth,web3,personal" --datadir "eth_data" --olympic console

기본 원리

proof of work -> 어려운 문제를 푼 사람이 토큰을 가져간다.
풀기는 어렵지만 증명은 쉬운 해쉬를 사용한다.

컴퓨터는 nonce에 무작위값을 계속 대입하여 해쉬를 풀고 이를 mining 이라고 한다.
mine이 된 이후에는 점점 난이도가 올라간다.

이더리움의 활용

이더리움은 개인과 개인간의 약속에 기반한 모든 경제적 모델을 온라인 상에서 도입하는 것을 매우 간편하게 만들어 준다.
가령 국가가 특정 공약을 내세우고 이를 위한 자금을 이더리움에서 모금한다고 하면, 해당 공약이 이루어지지 않을 경우 스마트 계약에 따라 참여자에게 돈이 재분배 되게 되는 방식을 사용하는 예처럼 스스로에게 약속 불이행시 제약을 둠으로써 신뢰도 높은 거래를 할 수 있다.

즉, 이더리움은 실제 경제모델과 정치모델을 모두 온라인 상에서 신뢰도있게 구현이 가능하다는 측면에서 그 가치가 높다.


Blockchain technology for enterprise service

건강 보험 등 이력에 대한 불변의 상태기록을 원하는 비즈니스에서는 상당히 유용하게 사용될 수 있다.

인센티브의 경우 네트워크 망을 유지하고 서비스에서 인센티브를 제공하는 기능을 어떻게 활용 가능한가?

Case1 분산 원장으로써의 블록체인

롯데카드 -> 블록체인 기반 생체 인증

삼성페이에서 로그인 정보를 다른 쪽에도 유지하기 위해 사용 =>

Case2 스마트 컨트랙트로써의 블록체인

현대카드 포인트 페이먼트를 스마트 컨트랙트로 구성

제일 큰 문제는 성능문제. => 추가로 컨센서스를 만드는 작업 등

신한금융 => 인증서 발급 로직을 스마트 컨트랙트로 구성

금융보안원, 금융 결제원 => 폰뱅킹 및 은행 송금 시스템

은행 송금 시스템을 블록체인화, 기존에는 중앙 시스템이 모든 은행의 거래 내역을 다 처리하고 매일 한번씩 정산하여 데이터베이스를 맞추는 식으로 햇었음

이 경우 스마트 컨트랙을 통해 했는데 역시 성능문제가 생겼음

여기서 가장 중요한 점은 고객 데이터는 데이터베이스에 올라갈 수 없음

때문에 블록체인과 외부 디비가 어떤 식으로 연동하는 것이 매우 중요한 포인트임

고객의 주요 쟁점

  1. 퍼포먼스 컨트랙트 내부 병렬화에 대한 요구가 나온다. 보통 컨트랙트 내에서 락을 걸어서 처리를 하는데 이 경우 처리가 빠르게 일어나지 못함
  2. privacy개인정보를 올리려면 어떻게? => 난스 만들어라
  3. Multi chain
  4. 익명 기술
  5. 파이널리티 가령 블록이 생성되어 트랜잭션이 만들어 지더라도 블럭이 폐기되면 다시 뒤로 돌아가기 때문에 고객의 지갑이 변동되는 문제가 생기며 이는 매우 큰 이슈이다,

블록체인 비즈니스 활용 Tip

사이드 체인을 유지하고 퍼블릭 네트워크와 연동하는 형태로 많이 서비스를 하게 된다.

이렇게 하면 기존 서비스의 품질을 해치지 않으면서도 블록체인을 적용할 수 있다.

가령 포인트를 적립시킨다고 하면 별도 사이드 체인을 만들어서 포인트를 등록하고 해당 체인을 다른 퍼블릭체인과 연동하여 포인트를 유통시킬 수 있다.

즉 이더 송금 수수료를 한번만 이용하지만 여러 거래를 별도 사이드체인에서 동작시키고 퍼블릭체인과 연동함으로써 해결이 가능하다.

Ex) aergo => 블록체인 sass 서비스

업그레이드 가능한 스마트 컨트랙트

투명성, 위변조 불가성

왜 업그레이드 가능한 스마트 컨트랙트가 필요한가?

  1. 배포 후 취약점이 발견되면 수정이 가능하다.
  2. 비즈니스 로직이 수정 불가하기 때문에 겪게 되는 불편함이 있다.

Delegate call 특정 컨트랙트를 통해 다른 컨트랙트를 실행시킴

조건

업그레이드로 스마트 컨트랙트 주소 안변함데이터 마이그레이션 없이 데이터보존여러 스마트 컨트랙을 한번에 배포

Proxy contract 를 만들어 버전관리를 하고 유저는 proxy contract 로 전달하고 proxy contract는 최신버전의 contract로 명령을 전달한다.

Registry contract upgrade Earl => 업그레이드하고자 하는 proxy contract의 주소를 받아온다. registry contract 모두를 업그레이드 하기 위해 registry contract를 실행시킨다.

스마트 컨트랙트 버전관리 툴

  1. deploy
  2. Registry contract 가 없으면 registry contract 배포

업그레이 가능한 스마트 컨트랙트의 이점

유저 입장에서는 스마트 컨트랙트 주소가 고정됨, 버전 정볼르 생각하지 않고 특정 호출만 계속 함개발자 입장에서는 모든 데이터가 그대로 유지되고 재사용 되게 됨업그레이드가 매우 편리함.

Token Model Design Process

토큰 모델이랑 탈중앙화 네트워크의 보이지 않는 손이다.

토큰이라는 인센티브를 가지고 경제가 어떻게 굴러가는지를 설계한다.

게임 이론

주어진 게임의 규칙에서 최선의 전략을 찾는 이론

메커니즘 디자인

모든 플레이어가 게임에 충실하게 참여를 했을 때 이를 원하는 방향으로 굴러가게 하기 위한 메커니즘에 대한 디자인

어떻게 기존의 경제 시장에서 토큰 모델을 적용시킬 것인가?

메커니즘 디자인의 기초

Agent 행동 주체

Type agent의 사적인 정보

Decision 가능한 사회적 결과의 집합

Utility function 에이전트가 특정 결과에 대해 얻는 효용

Decision function agent의 각 행동을 종합한 결정 규칙

Transfer function agent의 행동에 따라서 받거나 내야하는 돈

Social choice function

가령 마을에 쓰레기 처리장을 짓는 문제를 생각해 보자.

제일 쉬운 방법은 누군가가 모든 사람들에게 의견을 물어보는 것이다.

여기서 transfer function 은 agent의 type 에따라서 받거나 내야하는 돈의 규칙이다.

메커니즘의 특성

Efficiency

최대 다수의 최대 행복

trustfulness

모든 에이전트의 균형 전략이 자신의 type을 솔직하게 보고하는 것일때

Budget balanced

agent의 type이 바뀌더라도 메커니즘이 transfer function으로 얻는 수입이 일정할 때

메커니즘을 최적화 문제로 정의할 수 있다!!

메커니즘 최적화 적용

가령 서울의 평균 기온을 블록체인에 기록하는 메커니즘을 만든다고 해보자

  1. 오라클 선출 => 신뢰할 수 있는 외부 데이터를 선정한다.
  2. Shelling coin 많은 사람들이 준 값들의 중간값을 실제값으로 정한다.

계속해서 decision function 과 transfer function 을 바꾸어 보면서 실 데이터를 분석하여 효율적인 메커니즘을 도출해 내야 한다.

토큰 모델 디자인 프로세스

agents와 목표 행동 정의최적화 문제 설정반복메커니즘 규칙 설정규칙 변경결과 추론제약조건 변경

예시 - steemit

Object => 좋은 글의 공급을 극대화

Constraint => 초보 작가들이 글을 쓰기가 쉬워야 함, 독자들은 글을 쓸 때 돈을 내지 않아야 함 등

Decision => 추천수에 스팀 파워 가중치를 계산해 퀄리티로 인정함

Transfer =>

더 나은 설계를 위해 필요한 것들

좋은 규칙의 집합, 패턴실제 돌아가는 프로젝트에서 나오는 실증 데이터복잡한 메커니즘의 정량적 추론을 위한 시뮬레이션 툴

토큰 디자인 패턴

Incentive, curation , judgement, governance

메커니즘 디자인의 한계

닫힌 시스템을 가정한 설계이기 때문에 경쟁 프로토콜, 암호화폐 시장 등 외부 요소는 고려하지 못하기에

블록체인과 같은 완벽하게 공개된 플랫폼 내에서 어떤 사이드 이펙트가 나올지 알 수 없다.

토큰 디자이너를 위한 팁

  1. 플레이어가 아니라 디자이너처럼 생각하라.
  2. 목적과 제약조건 정의만 잘해도 반은 먹고 들어간다. => 토큰 가치 상승이 목적인가 이중 지불 방지가 목적인가, 목적과 제약조건만 확실하다면 솔루션은 얼마든지 바꿀 수 있음
  3. 솔루션을 decision function 과 transfer function 으로 바꾼다.
  4. 알고 있는 패턴이 풍부해야 문제를 잘 풀어나갈 수 있다.

화폐가치와 메커니즘 디자인은 어떻게 결합될 것인가

IOT에서의 블록체인

오프라인 데이터의 위변조를 막기 위해 가량 씨씨티비의 경우 해당 영상의 해시값을 저장하여 블록체인에 저장하고 추후 검증이 필요한 경우 해당 해시와 비교를 통해 할 수 있따.

Digital forensic => 영상 데이터의 법정에서 신뢰를 얻을 수 있음

가령 자율주행차의 경우 수동으로 운전을 했는가 혹은 자동으로 운동을 했는가가 과실에 매우 중요하다. 이를 블록체인에 실시간으로 저장하면 이를 막을 수 있다.

DAICO 모델 - 블록체인 위에서 ico 플랫폼

메커니즘

하스켈

Five changes that blockchain technology will bring

The rise of blockchain technology

One of the hottest topics of the day is AI technology.
The intellectual ability of AI surpasses human experts overwhelmingly in certain areas, and the effects of AI in many areas are astonishing.
However I think that the technology that will transform our lifestyle in the near future is by far the blockchain.
Block chain technology is a technology that blocks transaction ledger, stores them on their computers and smartphones, and binds them with chains.
These blockchain technologies completely transform existing online platforms that require existing central DBs and central servers, and are expected to make the following significant changes

Decentralized database

The Internet was created and all the internet service and products were consists of servers who keeps all the data and the clients who provide data and can use very small amount of data.

Although all the information is freely available through the Internet, in fact, there have been many problems in the context of the fact that a small number of companies can run businesses with their own database and generate huge profits from these data.

어떤 경우에는

For example, in Honduras, the ownership of land in certain parts of Honduras is based solely on information stored in the central database, and thus, in many underdeveloped countries, personal ownership, if exploited by a third party or government, was virtually a piece of waste paper that existed only.
But blockchain technology does not need a central DB and it is safe to call it democratization of information because everyone can know, share, and preserve personal information and ownership because all participants on the platform act as notaries.
Through these blockchain technologies, individuals can escape the gull of exploitation of large enterprises, and realize the democratization of information in the real sense.

진정한 의미의 공유경제의 실현

최근에는 많은 공유기업들의 전성시대 였다. 가령 우버, AirBnb 등과 같은 기업은 개인의 유휴자산을 다른 사람들에게 판매할 수 있는 창구를 만들어 주고, 사회 전체의 입장에서 재화의 효율적인 사용을 해 줄 수 있는 창구가 되었지만, 기업의 입장에서 보면 수많은 유휴자산을 거래하는 중심자 역할을 하고 막대한 양의 수수료로 수익을 거두었다. 사실상 공유경제라기 보다는 새로운 시장을 창출해 내었다고 하는 편이 무방하겠다.

하지만 블록체인 기술은 이러한 공유경제 기술의 최고봉이라 할 수 있다.
가령 숙방업을 공유하는 블록체인 플랫폼을 만들었다고 가정하다. 만약 누군가가 집을 공유하고 싶다면 이러한 블록체인에 자신의 집을 등록하기만 하면 모든 시스템 적인 부분을 제공받을 수 있다.
누가 어떤 숙소를 이용하는 지에 대한 모든 정보는 플랫폼에 남게 되고 모두가 공증을 서므로 기존에 비해 훨씬 안전하다.
또한 블록체인을 통한 결제가 이루어 지므로 매우 저렴하고 안전하게 결제까지 이루어 질 수 있다.
기존에는 자신의 재화를 판매하기 위해 마케팅 등 다양한 노력이 필요했지만, 블록체인 이후의 사회에서는 재화 자체가 하나의 비즈니스를 뜻하게 된다 해도 무방하다.

세계의 부의 흐름

바람직한 사회라면 선진국에서 후진국으로의 자금의 흐름이 원활해야 한다는 것은 그 누구도 이견이 없을 것이다.
하지만 이러한 자금의 흐름을 살펴보면 대부분은 기업의 원조, 혹은 사회 단체의 원조가 아닌 개인의 송금이 가장 크다.
후진국의 국민이 다른 나라에 가서 취업을 하고 받은 임금을 다른 나라로 송금하는 경우가 매우 많고 이것이 선진국에서 후진국으로의 화폐이동의 가장 큰 부분을 담당한다.

하지만 현재의 경우 국가와 국가 사이에 돈이 오고가기 위해서는 수많은 단계가 필요하며 금융 시스템을 통과하면수 막대한 양의 중간 수수료(약 20% 가량)이 발생하게 되고 이는 후진국의 경제 개발에 큰 걸림돌이 되고 있다. 하지만 최근 생겨나오는 블록체인을 통한 거래를 통해서는 거래 수수료가 2%에 불과하기 때문에 부가 훨씬 더 원활하게 돌 수 있다.

데이터의 민주화

현대 사회에서는 수많은 디지털 정보들이 발생하고 개인의 디지털 정보들이 모이면 디지털 상에서의 자신을 대변할 수 있는 일종의 디지털 트윈이 생겨나게 된다.
현대 사회의 많은 기업들은 개인의 이러한 디지털 트윈을 카피하여 어떤 상품을 제공하고 마케팅을 할지에 대한 의사결정을 하며 이는 다시 거대 기업의 이윤증가에 기여하게 된다.
하지만 블록체인 기술은 자신의 디지털 트윈을 자신이 소유하고 필요한 부분만을 기업에게 공급함으로써 자신의 개인 정보를 보호받을 수 있고, 기업도 필요한 정보만을 쉽게 취득할 수 있기에 양측에 보탬이 된다.

콘텐츠의 가치를 지켜라

인터넷이 발명되어 가장 큰 가치를 잃은 사람들은 아마도 콘텐츠 제작자일 것이다.
기존에는 훌륭한 컨텐츠를 만들면 대부분의 수익을 해당 콘텐츠 제작자가 가져갔고, 사실 이것이 자유 경제사회에서 어쩌면 당연한 부분이다.
하지만 소수의 독점기업들이 판권을 뒤흔들고 판매처를 확고히 부여잡은 오늘의 사회에서는 컨텐츠 제작자에게 합당한 보상이 돌아가지 못한다.
하지만 블록체인 기술은 개인의 지적재산권을 확실하게 지켜주기에 콘텐츠 자체의 가치를 높일 수 있다.

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×