Repository: sunpy/sunpy

Issue:
HelioviewerClient.data_sources() error
<!-- This comments are hidden when you submit the issue so you do not need to remove them!
Please be sure to check out our contributing guidelines: https://github.com/sunpy/sunpy/blob/master/CONTRIBUTING.rst
Please be sure to check out our code of conduct:
https://github.com/sunpy/sunpy/blob/master/CODE_OF_CONDUCT.rst -->

<!-- Please have a search on our GitHub repository to see if a similar issue has already been posted.
If a similar issue is closed, have a quick look to see if you are satisfied by the resolution.
If not please go ahead and open an issue! -->

### Description
First detected while using `HelioviewerClient.get_closest_image()` for SDO/HMI, working fine in Sunpy 0.9.x but crashed in dev version 1.0.0 when fetching the `sourceId` of the instrument. It seems to come down to `HelioviewerClient.data_sources()`, which impairs any use of `HelioviewerClient.get_closest_image()`  regardless of the instrument, unless `source_id` is used directly instead. 


### Actual behavior
```
---------------------------------------------------------------------------
KeyError                                  Traceback (most recent call last)
<ipython-input-3-a5380a448152> in <module>
      2 kwargs = {'observatory': 'SDO', 'instrument': 'HMI', 'detector': 'HMI', 'measurement': 'continuum'}
      3 # Check how far requested time in metadata is from requested hek time
----> 4 metadata = hv.get_closest_image(hek_time, **kwargs)
 
~/Dev/sunpy-git/sunpy/net/helioviewer.py in get_closest_image(self, date, observatory, instrument, detector, measurement, source_id)
    115         """
    116         if source_id is None:
--> 117             source_id = self._get_source_id((observatory, instrument, detector, measurement))
    118
    119         params = {
 
~/Dev/sunpy-git/sunpy/net/helioviewer.py in _get_source_id(self, key)
    453         Returns source_id based on the key.
    454         """
--> 455         source_id_list = list(partial_key_match(key, self.data_sources))
    456         if len(source_id_list) > 1:  # or maybe != 1
    457             raise KeyError(f"The values used: {key} do not correspond to one source_id "
 
~/anaconda/envs/sunpy-dev/lib/python3.7/site-packages/astropy/utils/decorators.py in __get__(self, obj, owner)
    742                 return val
    743             else:
--> 744                 val = self.fget(obj)
    745                 obj.__dict__[self._key] = val
    746                 return val
 
~/Dev/sunpy-git/sunpy/net/helioviewer.py in data_sources(self)
     54                                 data_sources_dict[(name, inst, wavelength, wave)] = adict['sourceId']
     55                         else:
---> 56                             data_sources_dict[(name, inst, None, wavelength)] = params['sourceId']
     57         # Sort the output for printing purposes
     58         return OrderedDict(sorted(data_sources_dict.items(), key=lambda x: x[1]))
 
KeyError: 'sourceId'
```

### Steps to Reproduce
```
from sunpy.net import helioviewer
from sunpy.time import parse_time
 
hek_time = parse_time('2018/07/15 14:42:46')
 
hv = helioviewer.HelioviewerClient()
kwargs = {'observatory': 'SDO', 'instrument': 'HMI', 'detector': 'HMI', 'measurement': 'continuum'}
# Check how far requested time in metadata is from requested hek time
metadata = hv.get_closest_image(hek_time, **kwargs)
```
or you can simply try fetching the data sources directly:
```
hv.data_sources
```

### System Details
<!-- We at least need to know the SunPy version you are using. -->
<!-- We provide a short function in SunPy that will provide some of the below information. -->
<!-- It is sunpy.util.system_info(), this is optional but strongly recommended. -->

  - SunPy Version: 1.0.0.dev1809+gfa27a3d83
  - Python Version: 3.6 and 3.7
  - OS information: MacOS 10.13.6



Discussion:
I will fix that right now. 

Resolving patch:
diff --git a/sunpy/net/helioviewer.py b/sunpy/net/helioviewer.py
--- a/sunpy/net/helioviewer.py
+++ b/sunpy/net/helioviewer.py
@@ -48,12 +48,12 @@ def data_sources(self):
             else:
                 for inst, detect in observ.items():
                     for wavelength, params in detect.items():
-                        # These observatories and wavelengths are nested by more one level
-                        if name in ["Hinode", "STEREO_A", "STEREO_B"] or wavelength in ["C2", "C3"]:
+                        if 'sourceId' in params:
+                            data_sources_dict[(name, inst, None, wavelength)] = params['sourceId']
+                        else:
                             for wave, adict in params.items():
                                 data_sources_dict[(name, inst, wavelength, wave)] = adict['sourceId']
-                        else:
-                            data_sources_dict[(name, inst, None, wavelength)] = params['sourceId']
+
         # Sort the output for printing purposes
         return OrderedDict(sorted(data_sources_dict.items(), key=lambda x: x[1]))
 
@@ -453,9 +453,8 @@ def _get_source_id(self, key):
         Returns source_id based on the key.
         """
         source_id_list = list(partial_key_match(key, self.data_sources))
-        if len(source_id_list) > 1:  # or maybe != 1
+        if len(source_id_list) != 1:
             raise KeyError(f"The values used: {key} do not correspond to one source_id "
                            f"but {len(source_id_list)} source_id(s)."
                            " Please check the list using HelioviewerClient.data_sources.")
         return source_id_list[0]
-            


Test patch: