Initial commit
This commit is contained in:
commit
79c265c408
|
@ -0,0 +1,82 @@
|
|||
# Overview
|
||||
|
||||
This interface layer handles the communication with MySQL via the `mysql-shared`
|
||||
interface protocol.
|
||||
|
||||
# Usage
|
||||
|
||||
## Requires
|
||||
|
||||
The interface layer will set the following states, as appropriate:
|
||||
|
||||
* `{relation_name}.connected` The relation is established, but MySQL has not
|
||||
been provided the database information.
|
||||
* `{relation_name}.available` MySQL is ready for use. You can get the base
|
||||
connection information via the following methods:
|
||||
* `allowed_units()`
|
||||
* `database()`
|
||||
* `db_host()`
|
||||
* `hostname()`
|
||||
* `username()`
|
||||
* `password()`
|
||||
* `{relation_name}.available.access_network` MySQL access network is ready
|
||||
for use. You can get this optional connection information via the following
|
||||
method:
|
||||
* `access_network()`
|
||||
* `{relation_name}.available.ssl` MySQL ssl data is ready for use. You can
|
||||
get this optional connection information via the following methods:
|
||||
* `ssl_ca()`
|
||||
* `ssl_cert()`
|
||||
* `ssl_key()`
|
||||
|
||||
For example:
|
||||
|
||||
```python
|
||||
from charmhelpers.core.hookenv import log, status_set, unit_get
|
||||
from charms.reactive import when, when_not
|
||||
|
||||
|
||||
@when('database.connected')
|
||||
def setup_database(database):
|
||||
host = unit_get('private-address')
|
||||
database.configure('mydatabase', 'myusername', host, prefix="first")
|
||||
database.configure('mydatabase2', 'myusername2', host, prefix="second")
|
||||
|
||||
@when('database.available')
|
||||
def use_database(database):
|
||||
# base data provided by our charm layer
|
||||
log("first_database=%s" % database.database("first"))
|
||||
log("first_username=%s" % database.username("first"))
|
||||
log("first_hostname=%s" % database.hostname("first"))
|
||||
log("second_database=%s" % database.database("second"))
|
||||
log("second_username=%s" % database.username("second"))
|
||||
log("second_hostname=%s" % database.hostname("second"))
|
||||
|
||||
# base data provided by mysql
|
||||
log("db_host=%s" % database.db_host())
|
||||
log("first_password=%s" % database.password("first"))
|
||||
log("first_allowed_units=%s" % database.allowed_units("first"))
|
||||
log("second_password=%s" % database.password("second"))
|
||||
log("second_allowed_units=%s" % database.allowed_units("second"))
|
||||
|
||||
@when('database.available.access_network')
|
||||
def use_database_access_network(database):
|
||||
# optional data provided by mysql
|
||||
log("access-network=%s" % database.access_network())
|
||||
|
||||
@when('database.available.ssl')
|
||||
def use_database_ssl(database):
|
||||
# optional data provided by mysql
|
||||
log("ssl_ca=%s" % database.ssl_ca())
|
||||
log("ssl_cert=%s" % database.ssl_cert())
|
||||
log("ssl_key=%s" % database.ssl_key())
|
||||
|
||||
@when('database.connected')
|
||||
@when_not('database.available')
|
||||
def waiting_mysql(database):
|
||||
status_set('waiting', 'Waiting for MySQL')
|
||||
|
||||
@when('database.connected', 'database.available')
|
||||
def unit_ready(database):
|
||||
status_set('active', 'Unit is ready')
|
||||
```
|
|
@ -0,0 +1,9 @@
|
|||
Format: http://www.debian.org/doc/packaging-manuals/copyright-format/1.0
|
||||
|
||||
Files: *
|
||||
Copyright: 2015, Canonical Ltd.
|
||||
License: GPL-3
|
||||
|
||||
License: GPL-3
|
||||
On Debian GNU/Linux system you can find the complete text of the
|
||||
GPL-3 license in '/usr/share/common-licenses/GPL-3'
|
|
@ -0,0 +1,3 @@
|
|||
name: mysql-shared
|
||||
summary: Interface for intergrating with MySQL
|
||||
maintainer: OpenStack Charmers <openstack-charmers@lists.ubuntu.com>
|
|
@ -0,0 +1,153 @@
|
|||
from charms.reactive import RelationBase
|
||||
from charms.reactive import hook
|
||||
from charms.reactive import scopes
|
||||
|
||||
|
||||
class MySQLSharedRequires(RelationBase):
|
||||
scope = scopes.GLOBAL
|
||||
|
||||
# These remote data fields will be automatically mapped to accessors
|
||||
# with a basic documentation string provided.
|
||||
auto_accessors = ['access-network', 'db_host',
|
||||
'ssl_ca', 'ssl_cert', 'ssl_key']
|
||||
|
||||
@hook('{requires:mysql-shared}-relation-joined')
|
||||
def joined(self):
|
||||
self.set_state('{relation_name}.connected')
|
||||
|
||||
@hook('{requires:mysql-shared}-relation-changed')
|
||||
def changed(self):
|
||||
if self.base_data_complete():
|
||||
self.set_state('{relation_name}.available')
|
||||
if self.access_network_data_complete():
|
||||
self.set_state('{relation_name}.available.access_network')
|
||||
if self.ssl_data_complete():
|
||||
self.set_state('{relation_name}.available.ssl')
|
||||
|
||||
@hook('{requires:mysql-shared}-relation-{broken,departed}')
|
||||
def departed(self):
|
||||
self.remove_state('{relation_name}.connected')
|
||||
self.remove_state('{relation_name}.available')
|
||||
self.remove_state('{relation_name}.available.access_network')
|
||||
self.remove_state('{relation_name}.available.ssl')
|
||||
|
||||
def configure(self, database, username, hostname, prefix=None):
|
||||
"""
|
||||
Called by charm layer that uses this interface to configure a database.
|
||||
"""
|
||||
if prefix:
|
||||
relation_info = {
|
||||
prefix + '_database': database,
|
||||
prefix + '_username': username,
|
||||
prefix + '_hostname': hostname,
|
||||
}
|
||||
self.set_prefix(prefix)
|
||||
else:
|
||||
relation_info = {
|
||||
'database': database,
|
||||
'username': username,
|
||||
'hostname': hostname,
|
||||
}
|
||||
self.set_remote(**relation_info)
|
||||
self.set_local(**relation_info)
|
||||
|
||||
def set_prefix(self, prefix):
|
||||
"""
|
||||
Store all of the database prefixes in a list.
|
||||
"""
|
||||
prefixes = self.get_local('prefixes')
|
||||
if prefixes:
|
||||
if prefix not in prefixes:
|
||||
self.set_local('prefixes', prefixes + [prefix])
|
||||
else:
|
||||
self.set_local('prefixes', [prefix])
|
||||
|
||||
def get_prefixes(self):
|
||||
"""
|
||||
Return the list of saved prefixes.
|
||||
"""
|
||||
return self.get_local('prefixes')
|
||||
|
||||
def database(self, prefix=None):
|
||||
"""
|
||||
Return a configured database name.
|
||||
"""
|
||||
if prefix:
|
||||
return self.get_local(prefix + '_database')
|
||||
return self.get_local('database')
|
||||
|
||||
def username(self, prefix=None):
|
||||
"""
|
||||
Return a configured username.
|
||||
"""
|
||||
if prefix:
|
||||
return self.get_local(prefix + '_username')
|
||||
return self.get_local('username')
|
||||
|
||||
def hostname(self, prefix=None):
|
||||
"""
|
||||
Return a configured hostname.
|
||||
"""
|
||||
if prefix:
|
||||
return self.get_local(prefix + '_hostname')
|
||||
return self.get_local('hostname')
|
||||
|
||||
def password(self, prefix=None):
|
||||
"""
|
||||
Return a database password.
|
||||
"""
|
||||
if prefix:
|
||||
return self.get_remote(prefix + '_password')
|
||||
return self.get_remote('password')
|
||||
|
||||
def allowed_units(self, prefix=None):
|
||||
"""
|
||||
Return a database's allowed_units.
|
||||
"""
|
||||
if prefix:
|
||||
return self.get_remote(prefix + '_allowed_units')
|
||||
return self.get_remote('allowed_units')
|
||||
|
||||
def base_data_complete(self):
|
||||
"""
|
||||
Check if required base data is complete.
|
||||
"""
|
||||
data = {
|
||||
'db_host': self.db_host(),
|
||||
}
|
||||
if self.get_prefixes():
|
||||
suffixes = ['_password', '_allowed_units']
|
||||
for prefix in self.get_prefixes():
|
||||
for suffix in suffixes:
|
||||
key = prefix + suffix
|
||||
data[key] = self.get_remote(key)
|
||||
else:
|
||||
data['password'] = self.get_remote('password')
|
||||
data['allowed_units'] = self.get_remote('allowed_units')
|
||||
if all(data.values()):
|
||||
return True
|
||||
return False
|
||||
|
||||
def access_network_data_complete(self):
|
||||
"""
|
||||
Check if optional access network data provided by mysql is complete.
|
||||
"""
|
||||
data = {
|
||||
'access-network': self.access_network(),
|
||||
}
|
||||
if all(data.values()):
|
||||
return True
|
||||
return False
|
||||
|
||||
def ssl_data_complete(self):
|
||||
"""
|
||||
Check if optional ssl data provided by mysql is complete.
|
||||
"""
|
||||
# Note: ssl_ca can also be set but isn't required
|
||||
data = {
|
||||
'ssl_cert': self.ssl_cert(),
|
||||
'ssl_key': self.ssl_key(),
|
||||
}
|
||||
if all(data.values()):
|
||||
return True
|
||||
return False
|
Loading…
Reference in New Issue