private void deriveFunctionProperties(Map<String, RankProfile.RankingExpressionFunction> functions,
                                              Map<String, String> functionProperties,
                                              SerializationContext context) {
            for (Map.Entry<String, RankProfile.RankingExpressionFunction> e : functions.entrySet()) {
                String propertyName = RankingExpression.propertyName(e.getKey());
                if (! context.serializedFunctions().containsKey(propertyName)) {
                    String expressionString = e.getValue().function().getBody().getRoot().toString(context).toString();
                    context.addFunctionSerialization(propertyName, expressionString);

                    e.getValue().function().argumentTypes().entrySet().stream().sorted(Map.Entry.comparingByKey())
                            .forEach(argumentType -> context.addArgumentTypeSerialization(e.getKey(), argumentType.getKey(), argumentType.getValue()));
                }
                e.getValue().function().returnType().ifPresent(t -> context.addFunctionTypeSerialization(e.getKey(), t));

                // else if (e.getValue().function().arguments().isEmpty()) TODO: Enable this check when we resolve all types
                //     throw new IllegalStateException("Type of function '" + e.getKey() + "' is not resolved");
            }
            functionProperties.putAll(context.serializedFunctions());
        }
Creates a raw rank profile from the given rank profile
config-model/src/main/java/com/yahoo/schema/derived/RawRankProfile.java