Ligntning Network
비트코인을 통해서 어떤 상품을 결제한다고 하면, 기존의 비트코인 프로토콜 상에서는 최소한 10분은 기다려야 안심하고 상품이나 서비스를 제공받을 수 있다. 내가 비트코인을 전송하는 트랜잭션이 블록에 포함되어서 컨펌되려면 10분의 시간이 필요하기 때문이다.
만약 그 금액이 크다면 판매자 입장에서는 1컨펌으로는 안심할 수 없으니 더 긴 시간을 기다려서 충분한 수의 컨펌이 이루어질 때까지 기다려야 안심하고 상품이나 서비스를 제공할 수 있을 것이다.
라이트닝 네트워크 (줄여서 LN이라고도 한다.) 는 이 문제를 해결하기 위해, 비트코인 프로토콜을 기반의 즉각적인 페이먼트를 할 수 있는 프로토콜이다. 그래서 비트코인을 첫 번째 레이어 프로토콜로 봐서 LN을 그 위에 세컨드 레이어로 프로토콜로 볼 수도 있다. 이름이 '라이트닝' 인 이유는 번개처럼 빠른 결제 시스템을 위한 프로토콜이라는 뜻에서 나왔다.
예시
세그윗 정리에서도 나왔던 예시이지만, B는 커피를 파는 카페 사장이고, A는 손님이라고 해보자.
A는 비트코인을 사용하여 B의 카페에서 커피를 사 마시고자 한다.
그런데 비트코인은 상술했듯 트랜잭션이 확정되는데 10분의 시간이 필요하다.
커피를 파는 사람 입장에서는 이 트랜잭션이 확정되지 않으면 자신이 해당 돈을 꺼내서 쓸 수 없으며, double spend 문제가 발생할 수도 있으므로 10분의 시간이 지나기 전에 커피를 제공하는 것이 부담스럽다.
하지만 그렇다고 10분을 기다렸다가 커피를 제공하자니 손님 입장에서는 커피 한잔 받는데 10분의 시간을 기다리는 것이 불편하다. 또한 만약 A가 B의 카페를 자주 방문하는 손님이라고 한다면, A는 매번 커피를 사마실 때마다 트랜잭션을 만드므로 트랜잭션 수수료를 지불해야 한다.
그런데 커피값 기준으로 트랜잭션 수수료는 커피값의 거의 절반정도를 차지할 수 있다.
그러면 커피를 사마시는 사람 입장에서는 그냥 현금이나 신용카드를 쓰고 말지 비트코인을 쓸 이유가 없다.
해결 방법
만약 A가 B가 운영하는 카페의 단골 손님이라서 여러번 방문해서 커피를 사마실 의향이 있는 사람이라고 해보자.
그러면 매번 커피 결제 트랜잭션을 발생시키지 말고, 언제든 비트코인 네트워크에 뿌릴 수 있는 임시 트랜잭션을 만들고, 커피를 사마실 때마다 임시 트랜잭션의 송금 금액을 바꿔서 나중에 최종 금액에 대한 트랜잭션을 한번에 뿌리면 어떨까?
임시 트랜잭션을 만드는 순간 결제가 된 것으로 합의하고 바로 상품/서비스를 제공할 수 있으므로 컨펌을 기다릴 필요가 없고, 최종 금액에 대한 트랜잭션 수수료만 내면 되므로 구매자 입장에서도 트랜잭션 수수료 부담이 적어진다.
구체적인 예시로 보자.
A와 B의 카페를 자주 방문할 의향이 있다고 생각해서 100만원 어치의 돈을 미리 펀드로 만들어둔다.
이 펀드는 A와 B가 모두 접근해서 돈을 꺼내쓸 수 있는 공동 계좌이다.
물론 이 계좌에서 돈을 꺼내려면 당연히 A, B 모두의 서명이 있어야 할 것이다.
최초에는 이 펀드의 돈 100만원을 모두 A에게 보내는 트랜잭션을 만든다.
그리고 A가 커피를 사마실 때마다 A에게 보내는 금액을 줄이고 B에게 보내는 금액을 늘리는 트랜잭션을 새로 만든다.
처음에는 100만원을 전부 A에게 보내는 트랜잭션이었지만,
1만원 커피를 사 마신 후에는 100만원 중 99만원은 A, 1만원은 B에게 보내는 트랜잭션으로 바꾼다.
1만원 커피를 또 사 마신 후에는 100만원 중 98면원은 A, 2만원은 B에게 보내는 트랜잭션으로 바꾼다.
이 과정에서 만들어지는 트랜잭션들은 모두 임시 트랜잭션으로, 비트코인 네트워크에 뿌리지 않고, A, B가 서로 갖고만 있는 트랜잭션이다. (비트코인 네트워크에 매번 뿌리면 매번 트랜잭션 수수료를 내야한다)
이렇게 트랜잭션의 금액 전송 비율을 조정해서 최종적으로 A가 50만원 어치 커피를 사먹고 더 이상 커피를 안 마신다면
100만원 중 50만원은 A, 50만원은 B에게 보내는 최종 트랜잭션 하나만 비트코인 네트워크에 뿌린다.
라이트닝 네트워크 개요
라이트닝 네트워크는 비트코인 블록체인 위에서 동작하는 P2P 네트워크, 페이먼트 채널이며, 통신 프로토콜이다.
이 페이먼트 채널도 일종의 스마트 컨트랙트이다. (비트코인의 스마트 컨트랙트는 스크립트 문법의 한계에 의해 제한적이다.)
이 '페이먼트 채널'을 열게 되면, 위에 적은 임시 트랜잭션을 주고받는 형태로 결제가 가능하다.
이때 라이트닝 네트워크를 쓴다고 해서 트랜잭션 수수료를 전혀 지불하지 않는 것은 아니다.
최초에 펀드를 만드는 트랜잭션과, 최종 잔액에 대한 트랜잭션은 비트코인 네트워크로 보내야 하므로 이 2개 트랜잭션에 대해서는 수수료를 지불해야한다.
페이먼트 채널은 어떤 페이먼트에 대한 관계와 같다.
이 관계에 참여하는 두 상대방을 '채널 파트너' 라고 부른다.
A의 채널 파트너는 B,
B의 채널 파트너는 A인 것이다.
페이먼트 채널에는 처음에 밀리 사토시 단위의 fund balance 가 할당된다.
위 예시에서는 처음에 넣어두는 100만원이 초기 밸런스가 되며, 앨리스가 100만원, 밥이 0원을 갖는 상태로 시작한다.
그리고 결제가 발생할 때마다 암호화 프로토콜에 따라 이 잔액이 조정된다.
암호화 프로토콜은 한 채널 파트너가 다른 채널 파트너를 속이고 돈을 갈취하려고 하는 경우, 이를 응징할 수 있는 수단을 제공한다. 예를 들어 10일 동안 거리했는데, 8일째 거래가 마치 최종인 것처럼 속여서 8일차의 트랜잭션을 비트코인 네트워크에 뿌릴 수 있다. 이런 경우에 상대방을 응징할 수 있다. 따라서 두 채널 파트너는 서로를 신뢰하지 않아도 되며, 중간 결제 트랜잭션들이 블록체인에 포함되지 않았음에도 상대방에게 서비스나 상품을 안심하고 제공할 수 있다.
이 프로토콜은 2-of-2 멀티 시그니처 주소로 펀드를 만든다.
따라서 펀드로부터 돈을 꺼낼 때는 두 명의 서명이 모두 필요하므로, 한쪽이 혼자서 마음대로 돈을 꺼내 쓸 수 없다.
이제 이 펀드를 기반으로 거래가 발생할 때마다 A에서 B로, 또는 B에서 A로 돈을 보낼 수 있다.
(B에서 A로 보내는 것은 일종의 환불 개념)
그리고 거래가 발생할 때마다 이 거래에 대한 트랜잭션 시퀀스가 쌓인다.
이 트랜잭션들은 즉각적으로 블록에 포함되지 않는다.
하지만 상대방이 나를 속일 수도 있으므로, 트랜잭션을 갖고 있다가, 만약 상대방이 나를 속였음을 알았다면 내가 가진 트랜잭션을 뿌려서 상대방을 응징한다.
그림을 보면서 이해해보자.
위 그림에서 진한 파란색 사각형은 라이트닝 네트워크로 결제를 진행하는 트랜잭션들을 의미한다.
먼저 On-chain tranasactions 에 있는 부분이 기존의 블록체인 레이어이고, 점선 위에 있는 Off-chain transactions 는 LN 에 의해 만드는 트랜잭션들이다. 이 계층이 두번째 레이어가 된다.
왼쪽에서 오른쪽 시간 순으로 블록이 생성될 때, 먼저 첫번째 블록에 펀드를 만드는 트랜잭션을 컨펌시켜서 네트워크에 뿌린다.
이후에 이 펀드를 기반으로 거래가 발생할 때마다 off-chain transactions 영역에서 트랜잭션을 만든다.
모든 거래가 끝나면 최종 거래가 완료된 트랜잭션 하나를 비트코인 네트워크에 뿌리고 컨펌시킨다.
그 중간에 있는 트랜잭션들은 비트코인 네트워크에 뿌려지지 않고, LN 계층상에서만 존재한다.
최종적으로는 처음 펀딩을 만드는 트랜잭션과, 최종 결제 내역에 대한 트랜잭션 2개에 대해서만 트랜잭션 수수료를 지불한다.
최초의 펀딩 트랜잭션은 위와 같이 생성한다.
먼저 앨리스가 자신이 갖고 있는 20만 사토시 중에서 14만 사토시를 펀딩 금액으로 만들어 펀드 계좌에 넣는다.
이 펀딩 금액을 이 페이먼트 채널의 capacity 라고도 부른다. 이 채널을 통해서 금액이 이동하는 것은 양방향으로 이동할 수 있기 때문에 실제 금액 이동의 flow 총량이 capacity 만큼으로 제한되지는 않는다.
(A가 B로 10만 보내고, B가 A로 3만 보내고, 다시 A가 B로 3만을 보내면 총 플로우는 16만)
펀드 계좌를 만들 때는 밥의 협조를 받아 밥의 퍼블릭 키를 받아 포함시킨다.
퍼블릭 키는 민감한 정보가 아니므로 밥은 충분히 협조할 수 있다.
이 계좌에서 돈을 꺼낼 때는 앨리스와 밥 두 명 모두의 서명이 필요하다.
14만 사토시를 펀딩 계좌에 보내고 남은 잔액 6만 사토시는 앨리스 본인의 계좌로 보낸다.
이 트랜잭션은 비트코인 네트워크에 뿌려서 확정된다.
밥 입장에서 이 트랜잭션이 뿌려지지 않으면 불안할 수 있기 때문이다.
펀딩조차 비트코인 네트워크에 기록이 되지 않았는데, 그 중간에 페이먼트에 대해서 내가 이 페이먼트 대로 돈을 정말 받을 수 있는지 의심할 수 있다.
따라서 밥은 이 펀딩 트랜잭션이 6 컨펌 정도를 받은 뒤에는 그때부터는 라이트닝 네트워크 페이먼트를 통해서 커피값을 받은 것을 신뢰하고 커피를 제공할 수 있다.
펀딩 트랜잭션에서 14만 사토시의 돈을 꺼내려면 앨리스와 밥 모두의 서명이 필요한데, 만약 밥이 펀딩 트랜잭션을 만들고나서 잠수타고 서명을 제공하지 않으면 14만 사토시는 영영 꺼낼 수 없게 된다.
이를 방지하기 위해, 펀딩 트랜잭션을 만들고 나서 앨리스는 Refund Transaction 을 만든다.
환불 트랜잭션은 자신이 펀딩 계좌에 넣은 14만 사토시를 모두 자신의 계좌로 돌려보내는 트랜잭션이다.
이 트랜잭션을 사용하려면 이 트랜잭션에 대한 밥의 서명이 필요하므로, 밥은 이에 대한 서명을 만들어서 앨리스에게 제공해준다. 앨리스는 이 서명을 받은 후에야 펀딩 트랜잭션을 네트워크에 안심하고 뿌릴 것이다.
이 Refund Transaction은 비트코인 네트워크에 뿌리지 않고, LN 위에서 두 파트너가 가지고만 있는다.
페이먼트 채널을 만드는 과정은 구체적으로 위와 같다.
먼저 A가 새로운 private / public key 쌍을 만들고, B에게 채널을 열자고 제안한다.
(2-of-2 멀티 시그니처에 사용하기 위해 새로운 키 쌍을 만든다.)
B가 수락하면 B도 새로운 키 쌍을 만들고 A에게 public key를 제공한다.
A는 밥이 제공한 public key 를 가지고 펀딩 트랜잭션을 만든다.
펀딩 트랜잭션은 2-of-2 멀티 시그니처 방식이며, A, B의 서명이 모두 필요하다.
따라서 펀딩 트랜잭션을 뿌리기 전에 B에게 펀딩 트랜잭션의 해시값을 주고 Refund Transaction에 대한 서명을 요구한다.
B가 Refund transaction 서명을 주면 이제 안심하고 펀딩 트랜잭션을 뿌린다.
B가 Refund Transaction 에 대한 서명을 제공하려면 Refund Transaction 의 구조를 알아야 하며, Rerfund Transaction의 구조를 알려면 Funding Transaction의 해시값이 필요하고, 이 해시값을 얻으려면 A는 funding transaction의 형태를 알고 있으므로 그 형태를 따라 만들어서 해시값을 계산해서 B에게 제공한다. B는 이 해시값을 가지고 refund transaction을 미리 구성할 수 있고, 이 구성된 트랜잭션에 대한 서명을 A에게 제공한다. A는 같은 형태로 refund transaction을 구성해두고, 필요한 경우, B가 제공한 서명을 이용해서 자신의 계좌로 펀딩 금액을 환불받는 트랜잭션을 네트워크에 뿌릴 수 있다.
이렇게 Refund Transaction 이 만들어지면, A는 Funding Transaction 을 비트코인 네트워크에 뿌려서 컨펌 시킨다.
이를 가리켜 '펀딩이 락된다.' 고 표현한다.
펀딩 트랜잭션이 락되면 이 트랜잭션은 비트코인 네트워크에 존재하므로 On-Chain 레이어에 존재한다.
14만 사토시 예시를 그대로 가져오면, 위 그림에서는 이전에 앨리스가 자신의 20만 사토시 중 14만 사토시를 공동 계좌에 넣고, 남은 6만 사토시를 자신의 계좌로 보내는 펀딩 트랜잭션을 간략하게 2-of-2 만으로 표현하였다.
Off-Chian 에서는 펀딩 트랜잭션을 기반으로 거래가 발생할 때마다 트랜잭션 시퀀스가 생긴다.
이 각각의 페이먼트에 대한 트랜잭션을 commitment transaction 이라고 부른다.
페이먼트가 진행될 때마다 commitment transaction 의 번호가 증가하며, 제일 큰 번호가 제일 최신의 트랜잭션이다.
이 시퀀스에서 최초의 트랜잭션 (0번 commitment) 은 앨리스 자신의 계좌로 14만 사토시의 펀딩 금액을 모두 돌려받는 트랜잭션이다.
0번 커밋먼트에서는 (앨리스 14만 - 밥 0) 의 잔고를 갖는다.
앨리스가 7만 사토시 어치의 커피를 결제하면, 1번 커밋먼트가 생긴다.
이 트랜잭션은 공동 편딩 계좌에서 (앨리스 7만 - 밥 7만) 의 잔고를 갖도록 잔액 배분을 재조정한다.
다시 앨리스가 1만 사토시 어치 커피를 결제하면 2번 커밋먼트가 생긴다.
이 트랜잭션은 공동 펀딩 계좌에서 (앨리스 6만 - 밥 8만) 의 잔고를 갖도록 잔액 배분을 재조정한다.
다시 앨리스가 2만 사토시 어치 커피를 결제하면 3번 커밋먼트가 생긴다.
이 트랜잭션은 공동 펀딩 계좌에서 (앨리스 4만 - 밥 10만) 의 잔고를 갖도록 잔액 배분을 재조정한다.
즉, 14만에서 계속 까는 방식이 아니라, 14만이라는 금액에서 얼마씩 나눠가질 것인지, 그 비율을 재조정하는 과정을 거치는 것이라고 보면 된다.
그런데 지금 4개의 commitment 트랜잭션들을 보면, 모두 같은 공동 펀딩 계좌에서 돈을 꺼내고 있다.
따라서 비트코인 네트워크에는 4개의 트랜잭션 중 하나만 유효한 트랜잭션으로 컨펌될 수 있다.
만약 앨리스가 커피를 10만 사토시 어치 사먹고나서, 초기의 14만 사토시를 자신에게로 보내는 트랜잭션을 네트워크에 뿌려버리면 어떻게 될까?
밥으로부터 서명도 받았겠다, 이렇게 하면 앨리스는 공짜로 10만 사토시 어치의 커피를 먹는 셈이 된다.
LN에는 이를 막기 위한 방법도 정의되어있다.
그 방법을 설명하기에 앞서, LN에서는 같은 번호에 대한 Commitment 트랜잭션은 각 파트너가 서로 다른 구조로 갖고 있다.
commitment #2 트랜잭션은 앨리스에게 6만, 밥에게 8만 사토시를 보내는 트랜잭션이다.
이때 앨리스와 밥은 모두 0번 output 은 자신에게 보내는 output을 명시하고, 1번 output 에는 상대방에게 보내는 output을 명시한다.
앨리스 입장에서는 6만 사토시를 자신에게, 8만 사토시를 상대방에게 보낼 것이고,
밥 입장에서는 8만 사토시를 자신에게, 6만 사토시를 상대방에게 보낼 것이다.
이렇게 앨리스와 밥이 갖고 있는 트랜잭션의 output 순서가 다르기 때문에, 이 두 트랜잭션의 해시값 역시 서로 달라진다.
이를 이용하면 위에서 말한 앨리스의 치팅을 막을 수 있다.
그 방법은 바로 자기 자신에게로 보내는 아웃풋에 대해서는 타임 락을 걸어서 딜레이를 주는 것이다.
그 락의 시간은 432블록의 컨펌 (대략 3일) 이며, 이 시간이 지나야만 이 output 으로부터 비트코인을 꺼내 쓸 수 있게 된다.
(하루 = 1440분 = 144블록 채굴, 144 * 3 = 432)
타임 락 블록 수는 원하는 경우 2016까지 키울 수 있다.
만약 앨리스가 치팅해서 이 트랜잭션을 상의없이 뿌렸다고 해보자.
그러면 그 트랜잭션이 컨펌되더라도, 앨리스는 그 트랜잭션으로부터 6만 사토시를 꺼내 쓰려면 3일의 시간이 지나야 쓸 수 있다.
그 시간동안 밥은 앨리스가 치팅했다는 것을 알아내고 대응할 수 있다.
이때 밥이 대응할 수 있도록 하기 위해서 자기 자신에게 보내는 output을 다음과 같이 수정한다.
6만 사토시를 보내는데, 6만 사토시를 꺼내 쓰려는 경우, 432블록이 컨펌된 후에 앨리스가 자신의 서명을 제시해서 가져다 쓰거나, 밥이 remote_key 에 대한 서명을 제시해서 즉각적으로 꺼내 쓸 수 있다.
스크립트 검증 조건이 OR로 연결되어 있기 때문에, 둘 중 하나만 만족하면 TRUE가 되어 스크립트 검증에 성공하므로 경우에 따라서 밥도 충분히 앨리스에게 보내려던 6만 사토시를 가져다가 쓸 수 있게 되었다.
이때 remote_key 에 대한 서명은 앨리스가 밥에게 제공해야 하며, remote_key에 대한 서명은 commitment #2 트랜잭션 이후에 commitment #3 트랜잭션을 만들 때 밥에게 #3에 대한 서명을 받은 후 제공한다.
commitment #3 트랜잭션을 만들 때 앨리스는 밥에게 '자신의 commitment #2 트랜잭션' 에 대해 remote_key에 대한 서명을 제공하여, '만약 내가 치팅하는 경우, 나에게 보내려던 6만 사토시도 너가 가져라' 라고 할 수 있는 것이다.
이 모든 과정은 output 순서를 뒤집어서 밥도 똑같이 수행한다.
만약 앨리스가 정말 치팅하는 경우, 밥은 앨리스가 제공한 remote_key 에 일치하는 서명을 제시해서 #2 트랜잭션의 0번 output 에서 6만 사토시를 가져올 수 있다.
이렇게 스크립틑를 사용해서 제한된 형태의 스마트 컨트랙트 (계약) 를 구현할 수 있다.
'CS > 블록체인' 카테고리의 다른 글
[블록체인] 17. Lightning Network (3) : 라이트닝 네트워크 vs 비트코인 (1) | 2024.12.09 |
---|---|
[블록체인] 16. Lightning Network (2) : Commitment Sign & Payment Channel (0) | 2024.12.04 |
[블록체인] 14. 비트코인 Consensus (2) | 2024.11.30 |
[블록체인] 13. Mining (0) | 2024.10.25 |
[블록체인] 12. 비트코인 script (2) (3) | 2024.10.25 |