Enable passing the certificate authority on the relation in order to enable TLS communication to the MySQL DB. In order to enable MySQL to use TLS for client connections all that is required is the CA certificate. A certificate and key may be used for client certificate authentication. However, since almost all deployments will not use certificate authentication, focusing on the CA as SSL data complete makes sense. Change-Id: I785afe7f64cb57caa857178d529e3cabdcf63517
102 lines
3.9 KiB
Python
102 lines
3.9 KiB
Python
# Copyright 2019 Canonical Ltd
|
|
#
|
|
# 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 charms import reactive
|
|
import charmhelpers.contrib.network.ip as ch_net_ip
|
|
|
|
|
|
class MySQLSharedProvides(reactive.Endpoint):
|
|
|
|
def __init__(self, *args, **kwargs):
|
|
super().__init__(*args, **kwargs)
|
|
self.ingress_address = ch_net_ip.get_relation_ip(self.endpoint_name)
|
|
|
|
def relation_ids(self):
|
|
return [x.relation_id for x in self.relations]
|
|
|
|
def set_ingress_address(self):
|
|
for relation in self.relations:
|
|
relation.to_publish_raw["ingress-address"] = self.ingress_address
|
|
relation.to_publish_raw["private-address"] = self.ingress_address
|
|
|
|
def available(self):
|
|
for unit in self.all_joined_units:
|
|
if unit.received['username']:
|
|
return True
|
|
for key in unit.received.keys():
|
|
if "_username" in key:
|
|
return True
|
|
return False
|
|
|
|
@reactive.when('endpoint.{endpoint_name}.joined')
|
|
def joined(self):
|
|
reactive.clear_flag(self.expand_name('{endpoint_name}.available'))
|
|
reactive.set_flag(self.expand_name('{endpoint_name}.connected'))
|
|
self.set_ingress_address()
|
|
|
|
@reactive.when('endpoint.{endpoint_name}.changed')
|
|
def changed(self):
|
|
flags = (
|
|
self.expand_name(
|
|
'endpoint.{endpoint_name}.changed.database'),
|
|
self.expand_name(
|
|
'endpoint.{endpoint_name}.changed.username'),
|
|
self.expand_name(
|
|
'endpoint.{endpoint_name}.changed.hostname'),
|
|
)
|
|
if reactive.all_flags_set(*flags):
|
|
for flag in flags:
|
|
reactive.clear_flag(flag)
|
|
|
|
if self.available():
|
|
reactive.set_flag(self.expand_name('{endpoint_name}.available'))
|
|
else:
|
|
reactive.clear_flag(self.expand_name('{endpoint_name}.available'))
|
|
|
|
@reactive.when_any('endpoint.{endpoint_name}.broken',
|
|
'endpoint.{endpoint_name}.departed')
|
|
def departed(self):
|
|
flags = (
|
|
self.expand_name('{endpoint_name}.connected'),
|
|
self.expand_name('{endpoint_name}.available'),
|
|
)
|
|
for flag in flags:
|
|
reactive.clear_flag(flag)
|
|
|
|
def set_db_connection_info(
|
|
self, relation_id, db_host, password,
|
|
allowed_units=None, prefix=None, wait_timeout=None, db_port=3306,
|
|
ssl_ca=None):
|
|
# Implementations of shared-db pre-date the json encoded era of
|
|
# interface layers. In order not to have to update dozens of charms,
|
|
# publish in raw data
|
|
|
|
# No prefix for db_host and wait_timeout
|
|
self.relations[relation_id].to_publish_raw["db_host"] = db_host
|
|
self.relations[relation_id].to_publish_raw["db_port"] = db_port
|
|
if wait_timeout:
|
|
self.relations[relation_id].to_publish_raw["wait_timeout"] = (
|
|
wait_timeout)
|
|
if ssl_ca:
|
|
self.relations[relation_id].to_publish_raw["ssl_ca"] = ssl_ca
|
|
if not prefix:
|
|
self.relations[relation_id].to_publish_raw["password"] = password
|
|
self.relations[relation_id].to_publish_raw[
|
|
"allowed_units"] = allowed_units
|
|
else:
|
|
self.relations[relation_id].to_publish_raw[
|
|
"{}_password".format(prefix)] = password
|
|
self.relations[relation_id].to_publish_raw[
|
|
"{}_allowed_units".format(prefix)] = allowed_units
|