session: Extend warning about multiple sessions
plcont: Fix error in example
docs: Bump copyright year
utils: Rename Observer to EventEmitter
utils: Add EventEmitter.num_listeners()
utils: Add EventEmitter.call()
session: Redesign event listening
examples: Update shell with new event listeners
docs: Add waiting for logged_in event to quickstart guide
docs: Update changelog and dev plans
init: Move package init code into functions
docs: Fix event listener args
search: Fix behavior when search isn't loaded
playlist: Add PlaylistContainerEvent
session: Simplify import
utils: Add to_{bytes,unicode}_or_none() helpers
Check equality with NULL, not identity
session: Make SessionConfig wrap sp_session_config

Instead of setting plain attributes and having a method for converting those
into an sp_session_config object, the SessionConfig class now wraps an
sp_session_config object from it is created, and all attributes are setters
and getters storing their values in this struct.

This change moves any config value validation to the setters, raising the
errors much closer to where the end user made the error. Previously,
validation was done first when the Session needed the sp_session_config and
thus built it from the SessionConfig attributes.

The Session instance maintains a reference to the SessionConfig instance,
keeping it alive as long as the Session lives.

This removes all use of spotify.weak_key_dict.
Remove unused spotify.weak_key_dict
session: Move sp_session_callbacks into _SessionCallbacks