protected U convertAttributesToProfile(final List<Map<String, Object>> listStorageAttributes, final String username) {
        if (listStorageAttributes == null || listStorageAttributes.size() == 0) {
            return null;
        }
        val storageAttributes = listStorageAttributes.get(0);

        val linkedId = (String) storageAttributes.get(LINKEDID);
        // legacy mode: only read the defined attributes
        if (isLegacyMode()) {
            val profile = (U) getProfileDefinition().newProfile();
            for (val attributeName : attributeNames) {
                getProfileDefinition().convertAndAdd(profile, PROFILE_ATTRIBUTE, attributeName, storageAttributes.get(attributeName));
            }
            val retrievedUsername = storageAttributes.get(getUsernameAttribute());
            if (retrievedUsername != null) {
                profile.setId(ProfileHelper.sanitizeIdentifier(retrievedUsername));
            } else {
                profile.setId(username);
            }
            if (StringUtils.isNotBlank(linkedId)) {
                profile.setLinkedId(linkedId);
            }
            return profile;
        } else {
            // new behaviour (>= v2.0): read the serialized profile
            val serializedProfile = (String) storageAttributes.get(SERIALIZED_PROFILE);
            if (serializedProfile == null) {
                throw new TechnicalException("No serialized profile found. You should certainly define the explicit attribute names you " +
                    "want to retrieve");
            }
            val profile = (U) serializer.deserializeFromString(serializedProfile);
            if (profile == null) {
                throw new TechnicalException("No deserialized profile available. You should certainly define the explicit attribute " +
                    "names you want to retrieve");
            }
            val id = storageAttributes.get(getIdAttribute());
            if (StringUtils.isBlank(profile.getId()) && id != null) {
                profile.setId(ProfileHelper.sanitizeIdentifier(id));
            }
            if (StringUtils.isBlank(profile.getLinkedId()) && StringUtils.isNotBlank(linkedId)) {
                profile.setLinkedId(linkedId);
            }
            return profile;
        }
    }
Convert the list of map of attributes from the storage into a profile.

@param listStorageAttributes the list of map of attributes
@param username the username used for login
@return the profile
pac4j-core/src/main/java/org/pac4j/core/profile/service/AbstractProfileService.java