partially decouple protocol from user