type_possible_types(agooErr err, gqlDoc doc, gqlCobj obj, gqlField field, gqlSel sel, gqlValue result, int depth) {
    gqlType		type = (gqlType)obj->ptr;
    const char		*key = sel->name;
    gqlTypeLink    	tl;
    gqlValue		co;
    gqlValue		list;
    struct _gqlField	cf;
    struct _gqlCobj	child = { .clas = &type_class };
    int			d2 = depth + 1;

    if (NULL != sel->alias) {
	key = sel->alias;
    }
    memset(&cf, 0, sizeof(cf));
    cf.type = sel->type->base;

    switch (type->kind) {
    case GQL_INTERFACE: {
	list = gql_list_create(err, NULL);
	struct _posCtx	pc = {
	    .err = err,
	    .doc = doc,
	    .sel = sel,
	    .depth = depth + 1,
	    .list = list,
	    .interface = type,
	    .child = &child,
	    .cf = &cf,
	};
	if (NULL == list ||
	    AGOO_ERR_OK != gql_object_set(err, result, key, list)) {
	    return err->code;
	}
	gql_type_iterate(possible_cb, &pc);
	break;
    }
    case GQL_UNION:
	if (NULL == (list = gql_list_create(err, NULL)) ||
	    AGOO_ERR_OK != gql_object_set(err, result, key, list)) {
	    return err->code;
	}
	for (tl = type->types; NULL != tl; tl = tl->next) {
	    if (NULL == (co = gql_object_create(err)) ||
		AGOO_ERR_OK != gql_list_append(err, list, co)) {
		return err->code;
	    }
	    child.ptr = tl->type;
	    if (AGOO_ERR_OK != gql_eval_sels(err, doc, (gqlRef)&child, &cf, sel->sels, co, d2)) {
		return err->code;
	    }
	}
	break;
    default:
	if (NULL == (list = gql_null_create(err)) ||
	    AGOO_ERR_OK != gql_object_set(err, result, key, list)) {
	    return err->code;
	}
	break;
    }
    return AGOO_ERR_OK;
}
type_possible_types(agooErr err, gqlDoc doc, gqlCobj obj, gqlField field, gqlSel sel, gqlValue result, int depth) {
    gqlType		type = (gqlType)obj->ptr;
    const char		*key = sel->name;
    gqlTypeLink    	tl;
    gqlValue		co;
    gqlValue		list;
    struct _gqlField	cf;
    struct _gqlCobj	child = { .clas = &type_class };
    int			d2 = depth + 1;

    if (NULL != sel->alias) {
	key = sel->alias;
    }
    memset(&cf, 0, sizeof(cf));
    cf.type = sel->type->base;

    switch (type->kind) {
    case GQL_INTERFACE: {
	list = gql_list_create(err, NULL);
	struct _posCtx	pc = {
	    .err = err,
	    .doc = doc,
	    .sel = sel,
	    .depth = depth + 1,
	    .list = list,
	    .interface = type,
	    .child = &child,
	    .cf = &cf,
	};
	if (NULL == list ||
	    AGOO_ERR_OK != gql_object_set(err, result, key, list)) {
	    return err->code;
	}
	gql_type_iterate(possible_cb, &pc);
	break;
    }
    case GQL_UNION:
	if (NULL == (list = gql_list_create(err, NULL)) ||
	    AGOO_ERR_OK != gql_object_set(err, result, key, list)) {
	    return err->code;
	}
	for (tl = type->types; NULL != tl; tl = tl->next) {
	    if (NULL == (co = gql_object_create(err)) ||
		AGOO_ERR_OK != gql_list_append(err, list, co)) {
		return err->code;
	    }
	    child.ptr = tl->type;
	    if (AGOO_ERR_OK != gql_eval_sels(err, doc, (gqlRef)&child, &cf, sel->sels, co, d2)) {
		return err->code;
	    }
	}
	break;
    default:
	if (NULL == (list = gql_null_create(err)) ||
	    AGOO_ERR_OK != gql_object_set(err, result, key, list)) {
	    return err->code;
	}
	break;
    }
    return AGOO_ERR_OK;
}