Changeset ef1c1c7 for server/market.go
- Timestamp:
- 09/24/26 17:43:19 (6 days ago)
- Branches:
- main
- Children:
- 0cee8ec
- Parents:
- a531b45
- File:
-
- 1 edited
-
server/market.go (modified) (4 diffs)
Legend:
- Unmodified
- Added
- Removed
-
server/market.go
ra531b45 ref1c1c7 4 4 "database/sql" 5 5 "fmt" 6 "strconv" 6 7 7 8 "bp_project/server/db" … … 16 17 } 17 18 18 // ListMarkets prints all active markets with their latest price. 19 func ListMarkets() { 19 // ListMarkets prints all active markets, numbered, with their latest price, 20 // and returns them in the printed order so a caller can pick one by number. 21 func ListMarkets() []Market { 20 22 rows, err := db.DB.Query(` 21 SELECT m.id, c. symbol, m.quote_currency,23 SELECT m.id, c.id, c.symbol, m.quote_currency, 22 24 COALESCE(lp.price, 0) AS price 23 25 FROM markets m … … 28 30 if err != nil { 29 31 fmt.Println("Error:", err) 30 return 32 return nil 31 33 } 32 34 defer rows.Close() … … 35 37 fmt.Printf(" %-4s %-8s %-5s %15s\n", "#", "Symbol", "Quote", "Last price") 36 38 fmt.Println(" -----------------------------------------") 37 i := 139 var list []Market 38 40 for rows.Next() { 39 var id, sym, quote string41 var m Market 40 42 var price float64 41 if err := rows.Scan(& id, &sym, "e, &price); err != nil {43 if err := rows.Scan(&m.ID, &m.CryptoID, &m.Symbol, &m.Quote, &price); err != nil { 42 44 fmt.Println("scan error:", err) 43 return 45 return nil 44 46 } 45 fmt.Printf(" %-4d %-8s %-5s %15.6f\n", i, sym, quote, price)46 i++47 list = append(list, m) 48 fmt.Printf(" %-4d %-8s %-5s %15.6f\n", len(list), m.Symbol, m.Quote, price) 47 49 } 50 return list 48 51 } 49 52 50 // ChooseMarket asks the user to pick a market by symbol and returns it. 53 // pickNumber reads a 1-based choice from a list of n items. 54 func pickNumber(label string, n int) (int, error) { 55 if n == 0 { 56 return 0, fmt.Errorf("Nothing to choose from.") 57 } 58 k, err := strconv.Atoi(prompt(label)) 59 if err != nil || k < 1 || k > n { 60 return 0, fmt.Errorf("Invalid choice, enter a number from 1 to %d.", n) 61 } 62 return k - 1, nil 63 } 64 65 // ChooseMarket lists the active markets and lets the user pick one by its 66 // number in the list. 51 67 func ChooseMarket() (*Market, error) { 52 ListMarkets() 53 sym := prompt("Market symbol (e.g. BTC): ") 54 if sym == "" { 55 return nil, fmt.Errorf("no symbol entered") 56 } 57 var m Market 58 err := db.DB.QueryRow(` 59 SELECT m.id, c.id, c.symbol, m.quote_currency 60 FROM markets m 61 JOIN crypto c ON c.id = m.crypto_id 62 WHERE upper(c.symbol) = upper($1) 63 AND m.is_active = true 64 LIMIT 1`, sym, 65 ).Scan(&m.ID, &m.CryptoID, &m.Symbol, &m.Quote) 66 if err == sql.ErrNoRows { 67 return nil, fmt.Errorf("market %s not found", sym) 68 } 68 list := ListMarkets() 69 k, err := pickNumber("Market #: ", len(list)) 69 70 if err != nil { 70 71 return nil, err 71 72 } 72 return &m, nil 73 return &list[k], nil 74 } 75 76 // ChooseHolding lists only the markets the user can sell in — cryptos they 77 // hold with some quantity still free (not reserved by an open sell order) — 78 // with how much is held and free, and lets them pick one by number. 79 func ChooseHolding(s *Session) (*Market, error) { 80 rows, err := db.DB.Query(` 81 SELECT m.id, c.id, c.symbol, m.quote_currency, 82 h.quantity, h.quantity - h.reserved_quantity AS free, 83 COALESCE(lp.price, 0) AS price 84 FROM holdings h 85 JOIN crypto c ON c.id = h.crypto_id 86 JOIN markets m ON m.crypto_id = c.id AND m.is_active = true 87 LEFT JOIN v_latest_prices lp ON lp.market_id = m.id 88 WHERE h.user_id = $1 89 AND h.quantity - h.reserved_quantity > 0 90 ORDER BY c.symbol`, s.UserID) 91 if err != nil { 92 return nil, err 93 } 94 defer rows.Close() 95 96 fmt.Println() 97 fmt.Printf(" %-4s %-8s %-5s %12s %12s %15s\n", "#", "Symbol", "Quote", "Held", "Free to sell", "Last price") 98 fmt.Println(" -------------------------------------------------------------------") 99 var list []Market 100 for rows.Next() { 101 var m Market 102 var held, free, price float64 103 if err := rows.Scan(&m.ID, &m.CryptoID, &m.Symbol, &m.Quote, &held, &free, &price); err != nil { 104 return nil, err 105 } 106 list = append(list, m) 107 fmt.Printf(" %-4d %-8s %-5s %12.4f %12.4f %15.6f\n", len(list), m.Symbol, m.Quote, held, free, price) 108 } 109 if len(list) == 0 { 110 return nil, fmt.Errorf("you hold no crypto that is free to sell") 111 } 112 k, err := pickNumber("Holding #: ", len(list)) 113 if err != nil { 114 return nil, err 115 } 116 return &list[k], nil 73 117 } 74 118
Note:
See TracChangeset
for help on using the changeset viewer.
