The master_secret setting is a `Vec<u8>`, for which there is no default deserialization. This change pulls it out to a struct and implements Deserialize so that it can be set with a string via environment variable or config file. That change also represented an opportunity to cache the value of signing_secret, which was being freshly calculated on every request even though the value is a constant derived from master_secret. So the struct is actually called `Secrets` and has two properties. This does leave a slightly weird naming mismatch that I wasn't sure what to do with. `master_secret` makes sense from the perspective of setting e.g. a `SYNC_MASTER_SECRET` environment variable, but it looks kind of funny when the code accesses that property internally as a `Secrets` struct with its own `master_secret` and `signing_secret` properties. I tried to minimise the weirdness by passing around the `Secrets` instance and elsewhere referring to that variable/argument as `secrets`.