NFT(Non-Fungible Token)는 블록체인 기술을 이용해서 디지털 자산의 소유주를 증명하는 가상의 토큰(token)이며, 디지털 자산의 한 형태이다. 그림·영상 등의 디지털 파일을 가리키는 주소를 토큰 안에 담음으로써 그 고유한 원본성 및 소유권을 나타내는 용도로 사용된다. NFT를 개발하는 과정에서 용량이 큰 디지털 파일을 블록체인에 저장하는 것은 많은 리소스가 소요되기 때문에, 블록체인에 부담을 줄여주고 데이터의 불변성을 보장해줄 저장소가 필요하다. 또한, 블록체인에 기록되는 NFT metadata의 원본이 중앙집중식 서버에 있으면 NFT에 대한 신뢰성이 떨어질 수 있다. 이를 위해 metadata를 IPFS에 저장하여 불변성을 보장해야 NFT의 가치를 지킬 수 있다.
하지만 콘텐츠를 제공하는 IPFS 노드가 컴퓨터에서 멀리 떨어져 있으면 데이터 액세스가 지연될 수 있으며, 이는 전 세계에 분산된 노드에서 콘텐츠가 제공되는 IPFS와 같은 분산형 시스템의 일반적인 문제이다. 이러한 지연으로 인해 콘텐츠 렌더링 속도가 늦어지거나 콘텐츠를 제공받지 못해 사용자에게 불편함을 야기한다.
대부분의 NFT 거래소는 위 문제 해결을 위해 중앙집중식 서버에 저장해놓은 사본 콘텐츠를 먼저 제공하며, 필요에 따라 IPFS에 저장해놓은 원본을 따로 제공한다. 하지만 이 프로젝트에서는 NFT marketplace를 구축하는 과정에서 web3.0의 저장방식인 IPFS를 이용해서 데이터를 분산 저장하고, 분산된 데이터를 사용자에게 제공하고 이러한 과정에서 나타나는 성능저하 (속도, 안정성)를 IPFS cluster 구축을 통해 개선하여 안정적인 NFT 거래소를 구축하고자 한다.
핵심 기술
(가) NFT
NFT는 암호화폐 같은 디지털 자산이다. 대게 예술품과 관련되는 디지털 아트워크이자 수집품으로, 직역하면 Non-Fungible Token으로 대체 불가능 토큰 이라는 뜻이다. NFT는 고유하면서 대체가 불가능한 아이템의 소유권을 증명하는데 사용된다. NFT는 ① 사람들에게 보이는 역할을 하는 미디어 파일과 ② NFT에 대한 상세 정보를 기록한 메타 데이터, ③ 앞 데이터들을 블록체인에 기록하는 스마트 계약(Smaer Contract)로 이루어져 있다.
(나) IPFS
본 작품에서 NFT의 미디어 파일과 메타데이터를 저장할 시스템으로, IPFS는 InterPlanetary File System의 약자로서, 분산형 파일 시스템에 데이터를 저장하고 공유하기 위한 프로토콜이다. 기존 HTTP의 방식은 데이터가 위치한 주소로 접근하여 콘텐츠를 가져오는 방식이지만, IPFS는 데이터의 내용을 변환한 해시값을 이용해 여러 컴퓨터에 분산 저장되어 있는 콘텐츠를 찾아서 가져오는 방식으로 작동한다. 파일을 고유한 해시로 식별하기 때문에, 파일의 내용이 변경되지 않는 한 항상 동일한 해시값을 갖게 되고 이는 파일의 무결성을 보장한다.
(다) SMART CONTRACT
스마트 컨트랙트는 블록체인에서 실행되는 계약으로 코드로 작성되기 때문에 프로그래밍 가능하고 자동으로 실행이 되며 계약 조건의 충족 여부를 자동으로 검증하고 결과를 실행하여 계약 참여자들 간에 상호작용을 가능하게 한다. 이를 통해 중개인(제 3의 인증기관) 필요 없이 신뢰성과 안정성을 보장할 수 있다. 스마트 컨트랙트는 블록체인에 저장되어 변경되지 않기 때문에 계약의 조건과 결과를 추적할 수 있으며, 거래의 투명성과 무결성을 보장해준다.
관련 플랫폼
사용자가 직접 IPFS 노드를 호스팅 할 필요 없이 api 형식으로 제공하는 대표적인 플랫폼으로 INFURA와 PINATA가 있다. 두 플랫폼 모두 가입후 api 키를 발급받아 인증 헤더와 함께 요청을 보내면 간편하게 콘텐츠를 pinning 해주는 서비스로 본 작품에서 운영하는 IPFS를 따로 개인이나 사업체에게 대여해주는 형태이다. 특이점으로는 INFRA에서는 사용자가 원하는 url로 사용자 전용 INFURA IPFS gateway를 제공한다.
최근 IPFS와 스마트 컨트랙트를 이용한 분산 앱 연구들이 많이 이뤄지고는 있으나 IPFS 자체가 어느 정도 완성된 시스템이기에 해당 시스템을 이용해 새로운 분야에 접목하려는 시도들이 대부분이었고, 이에 따라 NFT 거래소 들도 INFURA와 PINATA같은 노드 호스팅 업체를 통해 IPFS에 NFT 메타데이터, 콘텐츠 파일을 저장하고, 사용자들에게는 중앙집중형 서버에 있는 파일들을 일차적으로 제공하며, 원본에 대한 접근은 선택적인 요소로 미뤄두어 사용자의 불편을 최소화시킨 것으로 파악된다. 아래의 <그림. 2>와 같이 초기 렌더링 속도 때문에 항상 원본을 보여주는 거래소는 존재 하지 않으며, 특정 거래소 들만이 원본에 대한 직접적인 링크를 제공하고 있으며, 그렇지 않은 경우 직접 etherscan을 통해 해당 스마트 컨트랙트에 조회하여 cid를 반환 받고 IPFS gateway를 통해 접근해서 확인해야 한다.
개발 환경
프론트엔드 : React
백엔드 : Node.js 16 running on 64bit Amazon Linux 2/5.8.0
인프라 : AWS Elastic Beanstalk, AWS Codepipeline, Docker(Ubuntu 22.04.2)
블록체인 : Ethereum, hardhat, remix, ERC-721표준
데이터베이스 :MongoDB
미디어 파일 플랫폼 : IPFS(version 0.20.0)
IPFS 구조
Docker를 사용해 3개의 peer로 구성된 IPFS 클러스터를 구축
IPFS 클러스터를 이용해 여러 대의 컴퓨터를 사용해 파일을 저장하고 관리한다. 이 클러스터는 파일을 파티션하고 각 노드에 분산하여 저장함으로써 파일의 가용성을 향상시키며 이를 통해 파일에 대한 높은 내구성과 고가용성을 제공할 수 있다. 또한, 클러스터의 각 노드는 IPFS의 기본 기능을 사용하여 파일을 저장하고 효율적으로 검색할 수 있다. 본 프로젝트에서는 실제로 여러대의 컴퓨터를 사용하는 것이 아닌, 3개의 도커 컨테이너에 ipfs/go-ipfs이미지를 이용해 3개의 IPFS 노드를 배포한 후 이를 클러스터로 구성하였다.
3개의 도커 컨테이너에 IPFS 노드를 배포하기 위해서 다음과 같이 수행하였다. 기본적으로 IPFS는 아와 같은 포트를 사용한다.
때문에, 컨테이너간의 포트 충돌을 피하기 위해 다른 포트로 매핑해야 하며 여러 노드가 다른 데이터 디렉토리를 사용할 수 있게 호스트의 다른 디렉토리를 컨테이너의 데이터 볼륨에 마운트 해야한다. 또한, 도커 네트워크를 생성하여 IPFS 노드 간의 통신을 위한 네트워크를 설정해주었다.
이노드들을클러스터로구성하기위해클러스터에대한공유secret key와 각 노드의 ID와 Private key를 생성해야 한다. secret key는 32바이트의 무작위 바이트 시퀀스를 생성하여 저장하고, 각 노드에 대한 peer id와 private key는 golang 컨테이너 내에서 "ipfs-key" 유틸리티를 사용해서 생성한다. 생성 결과로 아래와 같은 문자열이 출력된다.
# node1의 IPFS Cluster key Generating a 2048 bit RSA key... Success! ID for generated key: QmVYVacmo58TCgJLBnT9SuHTgUdo9efiam1qErxw8VRZGn CAASqQkwggSlAgEAAoIBAQDFRlF2wS6LcGNH0LO0CUYsAauhRntrksLQcL6uzCds7m233MfeV ...생략 |
각 피어에 data/ipfs-cluster/service.json파일과 data/ipfs-cluster/peerstore 파일을 작성하여 각 피어마다의 id와 private key, cluster secret key등을 삽입하고 연결 포트 등 설정을 해주면 cluster 구성이 완료된다.
IPFS는 원본 파일을 암호화한 후, 여러 샤드(shard)로 분할 한 후, IPFS에 연결된 여러 노드에 분산 저장하여 데이터 파일의 위조,변조가 불가능하게 한다. 분산 되어 저장된 데이트들은 DHT(Distributed Hash Table)이라는 구조를 통해서 관리된다. 각 노드들은 키와 값 쌍의 구조를 가지고, 각 노드를 구별할 수 있는 교유 해시 값을 키로 나타낸다. IPFS는 네트워크에 존재하는 파일들을 Merkle DAG형식으로 정리하는데, 이는 이진 트리 데이터 구조이다. 연쇄적인 해시 함수가 사용되기 때문에, 데이터가 바뀔 경우, root hash가 달라지고, 데이터 무결성 확인이 가능하다.
이를 활용해 데이터를 저장할 때 일정 크기로 chunk 해보았다. 예시로 아래 그림11에서는 nft.txt파일을 생성한 후 24바이트로설정한 후 진행하였다. 결과물인 해시 파일 청크의 내용물에서 link와 data를 확인할 수 있다. 각 블록 마다 해시값을 갖게된다. IPFS는 중복블록은 저장하지 않으며, 청크를 이미 존재하는 DAG 노드에 연결한다.
IPFS노드와의연결은ipfs-http-client를사용하였다. ipfs-http-client플랫폼과 IPFS노드들을연결해주는자바스크립트기반API이다.파일을저장하면노드들 에게파일을전달하고저장한콘텐츠의주소값인CID(파일내용을기반으로한 고유한해시)값을반환하며,이CID를통해파일을조회할수있다.
NFT 거래소
이 NFT 거래 플랫폼은 IPFS(분산형 파일 저장 시스템)와 이더리움 기반의 웹 어플리케이션으로 구현하였다. 이더리움은 이더(eth)라는 고유의 암호화폐를 사용하는 블록체인이며, 프로그래밍이 가능하고 이더리움에 스마트 컨트랙트가 배포되면 프로그래밍 된 대로 동작하기 때문에 완전히 신뢰할 수 있다. 하지만, 이더리움의 높은 수수료(가스비) 문제도 있고 이더리움의 메인넷(Layer 1)의 과부하를 줄이고, 빠르고 저렴한 트랜잭션을 처리하기 위한 별도의 Layer 2 솔루션인 폴리곤 ( Matic Network )을 이용했다.
플랫폼과 이더리움 노드가 상호 작용하게 하려고 javascript 기반 라이브러리인 web3modal을 사용하였고, 사용자와 web3modal간 인터페이스를 제공하기 위해서
암호화폐 지갑인 메타마스크(Metamask)를 사용했다. 이를 통해 사용자의 metamask 지갑 주소를 통한 플랫폼 로그인과 nft구매 등에 필요한 결제 인터페이스를 구현하였다.
'
스마트 컨트랙트는 NFT 민팅, NFT 조회, NFT 구매, NFT 리셀 등 무결성의 보장이 필요한 트랙잭션을 관리한다. NFT 민팅은 사용자가 NFT를 생성하기 위 해 NFT의 미디어 파일과 메타데이터를 등록하는 것이고 민팅과 동시에 거래소 에 등록되어 진다. NFT 구매는 판매자가 플랫폼에 등록한 NFT 중 구매자가 원 하는 NFT를 구매하는 것이다. 스마트 컨트랙트의 주소로 NFT의 금액을 송금하 고 구매자와 판매자의 지갑 주소, NFT가격, 거래 ID, 가스비, 거래 가격 등을 블 록체인에 기록한다. NFT 리셀은 구매한 NFT를 본인이 소유하고 있는 상태에서 다시 거래소에 등록하는 행위로 원하는 가격을 설정하여 다시 블록체인에 기록 한다.
NFT를 민팅하는데 필요한 콘텐츠 파일을 업로드하고 NFT의 이름, 설명을 입 력하고 가격을 설정 후 업로드하면 Metamask로부터 NFT를 생성하는데 필요한 가스비 지불 트랜잭션 요청을 받는다.
업로드가 완료되면 IPFS에서 반환한 IPFS CID와 해당 파일로 접근 할 수 있는 링크가 로그로 출력된다.
NFT 조회 페이지에서는 token의 메타데이터뿐만 아니라 소유자와 판매자, 가격, 토큰의 id 등을 같이 요 청 후 로그로 출력한다.
본 프로젝트에서 구현하는 NFT 거래소는 이더리움 기반의 웹 어플리케이션이기 때문에 거래소에 접속시 메타마스크가 설치되어 있는지 확인을 한 후 설치되어 있지 않으면 설치를 요청하는 경고 메세지를 띄우고, 설치되어 있다면 거래소와 암호화폐 지갑의 연동 요청을 한다. <그림19>와 <그림20>은 거래소와 지갑의 연결을 요청하는 화면이며, <그림21>은 메타마스크를 설치할 것을 알리는 경고 메시지이다.
거래소에 연결되면 배포해놓은 스마트 컨트랙트 주소와 정보가 담긴 abi json 파일을 토대로 스마트 컨트랙트와 거래소를 연결시킨다. 아래는 그 연결에 대한 로그이다. 스마트 컨트랙트의 배포주소와 ERC-721에 정의되어 있는 내장 메서드들, 그리고 직접 정의한 메서드들이 포함되어 있다.
NFT를 민팅하는데 필요한 콘텐츠 파일을 업로드하고 NFT의 이름, 설명을 입력하고 가격을 설정 후 업로드하면 Metamask로부터 NFT를 생성하는데 필요한 가스비 지불 트랜잭션 요청을 받는다.
업로드가 완료되면 IPFS에서 반환한 IPFS CID와 해당 파일로 접근할 수 있는 링크가 로그로 출력된다.
*Doodles는 개인적으로 좋아하는 NFT라 해당 컬렉션의 이미지들을 이용했다. 귀여워... 사줘..
다음은 NFT를 구매하는 상세 페이지이다. buy NFT 버튼을 클릭하면 Metamask로 부터 NFT 구매 트랜잭션 요청을 받는다.
구매한 NFT를 재판매 하는 페이지이다. 가격을 설정 후 Resell NFT 버튼을 클릭하면 Metamask로부터 NFT를 생성하는데 필요한 가스비 지불 트랜잭션 요청을 받는다.
등록된 NFT들을 조회하는 페이지이다. 스마트 컨트랙트를 통해 해당 컨트랙트에 등록된 모든 NFT들을 불러온 후 블록에 기록되어 있는 tokenURI를 조회해 IPFS로부터 이미지를 응답받아 화면에 렌더링 한다.
token의 메타데이터뿐만 아니라 소유자와 판매자, 가겨그 토큰의 id등을 요청 후 로그로 출력해 보았다.
사용자가 구매한 NFT들을 조회할 수 있는 페이지이다. 현재 사용자가 구매한 NFT를 조회하는 스마트 컨트랙트를 호출해 블록의 기록을 가져온다.
참고자료
[1] IPFS 공식 문서, https://docs.ipfs.tech/
[2] 거래소 opensea, ,https://opensea.io/
[3] 거래소 blur, https://blur.io/
[4] IPFS 포럼, https://discuss.ipfs.tech/
[5] 이경식, 김상균. (2019). 블록체인 및 분산저장시스템을 활용한 음원 및 시 그니쳐 저장방법. 한국방송공학회 학술발표대회 논문집, Vol.2019
[6] Jagger Bellagarda 1,∗ and Adnan M. Abu-Mahfouz, Connect2NFT: A Web-Based, Blockchain Enabled NFT Application with the Aim of Reducing Fraud and Ensuring Authenticated Social, Non-Human Verified Digital Identitㅛ
'IPFS' 카테고리의 다른 글
IPFS 폴더 업로드 (1) | 2023.03.29 |
---|---|
ElasticSearch를 이용한 IPFS 검색 속도 개선 (0) | 2023.03.27 |
IPFS 파일 추가 (add, pinning) (0) | 2023.03.27 |
NFT marketplace와 IPFS, 응답 지연 해결 방법 (0) | 2023.03.27 |
ipfs 파일접근 : public gateway vs local node access (0) | 2023.03.27 |