various improvements, add tests and documentation.