refactor and added a few tests