# Changes in Release 0.4 Major changes in Release 0.4: * [Unnumbered interface support](../addressing.md#unnumbered-interface-support) * Link [names](../links.md#link-names) and [roles](../links.md#selecting-custom-address-pools) * [Configuration modules](../modules.md) * [OSPF configuration module](../module/ospf.md) Minor fixes: * Use custom SSH port in **connect.sh** (**netlab connect** since release 0.8) * Tags added to **initial-config.ansible** (**netlab initial** since release 0.8) * Changed default Ansible inventory format * *Bandwidth* became a [core link attribute](../links.md#link-attributes) Internal changes (detailed below): * Using **python-box** instead of Python dictionaries * Unit tests ## Migrating to python-box If you ever programmed in any programming language with decent support for hierarchical data structure you might have noticed how crazy navigating through a deep dictionary structure looks like in Python. Fortunately some people do more than yammer - Chris Griffith created [Box](https://github.com/cdgriffith/Box) to address that, and I found it much easier (and more fluent, and more readable) to use than standard dictionaries. Unfortunately, Box uses copy-on-use approach which means that you might work on multiple copies of the same dictionary without realizing that (bummer). The only way to make sure nothing is broken was to: * Create tons of tests * Get results with the dictionary-only implementation * Repeat the tests with Box implementation * Fix stuff until the results match. I think we're there or the code wouldn't be in **master** branch. ## Tests, tests, tests The only way to check whether I fixed all instances of intricate differences between dictionaries and Boxes (and there were quite a few of them) was to write tons of tests, including automated CI pipeline implemented with GitHub Actions: * All tests are in **tests** directory * Topology transformation tests are YAML files starting with **topology-**. Expected results are in **exp-topology-** YAML files. * Tests that should result in an error are in **err-** YAML files. Run tests with **pytest** (parent directory must be in Python include path). To create code coverage report, run **coverage.sh**. Please feel free to add further tests to bring code coverage closer to 100%. Thank you.