본문으로 건너뛰기

패키지 업그레이드하기

컨트랙트를 배포한 후에 버그를 수정하거나 기능을 추가하고 싶을 때가 있습니다. Sui에서는 패키지 업그레이드 기능을 통해 기존 패키지를 업데이트할 수 있습니다. 어렵지 않습니다. 순서대로 살펴보겠습니다.


UpgradeCap이란?

sui client publish로 패키지를 배포하면, 트랜잭션 결과로 UpgradeCap 이라는 오브젝트가 발행됩니다.

이 오브젝트가 "업그레이드의 열쇠"입니다.

  • 일반적으로 UpgradeCap을 보유한 주체만 패키지를 업그레이드할 수 있습니다
  • 다른 사람에게 양도하거나 소각할 수 있습니다(소각하면 업그레이드가 영구적으로 불가능해집니다)
  • 업그레이드하면 새로운 패키지 ID가 발행됩니다(기존 ID의 컨트랙트는 계속 동작합니다)

sui client publish가 성공하면 프로젝트 루트에 Published.toml 파일이 자동 생성됩니다. 이 파일에 UpgradeCap의 오브젝트 ID가 기록되므로, 업그레이드 시 수동으로 지정할 필요가 없습니다.

이 파일은 소스 컨트롤에 커밋하는 것을 권장합니다.

내용은 다음과 같습니다:

# Generated by Move
# This file SHOULD be committed to source control

[published.devnet]
chain-id = "3d6c67b7"
published-at = "0x36d821b7..."
original-id = "0xbe356beb..."
version = 1
toolchain-version = "1.68.0"
build-config = { flavor = "sui", edition = "2024" }
upgrade-capability = "0xe569f7ab..."
  • published-at: 현재 패키지 ID(업그레이드할 때마다 새로운 ID로 업데이트됨)
  • original-id: 최초 배포 시의 패키지 ID(변경 없음)
  • version: 업그레이드할 때마다 증가하는 번호
  • upgrade-capability: UpgradeCap의 오브젝트 ID

코드 수정하기

업그레이드 예시로, reset 함수를 추가해 보겠습니다. L16에서 만든 counter 모듈에 다음 함수를 추가합니다.

entry fun reset(counter: &mut Counter, _ctx: &mut TxContext) {
counter.value = 0;
}
업그레이드 제약 사항

이미 배포한 코드에서는 다음과 같은 변경을 할 수 없습니다:

  • 배포한 모듈을 삭제하는 것
  • 기존 public 함수의 이름·인수·반환값을 변경하는 것
  • 기존 struct의 필드를 추가·변경·재정렬하는 것

반면, 새로운 함수나 struct의 추가, 함수 내부 로직의 변경은 자유롭게 할 수 있습니다.


업그레이드 실행하기

코드 수정이 완료되면 다음 명령어로 업그레이드합니다.

sui client upgrade

UpgradeCap을 보유한 주소가 활성 주소라면, 이 명령어 하나로 업그레이드할 수 있습니다.


업그레이드 확인하기

Published.toml로 확인하기

업그레이드가 성공하면 Published.toml이 자동으로 업데이트됩니다.

[published.devnet]
published-at = "0xNEW_PACKAGE_ID..." # ← 새로운 패키지 ID로 업데이트됨
original-id = "0xbe356beb..." # ← 변경 없음
version = 2 # ← 증가됨
upgrade-capability = "0xe569f7ab..." # ← 변경 없음

published-at이 새로운 패키지 ID로 변경되어 있으면 업그레이드 성공입니다.

Sui Explorer에서 확인하기

suiscan.xyz에서 트랜잭션을 확인할 수도 있습니다.

  1. 업그레이드 트랜잭션 다이제스트로 검색합니다
  2. "Object Changes" 섹션을 엽니다
  3. type: "published" 항목에 새로운 패키지 ID가 표시되어 있는지 확인합니다

이 새로운 패키지 ID가 업그레이드된 패키지의 주소입니다. 이후에는 이 ID를 사용해 컨트랙트를 호출합니다.

기존 패키지 ID의 컨트랙트는 계속 동작합니다. 다만, 기존 클라이언트 코드나 의존 관계는 자동으로 새로운 패키지 ID로 전환되지 않습니다. 새로운 버전을 사용하려면 참조하는 패키지 ID를 업데이트해야 합니다.


수고하셨습니다! 이제 패키지를 업그레이드할 수 있게 되었습니다. 고급 코스에서는 TypeScript를 사용해 컨트랙트를 프로그래밍 방식으로 조작하는 방법을 배웁니다.