Source Code

;; Outcome token contract for prediction market shares
;; Each market mints a YES token and a NO token to represent user positions

(define-constant ERR_UNAUTHORIZED (err u1001))
(define-constant ERR_INVALID_MARKET (err u1002))
(define-constant ERR_INVALID_OUTCOME (err u1003))
(define-constant ERR_INSUFFICIENT_BALANCE (err u1004))

(define-map token-id-yes-map uint uint)
(define-map token-id-no-map uint uint)
(define-map token-metadata uint
    {
        name: (string-ascii 32),
        symbol: (string-ascii 10),
        decimals: uint,
        market-id: uint,
        outcome: uint
    }
)
(define-map balances (tuple (owner principal) (token-id uint)) uint)
(define-map total-supply-map uint uint)

(define-data-var contract-owner principal 'ST1PQHQKV0RJXZFY1DGX8MNSNYVE3VGZJSRTPGZGM)

;; Looks up the token identifier for a given market and outcome type
;; Outcome 1 represents YES, outcome 0 represents NO
(define-read-only (get-token-id (market-id uint) (outcome uint))
    (if (is-eq outcome u1)
        (ok (default-to u0 (map-get? token-id-yes-map market-id)))
        (ok (default-to u0 (map-get? token-id-no-map market-id)))
    )
)

;; Returns stored information about a specific token type
(define-read-only (get-token-metadata (token-id uint))
    (ok (map-get? token-metadata token-id))
)

;; Checks how many shares of a specific token a user owns
(define-read-only (get-balance (token-id uint) (owner principal))
    (ok (default-to u0 (map-get? balances (tuple (owner owner) (token-id token-id)))))
)

;; Returns the total number of shares minted for a token type
(define-read-only (get-total-supply (token-id uint))
    (ok (default-to u0 (map-get? total-supply-map token-id)))
)

;; Moves shares between user accounts
;; Requires sender to authorize the transfer
(define-public (transfer (token-id uint) (amount uint) (sender principal) (recipient principal))
    (begin
        (asserts! (is-eq tx-sender sender) ERR_UNAUTHORIZED)
        (asserts! (>= (default-to u0 (map-get? balances (tuple (owner sender) (token-id token-id)))) amount) ERR_INSUFFICIENT_BALANCE)
        (map-set balances (tuple (owner sender) (token-id token-id)) (- (default-to u0 (map-get? balances (tuple (owner sender) (token-id token-id)))) amount))
        (map-set balances (tuple (owner recipient) (token-id token-id)) (+ (default-to u0 (map-get? balances (tuple (owner recipient) (token-id token-id)))) amount))
        (ok true)
    )
)

;; Creates new shares when users purchase outcome positions
;; Restricted to the authorized market contract
(define-public (mint (token-id uint) (recipient principal) (amount uint))
    (begin
        (asserts! (is-eq tx-sender (var-get contract-owner)) ERR_UNAUTHORIZED)
        (map-set balances (tuple (owner recipient) (token-id token-id)) (+ (default-to u0 (map-get? balances (tuple (owner recipient) (token-id token-id)))) amount))
        (map-set total-supply-map token-id (+ (default-to u0 (map-get? total-supply-map token-id)) amount))
        (ok true)
    )
)

;; Destroys shares when users claim winnings
;; Restricted to the authorized market contract
(define-public (burn (token-id uint) (owner principal) (amount uint))
    (begin
        (asserts! (is-eq tx-sender (var-get contract-owner)) ERR_UNAUTHORIZED)
        (asserts! (>= (default-to u0 (map-get? balances (tuple (owner owner) (token-id token-id)))) amount) ERR_INSUFFICIENT_BALANCE)
        (map-set balances (tuple (owner owner) (token-id token-id)) (- (default-to u0 (map-get? balances (tuple (owner owner) (token-id token-id)))) amount))
        (map-set total-supply-map token-id (- (default-to u0 (map-get? total-supply-map token-id)) amount))
        (ok true)
    )
)

;; Registers a new pair of outcome tokens when a market is created
;; Sets up metadata and assigns unique token IDs
(define-public (initialize-token (market-id uint) (token-id-yes uint) (token-id-no uint) (name-yes (string-ascii 32)) (name-no (string-ascii 32)) (symbol-yes (string-ascii 10)) (symbol-no (string-ascii 10)))
    (begin
        (asserts! (is-eq tx-sender (var-get contract-owner)) ERR_UNAUTHORIZED)
        (map-set token-id-yes-map market-id token-id-yes)
        (map-set token-id-no-map market-id token-id-no)
        (map-set token-metadata token-id-yes { name: name-yes, symbol: symbol-yes, decimals: u6, market-id: market-id, outcome: u1 })
        (map-set token-metadata token-id-no { name: name-no, symbol: symbol-no, decimals: u6, market-id: market-id, outcome: u0 })
        (ok true)
    )
)

;; Sets the contract owner which will be the market contract address
(define-public (initialize (owner principal))
    (begin
        (var-set contract-owner owner)
        (ok true)
    )
)

Functions (9)

FunctionAccessArgs
get-token-idread-onlymarket-id: uint, outcome: uint
get-token-metadataread-onlytoken-id: uint
get-balanceread-onlytoken-id: uint, owner: principal
get-total-supplyread-onlytoken-id: uint
transferpublictoken-id: uint, amount: uint, sender: principal, recipient: principal
mintpublictoken-id: uint, recipient: principal, amount: uint
burnpublictoken-id: uint, owner: principal, amount: uint
initialize-tokenpublicmarket-id: uint, token-id-yes: uint, token-id-no: uint, name-yes: (string-ascii 32
initializepublicowner: principal