If a contract has an inline action, the permission for running that action must be eosio.code from that contract account.
accounta is a smart contract with an inline action to accountb. Therefore accounta will need the permission firstname.lastname@example.org, as the contract will need to execute the inline action.
The problem is your inline action, you are trying to transfer the funds onto the to account, but you are trying to do this with the permission of the from account, but it should be with the permission of self.
So change your inline action to say:
Contract console out in nodeos log is debug level, but default logging level of nodeos is changed from debug to info. If you want to print console out, put next logging.json in your config directory.
eosio.code permission on your account will give access to target account from contract-code, which eosio.code permission you use.
For example, if account Bob will set contractA@eosio.code on their active permission slot, contractA will get active permissions from the code to Bob's account.
Not sure why this happens, but I've also been struggling with it.
I get around it by doing
eosio::check(false, "uh oh");
So when I do cleos push action ... it then errors out the transaction, but prints "hello!" in the console.
Would also love to know a better way to print, but for now maybe this could help!