From 5a29ced8b26f3208341ac7959f988c7c69652be6 Mon Sep 17 00:00:00 2001 From: Pino de Candia Date: Fri, 2 Mar 2018 21:13:47 +0000 Subject: [PATCH] Devstack plugin fixes Change-Id: Ie9798fe1bb4c6d511c601306ed1d366d97ff09f7 Signed-off-by: Pino de Candia --- devstack/README.rst | 2 +- .../local.conf => devstack/local-df.conf | 6 +- devstack/local.conf | 21 ++ devstack/plugin.sh | 73 ++++--- devstack/settings | 15 +- devstack/tatu_stack.sh | 188 ++++++++++++++++++ devstack_old/README.md | 21 -- devstack_old/plugin.sh | 50 ----- devstack_old/settings | 1 - files/paste.ini => etc/tatu/api-paste.ini | 7 - requirements.txt | 2 +- setup.cfg | 2 +- tatu/api/app.py | 9 +- tatu/api/models.py | 17 +- tatu/config.py | 34 ++-- tatu/notifications.py | 9 +- tatu/pat.py | 8 +- 17 files changed, 313 insertions(+), 152 deletions(-) rename devstack_old/local.conf => devstack/local-df.conf (87%) create mode 100644 devstack/local.conf create mode 100755 devstack/tatu_stack.sh delete mode 100644 devstack_old/README.md delete mode 100644 devstack_old/plugin.sh delete mode 100644 devstack_old/settings rename files/paste.ini => etc/tatu/api-paste.ini (70%) diff --git a/devstack/README.rst b/devstack/README.rst index 5b24a34..b638868 100644 --- a/devstack/README.rst +++ b/devstack/README.rst @@ -15,6 +15,6 @@ repository. See contrib/vagrant to create a vagrant VM. > cat local.conf [[local|localrc]] - enable_plugin tatu https://github.com/pinodeca/tatu + enable_plugin tatu https://github.com/openstack/tatu 3. run ``stack.sh`` diff --git a/devstack_old/local.conf b/devstack/local-df.conf similarity index 87% rename from devstack_old/local.conf rename to devstack/local-df.conf index 40aa7f1..82d2c3f 100644 --- a/devstack_old/local.conf +++ b/devstack/local-df.conf @@ -6,7 +6,7 @@ SERVICE_PASSWORD=pinot SERVICE_TOKEN=pinot ADMIN_PASSWORD=pinot -enable_plugin tatu https://github.com/pinodeca/tatu +enable_plugin tatu https://git.openstack.org/openstack/tatu enable_plugin designate https://git.openstack.org/openstack/designate enable_plugin barbican https://git.openstack.org/openstack/barbican enable_plugin dragonflow https://github.com/pinodeca/dragonflow tatu @@ -41,6 +41,6 @@ PUBLIC_NETWORK_NAME=public PUBLIC_NETWORK_GATEWAY=172.24.4.1 IMAGE_URL_SITE="http://download.fedoraproject.org" -IMAGE_URL_PATH="/pub/fedora/linux/releases/25/CloudImages/x86_64/images/" -IMAGE_URL_FILE="Fedora-Cloud-Base-25-1.3.x86_64.qcow2" +IMAGE_URL_PATH="/pub/fedora/linux/releases/27/CloudImages/x86_64/images/" +IMAGE_URL_FILE="Fedora-Cloud-Base-27-1.6.x86_64.qcow2" IMAGE_URLS+=","$IMAGE_URL_SITE$IMAGE_URL_PATH$IMAGE_URL_FILE diff --git a/devstack/local.conf b/devstack/local.conf new file mode 100644 index 0000000..9fe31ff --- /dev/null +++ b/devstack/local.conf @@ -0,0 +1,21 @@ +[[local|localrc]] + +DATABASE_PASSWORD=pinot +RABBIT_PASSWORD=pinot +SERVICE_PASSWORD=pinot +SERVICE_TOKEN=pinot +ADMIN_PASSWORD=pinot + +enable_plugin tatu https://git.openstack.org/openstack/tatu +enable_plugin designate https://git.openstack.org/openstack/designate +enable_plugin barbican https://git.openstack.org/openstack/barbican + +Q_USE_PROVIDERNET_FOR_PUBLIC=True +Q_FLOATING_ALLOCATION_POOL=start=172.24.4.10,end=172.24.4.200 +PUBLIC_NETWORK_NAME=public +PUBLIC_NETWORK_GATEWAY=172.24.4.1 + +IMAGE_URL_SITE="http://download.fedoraproject.org" +IMAGE_URL_PATH="/pub/fedora/linux/releases/27/CloudImages/x86_64/images/" +IMAGE_URL_FILE="Fedora-Cloud-Base-27-1.6.x86_64.qcow2" +IMAGE_URLS+=","$IMAGE_URL_SITE$IMAGE_URL_PATH$IMAGE_URL_FILE diff --git a/devstack/plugin.sh b/devstack/plugin.sh index 5ba4fce..96282cc 100644 --- a/devstack/plugin.sh +++ b/devstack/plugin.sh @@ -13,10 +13,6 @@ function setup_colorized_logging_tatu { local user_var=${4:-"user_name"} setup_colorized_logging $conf_file $conf_section $project_var $user_var - - # Override the logging_context_format_string value chosen by - # setup_colorized_logging. - iniset $conf_file $conf_section logging_context_format_string "%(asctime)s.%(msecs)03d %(color)s%(levelname)s %(name)s [%(request_id)s %(user_identity)s%(color)s] %(instance)s%(color)s%(message)s" } # DevStack Plugin @@ -26,7 +22,6 @@ function setup_colorized_logging_tatu { # runs that a clean run would need to clean up function cleanup_tatu { sudo rm -rf $TATU_STATE_PATH $TATU_AUTH_CACHE_DIR - cleanup_tatu_backend } # configure_tatu - Set config files, create data dirs, etc @@ -40,34 +35,50 @@ function configure_tatu { # (Re)create ``tatu.conf`` rm -f $TATU_CONF + local admin_project + admin_project=$(openstack project show "admin" -f value -c id) + local admin_user + admin_user=$(openstack user show "admin" -f value -c id) + + iniset $TATU_CONF tatu auth_url $KEYSTONE_SERVICE_URI/v3 + iniset $TATU_CONF tatu user_id $admin_user + iniset $TATU_CONF tatu password $ADMIN_PASSWORD + iniset $TATU_CONF tatu project_id $admin_project + iniset $TATU_CONF tatu use_barbican_key_manager True + iniset $TATU_CONF tatu use_pat_bastions False + iniset $TATU_CONF tatu ssh_port 2222 + iniset $TATU_CONF tatu num_total_pats 1 + iniset $TATU_CONF tatu num_pat_bastions_per_server 1 + iniset $TATU_CONF tatu pat_dns_zone_name tatuDemo.com. + iniset $TATU_CONF tatu pat_dns_zone_email my@tatu.devstack + iniset $TATU_CONF tatu sqlalchemy_engine `database_connection_url tatu` + + # Need Keystone and Nova notifications + iniadd $KEYSTONE_CONF oslo_messaging_notifications topics tatu_notifications + iniadd $NOVA_CONF oslo_messaging_notifications topics tatu_notifications + + iniset /etc/nova/nova-cpu.conf DEFAULT force_config_drive TRUE + + # Set up Tatu static vendor data. + $TATU_DIR/scripts/cloud-config-to-vendor-data $TATU_DIR/files/user-cloud-config > /etc/nova/tatu_static_vd.json + iniset /etc/nova/nova-cpu.conf api vendordata_providers StaticJSON,DynamicJSON + iniset /etc/nova/nova-cpu.conf api vendordata_jsonfile_path /etc/nova/tatu_static_vd.json + # General Configuration iniset_rpc_backend tatu $TATU_CONF DEFAULT iniset $TATU_CONF DEFAULT rpc_response_timeout 5 iniset $TATU_CONF DEFAULT debug $ENABLE_DEBUG_LOG_LEVEL iniset $TATU_CONF DEFAULT state_path $TATU_STATE_PATH - iniset $TATU_CONF DEFAULT root-helper sudo tatu-rootwrap $TATU_ROOTWRAP_CONF iniset $TATU_CONF storage:sqlalchemy connection `database_connection_url tatu` # API Configuration sudo cp $TATU_DIR/etc/tatu/api-paste.ini $TATU_APIPASTE_CONF iniset $TATU_CONF service:api api_base_uri $TATU_SERVICE_PROTOCOL://$TATU_SERVICE_HOST:$TATU_SERVICE_PORT/ - # Root Wrap - sudo cp $TATU_DIR/etc/tatu/rootwrap.conf.sample $TATU_ROOTWRAP_CONF - iniset $TATU_ROOTWRAP_CONF DEFAULT filters_path $TATU_DIR/etc/tatu/rootwrap.d root-helper - # Oslo Concurrency iniset $TATU_CONF oslo_concurrency lock_path "$TATU_STATE_PATH" - # Set up the rootwrap sudoers for tatu - local rootwrap_sudoer_cmd="$TATU_BIN_DIR/tatu-rootwrap $TATU_ROOTWRAP_CONF *" - local tempfile=`mktemp` - echo "$STACK_USER ALL=(root) NOPASSWD: $rootwrap_sudoer_cmd" >$tempfile - chmod 0440 $tempfile - sudo chown root:root $tempfile - sudo mv $tempfile /etc/sudoers.d/tatu-rootwrap - # TLS Proxy Configuration if is_service_enabled tls-proxy; then # Set the service port for a proxy to take the original @@ -125,11 +136,6 @@ function init_tatu { # (Re)create tatu database recreate_database tatu utf8 - - # Init and migrate tatu database - tatu-manage database sync - - init_tatu_backend } # install_tatu - Collect source and prepare @@ -152,34 +158,37 @@ function install_tatudashboard { for panel in _3980_tatu_panel_group.py \ _3981_tatu_ca_panel.py \ _3982_tatu_user_panel.py \ - _3983_tatu_host_panel.py; do + _3983_tatu_host_panel.py \ + _3984_tatu_pat_panel.py \ + _3985_tatu_host_cert_panel.py; do ln -fs $TATUDASHBOARD_DIR/tatudashboard/enabled/$panel $HORIZON_DIR/openstack_dashboard/local/enabled/$panel done } # start_tatu - Start running processes function start_tatu { - start_tatu_backend - - run_process tatu-central "$TATU_BIN_DIR/tatu-central --config-file $TATU_CONF" - run_process tatu-api "$TATU_BIN_DIR/tatu-api --config-file $TATU_CONF" + local PSERVE=`which pserve` + run_process tatu-api "$PSERVE $TATU_APIPASTE_CONF" + local PYTHON=`which python` + run_process tatu-agent "$PYTHON $TATU_DIR/tatu/notifications.py" # Start proxies if enabled if is_service_enabled tatu-api && is_service_enabled tls-proxy; then start_tls_proxy tatu-api '*' $TATU_SERVICE_PORT $TATU_SERVICE_HOST $TATU_SERVICE_PORT_INT & fi - if ! timeout $SERVICE_TIMEOUT sh -c "while ! wget --no-proxy -q -O- $TATU_SERVICE_PROTOCOL://$TATU_SERVICE_HOST:$TATU_SERVICE_PORT; do sleep 1; done"; then + local wget_cmd + wget_cmd="wget --no-proxy -q -O- $TATU_SERVICE_PROTOCOL://$TATU_SERVICE_HOST:$TATU_SERVICE_PORT/noauth" + echo waiting on $wget_cmd + if ! timeout $SERVICE_TIMEOUT sh -c "until $wget_cmd; do sleep 1; echo re-trying; done"; then die $LINENO "Tatu did not start" fi } # stop_tatu - Stop running processes function stop_tatu { - stop_process tatu-central stop_process tatu-api - - stop_tatu_backend + stop_process tatu-agent } # This is the main for plugin.sh diff --git a/devstack/settings b/devstack/settings index 10a442c..adc9faa 100644 --- a/devstack/settings +++ b/devstack/settings @@ -1,7 +1,6 @@ define_plugin tatu plugin_requires tatu designate plugin_requires tatu barbican -plugin_requires tatu dragonflow # TODO(pino): remove this dependency # Default options TATU_USE_BARBICAN=${TATU_USE_BARBICAN:-"True"} @@ -19,8 +18,8 @@ fi # Default IP/port settings TATU_SERVICE_PROTOCOL=${TATU_SERVICE_PROTOCOL:-$SERVICE_PROTOCOL} TATU_SERVICE_HOST=${TATU_SERVICE_HOST:-$SERVICE_HOST} -TATU_SERVICE_PORT=${TATU_SERVICE_PORT:-8322} -TATU_SERVICE_PORT_INT=${TATU_SERVICE_PORT_INT:-18322} +TATU_SERVICE_PORT=${TATU_SERVICE_PORT:-18322} +TATU_SERVICE_PORT_INT=${TATU_SERVICE_PORT_INT:-28322} # Default directories TATU_BIN_DIR=$(get_python_exec_prefix) @@ -31,22 +30,22 @@ TATU_STATE_PATH=${TATU_STATE_PATH:=$DATA_DIR/tatu} TATU_CONF=$TATU_CONF_DIR/tatu.conf TATU_LOG_DIR=/var/log/tatu TATU_AUTH_CACHE_DIR=${TATU_AUTH_CACHE_DIR:-/var/cache/tatu} -TATU_ROOTWRAP_CONF=$TATU_CONF_DIR/rootwrap.conf TATU_APIPASTE_CONF=$TATU_CONF_DIR/api-paste.ini # Default repositories -TATU_GIT_BASE=https://github.com -TATU_REPO=${TATU_REPO:-${TATU_GIT_BASE}/pinodeca/tatu.git} +TATU_GIT_BASE=https://git.openstack.org +TATU_REPO=${TATU_REPO:-${TATU_GIT_BASE}/openstack/tatu} TATU_BRANCH=${TATU_BRANCH:-master} -GITREPO["tatu-dashboard"]=${TATUDASHBOARD_REPO:-${TATU_GIT_BASE}/pinodeca/tatu-dashboard.git} +GITREPO["tatu-dashboard"]=${TATUDASHBOARD_REPO:-${TATU_GIT_BASE}/openstack/tatu-dashboard} GITBRANCH["tatu-dashboard"]=${TATUDASHBOARD_BRANCH:-master} GITDIR["tatu-dashboard"]=$DEST/tatu-dashboard -GITREPO["python-tatuclient"]=${TATUCLIENT_REPO:-${TATU_GIT_BASE}/pinodeca/python-tatuclient.git} +GITREPO["python-tatuclient"]=${TATUCLIENT_REPO:-${TATU_GIT_BASE}/openstack/python-tatuclient} GITBRANCH["python-tatuclient"]=${TATUCLIENT_BRANCH:-master} GITDIR["python-tatuclient"]=$DEST/python-tatuclient # Turn on all Tatu services by default enable_service tatu enable_service tatu-api +enable_service tatu-agent diff --git a/devstack/tatu_stack.sh b/devstack/tatu_stack.sh new file mode 100755 index 0000000..292572f --- /dev/null +++ b/devstack/tatu_stack.sh @@ -0,0 +1,188 @@ +#!/bin/bash + +# **tatu_stack.sh** + +# ``tatu_stack.sh`` is meant to run after devstack's stack.sh and stacks only Tatu. +# - it must be run from the openstack-dev/devstack directory as the stack user. + +# OpenStack is designed to be run as a non-root user; Horizon will fail to run +# as **root** since Apache will not serve content from **root** user). +# ``stack.sh`` must not be run as **root**. It aborts and suggests one course of +# action to create a suitable user account. + +set -o xtrace + +unset GREP_OPTIONS + +unset LANG +unset LANGUAGE +LC_ALL=en_US.utf8 +export LC_ALL + +# Make sure umask is sane +umask 022 + +# Not all distros have sbin in PATH for regular users. +PATH=$PATH:/usr/local/sbin:/usr/sbin:/sbin + +# Keep track of the DevStack directory +TOP_DIR=$(cd $(dirname "$0") && pwd) + +# Check for uninitialized variables, a big cause of bugs +NOUNSET=${NOUNSET:-} +if [[ -n "$NOUNSET" ]]; then + set -o nounset +fi + +# ``stack.sh`` keeps the list of ``deb`` and ``rpm`` dependencies, config +# templates and other useful files in the ``files`` subdirectory +FILES=$TOP_DIR/files +if [ ! -d $FILES ]; then + die $LINENO "missing devstack/files" +fi + +# ``stack.sh`` keeps function libraries here +# Make sure ``$TOP_DIR/inc`` directory is present +if [ ! -d $TOP_DIR/inc ]; then + die $LINENO "missing devstack/inc" +fi + +# ``stack.sh`` keeps project libraries here +# Make sure ``$TOP_DIR/lib`` directory is present +if [ ! -d $TOP_DIR/lib ]; then + die $LINENO "missing devstack/lib" +fi + +if [[ "${POSIXLY_CORRECT}" == "y" ]]; then + set +o xtrace + echo "You are running POSIX compatibility mode, DevStack requires bash 4.2 or newer." + exit 1 +fi + +if [[ $EUID -eq 0 ]]; then + set +o xtrace + echo "DevStack should be run as a user with sudo permissions, " + echo "not root." + echo "A \"stack\" user configured correctly can be created with:" + echo " $TOP_DIR/tools/create-stack-user.sh" + exit 1 +fi + +# Initialize variables: +LAST_SPINNER_PID="" + +# Import common functions +source $TOP_DIR/functions + +# Import config functions +source $TOP_DIR/inc/meta-config + +# Import 'public' stack.sh functions +source $TOP_DIR/lib/stack + +# Determine what system we are running on. This provides ``os_VENDOR``, +# ``os_RELEASE``, ``os_PACKAGE``, ``os_CODENAME`` +# and ``DISTRO`` +GetDistro + +# Phase: local +rm -f $TOP_DIR/.localrc.auto +extract_localrc_section $TOP_DIR/local.conf $TOP_DIR/localrc $TOP_DIR/.localrc.auto + +if [[ ! -r $TOP_DIR/stackrc ]]; then + die $LINENO "missing $TOP_DIR/stackrc - did you grab more than just stack.sh?" +fi + +source $TOP_DIR/stackrc +source $TOP_DIR/openrc admin admin + +export_proxy_variables + +disable_negated_services + +# Destination path for installation ``DEST`` +DEST=${DEST:-/opt/stack} + +# Destination path for service data +DATA_DIR=${DATA_DIR:-${DEST}/data} + +LOCAL_HOSTNAME=`hostname -s` + +VERBOSE=$(trueorfalse True VERBOSE) +VERBOSE_NO_TIMESTAMP=$(trueorfalse False VERBOSE) + +TIMESTAMP_FORMAT=${TIMESTAMP_FORMAT:-"%F-%H%M%S"} +LOGDAYS=${LOGDAYS:-7} +CURRENT_LOG_TIME=$(date "+$TIMESTAMP_FORMAT") + +if [[ true ]]; then + # Set up output redirection without log files + # Set fd 3 to a copy of stdout. So we can set fd 1 without losing + # stdout later. + exec 3>&1 + if [[ "$VERBOSE" != "True" ]]; then + # Throw away stdout and stderr + exec 1>/dev/null 2>&1 + fi + # Always send summary fd to original stdout + exec 6> >( $TOP_DIR/tools/outfilter.py -v >&3 ) +fi + +# Basic test for ``$DEST`` path permissions (fatal on error unless skipped) +check_path_perm_sanity ${DEST} + +# Print the kernel version +uname -a + +SSL_BUNDLE_FILE="$DATA_DIR/ca-bundle.pem" + +# Import common services (database, message queue) configuration +source $TOP_DIR/lib/database +source $TOP_DIR/lib/rpc_backend + +# Configure Projects +# ================== + +# Clone all external plugins +fetch_plugins + +# Plugin Phase 0: override_defaults - allow plugins to override +# defaults before other services are run +run_phase override_defaults + +# Import Apache functions +source $TOP_DIR/lib/apache + +# Import TLS functions +source $TOP_DIR/lib/tls + +# Source project function libraries +source $TOP_DIR/lib/infra +source $TOP_DIR/lib/libraries +source $TOP_DIR/lib/lvm +source $TOP_DIR/lib/horizon +source $TOP_DIR/lib/keystone +source $TOP_DIR/lib/glance +source $TOP_DIR/lib/nova +source $TOP_DIR/lib/placement +source $TOP_DIR/lib/cinder +source $TOP_DIR/lib/swift +source $TOP_DIR/lib/neutron +source $TOP_DIR/lib/ldap +source $TOP_DIR/lib/dstat +source $TOP_DIR/lib/etcd3 + +# Extras Source +# -------------- + +# Phase: source +run_phase source + +initialize_database_backends && echo "Using $DATABASE_TYPE database backend" || echo "No database enabled" + +source $DEST/tatu/devstack/settings +source $DEST/tatu/devstack/plugin.sh stack pre-install +source $DEST/tatu/devstack/plugin.sh stack install +source $DEST/tatu/devstack/plugin.sh stack post-config +source $DEST/tatu/devstack/plugin.sh stack extra +source $DEST/tatu/devstack/plugin.sh stack test-config diff --git a/devstack_old/README.md b/devstack_old/README.md deleted file mode 100644 index 4119309..0000000 --- a/devstack_old/README.md +++ /dev/null @@ -1,21 +0,0 @@ -This directory contains the Tatu (SSH-as-a-Service) DevStack plugin. - -To configure Tatu with DevStack, you will need to enable this plugin and -the Tatu service by adding one line to the [[local|localrc]] section of -your local.conf file. - -To enable the plugin, add a line of the form: - - enable_plugin tatu [GITREF] - -where - - is the URL of a Tatu repository - [GITREF] is an optional git ref (branch/ref/tag). The default is master. - -For example - - enable_plugin tatu https://github.com/pinodeca/tatu stable/queens - -For more information, see the "Externally Hosted Plugins" section of -https://docs.openstack.org/devstack/latest/plugins.html \ No newline at end of file diff --git a/devstack_old/plugin.sh b/devstack_old/plugin.sh deleted file mode 100644 index 1c8eb50..0000000 --- a/devstack_old/plugin.sh +++ /dev/null @@ -1,50 +0,0 @@ -# plugin.sh - DevStack plugin.sh dispatch script - -function install_tatu { - ... -} - -function init_tatu { - ... -} - -function configure_tatu { - ... -} - -# check for service enabled -if is_service_enabled tatu; then - - if [[ "$1" == "stack" && "$2" == "pre-install" ]]; then - # Set up system services - echo_summary "Configuring system services tatu" - - elif [[ "$1" == "stack" && "$2" == "install" ]]; then - # Perform installation of service source - echo_summary "Installing tatu" - install_tatu - - elif [[ "$1" == "stack" && "$2" == "post-config" ]]; then - # Configure after the other layer 1 and 2 services have been configured - echo_summary "Configuring tatu" - configure_tatu - - elif [[ "$1" == "stack" && "$2" == "extra" ]]; then - # Initialize and start the tatu service - echo_summary "Initializing tatu" - init_tatu - fi - - if [[ "$1" == "unstack" ]]; then - # Shut down tatu services - # no-op - : - fi - - if [[ "$1" == "clean" ]]; then - # Remove state and transient data - # Remember clean.sh first calls unstack.sh - # no-op - : - fi -fi \ No newline at end of file diff --git a/devstack_old/settings b/devstack_old/settings deleted file mode 100644 index 308ee54..0000000 --- a/devstack_old/settings +++ /dev/null @@ -1 +0,0 @@ -enable_service tatu \ No newline at end of file diff --git a/files/paste.ini b/etc/tatu/api-paste.ini similarity index 70% rename from files/paste.ini rename to etc/tatu/api-paste.ini index 6a01a16..764e38c 100644 --- a/files/paste.ini +++ b/etc/tatu/api-paste.ini @@ -13,13 +13,6 @@ pipeline = authtoken main [filter:authtoken] paste.filter_factory = keystonemiddleware.auth_token:filter_factory -www_authenticate_uri = http://localhost/identity -identity_uri = http://localhost/identity -#auth_version = v2 -admin_token = gAAAAABaPEXR3jF2TqsraXh7qkpKOiPcVbnmHdMEsrSYRKUnfQvpCAR9Sq02vDZNcQLoodVLdxu449zc0AwGXeleRMuf7pEPBgjHPfR6ykkYV6_WXNuMt_Cmqvo_fnRdvPh8bJzjsWEqvEM9s_aCM-le8DkaatoacDrUDA3odBAP1AVdJ0PdJdM -#admin_user = nova -#admin_password = pinot -#admin_tenant_name = service [app:auth_app] paste.app_factory = tatu.api.app:auth_factory diff --git a/requirements.txt b/requirements.txt index 768af96..1038482 100644 --- a/requirements.txt +++ b/requirements.txt @@ -21,7 +21,7 @@ python-memcached python-designateclient python-neutronclient python-novaclient -dragonflow +#dragonflow eventlet vine python-designateclient diff --git a/setup.cfg b/setup.cfg index 70826ca..141efa1 100644 --- a/setup.cfg +++ b/setup.cfg @@ -6,7 +6,7 @@ license = Apache License, Version 2.0 summary = Management of SSH host/user certificates, plus bastions author = Pino de Candia author_email = pino.decandia@huawei.com -home-page = https://github.com/pinodeca/tatu +home-page = https://github.com/openstack/tatu classifier = Environment :: OpenStack Intended Audience :: Information Technology diff --git a/tatu/api/app.py b/tatu/api/app.py index cf90797..fb2fdd0 100644 --- a/tatu/api/app.py +++ b/tatu/api/app.py @@ -11,12 +11,18 @@ # under the License. import falcon +import json from oslo_log import log as logging from tatu.api import models from tatu.db.persistence import SQLAlchemySessionManager LOG = logging.getLogger(__name__) +class RootPage(object): + def on_get(self, req, resp): + resp.body = json.dumps({}) + resp.status = falcon.HTTP_OK + def create_app(sa): LOG.info("Creating falcon API instance for authenticated API calls.") api = falcon.API(middleware=[models.Logger(), sa]) @@ -39,10 +45,11 @@ def create_noauth_app(sa): api = falcon.API(middleware=[models.Logger(), sa]) api.add_route('/hostcerts', models.HostCerts()) api.add_route('/revokeduserkeys/{auth_id}', models.RevokedUserKeys()) + api.add_route('/', RootPage()) return api def auth_factory(global_config, **settings): return create_app(SQLAlchemySessionManager()) def noauth_factory(global_config, **settings): - return create_noauth_app(SQLAlchemySessionManager()) \ No newline at end of file + return create_noauth_app(SQLAlchemySessionManager()) diff --git a/tatu/api/models.py b/tatu/api/models.py index de08ccc..5c88eb7 100644 --- a/tatu/api/models.py +++ b/tatu/api/models.py @@ -21,9 +21,11 @@ from tatu.config import CONF from tatu.db import models as db from tatu.dns import add_srv_records from tatu.ks_utils import getProjectRoleNames, getProjectNameForID, getUserNameForID -from tatu.pat import create_pat_entries, getAllPats, ip_port_tuples_to_string from tatu.utils import canonical_uuid_string, datetime_to_string +if CONF.tatu.use_pat_bastions: + from tatu.pat import create_pat_entries, getAllPats, ip_port_tuples_to_string + LOG = logging.getLogger(__name__) @@ -349,12 +351,13 @@ class PATs(object): @falcon.before(validate) def on_get(self, req, resp): items = [] - for p in getAllPats(): - items.append({ - 'ip': str(p.ip_address), - 'chassis': p.chassis.id, - 'lport': p.lport.id, - }) + if CONF.tatu.use_pat_bastions: + for p in getAllPats(): + items.append({ + 'ip': str(p.ip_address), + 'chassis': p.chassis.id, + 'lport': p.lport.id, + }) body = {'pats': items} resp.body = json.dumps(body) resp.status = falcon.HTTP_OK diff --git a/tatu/config.py b/tatu/config.py index 89f68f2..be9fd29 100644 --- a/tatu/config.py +++ b/tatu/config.py @@ -11,8 +11,6 @@ # under the License. from designateclient.v2 import client as designate_client -from dragonflow import conf as dragonflow_cfg -from dragonflow.db import api_nb from keystoneauth1 import session as keystone_session from keystoneauth1.identity import v3 from keystoneclient.v3 import client as keystone_client @@ -60,7 +58,7 @@ opts = [ help='OpenStack Keystone admin project UUID'), ] -CONF = cfg.CONF +CONF = cfg.ConfigOpts() CONF.register_opts(opts, group='tatu') logging.register_options(CONF) @@ -68,23 +66,27 @@ log_levels = logging.get_default_log_levels() + \ ['tatu=DEBUG', '__main__=DEBUG'] logging.set_defaults(default_log_levels=log_levels) - -try: - CONF(args=[], default_config_files=['/etc/tatu/tatu.conf', - 'files/tatu.conf', - '/etc/neutron/dragonflow.ini']) -except Exception as e: - LOG.error("Failed to load configuration file: {}".format(e)) - +CONF(args=[], default_config_files=['/etc/tatu/tatu.conf']) logging.setup(CONF, "tatu") + +GCONF = cfg.CONF + if CONF.tatu.use_barbican_key_manager: LOG.debug("Using Barbican as key manager.") - set_castellan_defaults(CONF) + set_castellan_defaults(GCONF) else: LOG.debug("Using Tatu as key manager.") - set_castellan_defaults(CONF, + set_castellan_defaults(GCONF, api_class='tatu.castellano.TatuKeyManager') +global_config_files = ['/etc/tatu/tatu.conf'] +if CONF.tatu.use_pat_bastions: + from dragonflow import conf as dragonflow_cfg + from dragonflow.db import api_nb + global_files.append('/etc/neutron/dragonflow.ini') + +GCONF(args=[], default_config_files=global_config_files) + auth = v3.Password(auth_url=CONF.tatu.auth_url, user_id=CONF.tatu.user_id, password=CONF.tatu.password, @@ -95,8 +97,10 @@ NOVA = nova_client.Client('2', session=session) NEUTRON = neutron_client.Client(session=session) DESIGNATE = designate_client.Client(session=session) -dragonflow_cfg.CONF.set_override('enable_df_pub_sub', False, group='df') -DRAGONFLOW = api_nb.NbApi.get_instance(False) +DRAGONFLOW = None +if CONF.tatu.use_pat_bastions: + dragonflow_cfg.CONF.set_override('enable_df_pub_sub', False, group='df') + DRAGONFLOW = api_nb.NbApi.get_instance(False) # Create a context for use by Castellan CONTEXT = context.RequestContext(auth_token=auth.get_token(session), diff --git a/tatu/notifications.py b/tatu/notifications.py index 3f38f0f..78a3eb5 100644 --- a/tatu/notifications.py +++ b/tatu/notifications.py @@ -25,9 +25,11 @@ from tatu.config import KEYSTONE as ks from tatu.config import NOVA as nova from tatu.db import models as db from tatu.dns import delete_srv_records -from tatu.pat import deletePatEntries, string_to_ip_port_tuples from tatu.utils import canonical_uuid_string +if CONF.tatu.use_pat_bastions: + from tatu.pat import deletePatEntries, string_to_ip_port_tuples + LOG = logging.getLogger(__name__) @@ -138,8 +140,9 @@ def _deleteAuthority(session_factory, auth): def _deleteHost(session_factory, host): LOG.debug("Clean up DNS and PAT for deleted instance {} with ID {}" .format(host.name, host.id)) - delete_srv_records(host.srv_url) - deletePatEntries(string_to_ip_port_tuples(host.pat_bastions)) + if CONF.tatu.use_pat_bastions: + delete_srv_records(host.srv_url) + deletePatEntries(string_to_ip_port_tuples(host.pat_bastions)) se = session_factory() try: LOG.info( diff --git a/tatu/pat.py b/tatu/pat.py index 740caef..bc69cd0 100644 --- a/tatu/pat.py +++ b/tatu/pat.py @@ -24,14 +24,18 @@ from tatu.utils import dash_uuid LOG = logging.getLogger(__name__) #TODO(pino): periodically refresh this list -PATS = DRAGONFLOW.get_all(PAT) +PATS = None def getAllPats(): + if not CONF.tatu.use_pat_bastions: + return [] return DRAGONFLOW.get_all(PAT) def _sync_pats(): + if not CONF.tatu.use_pat_bastions: + return # TODO(pino): re-bind PATs when hypervisors fail (here and on notification) all_chassis = DRAGONFLOW.get_all(Chassis) # Filter the chassis that already have PATS assigned @@ -45,6 +49,8 @@ def _sync_pats(): for c in assigned_chassis: _add_pat(c) dns.sync_bastions(str(p.ip_address) for p in PATS) + global PATS + PATS = DRAGONFLOW.get_all(PAT) def _add_pat(chassis):