비트코인 라이트닝 네트워크(Lightning Network) (1/2) 강의 내용정리


강의 링크 https://www.youtube.com/watch?v=4yUd8pL8JMI





라이트닝 네트워크란?


- 2015년 Joseph Poon과 Thaddeus Dryja에 의해 소개

- 비트코인의 확장성(Scalability) 문제를 해결하기 위한 솔루션

//이더리움의 샤딩, 코스모스 및 폴카닷 텐더민트등의 인터 블록체인, IOTA나 EOS같이 블록체인을 병렬화 시키거나 1차원적인 구조에서 2차원적인 구조로 만드는 솔루션 등등 여러 솔루션등이 있다. 비트코인은 초당 3~5개의 Transaction만 처리가 가능하기 때문에 글로벌하게 사용하기 어렵다는 문제가 있다.


- 블록체인 외부(Off blockchain)에서 결제 채널의 네트워크를 통해 낮은 수수료로 다량의 소액거래(micropayment)를 처리할 수 있도록 하는 시스템

// On은 블록체인 자체의 용량을 증가시키는 방법으로 하는것. Off blockchain으로 분류되는 이유는 블록체인 위에 결제채널을 만들어서 블록체인 외부에서 해결하는 방법이기 때문이다. 이론적으로는 Lightening Network는 약 초당 10억건 이상의 거래를 처리할 수 있다고 한다.


- 거래 가변성(Transaction Melleablilty)문제가 해결되어야 구현가능. 세그윗(SegWit) 구현 필요

// 현재 비트코인 네트워크에서는 구현이 안된다. 그 이유가 거래 가변성(혹은 거래 ID의 가변성, 동일한 내역의 거래가 다른 여러 ID를 가질 수 있다. 나는 한명인데 여러 ID를 가질 수 있다는 문제, 필수 조건, 이 문제를 해결하는 것이 SegWit이다. )




White Paper을 읽을 수 있다. 59페이지 내용이기 때문에 나중에 시간이 있으면 읽을 예정이다.


// 라이트코인같은 경우에는 비트코인과 유사한 구조에서 SegWit을 구현하여 Lightening Network를 구현하였다. 


참고자료1. Lightening Network에 대한 Joseph Poon 해외 강의

https://www.youtube.com/watch?v=8zVzw912wPo


참고자료2.

Raiden Network라는 이더리움의 라이트닝 네트워크에 대한 자료


참고자료3.

Plasma: Scalable Autonomous Smart Contracts (이더리움에 스마트 컨트랙트로 또 다른 블록체인을 생성해서 블록체인에 Child 블록체인을 만든다?)



"Bitcoin Doesn't Scale"


- 1MB blocks: // 현재 비트코인 블록의 사이즈

-- 7transaction per second @ 250 bytes/tx

-- ~220 million transaction per year  // 1년에 처리되는 트랜잭션의 양

-- Not enough for a city, let alone the world // 하나의 도시에서 사용되기에도 너무 부족하다


- 1 Billion transaction per day:  // 하루 10억건의 거래가 발생한다는 가정이하

-- 1.6 GB blocks(1655 MB)  // 블록마다 1.6GB의 용량이 필요

-- 87 Terabytes/year (87029089 MB)  // 1년에 약 87 TB의 용량

-- Maybe enough for one large metro area?

-- Centralization(mining!)  // 이렇게 되면 발생하는 문제가 채굴의 중앙화의 문제가 발생한다.


● 7 billion people doing 2 blockchain transactions per day // 만약 전세계 70억명이 매일 2건씩의 Blockchain 거래를 진행한다면

○ 24 GB blocks //블록 사이즈

○ 3.5 TB/day // 하루에 증가되는 용량

○ 1.27 PB/year // 연간 증가되는 용량


● Bigger blocks = Centralization // 블록이 커지면 중앙화가 발생할 것이다.

○ Very few full nodes // full node의 수가 줄어들고

○ Very few miners  // 채굴자도 줄어들고

○ De facto inability to validate blockchain  // 이러할 경우 누구나 검증할 수는 있지만 누구도 검증하려고 하지 않을 것이다.



결제 채널(payment channel)의 형성 기본 절차


output script: 2<Alice_pubkey><Bob_pubkey> 2 CHECKMULTISIG



Alice와 Bob이 결제 채널을 형성하고자 할 때의 기본 절차는 다음과 같다.


1. Funding Tx(F) 생성 //Alice와 Bob이 결제채널을 형성한다고 한다면 먼저 Funding Tx를 생성한다. 얼마를 넣을지 결정, 


output script:  2 <Alice_pubkey> <Bob_pubkey> 2 CHECKMULTISIG

//이 출력값으로 Funding Tx를 생성한다. 이 의미는 Alice와 Bob이 넣은 돈은 Alice와 Bob 둘의 서명을 모두 넣어야 사용이 가능하다.


2. Commitment Transaction 생성

// Funding Tx를 생성해놓고 서명하기 전에, Alice와 Bob이 0.5 씩 넣은것을 refund하는 Transaction을 생성한다.


3. Commitment Transaction 서명

// 이 Commitment Tx를 먼저 서명한다.


4. Commitment Transaction 서명교환

// 서명을 교환한다. 이러면 Commitment Tx이 유효한 Tx가 된다.


5. Funding Transaction 서명


6. Funding Transaction 서명교환


7. Funding Transaction Broadcast


- Commitment Transaction은 블록체인에 공개되지 않으며 거래 당사자간의 현재 잔고(current Balance)를 나타냄


- Alice와 Bob은 자신이 원할 때에 Commitment Transaction을 블록체인 상에 공개함으로써 자신의 잔고를 환불받고 결제채널을 닫을 수 있다.



- Alice가 Bob에게 0.1 BTC 송금 (Alice: 0.4 BTC, Bob: 0.6 BTC)

// 엘리스와 Bob이 Commitment Tx를 생성한다.


- 업데이트된 장부에 따라 새로운 Commitment Transaction을 생성한다.


문제점: Alice의 경우 이전 Commitment Transaction을 블록체인 상에 공개하는 것이 유리하다.


1. 두 거래중 어떠한 것이 유효한 것인지 구분하고


2. 이전의 거래를 무효화 해야 한다.



핵심: 어떻게 이전 Commitment Transaction을 무효화 시킬 것인가?


- 비트코인의 Timelock 기능을 사용하여 Commitment Transaction의 출력값을 취소할 수 있는 거래(revocable transaction)로 만들고


- 특정 당사자가 이전 Commitment Transaction을 블록체인에 공개하는 경우 해당 당사자를 식별하고


- 취소할 수 있는 거래를 취소하고 Breach Remedy Transaction을 통해 계약을 어기는 거래 참가자의 예치금을 몰수하는 방식으로 벌금을 부과




누가 잘못했는가? (Ascribing Blame)



- 항상 Commitment Tx을 생성할 때 Commitment 1a, Commitment 1b이렇게 똑같은 Commitment를 2개씩 한쌍으로 만든다.

- 한쪽에는 Bob만 서명하고 한쪽에는 Alice만 서명하고 상대방에게 넘긴다.

- 만약 Commitment 1a가 공개된 경우 이미 Bob의 서명이 기록되었기 때문에 Alice만이 서명하여 Broadcast할 수 있기 때문에 Alice가 공개한 Commitment Tx인지 알 수 있는것이다.

- 즉, 누가 어겼는지 확인하는 방법은 이렇게 반만 서명된 Transaction을 나눠가졌기 때문에 어떤 Transaction인지 보고 확인할 수 있다.


2. 취소할 수 있는 거래(Revocable Transaction)


- 만약에 Alice가 이전 거래(본인에게 0.5 BTC를 돌려주는 거래)를 등록하였을 경우 이 거래를 취소할 수 있어야 한다.


- 보라색은 Bob이 서명을 해서 Alice만이 등록할 수 있는 Transaction들이다. 1a의 경우 Locktime이 걸려있다 보면 1000 confirmations라고 되어있다.

- Alice가 C1a를 공개하면 0.5 BTC를 받는다. 받기는 받는데 이게 1000 block confrimation이 난 후에 받는다.

- 반면에 Bob같은 경우에는 바로 0.5 BTC를 받는다. 



- Alice가 Bob에게 0.1 BTC 송금 (Alice: 0.4 BTC, Bob: 0.6 BTC)

- 새로운 거래가 일어날 때마다 Commitment Tx 한쌍을 생성



- Funding(F) 는 Alice와 Bob이 0.5 BTC 씩 결제 채널에 예치금을 넣어놓는 형태로 그 안에서 자유롭게 Fund를 왔다갔다 할 수 있게하는 약속이다.

- C2 까지 양쪽이 모두 동의를 하여 Alice가 Bob에게 0.1 BTC를 줘야하는데 Alice가 C1a를 Broadcast한 경우를 가정한다.

- 이 경우 Bob에게는 바로 0.5 BTC가 전송되고 아래의 빨간 트랜잭션 RD1a가 발행되어 Alice는 1000 Confirmation 이후에 이 0.5 BTC를 가져갈 수 있다.

- 그 전에 Breach Remedy(벌금을 부과하는 Tx)를 Alice와 Bob모두 합의한다. BR1a는 "만약에 Alice가 C1a를 발행한다면 Alice의 0.5 BTC를 모두 Bob에게 몰수 한다" 라는 내용이다.

- 이 BR1a와 BR1b는 C2a,b가 생성되기 바로 이전에 먼저 서명을 하고 C2를 발행하는 것이다.

- 때문에 C2a,b가 나온 다음에 C1a가 Broadcast가 되면 Alice는 모든 예치금을 Bob에게 모두 잃는것이 된다.

- 이러한 Commitment Tx는 블록체인에 기록하지 않고 계속 진행되기 때문에 수수료 없이 계속 소액결제를 처리할 수 있는 것이다.



거래의 청산(Settlement)


- Commitment Tx는 실제로 합의를 하기위한 도구이고 실제로 모든 거래가 끝나고 청산을 하는 경우에는 Locktime과 같은 복잡한 내용 없이 Funding Tx와 같이 바로 모두가 서명하여 작성하여 청산한다.




요약


- 라이트닝 네트워크는 일련의 연기된(deffered) 비트코인 거래와 벌금 부과를 통해 블록체인 외부에서 거래 당사자들간의 거래를 이행되도록 한다.

- 블록체인은 법원(Court)의 역할을 하는데 모든 계약이 법원에 의해 강제되는 것은 아니지만 분쟁시 법원에 의해 강제될 수 있기 때문에 실제 대부분의 계약은 아무 문제없이 이행되는 것과 같은 원리이다.

- 결제 채널은 거래 당사자가 폐쇄하기로 결정하기 전까지 영구적으로(in perpetuity) 사용될 수 있으며 분쟁이 있는 경우 언제든지 비트코인 블록체인 상에서 그 분쟁을 해결할 수 있다.




Further Study


- 서로 채널을 형성하지 않은 사람들끼리도 안전하게 거래 가능(HTLC: Hashed Timelock Contract)

- 결제 채널들의 네트워크 형성, 네트워크 수수료, 예치금, 효율성, 투명성 vs 익명성의 문제

- 응용 및 확장 : Raiden, State Channel, Plasma. Sharding과 결합되는 경우





On the timestamps in the tangle


Serguei Popov∗


August 6, 2017



Description of the problem and proposed algorithms(문제 및 제안 알고리즘에 대한 설명)




다음에서 우리는 고정 된 순간의 Tangle [1]을 고려한다; 즉, Tangle의 상태는 고정되어 있으므로 간단히 T로 나타냅니다. 일부 표기법 : x가 Tangle의 사이트 (트랜잭션)이면 A(x)는 x에 의해 승인 된 두 트랜잭션 집합을 나타냅니다.  우리는 만약 xj 모든 j = 1, ..., k에 대해 xj  ∈ A(xj−1)에서 x = x0, x1, ... , xk = y 일련의 사이트가 있는 경우 x는 y를 참조(간접적으로 승인)한다라고 말한다. x와 관련하여 "과거"와 "미래"에 대해 이렇게 쓰도록하겠습니다.




다시 말하면, 상기는 Tangle에 부분 순서 구조를 도입합니다. 또한 우리는 참조하거나 참조하지 않는 트랜잭션 집합을 Ind (x) = T / (P (x) ∪F (x))로 나타냅니다. (약어 사용됨). x ∈ Ind (x)를 정의하면된다.


다음으로 각 트랜잭션 x에 대해 타임 스탬프 t (x)가 있다고 가정합니다. 즉, 원칙적으로, t (x)는 트랜잭션이 Tangle에 부착 된 시간에 대응한다. 모든 x ∈ T에 대해 A (x) = {y1, y2} 인 t(x)> t (y1,2)가 필요하다. 즉, 트랜잭션은 "미래의" Timestamp 인 다른 트랜잭션을 승인 할 수 없습니다. 우리의 상정 된 가정은 대다수 (합리적인 의미에서) 대다수의 트랜잭션이 신뢰할 수있는 시계를 장착 한 정직한 노드에 의해 발행 된 것입니다. 



이제 타임 스탬프 t (x)를 가진 트랜잭션 x (전형적으로, 이미 Tangle의 "깊은 내부"입니다.) 를 생각해보십시오. 문제는 그것이 정직하고 악의적인 노드(또는, 어쩌면 정직한 노드에서 어떤 이유에 의해 시계가 오작동해서 발생할 수도 있습니다.)에 의해 발행되었는지 알지 못한다는 것입니다. 그러므로 t(x)가 x가 Tangle에 부착 된 실시간(심지어 대략적인) Tx인지 확실하지 않습니다. 우리의 목표는 Tx에 대한 신뢰 구간 [ax, bx]를 구성하는 것이다. 즉, 이벤트 Tx ∈ [ax, bx]가 높은 확률로 발생하도록 (확정적인) ax ≤ bx를 원한다.


다음에서는 이러한 구간을 구성하기위한 두 가지 절차를 고려합니다.



Procedure 1. β ∈ (0, 1/2)를 고정한 다음, 데이터 수집을 고려한다 (사실, 다중 집합)


(t (y) : y ∈ Ind (x)).    (1)


그런 다음 ax와 bx를 상기 데이터 수집의 β-와 (1-β) - 분계선으로 정의하십시오.  β = 0 (즉, 위의 데이터 수집에서 ax와 bx를 최소값과 최대 값으로 취하는 것)이 좋은 아이디어가 아닌 이유를 설명해야합니다. 그 이유는 악의적인 개체가 ax를 0(과거의 다른 거래를 승인하는 새로운 거래를 발행하고 작은 t- 값을 가짐)으로, bx(x를 참조하지 않고 매우 큰 t- 값을 갖는 새로운 트랜잭션을 발행함으로써)를 무한하게하여 절차를 망칠 수 있기 때문입니다. β가 0에서 멀어지면 "분열"거래가 중단됩니다.


원칙적으로 β를 증가시킴으로써 위에서 설명한 악성 행동에 대한 방어력을 강화합니다. 반면에 β가 1/2에 "too close" 하다면 결과는 "too random"할 것이다(x가 정직한 노드에 의해 발행 된 경우 라 할지라도, β가 1/2에 가까울 때, t (x) 자체가 신뢰 구간으로 갈 수 없다는 것을 관찰 할 수있다)). 현재로서는 β의 "최적"값이 무엇인지는 불분명합니다. 실제로, 네트워크에서 악의적 인 노드의 비율과 이러한 분석을 수행하는 방법에 대한 가정을 만들어야합니다. 어쨌든, 경험적으로 [0.2,0.3]의 β 값이 효과가있을 것입니다. 


위의 절차의 단점으로, 각 x에 대해 개별적으로 계산을 수행해야한다는 점에 유의하십시오 (일반적으로 x != y 일 때 Ind(x) != Ind(y)를 관찰하십시오). 이것은 Tangle이 매우 큰 경우를 대비하여 계산상의 차이를 야기 할 수 있습니다.  On the other hand, the outcome of the procedure is deterministic, provided of course that the nodes use the same β and see the same state of the tangle. 


이제는 계산이 더 쉽고 동시에 많은 트랜잭션에서 작동하는 또 다른 절차를 설명하겠습니다. 반면에, random1 결과를 생성합니다. 



Procedure 2. Tangle의 깊숙한 곳에서 시작하여 [1]의 4.1 절에 설명 된 Random Walk를 실행하고 x가 참조하는 마지막 트랜잭션의 타임 스탬프가되도록 ax를 취하고, bx는 x를 참조하는 첫 번째 트랜잭션의 타임 스탬프가됩니다. 


악의적인 노드가 고정된 트랜잭션의 타임 스탬프를 위조하려고 시도하면, 이 트랜잭션은 Random Walk에 의해 선택되지 않을 것임을 관찰하십시오. 실제로, 악의적인 노드가 "과거로 부터의" 타임 스탬프를 두는 경우(즉, t (x)는 x가 발행 된 실제 시간보다 훨씬 크다), 이는 [1]의 섹션 4.1의 "Lazy Tip" 사례에 해당합니다. 그러한 거래는 오랜 시간 동안 누군가에 의해 참조되지 않을 것이고, 다시 Random Walk가 결국 그것을 통과하지 않을 것입니다.




Conclusion


Tangle은 트랜잭션의 정확한 시간 순서를 설정하기에 부적합한(사실, 일반적으로 불가능한) 부분 순서 구조만 있는 그래프입니다. 모든 트랜잭션에 타임 스탬프가 있어도 이 모든 타임 스탬프가 정확하다는 것을 확신 할 수 없습니다(거래가 나타나는 실제 시간에 대해 네트워크를 속이는 일부 악의적인 노드 및/또는 잘못된 시계가 있는 일부 노드가 있을 수 있습니다). 그럼에도 불구하고 합당한 정확도로 타임 스탬프의 신뢰 간격을 결정할 수 있습니다. 위의 텍스트에서 우리는이를 수행하기위한 두 가지 알고리즘을 설명했습니다; 첫 번째 것은 계산적으로 더 복잡하지만 결정론적(deterministic) 결과를 산출합니다 (동일한 β를 사용하고 Tangle의 동일한 상태를 보는 두 개의 노드는 동일한 신뢰 구간을 얻을 것이다). 다른 알고리즘은 더 간단하고 동시에 여러 트랜잭션에 대한 타임 스탬프의 신뢰 간격을 결정하지만 임의의 결과를 생성합니다 (랜덤 워크가 실제로 선택한 경로에 따라 다름).




References


[1] S. Popov (2015) The tangle. https://iota.org/IOTA Whitepaper.pdf


원문 출처:  https://medium.com/biilabs/in-depth-explanation-of-how-iota-making-a-transaction-bcdd9713b939


이 글은 IOTA에서 Transaction이 어떻게 생성되는지에 대한 설명을 담은 원문을 한글로 번역한 것 입니다. 오역이 있을 수 있으니 원문과 비교하여 읽으면 도움이 될 것 같습니다.



In depth explanation of how IOTA making a transaction




이 게시물은 IOTA가 트랜잭션에서 번들로, 해시에서 주소로, 개인 키에서 서명 메시지로 트랜잭션을 만드는 방법을 자세히 설명합니다. 이것은 IOTA가 한 주소에서 다른 주소로 거래를 제안하는 방법을 알기 위해 필요한 전부입니다.


0. Before We Start


이 두 가지 자료를 이미 읽었는지 확인하십시오. 당신에게 IOTA 거래의 기본 견해를 제공합니다.

  1. 1. Bundles — IOTA Documentations (https://iota.readme.io/v1.2.0/docs/bundles)
IOTA는 계정과 같은 체계를 사용합니다. 즉, 토큰을 전송하기 위해 지출해야하는 입력 사항 (주소)이 있음을 의미합니다. 주소는 개인 키에서 생성되며, 개인 키는 다시 try-encoded 시드에서 파생됩니다. IOTA에서의 Transfer(전송)은 산출물과 투입물로 구성된 번들입니다. 번들은 원자 전송(atomic transfers) 방식으로, 번들 내부의 모든 트랜잭션이 네트워크에 의해 받아 들여 지거나 전혀 사용되지 않습니다. IOTA의 일반적인 전송은 4 개의 트랜잭션으로 구성된 번들입니다.

     index

    Purpose 

    Value

    0

    Output . 거래 수령자 (Recipient of the transaction)

     > 0 (as defined by user)

    1

     주소 입력 전체를 소비하는 첫 x 째 번들 항목.  또한 이 번들 항목은 서명의 첫번째 부분을 포함합니다 (이 경우에는 Alice의 서명의 전반부가 됩니다)

     < 0 (spending of input)

    2

     Alice의 서명의 후반부 

    0

     Output . 나머지가있는 경우 (Alice가 각 키 인덱스에서 전체 잔액을 지출하지 않은 경우) 나머지 주소로 전송됩니다.

     > 0 (Input - output)


번들의 고유 한 기능은 트랜잭션이 번들 해시 뿐만 아니라 trunkTransaction을 통해서도 식별된다는 것입니다. 즉, Tail transaction(currentIndex : 0)은 trunkTransaction에서 트랜잭션 해시를 인덱스 1에서 참조하고, currentIndex 1 트랜잭션은 인덱스 2를 참조 (및 승인)합니다. 이렇게 하면 trunkTransaction을 순회하여 꼬리 트랜잭션에서 트랜잭션 번들 전체를 얻을 수 있습니다. 

단일 트랜잭션에는 분명히 여러 입력 및 출력이 포함될 수 있습니다.
  1. 2. Making a Transaction — IOTA Documentations (https://iota.readme.io/v1.2.0/docs/making-a-transaction)

앞서 언급했듯이 IOTA에는 채굴자(Miner)가 없습니다. 이와 같이 트랜잭션을 만드는 프로세스는 오늘날 블록 체인과 다릅니다. IOTA의 절차는 다음과 같습니다.

1. Signing: 개인 키를 사용하여 거래 입력에 서명합니다. 이 작업은 오프라인으로 수행 할 수 있습니다.

2. Tip Selection: MCMC는 트랜잭션 (branchTransaction 및 trunkTransaction)에서 참조 할 두 가지 팁을 무작위로 선택하는 데 사용됩니다.

3. Proof of Work: 네트워크에서 거래를 승인 받으려면 Bitcoin (스팸 및 sybil-resistance)이 아닌 Hashcash와 유사한 일부 작업 증명을 수행해야합니다. 이것은 보통 현대 PC에 몇 분이 소요됩니다.

이 작업이 완료되면 트랜잭션 객체의 trunkTransaction, branchTransaction 및 nonce가 업데이트되어야합니다. 즉, 거래를 네트워크에 지금 브로드 캐스트하고 다른 사람이 거래를 승인 할 때까지 기다릴 수 있습니다. 

1. The Steps to make a transaction



번들 만들기에는 모든 입력과 출력이 포함됩니다.

1. 출력 트랜잭션 준비

2. 입력 값이 출력 값을 만족할 때까지 입력 트랜잭션을 준비합니다.

3. Bundle hash를 얻고 모든 트랜잭션에 채우기 위해 최종 묶음

4. 서명 메시지 조각 작성에 대한 트랜잭션 처리

트렁크(trunk) 및 분기 해시(Branch hash)에 대한 두 가지 tip 얻기 

IRI getTransactionsToApprove를 통해


Proof of Work

1. 트랜잭션에 trunk branch hash 채우기

2. 태그가 설정되지 않은 경우 obsolete tag(오래된 태그)로 태그를 채우기.

3. 트랜잭션에 Timestamp 채우기

4. pearlDiver를 통해 nonce를 계산하고 Transaction hash를 얻습니다.

2. Making bundle


IOTA 번들에는 3 가지 유형의 트랜잭션이 포함되어 있습니다. Input transaction(입력 트랜잭션), Output transaction(출력 트랜잭션), and Meta transaction(메타 트랜잭션).

Input transaction: Transaction value가 음수
Output transaction: Transcation value가 양수.
Meta transaction: Transaction value 가 0, 그것은 서명의 carieer가 될 수 있거나 트랜잭션의 siganture 메시지 조각에 다른 메시지를 저장할 수 있습니다.


예를 들어 봅시다. A는 동일한 시드로부터 3 개의 주소를 가지며 몇개의 value를 가집니다.


Gather all transaction we need in bundle


- index 0: AAAAAAAA, balance: 50

- index 1: BBBBBBBB, balance: 70

- index 2: CCCCCCCC, balance: 20


A가 B의 주소 DDDDDDDD로 100i를 보낼 때, IOTA는 다음과 같이 할 것입니다 :


번들로 필요한 모든 거래를 모으기


B의 주소로 Output Transaction 준비 및 Bundle에 추가

Balance와 함께 A의 주소에서 Input Transaction 준비

Meta Transaction 슬롯을 사용하여 각각의 Input Transaction을 Bundle에 추가한다. 


메타 트랜잭션 슬롯 금액은 주소 보안 수준에 따라 다르며 주소의 기본 보안 수준은 2입니다. 즉, 트랜잭션 서명을 전달하는 데 하나의 추가 트랜잭션이 필요합니다.


번들의 잔액이 여전히 양수인 경우 사용되지 않은 출력 트랜잭션을 추가하여 소비되지 않은 값(Unspent value)을 이동합니다


Bundle finalized


 번들 Balance가 0인지 체크(입력 값 = 출력 값, Kirchhoff의 회선 법칙(Kirchhoff’s circuit laws)을 recall)



Generate bundle hash


- Kerl을 사용하여 transaction 유효성 검사 항목(address, value, obsolete tag, timestamp, current index, and last index)으로 흡수한다.


- Bundle trit을 집어 내고 Bundle hash로 변환한다.

- Secure bundle hash 생성 여부를 확인하고, 그렇지 않으면 obsolete tag(폐기 태그)를 증가시키고 다시 생성한다. (https://github.com/iotaledger/iota.lib.py/issues/84)


- 모든 트랜잭션에 Bundle hash 및 초기화 서명 조각을 채워넣는다 


- transaction hash, transaction tips, signature fragment and nonce가 이 단계에서 채워있지 않음을 확인하고 bundle hash만 결정됩니다.



Bundle signing


- seed를 통해 키 생성기(key generator) 가져 오기


- 트랜잭션을 반복하고 만약 트랜잭션이 Output transaction이면 이 transaction을 signing하려고 시도할 것이다(만약 필요하면 meta transaction으로). 


- 주소 index 및 security level으로 키 생성을 통해 Address private key를 얻는다.


- address private key와 bundle hash를 사용하여 signature fragment(서명 조각)을 생성하고 트랜잭션의 signature fragment 부분을 채 운다.


- 만약 security level이 2인 경우 2개의 transaction에 사인을 해야 한다. (output transaction과 다음 meta transaction인 경우 1개)



이 단계가 끝나면, bundle hash 및 transaction signature를 역순으로 (마지막 index부터 0 index 까지) transaction trytes들의 리스트를 얻는다.




3. Get two tips for trunk and branch


이 글에서 나는 MCMC 알고리즘을 다루지 않을 것이며, 이것을 블랙 박스라고 생각한다. getTransactionsToApprove를 통해 IRI로부터 두 가지 팁을 얻을 수있다.




4. Proof of Work


마지막 단계에서는 번들의 각 트랜잭션에 trunk, branch 및 nonce (여기에서 작업 증명!)를 채워야한다.


번들 설명서에 언급된 바와 같이, 번들은 Tangle 안의 Atomic transfer(원자적 전송) 항목이다. 즉, 하나의 bundle 안에서 같은 팁들을 가지고 있어야 한다.



그런 다음 Bundle의 모든 트랜잭션을 마지막 인덱스부터 0 인덱스까지 trunk, branch hash, time stamp을 채우기 위해 이동하고 nonce값을 찾ㄱ고 transaction hash를 생성하기 위한 PoW를 수행하고 PoW 결과의 유효성을 검사한다.


마지막 인덱스의 트랜잭션 트렁크와 분기 해시는 우리가 얻는 이전 팁이 될 것이다. 다른 트랜잭션의 트렁크는 이전 트랜잭션의 해시이고 분기 해시는 팁의 트렁크 트랜잭션이다. 



모든 것이 제대로 되었으면 모든 필드가 채워진 전체 트랜잭션 trytes를 얻을 수 있습니다!



5. PoC code for Python with PyOTA



# -*- coding: utf-8 -*-
# This is a POC code to generate IOTA transaction and bundle
#
# Note: You will need to implement getTransactionsToApprove
#
import iota
import pearldiver
SEED = 'GENERATE_YORU_SELF'
tag = iota.Tag('TESTINGPYTHON')
pt = iota.ProposedTransaction(
address=iota.Address('9TPHVCFLAZTZSDUWFBLCJOZICJKKPVDMAASWJZNFFBKRDDTEOUJHR9JVGTJNI9IYNVISZVXARWJFKUZWC'),
value=90,
tag=tag,
message=iota.TryteString('HELLO')
)
pb = iota.ProposedBundle([pt])
# pb.add_inputs([list])
# pb._create_input_transaction(addy)
addy = iota.Address('INDTKDAH9GGWDAJDWQLWUKCIHSYNEFQUGVHOYWLZRYPEZIZYQHQJNDLDPCLWMMO9UAEZUWPHMWZRLWGOB')
addy.balance = 100
addy.key_index = 2
addy.security_level = 2
inputs = [
iota.ProposedTransaction(
address=addy,
tag=tag,
value=-addy.balance
)
]
for input in inputs:
pb._transactions.append(input)
for _ in range(addy.security_level - 1):
pb._transactions.append(iota.ProposedTransaction(
address=addy,
tag=tag,
value=0
))
# send unspent inputs to
unspent = iota.Address('HWFZCLVY9RPTAWC9OIOSHXSWFIYMSYSYBHZER9BYZ9KUPUJTRUOLKSGISILWFCWJO9LNZOLWRCJMVDJGD')
pb.send_unspent_inputs_to(unspent)
# This will get the bundle hash
pb.finalize()
# If the transaction need sign, it will then sign-up the transaction
# to fill up signature fragements
kg = iota.crypto.signing.KeyGenerator(SEED)
# pb.sign_inputs(kg)
i = 0
while i < len(pb):
txn = pb[i]
if txn.value < 0:
if txn.address.key_index is None or txn.address.security_level is None:
raise ValueError
# pb.sign_input_at(i, kg.get_key_for(txn.address))
address_priv_key = kg.get_key_for(txn.address)
# Fill in signature fragement
# address_priv_key.sign_input_transactions(pb, i)
from iota.crypto.signing import SignatureFragmentGenerator
sfg = SignatureFragmentGenerator(address_priv_key, pb.hash)
for j in range(address_priv_key.security_level):
txn = pb[i + j]
txn.signature_message_fragment = next(sfg)
i += txn.address.security_level
else:
i += 1
# Now each transaction have their signature into bundle
# this is the end of the transaction construction.
# We can now propose the transaction to tangle
# At this moment, tips still not inside each transaction,
# and each transaction hash is not yet generated
trytes = pb.as_tryte_strings()
# Get tips by getTransactionsToApprove
# tips = getTransactionsToApprove()
trunk_hash = iota.Hash('')
branch_hash = iota.Hash('')
# Do PoW (attach to tangle)
prev_tx = None
for tx_tryte in trytes:
txn = iota.Transaction.from_tryte_string(tx_tryte)
txn.trunk_transaction_hash = trunk_hash if prev_tx is None else prev_tx.hash
txn.branch_transaction_hash = branch_hash if prev_tx is None else trunk_hash
# Copy obsolete tag if tag field is empty
if not txn.tag:
txn.tag = txn.obsolete_tag
# Copy timestamp
txn.timestamp = None
txn.timestamp_lower_bound = None
txn.timestamp_upper_bound = None
# Do the PoW for this transaction
diver = pearldiver.PearlDiver()
trits = txn.trits()
diver.search(trits, min_weight_magniude, -1)
# Validate PoW
# transactionValidator.validate(txn.as_trits())


6. Conclusion


여기서는 IOTA가 트랜잭션을 사용하여 Bundle을 구성하는 방법과 bundle hash, transaction hash, trunk hash, branch hash 및 nonce.와 같은 트랜잭션의 중요한 부분을 채울 때에 대해 설명한다.


우리는 명확하게 알고있다 트랜잭션을 생성하는 모든 단계에서 IoT 디바이스의 핵심 부분은 본인의 Transaction에 Signing하는 부분만 신경쓰고 나머지 other output transaction, tip selection and PoW 는 해당 디바이스에서 수행될 필요가 없다.



+ Recent posts