def dict2row(d, model, rel=None, exclude=None, exclude_pk=None,
             exclude_underscore=None, only=None, fk_suffix=None):
    if not isinstance(d, dict):
        raise TypeError('Source must be instance of dict, got %s instead' %
                        type(d).__name__)
    row = model()
    mapper = get_mapper(row)
    if rel is None:
        rel = getattr(row, ATTR_REL, DEFAULT_REL)
    if exclude is None:
        exclude = getattr(row, ATTR_EXCLUDE, DEFAULT_EXCLUDE)
    if exclude_pk is None:
        exclude_pk = getattr(row, ATTR_EXCLUDE_PK, DEFAULT_EXCLUDE_PK)
    if exclude_underscore is None:
        exclude_underscore = getattr(row, ATTR_EXCLUDE_UNDERSCORE,
                                     DEFAULT_EXCLUDE_UNDERSCORE)
    if only is None:
        only = getattr(row, ATTR_ONLY, DEFAULT_ONLY)
    if fk_suffix is None:
        fk_suffix = getattr(row, ATTR_FK_SUFFIX, DEFAULT_FK_SUFFIX)
    for c in mapper.columns.keys() + mapper.synonyms.keys():
        if c not in d or c in exclude or \
                check_exclude_pk(c, exclude_pk, fk_suffix=fk_suffix) or \
                check_exclude_underscore(c, exclude_underscore) or \
                check_only(c, only):
            continue
        setattr(row, c, d[c])
    for r in mapper.relationships.keys():
        if r not in d or r not in rel or check_only(r, only):
            continue
        kwargs = dict(rel=rel, exclude=exclude, exclude_pk=exclude_pk,
                      exclude_underscore=exclude_underscore, only=only,
                      fk_suffix=fk_suffix)
        if isinstance(d[r], list):
            setattr(row, r, collections.InstrumentedList())
            for i in d[r]:
                getattr(row, r).append(dict2row(i, rel[r], **kwargs))
        else:
            if not exclude_pk:
                rpk = d[r].get('id') if isinstance(d[r], dict) else None
                setattr(row, r + fk_suffix, rpk)
            setattr(row, r, dict2row(d[r], rel[r], **kwargs))
    return row