Repository: opendatacube/datacube-core

Issue:
AttributeError for LocalConfig during replication
### Expected behaviour
SSHTunnel for replication doesn't open due to AttributeError. I have tried to understand the replication process and ran also a separate script that failed with same error. 

### Actual behaviour
```
AttributeError: 'LocalConfig' object has no attribute 'db_hostname'
```

### Steps to reproduce the behaviour

```python
from paramiko import SSHClient, WarningPolicy
from sshtunnel import SSHTunnelForwarder
from datacube.config import LocalConfig, _DEFAULT_CONF
from configparser import ConfigParser

client = SSHClient()
client.load_system_host_keys()
client.set_missing_host_key_policy(WarningPolicy())
client.connect(hostname="host", username="user")
sftp = client.open_sftp()


remote_config = ConfigParser()
remote_config.read_string(_DEFAULT_CONF)
with sftp.open('.datacube.conf') as fin:
    remote_config.read_file(fin)

config = LocalConfig(remote_config)
print(config.db_hostname)

client.close()
```
Same with
```
datacube-simple-replica
```

### Environment information

* Which ``datacube --version`` are you using? 1.7
* What datacube deployment/enviornment are you running against? Conda environment + postgres docker db



Discussion:
@jankovicgd `db_hostname` is an optional parameter and is not guaranteed to be present. When missing, database connection is performed via local Unix socket interface, this can also have implications for authentication (process has to run as a specific user who is authorized to talk to the DB).

I'm not familiar with simple_replica code, but it looks like it makes an assumption that database is accessible via TCP connection, as it sets up port forward with SSHTunnel, so it won't work with databases that are only accessible via Unix socket. 

- Work around is to add `db_hostname = 127.0.0.1` to `.datacube.conf` on the remote system
- Proper fix is to inject `db_hostname` into config when reading it, or report more meaningful error and quit

Either this function should fill defaults:

https://github.com/opendatacube/datacube-core/blob/21e436e88f85e7247504b721d25a8b035731fe49/datacube_apps/simple_replica.py#L104-L109

or this function should do sanity checks on the remote configuration that was read

https://github.com/opendatacube/datacube-core/blob/21e436e88f85e7247504b721d25a8b035731fe49/datacube_apps/simple_replica.py#L83-L88






Hi @Kirill888, thanks for the reply. Forgot to mention that the remote already has a `.datacube.conf` as follows:

```conf
[datacube]
db_database:datacube
db_hostname:127.0.0.1 #also tried localhost
db_username:user
db_password:pass
```


Here is a longer stacktrace.
```
Traceback (most recent call last):
  File "/home/ubuntu/miniconda3/envs/datacube_replication/bin/datacube-simple-replica", line 10, in <module>
    sys.exit(replicate())
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/click/core.py", line 829, in __call__
    return self.main(*args, **kwargs)
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/click/core.py", line 782, in main
    rv = self.invoke(ctx)
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/click/core.py", line 1066, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/click/core.py", line 610, in invoke
    return callback(*args, **kwargs)
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/datacube_apps/simple_replica.py", line 197, in replicate
    replicate_data(config)
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/datacube_apps/simple_replica.py", line 181, in replicate_data
    replicator.run()
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/datacube_apps/simple_replica.py", line 86, in run
    self.connect_to_db()
  File "/home/ubuntu/miniconda3/envs/datacube_replication/lib/python3.6/site-packages/datacube_apps/simple_replica.py", line 115, in connect_to_db
    remote_bind_address=(self.remote_dc_config.db_hostname, int(self.remote_dc_config.db_port)))
AttributeError: 'LocalConfig' object has no attribute 'db_hostname'
```
Can you print `LocalConfig` object, also try adding space after `:` in your config
Added a space, no difference. Seems like its properly read, just not properly added to `LocalConfig`

```
LocalConfig<loaded_from=defaults, environment='datacube', config={'db_database': 'datacube', 'db_hostname': '127.0.0.1', 'db_username': 'postgres', 'db_password': '""', 'index_driver': 'default', 'db_connection_timeout': '60'}>
Traceback (most recent call last):
  File "test.py", line 20, in <module>
    print(config.db_hostname)
AttributeError: 'LocalConfig' object has no attribute 'db_hostname'
```
I see, I think it's because at some point we changed default section to be `default` and not `datacube`, so if you try changing `[datacube]->[default]` in your remote config file it might work.
Hey @Kirill888, I am still getting the same error.

Resolving patch:
diff --git a/datacube_apps/simple_replica.py b/datacube_apps/simple_replica.py
--- a/datacube_apps/simple_replica.py
+++ b/datacube_apps/simple_replica.py
@@ -112,7 +112,8 @@ def connect_to_db(self):
         self.tunnel = SSHTunnelForwarder(
             self.remote_host,
             ssh_username=self.remote_user,
-            remote_bind_address=(self.remote_dc_config.db_hostname, int(self.remote_dc_config.db_port)))
+            remote_bind_address=(self.remote_dc_config.get('db_hostname', '127.0.0.1'),
+                                 int(self.remote_dc_config.get('db_port', 5432))))
         self.tunnel.start()
 
         # pylint: disable=protected-access


Test patch: