diff --git a/chart/test-values.yaml b/chart/test-values.yaml index b7e832ec..ca339ea5 100644 --- a/chart/test-values.yaml +++ b/chart/test-values.yaml @@ -6,6 +6,7 @@ configMap: dbUri: "sqlite:///:memory:" glance: {} placement: {} + neutron: {} horizon: hostAliases: - hostnames: diff --git a/config/samples/operator-config.yaml b/config/samples/operator-config.yaml index 3cb7b9a4..8bb2fe9b 100644 --- a/config/samples/operator-config.yaml +++ b/config/samples/operator-config.yaml @@ -15,6 +15,7 @@ data: magnum: {} chronyd: {} placement: {} + neutron: {} backup: secretName: aws-backup url: s3://backups/ diff --git a/devstack/lib/neutron-legacy b/devstack/lib/neutron-legacy new file mode 100644 index 00000000..52028f9f --- /dev/null +++ b/devstack/lib/neutron-legacy @@ -0,0 +1,41 @@ +#!/bin/bash +# +# Copyright 2020 VEXXHOST, Inc. +# +# Licensed 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. + +function init_mutnauq { + recreate_database $Q_DB_NAME +} +export -f init_mutnauq + +function start_neutron_service_and_check { + neutron_plugin_configure_common + + kubectl -n openstack create secret generic neutron-config \ + --from-file=/etc/neutron/neutron.conf \ + --from-file=/etc/neutron/api-paste.ini \ + --from-file=/etc/neutron/policy.json + kubectl -n openstack create secret generic neutron-ml2-config \ + --from-file=/etc/neutron/plugins/ml2/ml2_conf.ini + + kubernetes_rollout_restart daemonset/neutron + kubernetes_rollout_status daemonset/neutron + proxy_pass_to_kubernetes /networking neutron neutron-api + + neutron_url=$Q_PROTOCOL://${Q_HOST}/networking/ + if ! wait_for_service $SERVICE_TIMEOUT $neutron_url; then + die $LINENO "neutron-api did not start" + fi +} +export -f start_neutron_service_and_check diff --git a/devstack/settings b/devstack/settings index d7165ebb..74a5545c 100644 --- a/devstack/settings +++ b/devstack/settings @@ -21,5 +21,6 @@ source $DEST/openstack-operator/devstack/lib/barbican source $DEST/openstack-operator/devstack/lib/glance source $DEST/openstack-operator/devstack/lib/horizon source $DEST/openstack-operator/devstack/lib/keystone +source $DEST/openstack-operator/devstack/lib/neutron-legacy source $DEST/openstack-operator/devstack/lib/placement source $DEST/openstack-operator/devstack/lib/rpc_backend diff --git a/images/neutron/Dockerfile b/images/neutron/Dockerfile new file mode 100644 index 00000000..d6cce6c5 --- /dev/null +++ b/images/neutron/Dockerfile @@ -0,0 +1,27 @@ +# Copyright (c) 2020 VEXXHOST, Inc. +# +# Licensed 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. + +FROM vexxhost/python-builder as builder +FROM vexxhost/python-base AS neutron-base + +FROM neutron-base AS neutron-api +COPY neutron-api /usr/local/bin/neutron-api +EXPOSE 9696 +ENV UWSGI_HTTP_SOCKET=:9696 UWSGI_WSGI_FILE=/usr/local/bin/neutron-api +CMD ["/usr/local/bin/uwsgi", "--ini", "/etc/uwsgi/uwsgi.ini"] + +FROM neutron-base AS neutron-rpc-server +COPY neutron-rpc-server /usr/local/bin/neutron-rpc-server +CMD ["/usr/local/bin/neutron-rpc-server"] diff --git a/images/neutron/bindep.txt b/images/neutron/bindep.txt new file mode 100644 index 00000000..64b038ba --- /dev/null +++ b/images/neutron/bindep.txt @@ -0,0 +1,2 @@ +gcc [compile] +libc-dev [compile] diff --git a/images/neutron/constraints.txt b/images/neutron/constraints.txt new file mode 100644 index 00000000..e483a913 --- /dev/null +++ b/images/neutron/constraints.txt @@ -0,0 +1 @@ +--constraint https://releases.openstack.org/constraints/upper/ussuri diff --git a/images/neutron/neutron-api b/images/neutron/neutron-api new file mode 100755 index 00000000..82941f3d --- /dev/null +++ b/images/neutron/neutron-api @@ -0,0 +1,28 @@ +#!/usr/local/bin/python +# Copyright (c) 2020 VEXXHOST, Inc. +# +# Licensed 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. + +import pkg_resources + +import sentry_sdk + +from neutron.server import get_application +from sentry_sdk.integrations import wsgi + +VERSION = pkg_resources.get_distribution("neutron").version +sentry_sdk.init(release="neutron@%s" % VERSION) + +application = get_application() +application = wsgi.SentryWsgiMiddleware(application) diff --git a/images/neutron/neutron-rpc-server b/images/neutron/neutron-rpc-server new file mode 100755 index 00000000..0cf23067 --- /dev/null +++ b/images/neutron/neutron-rpc-server @@ -0,0 +1,29 @@ +#!/usr/local/bin/python +# Copyright (c) 2020 VEXXHOST, Inc. +# +# Licensed 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. + +import pkg_resources +import re +import sys + +import sentry_sdk + +from neutron.cmd.eventlet.server import main_rpc_eventlet + +VERSION = pkg_resources.get_distribution("neutron").version +sentry_sdk.init(release="neutron@%s" % VERSION) + +sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0]) +sys.exit(main_rpc_eventlet()) diff --git a/images/neutron/requirements.txt b/images/neutron/requirements.txt new file mode 100644 index 00000000..c22d6f99 --- /dev/null +++ b/images/neutron/requirements.txt @@ -0,0 +1,5 @@ +uWSGI +PyMySQL +python-memcached +sentry-sdk +git+https://opendev.org/openstack/neutron@stable/ussuri diff --git a/openstack_operator/neutron.py b/openstack_operator/neutron.py new file mode 100644 index 00000000..8d45f10b --- /dev/null +++ b/openstack_operator/neutron.py @@ -0,0 +1,35 @@ +# Copyright 2020 VEXXHOST, Inc. +# +# Licensed 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. + +""" +Neutron service + +This code takes care of doing the operations of the OpenStack Neutron API +service. +""" + +from openstack_operator import utils + +MEMCACHED = True + + +def create_or_resume(spec, **_): + """Create and re-sync a Neutron instance + + This function is called when a new resource is created but also when we + start the service up for the first time. + """ + + utils.create_or_update('neutron/daemonset.yml.j2', spec=spec) + utils.create_or_update('neutron/service.yml.j2') diff --git a/openstack_operator/operator.py b/openstack_operator/operator.py index 9ac97e77..50e99c67 100644 --- a/openstack_operator/operator.py +++ b/openstack_operator/operator.py @@ -35,6 +35,7 @@ from openstack_operator import horizon from openstack_operator import keystone from openstack_operator import libvirtd_exporter from openstack_operator import magnum +from openstack_operator import neutron from openstack_operator import placement from openstack_operator import utils @@ -94,7 +95,10 @@ def deploy(name, namespace, new, **_): keystone.create_or_resume("keystone", spec) if "placement" in config: spec = set_service_config(config, "placement") - placement.create_or_resume("placement", spec) + neutron.create_or_resume(spec) + if "neutron" in config: + spec = set_service_config(config, "neutron") + placement.create_or_resume("neutron", spec) if "horizon" in config: spec = set_service_config(config, "horizon") horizon.create_or_resume("horizon", spec) @@ -114,16 +118,10 @@ def deploy(name, namespace, new, **_): spec = config["ceilometer"] ceilometer.create_or_resume(spec) - if "chronyd" in config: - spec = config["chronyd"] - else: - spec = {} + spec = config.get("chronyd", {}) chronyd.create_or_resume(spec) - if "libvirtd-exporter" in config: - spec = config["libvirtd-exporter"] - else: - spec = {} + spec = config.get("libvirtd_exporter", {}) libvirtd_exporter.create_or_resume(spec) diff --git a/openstack_operator/templates/neutron/daemonset.yml.j2 b/openstack_operator/templates/neutron/daemonset.yml.j2 new file mode 100644 index 00000000..f6eecafb --- /dev/null +++ b/openstack_operator/templates/neutron/daemonset.yml.j2 @@ -0,0 +1,113 @@ +--- +# Copyright 2020 VEXXHOST, Inc. +# +# Licensed 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. + +apiVersion: apps/v1 +kind: DaemonSet +metadata: + name: neutron + namespace: openstack + labels: + {{ labels("neutron") | indent(4) }} +spec: + updateStrategy: + rollingUpdate: + maxUnavailable: 1 + type: RollingUpdate + selector: + matchLabels: + {{ labels("neutron") | indent(6) }} + template: + metadata: + labels: + {{ labels("neutron") | indent(8) }} + spec: + automountServiceAccountToken: false + initContainers: + - name: db-sync + image: vexxhost/neutron-rpc-server:latest + imagePullPolicy: Always + command: + - neutron-db-manage + - upgrade + - heads + volumeMounts: + - name: config + mountPath: /etc/neutron + - name: ml2-config + mountPath: /etc/neutron/plugins/ml2 + containers: + - name: rpc-server + image: vexxhost/neutron-rpc-server:latest + imagePullPolicy: Always + env: + {% if 'sentryDSN' in spec %} + - name: SENTRY_DSN + value: {{ spec.sentryDSN }} + {% endif %} + securityContext: + runAsUser: 1001 + volumeMounts: + - name: config + mountPath: /etc/neutron + - name: ml2-config + mountPath: /etc/neutron/plugins/ml2 + - name: api + image: vexxhost/neutron-api:latest + imagePullPolicy: Always + env: + {% if 'sentryDSN' in spec %} + - name: SENTRY_DSN + value: {{ spec.sentryDSN }} + {% endif %} + ports: + - name: neutron + protocol: TCP + containerPort: 9696 + livenessProbe: + tcpSocket: + port: neutron + readinessProbe: + tcpSocket: + port: neutron + securityContext: + runAsUser: 1001 + volumeMounts: + - name: config + mountPath: /etc/neutron + - name: ml2-config + mountPath: /etc/neutron/plugins/ml2 + - name: uwsgi-config + mountPath: /etc/uwsgi + volumes: + - name: config + secret: + secretName: neutron-config + - name: ml2-config + secret: + secretName: neutron-ml2-config + - name: uwsgi-config + configMap: + defaultMode: 420 + name: uwsgi-default + nodeSelector: + node-role.kubernetes.io/master: "" + tolerations: + - key: node-role.kubernetes.io/master + effect: NoSchedule +{% if 'hostAliases' in spec %} + hostAliases: + {{ spec.hostAliases | to_yaml | indent(8) }} +{% endif %} + diff --git a/openstack_operator/templates/neutron/service.yml.j2 b/openstack_operator/templates/neutron/service.yml.j2 new file mode 100644 index 00000000..8967aece --- /dev/null +++ b/openstack_operator/templates/neutron/service.yml.j2 @@ -0,0 +1,28 @@ +--- +# Copyright 2020 VEXXHOST, Inc. +# +# Licensed 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. + +apiVersion: v1 +kind: Service +metadata: + name: neutron + namespace: openstack +spec: + ports: + - name: neutron + port: 80 + protocol: TCP + targetPort: neutron + selector: + {{ labels("neutron") | indent(4) }} diff --git a/zuul.d/functional-jobs.yaml b/zuul.d/functional-jobs.yaml index 2a54257f..2d038b8a 100644 --- a/zuul.d/functional-jobs.yaml +++ b/zuul.d/functional-jobs.yaml @@ -49,6 +49,7 @@ - magnum-tempest-plugin - tempest-horizon devstack_localrc: + NEUTRON_DEPLOY_MOD_WSGI: True TEMPEST_PLUGINS: /opt/stack/barbican-tempest-plugin /opt/stack/heat-tempest-plugin /opt/stack/magnum-tempest-plugin /opt/stack/tempest-horizon docker_use_buildset_registry: true @@ -66,6 +67,8 @@ soft: true - name: openstack-operator:images:build:ceilometer soft: true + - name: openstack-operator:images:build:neutron + soft: true - name: openstack-operator:images:build:rabbitmq soft: true - name: openstack-operator:images:build:keystone @@ -97,6 +100,8 @@ soft: true - name: openstack-operator:images:upload:ceilometer soft: true + - name: openstack-operator:images:upload:neutron + soft: true - name: openstack-operator:images:upload:rabbitmq soft: true - name: openstack-operator:images:upload:keystone diff --git a/zuul.d/neutron-jobs.yaml b/zuul.d/neutron-jobs.yaml new file mode 100644 index 00000000..24100106 --- /dev/null +++ b/zuul.d/neutron-jobs.yaml @@ -0,0 +1,48 @@ +- job: + name: openstack-operator:images:build:neutron + parent: vexxhost-build-docker-image + provides: openstack-operator:image:neutron + nodeset: &id001 + nodes: + - name: ubuntu-bionic + label: ubuntu-bionic-vexxhost + vars: &id002 + docker_images: + - context: images/neutron + repository: vexxhost/neutron-base + target: neutron-base + - context: images/neutron + repository: vexxhost/neutron-api + target: neutron-api + - context: images/neutron + repository: vexxhost/neutron-rpc-server + target: neutron-rpc-server + dependencies: + - openstack-operator:images:build:openstack-operator + files: &id003 + - ^images/neutron/.* +- job: + name: openstack-operator:images:upload:neutron + parent: vexxhost-upload-docker-image + provides: openstack-operator:image:neutron + nodeset: *id001 + vars: *id002 + dependencies: + - openstack-operator:images:upload:openstack-operator + files: *id003 +- job: + name: openstack-operator:images:promote:neutron + parent: vexxhost-promote-docker-image + nodeset: *id001 + vars: *id002 + files: *id003 +- project: + check: + jobs: + - openstack-operator:images:build:neutron + gate: + jobs: + - openstack-operator:images:upload:neutron + promote: + jobs: + - openstack-operator:images:promote:neutron