Prediction market with LMSR model on IBM Hyperledger Fabric (Blockchain)
Clone or download
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Type Name Latest commit message Commit time
Failed to load latest commit information.

Logarithmic Market Scoring Rule (LMSR) Prediction Market on Hyperledger Fabric

The project is a prototype implements Prediction Market with LMSR on IBM Hyperledger Fabric. Fabric is a block chain open source like Bitcoin or Ethereum.


  1. Logarithmic Market Scoring Rules for Modular Combinatorial Information Aggregation by Robin Hanson
  2. Hyperledger Fabric
  3. Gnosis
  4. Prediction Market (en)
  5. Prediction Market (ch)

How to Run

  1. Install golang and Hyperledger Fabric docker images.
  2. clone this project: git clone
  3. go to folder diviner/fixtures
  4. start fabric environment: ./
  5. watch cli (run docker logs cli) logs until chaincode is instantiated (you will see [main] main -> INFO 009 Exiting.....)
  6. open a new terminal, go to diviner/service, and start middle service: go run diviner_service.go
  7. open a new terminal, go to diviner/app, and play. :)

How to Play

  1. create member: go run app.go member create --ski [private key]
  • go run app.go member create --ski a7145e9a7b7bea5907bb022333beaac24bc4095d17f417f262b543de2c54bed1
  • go run app.go member create --ski f306ad8811b1d1649bf96d3faeffd7d0c3a21a1fc855481adc7b9be52c596ed6
  1. create event: go run app.go event create --title [title] --outcome [outcome1] --outcome [outcome2] --ski [private key]
  • go run app.go event create --title gogo --outcome yes --outcome no --ski a7145e9a7b7bea5907bb022333beaac24bc4095d17f417f262b543de2c54bed1

    ps: remember the event id on screen like: event:<id:"4f2107e3-6aa8-45b0-8419-fe8c492756d5" .... > (the event id is 4f2107e3-6aa8-45b0-8419-fe8c492756d5)

  1. create market: go run app.go market create --event [event_id got from step2] --number 100 --ski [private key]
  • go run app.go market create --ski a7145e9a7b7bea5907bb022333beaac24bc4095d17f417f262b543de2c54bed1 --event 4f2107e3-6aa8-45b0-8419-fe8c492756d5 --number 100

    ps: 4f2107e3-6aa8-45b0-8419-fe8c492756d5 is the event id got from step2

    ps: remember the market and share id on screen like: market:<id:"4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed" ... event:"4f2107e3-6aa8-45b0-8419-fe8c492756d5" liquidity:100 fund:69.31471805599453 cost:69.31471805599453 shares:<key:"4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed#4f2107e3-6aa8-45b0-8419-fe8c492756d5@0" value:0 > shares:<key:"4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed#4f2107e3-6aa8-45b0-8419-fe8c492756d5@1" value:0 > ... > (the market id is 4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed, yes share id is 4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed#4f2107e3-6aa8-45b0-8419-fe8c492756d5@0, and no share id is 4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed#4f2107e3-6aa8-45b0-8419-fe8c492756d5@1)

  1. buy or sell a ahare: go run app.go tx [buy or sell] [share id got from step3] [volume] --ski [private key]
  • go run app.go tx buy 4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed#4f2107e3-6aa8-45b0-8419-fe8c492756d5@0 100 --ski f306ad8811b1d1649bf96d3faeffd7d0c3a21a1fc855481adc7b9be52c596ed6

    ps. 4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed#4f2107e3-6aa8-45b0-8419-fe8c492756d5@0 is the yes share id got from step3

  1. query members and will see the balance and assets changed.
  • go run app.go member query --ski a7145e9a7b7bea5907bb022333beaac24bc4095d17f417f262b543de2c54bed1

    the balance is 99930.68528194401

  • go run app.go member query --ski f306ad8811b1d1649bf96d3faeffd7d0c3a21a1fc855481adc7b9be52c596ed6

    the balance is 99937.98854930417 and have asset 4f2107e3-6aa8-45b0-8419-fe8c492756d5#58c77b4c-f686-4170-a78a-0d96308496ed#4f2107e3-6aa8-45b0-8419-fe8c492756d5@0#aSq9DsNNvGhYxYyqA9wd2eduEAZ5AXWgJTbTJAb2Wjq7bj9GGAWwADm9W2UknFWmZhqxd2G21L9WTXyxSHfeR8z1moeVjHNjEFmRqHFRBPC8ckqwSfsKJZc814kR with volume 100

Clean All Data

  1. go to diviner/fixtures and run ./ to remove all container and dev images.

Other Commands

  • Query Member: go run app.go member query --ski [private key]

    1. go run app.go member query --ski a7145e9a7b7bea5907bb022333beaac24bc4095d17f417f262b543de2c54bed1
    2. go run app.go member query --ski f306ad8811b1d1649bf96d3faeffd7d0c3a21a1fc855481adc7b9be52c596ed6
  • Query Event: go run app.go event query --ski [private key]

    1. go run app.go event query --id [event id] --ski a7145e9a7b7bea5907bb022333beaac24bc4095d17f417f262b543de2c54bed1
  • Query Market: go run app.go market query --id [market id]

    1. go run app.go market query --id a124ddec-a673-437c-be5c-0c54bdf58366#3981d198-ca8f-4f33-a0aa-19a6466ce984 --ski f306ad8811b1d1649bf96d3faeffd7d0c3a21a1fc855481adc7b9be52c596ed6

Fixtures detail

Because all files are in folder, you may not run all steps in preparation


  1. cryptogen generate --config=./crypto-config.yaml
  2. export FABRIC_CFG_PATH=$PWD
  3. mkdir channel-artifacts
  4. configtxgen -profile TwoOrgsOrdererGenesis -outputBlock ./channel-artifacts/genesis.block
  5. configtxgen -profile DivinerChannel -outputCreateChannelTx ./channel-artifacts/diviner_channel.tx -channelID divinerchannel
  6. configtxgen -profile DivinerChannel -outputAnchorPeersUpdate ./channel-artifacts/DivinerMSPanchors.tx -channelID divinerchannel -asOrg DivinerMSP

The cli container will run scripts/ to initialize environment when starting. The detail is following:

join channel

  1. peer channel create -o -c divinerchannel -f ./channel-artifacts/diviner_channel.tx --tls $CORE_PEER_TLS_ENABLED --cafile /opt/gopath/src/

  2. peer channel join -b divinerchannel.block

  3. CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/ CORE_PEER_LOCALMSPID="DivinerMSP" CORE_PEER_TLS_ROOTCERT_FILE=/opt/gopath/src/ peer channel join -b divinerchannel.block

update anchor

  1. peer channel update -o -c divinerchannel -f ./channel-artifacts/DivinerMSPanchors.tx --tls $CORE_PEER_TLS_ENABLED --cafile /opt/gopath/src/


  1. peer chaincode install -n lmsr -v 1.0 -p diviner/chaincode
  2. peer chaincode instantiate -o --tls $CORE_PEER_TLS_ENABLED --cafile /opt/gopath/src/ -C divinerchannel -n lmsr -v 1.0 -c '{"Args":[]}' -P "OR ('DivinerMSP.member')"


  1. Because can not handle concurrent transactions on a market, it needs an transaction queue for each market
  2. Management
  3. Mobile App

Docker Others

  • start: docker-compose -f docker-compose-cli.yaml up -d
  • stop: docker-compose -f docker-compose-cli.yaml down
  • login cli: docker exec -it cli bash
  • rm containers: docker rm $(docker ps -aq)
  • rm dev images: docker rmi $(docker images --filter=reference='dev*' -q)
  • rm all images: dokcer rmi $(docker images -q)