-
Notifications
You must be signed in to change notification settings - Fork 188
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Config refactor #298
Config refactor #298
Conversation
…variable test; adding teardown logic for env vars; correcting typo
Codecov Report
@@ Coverage Diff @@
## demo #298 +/- ##
=======================================
Coverage 96.86% 96.86%
=======================================
Files 48 48
Lines 6222 6222
=======================================
Hits 6027 6027
Misses 195 195 Continue to review full report at Codecov.
|
… DEFAULT_CONFIG as module attribute
…r kwargs update; add logic for integer parsing from env vars; add tests
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks great @antalszava! Especially the thorough tests and clear separation of labour of the function.
Left a few suggestions for polishing etc.
Co-Authored-By: Nathan Killoran <[email protected]>
…rryfields into config_refactor
Locally I got the following for
Whereas the changes in other files will be affected by an upcoming refactor there. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is great, thanks @antalszava! While it looks like a lot of comments, most are just polish --- the new config logic is 💯 times clearer and better than the previous iteration!
strawberryfields/configuration.py
Outdated
hostname (str): the name of the host to connect to | ||
use_ssl (bool): specifies if requests should be sent using SSL | ||
port (int): the port to be used when connecting to the remote service | ||
debug (bool): determines if the debugging mode is requested |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm thinking it might be best to move all the configuration options to the module docstring. This has several advantages:
-
Less redundancy --- configuration options only need to be specified in one place, and linked from everywhere else
-
We can use Sphinx glossary notation to add more details
-
It is user facing, whereas these docstrings aren't
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've added them to the module docstring :) Added the list of environment variables, let me know if you think they need more adjustments :)
strawberryfields/configuration.py
Outdated
for section, sectionconfig in config.items(): | ||
for key in sectionconfig: | ||
if key in other_config[section]: | ||
config[section][key] = other_config[section][key] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could this be made more succinct using the dict.update
method?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've changed it so, however, will have to add certain validity check most probably, such that no problems can arise from updating with invalid configurations.
strawberryfields/configuration.py
Outdated
|
||
update_from_environment_variables(config) | ||
|
||
config_from_keyword_arguments = {"api": kwargs} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It might make sense to define the kwargs as 'belonging' to the "api" section when the defaults/types are defined.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Would that be referring to the defaults used in create_config
?
One of the problems I came across was that if I use create_config
and kwargs
here, then having defaults will result in an unexpected overwrite.
That is
In [1]: import strawberryfields.configuration as conf
In [3]: config = {
...: "api": {
...: "authentication_token": 'NotDefaultAuth',
...: "hostname": 'NotDefaultHostname',
...: "use_ssl": True,
...: "port": 123456789,
...: "debug": False
...: }
...: }
...: other_config = conf.create_config(authentication_token="MyToken")
...: conf.update_config(config, other_config)
...: config
Out[3]:
{'api': {'authentication_token': 'MyToken',
'hostname': 'localhost',
'use_ssl': True,
'port': 443,
'debug': False}}
where 'hostname'
and 'port'
were overwritten, whereas they were not defined in kwargs
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, I see. This is because the other_config
is replacing the default values 🤔
tests/frontend/test_configuration.py
Outdated
assert v != parsed_value | ||
|
||
# Tear-down | ||
del os.environ[env_var] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Mentioned this earlier, but better to use monkeypatch.setenv()
here to avoid side effects 🙂
… module level attributes
…dingly; change load_config using it
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You've addressed all my concerns @antalszava
I notice a lot of small changes (e.g., to function names, signatures, and return types). I assume these come out of other reviews, so I will defer to e.g., @josh146 for final approval
…tring, inserting refs to these in function docstrings, correcting Kwargs section naming in docstrings
43d385d
to
4614d83
Compare
Reason for the force-push: Traversing the parents of each commit starting from the source |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💯 Looks good from my end!
strawberryfields/configuration.py
Outdated
* **hostname (str)** (*optional*): the name of the host to connect to | ||
* **use_ssl (bool)** (*optional*): specifies if requests should be sent using SSL | ||
* **port (int)** (*optional*): the port to be used when connecting to the remote service | ||
* **debug (bool)** (*optional*): determines if the debugging mode is requested |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The bullet point list needs to be de-indented to match the indentation level of The following...
above.
strawberryfields/configuration.py
Outdated
* SF_API_HOSTNAME | ||
* SF_API_USE_SSL | ||
* SF_API_DEBUG | ||
* SF_API_PORT |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is sufficient for now, but we should create a new ticket to fix up the configuration keys documentation 🙂
strawberryfields/configuration.py
Outdated
|
||
update_from_environment_variables(config) | ||
|
||
config_from_keyword_arguments = {"api": kwargs} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, I see. This is because the other_config
is replacing the default values 🤔
Co-Authored-By: Josh Izaac <[email protected]>
Co-Authored-By: Josh Izaac <[email protected]>
… with kwargs, adding port to file and env vars
These last bit of modifications included:
The These modifications make up for using the Further changes were carried out to
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All comments are minor, this is in very good state :)
doc/introduction/configuration.rst
Outdated
* SF_API_AUTHENTICATION_TOKEN | ||
* SF_API_HOSTNAME | ||
* SF_API_USE_SSL | ||
* SF_API_PORT |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would combine the two sections above into one, something like (feel free to modify/clean):
Configuration options
*********************
**authentication_token (str)** (*required*)
The authentication token to use when connecting to the API. Will be sent with every request in
the header. Corresponding environment variable: ``SF_API_AUTHENTICATION_TOKEN``
**hostname (str)** (*optional*)
The hostname of the server to connect to. Defaults to ``localhost``. Must be one of the allowed
hosts. Corresponding environment variable: ``SF_API_HOSTNAME``
**use_ssl (bool)** (*optional*)
Whether to use SSL or not when connecting to the API. True or False.
Corresponding environment variable: ``SF_API_USE_SSL``
**port (int)** (*optional*)
The port to be used when connecting to the remote service.
Corresponding environment variable: ``SF_API_PORT``
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh thanks for that!
strawberryfields/configuration.py
Outdated
.. warning:: | ||
|
||
The following configuration options are available: | ||
:doc:`/introduction/configuration`. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For consistency with our other developer pages:
.. warning::
Unless you are a Strawberry Fields developer, you likely do not need to access this module directly.
See more details regarding Strawberry Fields configuration and available configuration options
on the :doc:`/introduction/configuration` page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sure! Here the first part will already be included from https:/XanaduAI/strawberryfields/blob/demo/doc/code/sf_configuration.rst
so I'll add the reworded second part :)
strawberryfields/configuration.py
Outdated
} | ||
|
||
BOOLEAN_KEYS = ("debug", "use_ssl") | ||
BOOLEAN_KEYS = {"use_ssl"} | ||
INTEGER_KEYS = {"port"} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Now that the above DEFAULT_CONFIG_SPEC
specifies the types, are these still needed?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh not at all, thanks for that!
VALID_KEYS = set(create_config()["api"].keys()) | ||
DEFAULT_CONFIG = create_config() | ||
configuration = load_config() | ||
config_filepath = get_config_filepath() |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is very nice :)
Co-Authored-By: Josh Izaac <[email protected]>
…t module attributes, reword module docstring
…rryfields into config_refactor
Context:
Currently, to configure a connection to a remote service the
Configuration
class is used which encompasses the creation and updating of configuration-related data, allowing environment variables and configuration files to be used. However, no keyword arguments can be passed to this class for configuration. Furthermore, storing an instance of this class that it is available from different components of SF (e.g.RemoteEngine
,LocalEngine
) seems to be problematic, as a globalConfiguration
instance would be needed for such use cases.Description of the Change:
This is the first part of replacing the
Configuration
class with functions, adding theload_config
and auxiliary functions.The configuration object (that is a nested dictionary) would be created based on the following (order defines the importance, going from most important to least important):
If a user wants to simply use a configuration, the
configuration
object is available fromconfiugration.py
which calls onload_config
without any arguments. This solves the issue of having a global configuration if needed. A default configuration object calledDEFAULT_CONFIG
is also available containing pre-defined data for configuration.Further changes regarding current implementation
kwargs.get("option", default)
callsFurther comments
xfail
Benefits:
load_config
function can be called anytime for configuration, without having to keep and update the state that was contained in aConfiguration
instance.Possible Drawbacks:
Currently, all three options of keyword arguments, environment variables and configuration file are taken into consideration, eventually giving a union of the options while also taking into consideration the precedence. For now, this wouldn't seem to be a problem with limited details available.
Related GitHub Issues:
N/A