refactored to increase flexibility