post-recoup-withdraw.rst (5990B)
1 .. http:post:: /recoup-withdraw 2 3 Demand that a batch of coins be refunded to the reserve, 4 from which the coins were originally withdrawn. 5 The coins must have been originated from the same call to withdraw, and be 6 a subset of that original batch. 7 The remaining amount on the coin will be credited to the reserve 8 that the coins were withdrawn from, in the same withdraw request. 9 10 Note that the original withdrawal fees will **not** be recouped. 11 12 .. note:: This endpoint still Work-in-Progress. It will be implemented in **vRECOUP**, sometime after **v32**. 13 14 **Request:** 15 16 The request body must be a `RecoupWithdrawRequest` object. 17 18 It provides sufficient information to 19 a) identify the originating withdraw request 20 b) proof that the coins to be recouped were part of that withdraw request 21 c) proof ownership of all coins requested to be recouped. 22 23 **Response:** 24 25 :http:statuscode:`200 OK`: 26 The request was successful, and the response is a `ReserveSummary`. 27 :http:statuscode:`403 Forbidden`: 28 A coin's signature is invalid 29 (``TALER_EC_EXCHANGE_RECOUP_SIGNATURE_INVALID``) 30 or the denomination signature is invalid 31 (``TALER_EC_EXCHANGE_DENOMINATION_SIGNATURE_INVALID``). 32 This response comes with a standard `ErrorDetail` response. 33 :http:statuscode:`404 Not found`: 34 A denomination key is unknown, 35 the withdraw commitment is unknown 36 or a blinded coin is not known to have been withdrawn 37 (``TALER_EC_EXCHANGE_RECOUP_WITHDRAW_NOT_FOUND``). 38 If a denomination key is unknown, the response will be 39 a `DenominationUnknownMessage`. 40 :http:statuscode:`409 Conflict`: 41 The operation is not allowed 42 as a coin has insufficient residual value, 43 or because the same public key of a coin 44 has been previously used with a different denomination. 45 Which case it is can be decided by looking at the error code 46 (usually ``TALER_EC_EXCHANGE_GENERIC_INSUFFICIENT_FUNDS``). 47 The response is a `DepositDoubleSpendError`. 48 :http:statuscode:`410 Gone`: 49 A requested denomination key is not yet or no longer valid. 50 It either before the validity start 51 (``TALER_EC_EXCHANGE_GENERIC_DENOMINATION_VALIDITY_IN_FUTURE``), 52 past the expiration 53 (``TALER_EC_EXCHANGE_GENERIC_DENOMINATION_EXPIRED``) 54 or was not yet revoked 55 (``TALER_EC_EXCHANGE_RECOUP_NOT_ELIGIBLE``). 56 The response is a `DenominationGoneMessage`. 57 Clients must evaluate the error code provided 58 to understand which of the cases this is and handle it accordingly. 59 :http:statuscode:`500 Internal Server Error`: 60 The exchange encountered an internal error. 61 This response comes with a standard `ErrorDetail` response. 62 Possible error codes include 63 ``TALER_EC_EXCHANGE_RECOUP_BLINDING_FAILED``, 64 ``TALER_EC_GENERIC_DB_FETCH_FAILED``, or 65 ``TALER_EC_GENERIC_DB_INVARIANT_FAILURE``. 66 67 **Details:** 68 69 .. ts:def:: RecoupWithdrawRequest 70 71 interface RecoupWithdrawRequest { 72 // Public key of the reserve that will receive the recoup. 73 // MUST be the same as the one from the original withdraw. 74 reserve_pub: EddsaPublicKey; 75 76 // The details about the coins: 77 // An array of either 78 // a) the hash code of a blinded coin envelope (not to be recouped) 79 // b) the disclosed coin details, in order to recoup it. 80 // From these, the hash of all coin envelopes 81 // from the original withdraw can be reconstructed. 82 coin_data: RecoupCoinData[]; 83 } 84 85 .. ts:def:: RecoupCoinData 86 87 // This is either 88 // a) the hash code of a blinded coin envelope (not to be recouped) 89 // b) the disclosed coin details, in order to recoup it. 90 type RecoupCoinData = 91 | NonRecoupedCoin 92 | RecoupDisclosedCoinDetails; 93 94 .. ts:def:: NonRecoupedCoin 95 96 interface NonRecoupedCoin { 97 type: "non_recouped_coin"; 98 99 // This is the SHA512 hash code of a blinded coin envelope, 100 // including the corresponding denomination's hash. 101 // It is the output of the TALER_coin_ev_hash function 102 // from libtalerutil. 103 coin_ev: BlindedCoinEnvelopeHash; 104 }; 105 106 .. ts:def:: BlindedCoinEnvelopeHash 107 108 // The hash value of a blinded coin envelope, 109 // as it its generated by the function TALER_coin_ev_hash 110 // in libtalerutil. 111 type BlindedCoinEnvelopeHash = HashCode; 112 113 .. ts:def:: RecoupDisclosedCoinDetails 114 115 // This object provides all necessary coin data 116 // in order to call TALER_denom_blind and retrieve 117 // a blinded coin planchet, from which we can 118 // calculate the blinded coin envelope hash. 119 // It also contains the denomination's signature 120 // for the (unblinded) coin's public key, 121 // and the coin's signature to authorize the recoup request. 122 interface RecoupDisclosedCoinDetails { 123 type: "recoup_coin_details"; 124 125 // The coin's public key 126 coin_pub: CoinPublicKey; 127 128 // The blinding secret for this coin 129 // that was used during withdraw 130 coin_blinding_key_secret: DenominationBlindingKeySecret; 131 132 // The coin's commitment for age restriction, 133 // if the denomination had age restriction support. 134 age_commitment_h?: AgeCommitmentHash; 135 136 // The blinding nonce that went into this coin's 137 // blinded envelope 138 cs_session_nonce?: HashCode; 139 140 // In case of Clause-Schnorr denomination, 141 // the blinding values that were provided 142 // for this coin, by the exchange, as response 143 // to a call to /blinding-prepare. 144 cs_r_pubs?: CSRPublicPair; 145 146 // Unblinded signature of the coins' public key, 147 // signed by the denomination key. 148 denom_pub_sig: DenominationSignature; 149 150 // The denomination public key. 151 // This denomination MUST be eligible for recoup, 152 // i.e. being listed in the "recoup" section of /config. 153 denom_pub_h: HashCode; 154 155 // Signature of `TALER_RecoupRequestPS`, 156 // created by this coin's private key. 157 coin_sig: EddsaSignature; 158 }