You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

355 lines
6.8 KiB

  1. package api
  2. import (
  3. "database/sql"
  4. "errors"
  5. "net/http"
  6. "github.com/gin-gonic/gin"
  7. "github.com/hermeznetwork/hermez-node/common"
  8. "github.com/hermeznetwork/hermez-node/db/historydb"
  9. )
  10. const (
  11. // maxLimit is the max permited items to be returned in paginated responses
  12. maxLimit uint = 2049
  13. // dfltOrder indicates how paginated endpoints are ordered if not specified
  14. dfltOrder = historydb.OrderAsc
  15. // dfltLimit indicates the limit of returned items in paginated responses if the query param limit is not provided
  16. dfltLimit uint = 20
  17. // 2^32 -1
  18. maxUint32 = 4294967295
  19. )
  20. var (
  21. // ErrNillBidderAddr is used when a nil bidderAddr is received in the getCoordinator method
  22. ErrNillBidderAddr = errors.New("biderAddr can not be nil")
  23. )
  24. func postAccountCreationAuth(c *gin.Context) {
  25. }
  26. func getAccountCreationAuth(c *gin.Context) {
  27. }
  28. func postPoolTx(c *gin.Context) {
  29. // Parse body
  30. var receivedTx receivedPoolTx
  31. if err := c.ShouldBindJSON(&receivedTx); err != nil {
  32. retBadReq(err, c)
  33. return
  34. }
  35. // Transform from received to insert format and validate
  36. writeTx, err := receivedTx.toDBWritePoolL2Tx()
  37. if err != nil {
  38. retBadReq(err, c)
  39. return
  40. }
  41. // Insert to DB
  42. if err := l2.AddTx(writeTx); err != nil {
  43. retSQLErr(err, c)
  44. return
  45. }
  46. // Return TxID
  47. c.JSON(http.StatusOK, writeTx.TxID.String())
  48. }
  49. func getPoolTx(c *gin.Context) {
  50. // Get TxID
  51. txID, err := parseParamTxID(c)
  52. if err != nil {
  53. retBadReq(err, c)
  54. return
  55. }
  56. // Fetch tx from l2DB
  57. dbTx, err := l2.GetTx(txID)
  58. if err != nil {
  59. retSQLErr(err, c)
  60. return
  61. }
  62. apiTx := poolL2TxReadToSend(dbTx)
  63. // Build succesfull response
  64. c.JSON(http.StatusOK, apiTx)
  65. }
  66. func getAccounts(c *gin.Context) {
  67. }
  68. func getAccount(c *gin.Context) {
  69. }
  70. func getExits(c *gin.Context) {
  71. // Get query parameters
  72. // Account filters
  73. tokenID, addr, bjj, idx, err := parseAccountFilters(c)
  74. if err != nil {
  75. retBadReq(err, c)
  76. return
  77. }
  78. // BatchNum
  79. batchNum, err := parseQueryUint("batchNum", nil, 0, maxUint32, c)
  80. if err != nil {
  81. retBadReq(err, c)
  82. return
  83. }
  84. // Pagination
  85. fromItem, order, limit, err := parsePagination(c)
  86. if err != nil {
  87. retBadReq(err, c)
  88. return
  89. }
  90. // Fetch exits from historyDB
  91. exits, pagination, err := h.GetExits(
  92. addr, bjj, tokenID, idx, batchNum, fromItem, limit, order,
  93. )
  94. if err != nil {
  95. retSQLErr(err, c)
  96. return
  97. }
  98. // Build succesfull response
  99. apiExits := historyExitsToAPI(exits)
  100. c.JSON(http.StatusOK, &exitsAPI{
  101. Exits: apiExits,
  102. Pagination: pagination,
  103. })
  104. }
  105. func getExit(c *gin.Context) {
  106. // Get batchNum and accountIndex
  107. batchNum, err := parseParamUint("batchNum", nil, 0, maxUint32, c)
  108. if err != nil {
  109. retBadReq(err, c)
  110. return
  111. }
  112. idx, err := parseParamIdx(c)
  113. if err != nil {
  114. retBadReq(err, c)
  115. return
  116. }
  117. // Fetch tx from historyDB
  118. exit, err := h.GetExit(batchNum, idx)
  119. if err != nil {
  120. retSQLErr(err, c)
  121. return
  122. }
  123. apiExits := historyExitsToAPI([]historydb.HistoryExit{*exit})
  124. // Build succesfull response
  125. c.JSON(http.StatusOK, apiExits[0])
  126. }
  127. func getHistoryTxs(c *gin.Context) {
  128. // Get query parameters
  129. tokenID, addr, bjj, idx, err := parseAccountFilters(c)
  130. if err != nil {
  131. retBadReq(err, c)
  132. return
  133. }
  134. // BatchNum
  135. batchNum, err := parseQueryUint("batchNum", nil, 0, maxUint32, c)
  136. if err != nil {
  137. retBadReq(err, c)
  138. return
  139. }
  140. // TxType
  141. txType, err := parseQueryTxType(c)
  142. if err != nil {
  143. retBadReq(err, c)
  144. return
  145. }
  146. // Pagination
  147. fromItem, order, limit, err := parsePagination(c)
  148. if err != nil {
  149. retBadReq(err, c)
  150. return
  151. }
  152. // Fetch txs from historyDB
  153. txs, pagination, err := h.GetHistoryTxs(
  154. addr, bjj, tokenID, idx, batchNum, txType, fromItem, limit, order,
  155. )
  156. if err != nil {
  157. retSQLErr(err, c)
  158. return
  159. }
  160. // Build succesfull response
  161. apiTxs := historyTxsToAPI(txs)
  162. c.JSON(http.StatusOK, &historyTxsAPI{
  163. Txs: apiTxs,
  164. Pagination: pagination,
  165. })
  166. }
  167. func getHistoryTx(c *gin.Context) {
  168. // Get TxID
  169. txID, err := parseParamTxID(c)
  170. if err != nil {
  171. retBadReq(err, c)
  172. return
  173. }
  174. // Fetch tx from historyDB
  175. tx, err := h.GetHistoryTx(txID)
  176. if err != nil {
  177. retSQLErr(err, c)
  178. return
  179. }
  180. apiTxs := historyTxsToAPI([]historydb.HistoryTx{*tx})
  181. // Build succesfull response
  182. c.JSON(http.StatusOK, apiTxs[0])
  183. }
  184. func getBatches(c *gin.Context) {
  185. }
  186. func getBatch(c *gin.Context) {
  187. }
  188. func getFullBatch(c *gin.Context) {
  189. }
  190. func getSlots(c *gin.Context) {
  191. }
  192. func getBids(c *gin.Context) {
  193. }
  194. func getNextForgers(c *gin.Context) {
  195. }
  196. func getState(c *gin.Context) {
  197. }
  198. func getConfig(c *gin.Context) {
  199. c.JSON(http.StatusOK, cg)
  200. }
  201. func getTokens(c *gin.Context) {
  202. // Account filters
  203. tokenIDs, symbols, name, err := parseTokenFilters(c)
  204. if err != nil {
  205. retBadReq(err, c)
  206. return
  207. }
  208. // Pagination
  209. fromItem, order, limit, err := parsePagination(c)
  210. if err != nil {
  211. retBadReq(err, c)
  212. return
  213. }
  214. // Fetch exits from historyDB
  215. tokens, pagination, err := h.GetTokens(
  216. tokenIDs, symbols, name, fromItem, limit, order,
  217. )
  218. if err != nil {
  219. retSQLErr(err, c)
  220. return
  221. }
  222. // Build succesfull response
  223. apiTokens := tokensToAPI(tokens)
  224. c.JSON(http.StatusOK, &tokensAPI{
  225. Tokens: apiTokens,
  226. Pagination: pagination,
  227. })
  228. }
  229. func getToken(c *gin.Context) {
  230. // Get TokenID
  231. tokenIDUint, err := parseParamUint("id", nil, 0, maxUint32, c)
  232. if err != nil {
  233. retBadReq(err, c)
  234. return
  235. }
  236. tokenID := common.TokenID(*tokenIDUint)
  237. // Fetch token from historyDB
  238. token, err := h.GetToken(tokenID)
  239. if err != nil {
  240. retSQLErr(err, c)
  241. return
  242. }
  243. apiToken := tokensToAPI([]historydb.TokenRead{*token})
  244. c.JSON(http.StatusOK, apiToken[0])
  245. }
  246. func getRecommendedFee(c *gin.Context) {
  247. }
  248. func getCoordinators(c *gin.Context) {
  249. // Pagination
  250. fromItem, order, limit, err := parsePagination(c)
  251. if err != nil {
  252. retBadReq(err, c)
  253. return
  254. }
  255. // Fetch coordinators from historyDB
  256. coordinators, pagination, err := h.GetCoordinators(fromItem, limit, order)
  257. if err != nil {
  258. retSQLErr(err, c)
  259. return
  260. }
  261. // Build succesfull response
  262. apiCoordinators := coordinatorsToAPI(coordinators)
  263. c.JSON(http.StatusOK, &coordinatorsAPI{
  264. Coordinators: apiCoordinators,
  265. Pagination: pagination,
  266. })
  267. }
  268. func getCoordinator(c *gin.Context) {
  269. // Get bidderAddr
  270. const name = "bidderAddr"
  271. bidderAddr, err := parseEthAddr(c, name)
  272. if err != nil {
  273. retBadReq(err, c)
  274. return
  275. } else if bidderAddr == nil {
  276. retBadReq(ErrNillBidderAddr, c)
  277. return
  278. }
  279. coordinator, err := h.GetCoordinator(*bidderAddr)
  280. if err != nil {
  281. retSQLErr(err, c)
  282. return
  283. }
  284. apiCoordinator := coordinatorsToAPI([]historydb.HistoryCoordinator{*coordinator})
  285. c.JSON(http.StatusOK, apiCoordinator[0])
  286. }
  287. func retSQLErr(err error, c *gin.Context) {
  288. if err == sql.ErrNoRows {
  289. c.JSON(http.StatusNotFound, errorMsg{
  290. Message: err.Error(),
  291. })
  292. } else {
  293. c.JSON(http.StatusInternalServerError, errorMsg{
  294. Message: err.Error(),
  295. })
  296. }
  297. }
  298. func retBadReq(err error, c *gin.Context) {
  299. c.JSON(http.StatusBadRequest, errorMsg{
  300. Message: err.Error(),
  301. })
  302. }