Incluidas las tarifas de transacción al enviar ETH desde un contrato inteligente

Digamos que tengo un contrato de billetera Solidity simple como se muestra a continuación. Cuando quiero rescindir el contrato utilizando send, las tarifas de transacción (costo del gas) se reducen de la cantidad que recibe la parte receptora. ¿Cómo puedo enviar ether desde el contrato inteligente para que el costo del gas se imponga en el contrato en sí, no en el receptor?

Además, quiero saber la tarifa impuesta a la billetera antes de llamar al contrato. ¿Es posible determinar la tarifa que se impone por send()la interfaz JSON-RPC?

/**
 * Simple hosted wallet contract.
 */
contract Wallet {

    event Deposit(address from, uint value);
    event Withdraw(address to, uint value);

    address owner;

    function Wallet() {
        owner = msg.sender;
    }

    /**
     * Simple withdrawal operation.
     */
    function withdraw(address _to, uint _value) {
        if(msg.sender != owner) {
            throw;
        }

        Withdraw(_to, _value);

        _to.send(_value);
    }


    /**
     * Somebody sends ETH to this contract address
     */
    function() {
        // just being sent some cash?
        if (msg.value > 0) {
            Deposit(msg.sender, msg.value);
        }
    }

}
Esta información se puede obtener de una transacción interna como aquí: testnet.etherscan.io/tx/…
El título parece opuesto a la pregunta "¿Cómo puedo enviar éter desde el contrato inteligente para que el costo del gas se imponga en el contrato en sí, no en el receptor?" ¿Debería reformularse el título?

Respuestas (2)

De acuerdo con los documentos de solidez, no creo que su primera solicitud sea posible. De hecho, los documentos recomiendan cambiar a un esquema de retiro:

Warning: There are some dangers in using send: The transfer fails if the call stack depth is at 1024 (this can
always be forced by the caller) and it also fails if the recipient runs out of gas. So in order to make safe Ether
transfers, always check the return value of send or even better: Use a pattern where the recipient withdraws the
money.

Después de cambiar a un patrón de retiro, simplemente puede usar web3.eth.estimateGas() .

¡Buen punto! En este caso, quiero ejecutar una billetera Ethereum en un servicio web alojado. Todas las transacciones normales de Ethereum deberían estar disponibles para el usuario, por lo que, lamentablemente, el patrón de retiro del destinatario no se puede realizar aquí.

Cuando quiero rescindir el contrato usando el envío, las tarifas de transacción (costo del gas) se reducen de la cantidad que recibe la parte receptora. ¿Cómo puedo enviar ether desde el contrato inteligente para que el costo del gas se imponga en el contrato en sí, no en el receptor?

El gas lo paga quien invoca withdraw.

_to.send(_value)siempre intentará enviar el número de wei especificado por _valuea la dirección _to. _valueno se reduce por ningún costo de gas. ( sendpuede fallar (devuelve falso) si se excede la profundidad de llamada de 1024 o si _totiene una función de respaldo que consume más de 2300 de gas. En general, se recomienda verificar el valor de retorno de send).

determinar la tarifa que se impone para enviar () a través de la interfaz geth JSON-RPC?

eth_estimateGas es un método JSON-RPC para estimar el costo del gas. Para el caso concreto de withdraw, dará una estimación razonable pero no será solo para el _to.send(_value). Para casos generales, considere ¿Cuáles son las limitaciones para estimar Gas y cuándo su estimación sería considerablemente incorrecta?