'Create a database of VO services from VO registry URL.
This is described in detail in :ref:`vo-sec-validator-build-db`,
except for the ``validate_xxx`` keys that are added by the
validator itself.
Parameters
registry_url : str
URL of VO registry that returns a VO Table.
For example, see ``astropy.vo.validator.validate.CS_MSTR_LIST``.
Pedantic is automatically set to `False` for parsing.
timeout : number
Temporarily set `astropy.utils.data.Conf.remote_timeout` to
this value to avoid time out error while reading the
entire registry.
kwargs : dict
Keywords accepted by
:func:`~astropy.utils.data.get_readable_fileobj`.
Returns
db : `VOSDatabase`
Database from given registry.
Raises
VOSError
Invalid VO registry.'

@classmethod
def from_registry(cls, registry_url, timeout=60, **kwargs):

    with data_conf.set_temp(u'remote_timeout', timeout):
        with get_readable_fileobj(registry_url, **kwargs) as fd:
            tab_all = parse_single_table(fd, pedantic=False)
    compulsory_fields = [u'title', u'accessURL']
    cat_fields = tab_all.array.dtype.names
    for field in compulsory_fields:
        if (field not in cat_fields):
            raise VOSError(u'"{0}"    is    missing    from    registry.'.format(field))
    title_counter = defaultdict(int)
    title_fmt = u'{0}    {1}'
    db = cls.create_empty()
    for arr in tab_all.array.data:
        cur_cat = {}
        cur_key = u''
        for field in cat_fields:
            if (field == u'title'):
                cur_title = arr[u'title']
                title_counter[cur_title] += 1
                if isinstance(cur_title, bytes):
                    cur_key = title_fmt.format(cur_title.decode(u'utf-8'), title_counter[cur_title])
                else:
                    cur_key = title_fmt.format(cur_title, title_counter[cur_title])
            if (field == u'accessURL'):
                cur_cat[u'url'] = unescape_all(arr[u'accessURL'])
            else:
                cur_cat[field] = arr[field]
        cur_cat[u'duplicatesIgnored'] = 0
        dup_keys = db._url_keys[cur_cat[u'url']]
        if (len(dup_keys) < 1):
            db.add_catalog(cur_key, VOSCatalog(cur_cat), allow_duplicate_url=False)
        else:
            db._catalogs[dup_keys[0]][u'duplicatesIgnored'] += 1
            warnings.warn(u'{0}    is    thrown    out    because    it    has    same    access    URL    as    {1}.'.format(cur_key, dup_keys[0]), AstropyUserWarning)
    return db
