This is an automated email from the ASF dual-hosted git repository. fgreg pushed a commit to branch v1.0.0-rc1 in repository https://gitbox.apache.org/repos/asf/incubator-sdap-ningesterpy.git
commit df99ec8989caf991589b509e6598ec1d19e38500 Author: fgreg <[email protected]> AuthorDate: Wed Aug 29 09:33:31 2018 -0700 Made the host and port options configurable and enabled an option for choosing a random available port and writing that port number to a file. Also upgraded to latest version of Flask (#9) --- .gitignore | 1 + .idea/ningesterpy.iml | 2 +- requirements.txt | 6 +++--- sdap/default_settings.py | 18 ++++++++++++++++++ sdap/ningesterpy.py | 38 ++++++++++++++++++++++++++++++++++---- tests/test_settings.py | 19 +++++++++++++++++++ 6 files changed, 76 insertions(+), 8 deletions(-) diff --git a/.gitignore b/.gitignore index cc74a02..6942e83 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,4 @@ +current_port ### Python template # Byte-compiled / optimized / DLL files diff --git a/.idea/ningesterpy.iml b/.idea/ningesterpy.iml index dcf2bcc..1f079f2 100644 --- a/.idea/ningesterpy.iml +++ b/.idea/ningesterpy.iml @@ -4,7 +4,7 @@ <content url="file://$MODULE_DIR$"> <sourceFolder url="file://$MODULE_DIR$" isTestSource="false" /> </content> - <orderEntry type="inheritedJdk" /> + <orderEntry type="jdk" jdkName="Python 3.5.4 (~/anaconda/envs/ningesterpy/bin/python)" jdkType="Python SDK" /> <orderEntry type="sourceFolder" forTests="false" /> </component> <component name="PyDocumentationSettings"> diff --git a/requirements.txt b/requirements.txt index 69e023e..0db4856 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,6 +1,6 @@ -werkzeug==0.12.2 -flask==0.12.2 -flask-accept==0.0.4 +werkzeug==0.14.1 +flask==1.0.2 +flask-accept==0.0.6 nexusproto===1.0.0-SNAPSHOT numpy==1.12.1 protobuf==3.2.0 diff --git a/sdap/default_settings.py b/sdap/default_settings.py new file mode 100644 index 0000000..be6bc06 --- /dev/null +++ b/sdap/default_settings.py @@ -0,0 +1,18 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +SERVER_NAME = '127.0.0.1:5000' +PORT_FILE = 'current_port' +CREATE_PORT_FILE = False diff --git a/sdap/ningesterpy.py b/sdap/ningesterpy.py index e036952..21ea1bb 100644 --- a/sdap/ningesterpy.py +++ b/sdap/ningesterpy.py @@ -13,6 +13,7 @@ # See the License for the specific language governing permissions and # limitations under the License. import logging +import pprint import sys import uuid @@ -101,11 +102,40 @@ def handle_error(e): if __name__ == '__main__': - host = '127.0.0.1' - port = 5000 - applog.info("Running app on %s:%d" % (host, port)) + app.register_error_handler(Exception, handle_error) for ex in default_exceptions: app.register_error_handler(ex, handle_error) app.json_encoder = ProtobufJSONEncoder - app.run(host=host, port=port) + app.config.from_object('sdap.default_settings') + try: + app.config.from_envvar('NINGESTERPY_SETTINGS') + except RuntimeError: + applog.warning("NINGESTERPY_SETTINGS environment variable not set or invalid. Using default settings.") + + # SERVER_NAME should be in the form of localhost:5000, 127.0.0.1:0, etc... + # So, split on : and take the second element as the port + # If the port is 0, we need to pick a random port and then tell the server to use that socket + if app.config['SERVER_NAME'] and int(app.config['SERVER_NAME'].split(':')[1]) == 0: + import socket, os + + # Chose a random available port by binding to port 0 + sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) + sock.bind((app.config['SERVER_NAME'].split(':')[0], 0)) + sock.listen() + + # Tells the underlying WERKZEUG server to use the socket we just created + os.environ['WERKZEUG_SERVER_FD'] = str(sock.fileno()) + + # Update the configuration so it matches with the port we just chose + # (sock.getsockname will return the actual port being used, not 0) + app.config['SERVER_NAME'] = '%s:%d' % (sock.getsockname()) + + # Optionally write the current port to a file on the filesystem + if app.config['CREATE_PORT_FILE']: + with open(app.config['PORT_FILE'], 'w') as port_file: + port_file.write(app.config['SERVER_NAME'].split(':')[1]) + + applog.info("Running app on %s" % (app.config['SERVER_NAME'])) + applog.info("Active Settings:%s" % pprint.pformat(app.config, compact=True)) + app.run() diff --git a/tests/test_settings.py b/tests/test_settings.py new file mode 100644 index 0000000..1c28c6a --- /dev/null +++ b/tests/test_settings.py @@ -0,0 +1,19 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +SERVER_NAME = '127.0.0.1:0' +ENV = 'development' +PORT_FILE = 'current_port' +CREATE_PORT_FILE = True
