LCOV - code coverage report
Current view: top level - contracts/extensions - bme000-0-governance-token.clar (source / functions) Coverage Total Hit
Test: lcov.info Lines: 97.6 % 126 123
Test Date: 2025-11-10 13:03:30 Functions: 96.7 % 30 29
Branches: 75.0 % 16 12

             Branch data     Line data    Source code
       1                 :             : ;; Title: BME00 Governance Token
       2                 :             : ;; Synopsis:
       3                 :             : ;; This extension defines the governance token of BigMarket DAO.
       4                 :             : ;; Description:
       5                 :             : ;; The governance token is a simple SIP010-compliant fungible token
       6                 :             : ;; with some added functions to make it easier to manage by
       7                 :             : ;; BigMarket DAO proposals and extensions.
       8                 :             : ;; The operations vesting schedule and recipients can be updated (see current-key and 
       9                 :             : ;; set-core-team-vesting) up till the first claim. If more recipients are added they 
      10                 :             : ;; allocation is proportionally diluted.
      11                 :             : 
      12                 :             : (impl-trait .governance-token-trait.governance-token-trait)
      13                 :             : (impl-trait 'SP2AKWJYC7BNY18W1XXKPGP0YVEK63QJG4793Z2D4.sip-010-trait-ft-standard.sip-010-trait)
      14                 :             : (impl-trait 'SP3JP0N1ZXGASRJ0F7QAHWFPGTVK9T2XNXDB908Z.extension-trait.extension-trait)
      15                 :             : 
      16                 :             : (define-fungible-token bmg-token u100000000000000) ;; 100M
      17                 :             : (define-fungible-token bmg-token-locked)
      18                 :             : 
      19                 :             : (define-constant core-team-max-vesting u1500000000000) ;; 15% of total supply (10,000,000 BIG)
      20                 :             : (define-constant SCALE u1000000)
      21                 :             : 
      22                 :             : (define-constant err-unauthorised (err u3000))
      23                 :             : (define-constant err-not-token-owner (err u3001))
      24                 :             : (define-constant err-not-core-team (err u3002))
      25                 :             : (define-constant err-no-vesting-schedule (err u3003))
      26                 :             : (define-constant err-nothing-to-claim (err u3004))
      27                 :             : (define-constant err-core-vesting-limit (err u3005))
      28                 :             : (define-constant err-cliff-not-reached (err u3006))
      29                 :             : (define-constant err-recipients-are-locked (err u3007))
      30                 :             : (define-constant err-transfers-blocked (err u3008))
      31                 :             : 
      32                 :             : (define-data-var token-name (string-ascii 32) "BigMarket Governance Token")
      33                 :             : (define-data-var token-symbol (string-ascii 10) "BIG")
      34                 :             : (define-data-var token-uri (optional (string-utf8 256)) none)
      35                 :             : (define-data-var token-decimals uint u6)
      36                 :             : (define-data-var core-team-size uint u0)
      37                 :             : 
      38                 :             : (define-data-var token-price uint u100000)
      39                 :             : (define-data-var transfers-active bool false)
      40                 :             : 
      41                 :             : (define-map core-team-vesting-tracker principal uint) ;; Tracks vested amount per recipient
      42                 :             : 
      43                 :             : ;; ---- Vesting Storage ----
      44                 :             : (define-data-var claim-made bool false)
      45                 :             : (define-data-var current-key uint u0)
      46                 :             : (define-map core-team-vesting {current-key: uint, recipient: principal}
      47                 :             :   {total-amount: uint, start-block: uint, duration: uint, claimed: uint}
      48                 :             : )
      49                 :             : 
      50                 :             : ;; --- Authorisation check
      51                 :             : 
      52                 :         421 : (define-public (is-dao-or-extension)
      53    [ + ][ +  + ]:        1085 :         (ok (asserts! (or (is-eq tx-sender .bigmarket-dao) (contract-call? .bigmarket-dao is-extension contract-caller)) err-unauthorised))
      54                 :             : )
      55                 :             : 
      56                 :             : ;; ---- Vesting Methods ----
      57                 :             : 
      58                 :             : ;; --- Vesting logic and sale
      59                 :           3 : (define-public (set-transfers-active (new-transfers-active bool))
      60                 :           3 :   (begin
      61                 :           3 :     (try! (is-dao-or-extension))
      62                 :           2 :     (var-set transfers-active new-transfers-active)
      63                 :           2 :     (ok true)
      64                 :             :   )
      65                 :             : )
      66                 :           3 : (define-read-only (get-transfers-active) (var-get transfers-active))
      67                 :             : 
      68                 :           3 : (define-public (set-token-price (new-token-price uint))
      69                 :           5 :   (begin
      70                 :           5 :     (try! (is-dao-or-extension))
      71                 :           2 :     (var-set token-price new-token-price)
      72                 :           2 :     (ok true)
      73                 :             :   )
      74                 :             : )
      75                 :             : 
      76                 :         421 : (define-public (set-core-team-vesting (core-team (list 200 {recipient: principal, start-block: uint, duration: uint})))
      77                 :         424 :   (begin
      78                 :         424 :         (try! (is-dao-or-extension))
      79            [ + ]:         423 :         (asserts! (not (var-get claim-made)) err-recipients-are-locked)
      80                 :         422 :         (var-set current-key (+ u1 (var-get current-key)))
      81                 :         422 :         (var-set core-team-size (len core-team))
      82                 :         422 :         (as-contract (fold set-core-team-vesting-iter core-team (ok true)))
      83                 :             :   )
      84                 :             : )
      85                 :         421 : (define-private (set-core-team-vesting-iter (item {recipient: principal, start-block: uint, duration: uint}) (previous-result (response bool uint)))
      86                 :        2108 :         (begin
      87                 :        2108 :                 (try! previous-result)
      88                 :        2108 :                 (let (
      89                 :        2108 :                                 (amount-scaled (/ (* core-team-max-vesting SCALE) (var-get core-team-size)))
      90                 :        2108 :                                 (amount (/ amount-scaled SCALE))
      91                 :             :                         )
      92                 :        2108 :                         (map-set core-team-vesting {current-key: (var-get current-key), recipient: (get recipient item)}
      93                 :        2108 :                                 {total-amount: amount, start-block: (get start-block item), duration: (get duration item), claimed: u0})
      94                 :        2108 :                         (map-set core-team-vesting-tracker (get recipient item) amount)
      95                 :        2108 :                         (print {event: "set-core-team-vesting", amount: amount, start-block: (get start-block item), duration: (get duration item), current-key: (var-get current-key)})
      96                 :        2108 :                         (ok true)
      97                 :             :                 )
      98                 :             :         )
      99                 :             : )
     100                 :             : 
     101                 :           8 : (define-public (core-claim)
     102                 :          11 :   (let
     103                 :             :     (
     104                 :          11 :         (vesting (unwrap! (map-get? core-team-vesting {current-key: (var-get current-key), recipient: tx-sender}) err-no-vesting-schedule))
     105                 :          10 :                 (current-block burn-block-height)
     106                 :          10 :                 (user tx-sender)
     107                 :          10 :                 (start-block (get start-block vesting))
     108                 :          10 :                 (duration (get duration vesting))
     109                 :          10 :                 (total-amount (get total-amount vesting))
     110                 :          10 :                 (claimed (get claimed vesting))
     111         [ +  - ]:          10 :                 (elapsed (if (> current-block start-block) (- current-block start-block) u0))
     112                 :          10 :                 (vested-scaled (if (> elapsed duration)
     113            [ + ]:           6 :                                 (* total-amount SCALE)
     114            [ + ]:           4 :                                 (/ (* (* total-amount elapsed) SCALE) duration)))
     115                 :          10 :                 (vested (/ vested-scaled SCALE))
     116                 :          10 :                 (claimable (- vested claimed))
     117                 :          10 :                 (midpoint (+ start-block (/ duration u2)))
     118                 :             :     )
     119                 :             :     
     120            [ + ]:          10 :         (asserts! (> burn-block-height midpoint) err-cliff-not-reached) 
     121            [ + ]:           9 :         (asserts! (> claimable u0) err-nothing-to-claim) 
     122                 :           8 :         (try! (as-contract (ft-mint? bmg-token claimable user)))
     123                 :             : 
     124                 :           8 :     (map-set core-team-vesting {current-key: (var-get current-key), recipient: tx-sender}
     125                 :           8 :         (merge vesting {claimed: (+ claimed claimable)}))
     126                 :           8 :         (var-set claim-made true)
     127                 :           8 :     (print {event: "core-claim", claimed: claimed, recipient: tx-sender, claimable: claimable, elapsed: elapsed, vested: vested})
     128                 :           8 :     (ok claimable)
     129                 :             :   )
     130                 :             : )
     131                 :             : 
     132                 :           7 : (define-read-only (get-vesting-schedule (who principal))
     133                 :          14 :   (map-get? core-team-vesting {current-key: (var-get current-key), recipient: who})
     134                 :             : )
     135                 :             : 
     136                 :             : ;; --- Internal DAO functions
     137                 :             : 
     138                 :             : ;; governance-token-trait
     139                 :             : 
     140                 :           3 : (define-public (bmg-transfer (amount uint) (sender principal) (recipient principal))
     141                 :           3 :         (begin
     142                 :           3 :                 (try! (is-dao-or-extension))
     143                 :           2 :                 (ft-transfer? bmg-token amount sender recipient)
     144                 :             :         )
     145                 :             : )
     146                 :             : 
     147                 :         114 : (define-public (bmg-lock (amount uint) (owner principal))
     148                 :         165 :         (begin
     149                 :         165 :                 (try! (is-dao-or-extension))
     150                 :         164 :                 (try! (ft-burn? bmg-token amount owner))
     151                 :         161 :                 (ft-mint? bmg-token-locked amount owner)
     152                 :             :         )
     153                 :             : )
     154                 :             : 
     155                 :           5 : (define-public (bmg-unlock (amount uint) (owner principal))
     156                 :           5 :         (begin
     157                 :           5 :                 (try! (is-dao-or-extension))
     158                 :           4 :                 (try! (ft-burn? bmg-token-locked amount owner))
     159                 :           4 :                 (ft-mint? bmg-token amount owner)
     160                 :             :         )
     161                 :             : )
     162                 :             : 
     163                 :           6 : (define-public (bmg-mint (amount uint) (recipient principal))
     164                 :          12 :         (begin
     165                 :          12 :                 (try! (is-dao-or-extension))
     166                 :          11 :                 (ft-mint? bmg-token amount recipient)
     167                 :             :         )
     168                 :             : )
     169                 :             : 
     170                 :           4 : (define-public (bmg-burn (amount uint) (owner principal))
     171                 :           4 :         (begin
     172                 :           4 :                 (try! (is-dao-or-extension))
     173                 :           3 :                 (ft-burn? bmg-token amount owner)
     174                 :             :                 
     175                 :             :         )
     176                 :             : )
     177                 :             : 
     178                 :             : ;; Other
     179                 :             : 
     180                 :           3 : (define-public (set-name (new-name (string-ascii 32)))
     181                 :           3 :         (begin
     182                 :           3 :                 (try! (is-dao-or-extension))
     183                 :           2 :                 (ok (var-set token-name new-name))
     184                 :             :         )
     185                 :             : )
     186                 :             : 
     187                 :           3 : (define-public (set-symbol (new-symbol (string-ascii 10)))
     188                 :           3 :         (begin
     189                 :           3 :                 (try! (is-dao-or-extension))
     190                 :           2 :                 (ok (var-set token-symbol new-symbol))
     191                 :             :         )
     192                 :             : )
     193                 :             : 
     194                 :           3 : (define-public (set-decimals (new-decimals uint))
     195                 :           3 :         (begin
     196                 :           3 :                 (try! (is-dao-or-extension))
     197                 :           2 :                 (ok (var-set token-decimals new-decimals))
     198                 :             :         )
     199                 :             : )
     200                 :             : 
     201                 :           1 : (define-public (set-token-uri (new-uri (optional (string-utf8 256))))
     202                 :           1 :         (begin
     203                 :           1 :                 (try! (is-dao-or-extension))
     204                 :           0 :                 (ok (var-set token-uri new-uri))
     205                 :             :         )
     206                 :             : )
     207                 :             : 
     208                 :         421 : (define-private (bmg-mint-many-iter (item {amount: uint, recipient: principal}))
     209                 :        2105 :         (ft-mint? bmg-token (get amount item) (get recipient item))
     210                 :             : )
     211                 :             : 
     212                 :         421 : (define-public (bmg-mint-many (recipients (list 200 {amount: uint, recipient: principal})))
     213                 :         421 :         (begin
     214                 :         421 :                 (try! (is-dao-or-extension))
     215                 :         421 :                 (ok (map bmg-mint-many-iter recipients))
     216                 :             :         )
     217                 :             : )
     218                 :             : 
     219                 :             : ;; --- Public functions
     220                 :             : 
     221                 :             : ;; sip-010-trait
     222                 :             : 
     223                 :           7 : (define-public (transfer (amount uint) (sender principal) (recipient principal) (memo (optional (buff 34))))
     224                 :          32 :         (begin
     225    [ - ][ +  - ]:          32 :                 (asserts! (or (is-eq tx-sender sender) (is-eq contract-caller sender)) err-not-token-owner)
     226    [ - ][ +  + ]:          32 :         (asserts! (or (var-get transfers-active) (unwrap! (is-dao-or-extension) err-unauthorised)) err-transfers-blocked)
     227                 :          31 :                 (ft-transfer? bmg-token amount sender recipient)
     228                 :             :         )
     229                 :             : )
     230                 :             : 
     231                 :           2 : (define-read-only (get-name)
     232                 :           3 :         (ok (var-get token-name))
     233                 :             : )
     234                 :             : 
     235                 :           2 : (define-read-only (get-symbol)
     236                 :           3 :         (ok (var-get token-symbol))
     237                 :             : )
     238                 :             : 
     239                 :           2 : (define-read-only (get-decimals)
     240                 :           3 :         (ok (var-get token-decimals))
     241                 :             : )
     242                 :             : 
     243                 :           4 : (define-read-only (get-balance (who principal))
     244                 :           8 :         (ok (+ (ft-get-balance bmg-token who) (ft-get-balance bmg-token-locked who)))
     245                 :             : )
     246                 :             : 
     247                 :           2 : (define-read-only (get-total-supply)
     248                 :           3 :         (ok (+ (ft-get-supply bmg-token) (ft-get-supply bmg-token-locked)))
     249                 :             : )
     250                 :             : 
     251                 :           1 : (define-read-only (get-token-uri)
     252                 :           1 :         (ok (var-get token-uri))
     253                 :             : )
     254                 :             : 
     255                 :             : ;; governance-token-trait
     256                 :             : 
     257                 :           0 : (define-read-only (bmg-get-balance (who principal))
     258                 :           0 :         (get-balance who)
     259                 :             : )
     260                 :             : 
     261                 :             : ;; governance-weight threshold check - does who own at least factor per cent of total supply
     262                 :           1 : (define-read-only (bmg-has-percentage-balance (who principal) (factor uint))
     263                 :           2 :         (ok (>= (* (unwrap-panic (get-balance who)) factor) (* (unwrap-panic (get-total-supply)) u1000)))
     264                 :             : )
     265                 :             : 
     266                 :           1 : (define-read-only (bmg-get-locked (owner principal))
     267                 :           1 :         (ok (ft-get-balance bmg-token-locked owner))
     268                 :             : )
     269                 :             : 
     270                 :             : ;; --- Extension callback
     271                 :             : 
     272                 :           2 : (define-public (callback (sender principal) (memo (buff 34)))
     273                 :           2 :         (ok true)
     274                 :             : )
        

Generated by: LCOV version 2.3.2-1