diff --git a/libs/utils/gtest/src/ArrayListTestSuite.cc b/libs/utils/gtest/src/ArrayListTestSuite.cc index aa0a1a7e9..7af65ac5a 100644 --- a/libs/utils/gtest/src/ArrayListTestSuite.cc +++ b/libs/utils/gtest/src/ArrayListTestSuite.cc @@ -495,3 +495,20 @@ TEST_F(ArrayListTestSuite, ReallocTest) { EXPECT_EQ(i, celix_arrayList_getLong(list, i)); } } + +TEST_F(ArrayListTestSuite, ElementTypeToStringTest) { + EXPECT_STREQ("CELIX_ARRAY_LIST_ELEMENT_TYPE_UNDEFINED", + celix_arrayList_elementTypeToString(CELIX_ARRAY_LIST_ELEMENT_TYPE_UNDEFINED)); + EXPECT_STREQ("CELIX_ARRAY_LIST_ELEMENT_TYPE_POINTER", + celix_arrayList_elementTypeToString(CELIX_ARRAY_LIST_ELEMENT_TYPE_POINTER)); + EXPECT_STREQ("CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING", + celix_arrayList_elementTypeToString(CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING)); + EXPECT_STREQ("CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG", + celix_arrayList_elementTypeToString(CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG)); + EXPECT_STREQ("CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE", + celix_arrayList_elementTypeToString(CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE)); + EXPECT_STREQ("CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL", + celix_arrayList_elementTypeToString(CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL)); + EXPECT_STREQ("CELIX_ARRAY_LIST_ELEMENT_TYPE_UNDEFINED", + celix_arrayList_elementTypeToString((celix_array_list_element_type_t)100 /*non existing*/)); +} diff --git a/libs/utils/gtest/src/CxxPropertiesTestSuite.cc b/libs/utils/gtest/src/CxxPropertiesTestSuite.cc index 2fad0b37f..1e65bb4f7 100644 --- a/libs/utils/gtest/src/CxxPropertiesTestSuite.cc +++ b/libs/utils/gtest/src/CxxPropertiesTestSuite.cc @@ -248,11 +248,11 @@ TEST_F(CxxPropertiesTestSuite, ArrayListTest) { EXPECT_EQ(5, props.size()); // Test get type - EXPECT_EQ(props.getType("key1"), celix::Properties::ValueType::StringArray); - EXPECT_EQ(props.getType("key2"), celix::Properties::ValueType::LongArray); - EXPECT_EQ(props.getType("key3"), celix::Properties::ValueType::DoubleArray); - EXPECT_EQ(props.getType("key4"), celix::Properties::ValueType::BooleanArray); - EXPECT_EQ(props.getType("key5"), celix::Properties::ValueType::VersionArray); + EXPECT_EQ(props.getType("key1"), celix::Properties::ValueType::Vector); + EXPECT_EQ(props.getType("key2"), celix::Properties::ValueType::Vector); + EXPECT_EQ(props.getType("key3"), celix::Properties::ValueType::Vector); + EXPECT_EQ(props.getType("key4"), celix::Properties::ValueType::Vector); + EXPECT_EQ(props.getType("key5"), celix::Properties::ValueType::Vector); // Test getAs with valid key auto strings = props.getAsStringVector("key1"); diff --git a/libs/utils/gtest/src/PropertiesErrorInjectionTestSuite.cc b/libs/utils/gtest/src/PropertiesErrorInjectionTestSuite.cc index f1dbd9c3d..da2e2af72 100644 --- a/libs/utils/gtest/src/PropertiesErrorInjectionTestSuite.cc +++ b/libs/utils/gtest/src/PropertiesErrorInjectionTestSuite.cc @@ -311,7 +311,7 @@ TEST_F(PropertiesErrorInjectionTestSuite, GetAsArrayWithArrayListCopyFailedTest) celix_properties_setArrayList(props, "versionArray", versionList); // When a celix_arrayList_createWithOptions error injection is set for celix_properties_getAsStringArrayList - celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsStringArrayList, 0, nullptr); + celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsStringArrayList, 1, nullptr); // Then the celix_properties_getAsStringArrayList call fails celix_array_list_t* strings = nullptr; @@ -320,7 +320,7 @@ TEST_F(PropertiesErrorInjectionTestSuite, GetAsArrayWithArrayListCopyFailedTest) ASSERT_EQ(nullptr, strings); //When a celix_arrayList_copy error injection is set for celix_properties_getAsLongArrayList - celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsLongArrayList, 0, nullptr); + celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsLongArrayList, 1, nullptr); // Then the celix_properties_getAsLongArrayList call fails celix_array_list_t* longs = nullptr; @@ -329,7 +329,7 @@ TEST_F(PropertiesErrorInjectionTestSuite, GetAsArrayWithArrayListCopyFailedTest) ASSERT_EQ(nullptr, longs); //When a celix_arrayList_copy error injection is set for celix_properties_getAsDoubleArrayList - celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsDoubleArrayList, 0, nullptr); + celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsDoubleArrayList, 1, nullptr); // Then the celix_properties_getAsDoubleArrayList call fails celix_array_list_t* doubles = nullptr; @@ -338,7 +338,7 @@ TEST_F(PropertiesErrorInjectionTestSuite, GetAsArrayWithArrayListCopyFailedTest) ASSERT_EQ(nullptr, doubles); //When a celix_arrayList_copy error injection is set for celix_properties_getAsBoolArrayList - celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsBoolArrayList, 0, nullptr); + celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsBoolArrayList, 1, nullptr); // Then the celix_properties_getAsBoolArrayList call fails celix_array_list_t* bools = nullptr; @@ -347,7 +347,7 @@ TEST_F(PropertiesErrorInjectionTestSuite, GetAsArrayWithArrayListCopyFailedTest) ASSERT_EQ(nullptr, bools); //When a celix_arrayList_createWithOptions error injection is set for celix_properties_getAsVersionArrayList - celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsVersionArrayList, 0, nullptr); + celix_ei_expect_celix_arrayList_copy((void*)celix_properties_getAsVersionArrayList, 1, nullptr); // Then the celix_properties_getAsVersionArrayList call fails celix_array_list_t* versions = nullptr; diff --git a/libs/utils/gtest/src/PropertiesTestSuite.cc b/libs/utils/gtest/src/PropertiesTestSuite.cc index ef2a54af5..a426bdde0 100644 --- a/libs/utils/gtest/src/PropertiesTestSuite.cc +++ b/libs/utils/gtest/src/PropertiesTestSuite.cc @@ -904,8 +904,50 @@ TEST_F(PropertiesTestSuite, GetTypedArrayListTest) { EXPECT_EQ(doubleList, retrievedDoubleList2); EXPECT_EQ(boolList, retrievedBoolList2); EXPECT_EQ(versionList, retrievedVersionList2); + + //When using the celix_properties_getArrayList function to retrieve the array lists + const auto* retrievedStringList3 = celix_properties_getArrayList(props, "stringList", nullptr); + const auto* retrievedLongList3 = celix_properties_getArrayList(props, "longList", nullptr); + const auto* retrievedDoubleList3 = celix_properties_getArrayList(props, "doubleList", nullptr); + const auto* retrievedBoolList3 = celix_properties_getArrayList(props, "boolList", nullptr); + const auto* retrievedVersionList3 = celix_properties_getArrayList(props, "versionList", nullptr); + + //Then the retrieved array lists should be the same as the original array lists + EXPECT_TRUE(celix_arrayList_equals(stringList, retrievedStringList3)); + EXPECT_TRUE(celix_arrayList_equals(longList, retrievedLongList3)); + EXPECT_TRUE(celix_arrayList_equals(doubleList, retrievedDoubleList3)); + EXPECT_TRUE(celix_arrayList_equals(boolList, retrievedBoolList3)); + EXPECT_TRUE(celix_arrayList_equals(versionList, retrievedVersionList3)); +} + +TEST_F(PropertiesTestSuite, GetAsTypedArrayListWithInvalidDefault) { + celix_autoptr(celix_array_list_t) ptrList = celix_arrayList_createPointerArray(); + celix_autoptr(celix_properties_t) props = celix_properties_create(); + + celix_array_list_t* outList = nullptr; + + EXPECT_EQ(CELIX_ILLEGAL_ARGUMENT, celix_properties_getAsStringArrayList(nullptr, "aKey", ptrList, &outList)); + EXPECT_EQ(1, celix_err_getErrorCount()); + celix_err_resetErrors(); + + EXPECT_EQ(CELIX_ILLEGAL_ARGUMENT, celix_properties_getAsLongArrayList(nullptr, "aKey", ptrList, &outList)); + EXPECT_EQ(1, celix_err_getErrorCount()); + celix_err_resetErrors(); + + EXPECT_EQ(CELIX_ILLEGAL_ARGUMENT, celix_properties_getAsDoubleArrayList(nullptr, "aKey", ptrList, &outList)); + EXPECT_EQ(1, celix_err_getErrorCount()); + celix_err_resetErrors(); + + EXPECT_EQ(CELIX_ILLEGAL_ARGUMENT, celix_properties_getAsBoolArrayList(nullptr, "aKey", ptrList, &outList)); + EXPECT_EQ(1, celix_err_getErrorCount()); + celix_err_resetErrors(); + + EXPECT_EQ(CELIX_ILLEGAL_ARGUMENT, celix_properties_getAsVersionArrayList(nullptr, "aKey", ptrList, &outList)); + EXPECT_EQ(1, celix_err_getErrorCount()); + celix_err_resetErrors(); } + TEST_F(PropertiesTestSuite, SetArrayListWithIllegalArgumentsTest) { //Given a properties object celix_autoptr(celix_properties_t) props = celix_properties_create(); diff --git a/libs/utils/include/celix/Properties.h b/libs/utils/include/celix/Properties.h index c1d0ac465..bc46b18e0 100644 --- a/libs/utils/include/celix/Properties.h +++ b/libs/utils/include/celix/Properties.h @@ -126,17 +126,14 @@ namespace celix { * @brief Enum representing the possible types of a property value. */ enum class ValueType { - Unset, /**< Property value is not set. */ - String, /**< Property value is a string. */ - Long, /**< Property value is a long integer. */ - Double, /**< Property value is a double. */ - Bool, /**< Property value is a boolean. */ - Version, /**< Property value is a Celix version. */ - LongArray, /**< Property value is an array of long integers. */ - DoubleArray, /**< Property value is an array of doubles. */ - BooleanArray, /**< Property value is an array of booleans. */ - VersionArray, /**< Property value is an array of Celix versions. */ - StringArray /**< Property value is an array of strings. */ + Unset, /**< Property value is not set. */ + String, /**< Property value is a string. */ + Long, /**< Property value is a long integer. */ + Double, /**< Property value is a double. */ + Bool, /**< Property value is a boolean. */ + Version, /**< Property value is a Celix version. */ + Vector, /**< Property value is a vector of long integers, doubles, booleans, celix::Version or + string. */ }; class ValueRef { @@ -995,16 +992,8 @@ namespace celix { return ValueType::Bool; case CELIX_PROPERTIES_VALUE_TYPE_VERSION: return ValueType::Version; - case CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY: - return ValueType::LongArray; - case CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY: - return ValueType::DoubleArray; - case CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY: - return ValueType::BooleanArray; - case CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY: - return ValueType::VersionArray; - case CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY: - return ValueType::StringArray; + case CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST: + return ValueType::Vector; default: /*unset*/ return ValueType::Unset; } diff --git a/libs/utils/include/celix_array_list.h b/libs/utils/include/celix_array_list.h index 47262f3e3..6c41f2af2 100644 --- a/libs/utils/include/celix_array_list.h +++ b/libs/utils/include/celix_array_list.h @@ -678,6 +678,15 @@ bool celix_arrayList_equals(const celix_array_list_t* listA, const celix_array_l CELIX_UTILS_EXPORT celix_array_list_t* celix_arrayList_copy(const celix_array_list_t* list); +/** + * @brief Returns the element type as a string. + * The returned string is owned by the celix_arrayList library and should not be freed. + * @param type The element type. + * @return The element type as a string. Returns "Undefined" if the element type is not recognized. + */ +CELIX_UTILS_EXPORT +const char* celix_arrayList_elementTypeToString(celix_array_list_element_type_t type); + #ifdef __cplusplus } #endif diff --git a/libs/utils/include/celix_properties.h b/libs/utils/include/celix_properties.h index e3c408b2b..4c23f2499 100644 --- a/libs/utils/include/celix_properties.h +++ b/libs/utils/include/celix_properties.h @@ -56,17 +56,17 @@ extern "C" { * @brief Enum representing the possible types of a property value. */ typedef enum celix_properties_value_type { - CELIX_PROPERTIES_VALUE_TYPE_UNSET = 0, /**< Property value is not set. */ - CELIX_PROPERTIES_VALUE_TYPE_STRING = 1, /**< Property value is a string. */ - CELIX_PROPERTIES_VALUE_TYPE_LONG = 2, /**< Property value is a long integer. */ - CELIX_PROPERTIES_VALUE_TYPE_DOUBLE = 3, /**< Property value is a double. */ - CELIX_PROPERTIES_VALUE_TYPE_BOOL = 4, /**< Property value is a boolean. */ - CELIX_PROPERTIES_VALUE_TYPE_VERSION = 5, /**< Property value is a Celix version. */ - CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY = 6, /**< Property value is an array of strings. */ - CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY = 7, /**< Property value is an array of longs. */ - CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY = 8, /**< Property value is an array of doubles. */ - CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY = 9, /**< Property value is an array of booleans. */ - CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY = 10, /**< Property value is an array of Celix versions. */ + CELIX_PROPERTIES_VALUE_TYPE_UNSET = 0, /**< Property value is not set. */ + CELIX_PROPERTIES_VALUE_TYPE_STRING = 1, /**< Property value is a string. */ + CELIX_PROPERTIES_VALUE_TYPE_LONG = 2, /**< Property value is a long integer. */ + CELIX_PROPERTIES_VALUE_TYPE_DOUBLE = 3, /**< Property value is a double. */ + CELIX_PROPERTIES_VALUE_TYPE_BOOL = 4, /**< Property value is a boolean. */ + CELIX_PROPERTIES_VALUE_TYPE_VERSION = 5, /**< Property value is a Celix version. */ + CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST = + 6, /**< Property value is an array list. The element type of the array list can be + CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING, CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG, + CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE, CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL or + CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION. */ } celix_properties_value_type_e; /** @@ -565,6 +565,32 @@ CELIX_UTILS_EXPORT celix_status_t celix_properties_assignArrayList(celix_propert const char* key, celix_array_list_t* values); +/** + * @brief Get the property value as an array without copying. + * + * This function provides a non-owning, read-only access to a array property value. + * It returns a const pointer to the array. If the property is not set or its value is not an array, + * the default value is returned. + * + * The returned array will have a element type of: + * - CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING + * - CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG + * - CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE + * - CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL + * - CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION + * + * Note that users should check the element type of the returned array list to determine the type of the elements. + * + * @param[in] properties The property set to search. + * @param[in] key The key of the property to get. + * @param[in] defaultValue The value to return if the property is not set or its value is not an array list. + * @return A const pointer to the array list property value, or the default value if the property + * is not set or its value is not an array list. The returned pointer should not be modified or freed. + */ +CELIX_UTILS_EXPORT const celix_array_list_t* celix_properties_getArrayList(const celix_properties_t* properties, + const char* key, + const celix_array_list_t* defaultValue); + /** * @brief Get a property value as an array of longs. * @@ -574,14 +600,19 @@ CELIX_UTILS_EXPORT celix_status_t celix_properties_assignArrayList(celix_propert * If the property is not set, its value is not an array of longs or its value cannot be converted to a long array, * the default value is returned as a copy. * + * An celix err is logged if the default value is needed and not an array list with long values. + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The default value to return if the property is not set or its value is not an array of longs. * @param[out] list A copy of the found list, a new array list with long values or a copy of the default value if the * property is not set, its value is not an array of longs or its value cannot be converted to an array * of longs. - * @return CELIX_SUCCESS if the operation was successful, CELIX_ENOMEM if there was not enough memory to create the - * array list. Note if the key is not found, the return status is still CELIX_SUCCESS. + * @return CELIX_SUCCESS if the operation was successful. Note if the key is not found or the value cannot be converted + * to an array of longs, the return status is still CELIX_SUCCESS. + * @returnval CELIX_ENOMEM if there was not enough memory to create the array list. + * @returnval CELIX_ILLEGAL_ARGUMENT if the provided default value is not NULL and not an array list with long values. + * In this case an error message is also logged to celix_err. */ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsLongArrayList(const celix_properties_t* properties, const char* key, @@ -591,10 +622,11 @@ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsLongArrayList(const celi /** * @brief Get the property value as an array of longs without copying. * - * This function provides a non-owning, read-only access to a property value interpreted as an array of longs. + * This function provides a non-owning, read-only access to a array of longs property value. * It returns a const pointer to the array. If the property is not set or its value is not an array of longs, * the default value is returned. * + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The value to return if the property is not set or its value is not an array of longs. @@ -620,8 +652,11 @@ CELIX_UTILS_EXPORT const celix_array_list_t* celix_properties_getLongArrayList(c * @param[out] list A copy of the found list, a new array list with double values or a copy of the default value if the * property is not set, its value is not an array doubles longs or its value cannot be converted to an * array of doubles. - * @return CELIX_SUCCESS if the operation was successful, CELIX_ENOMEM if there was not enough memory to create the - * array list. Note if the key is not found, the return status is still CELIX_SUCCESS. + * @return CELIX_SUCCESS if the operation was successful. Note if the key is not found or the value cannot be converted + * to an array of doubles, the return status is still CELIX_SUCCESS. + * @returnval CELIX_ENOMEM if there was not enough memory to create the array list. + * @returnval CELIX_ILLEGAL_ARGUMENT if the provided default value is not NULL and not an array list with double values. + * In this case an error message is also logged to celix_err. */ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsDoubleArrayList(const celix_properties_t* properties, const char* key, @@ -631,10 +666,11 @@ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsDoubleArrayList(const ce /** * @brief Get the property value as an array of doubles without copying. * - * This function provides a non-owning, read-only access to a property value interpreted as an array of doubles. + * This function provides a non-owning, read-only access to a array of doubles property value. * It returns a const pointer to the array. If the property is not set or its value is not an array of doubles, * the default value is returned. * + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The value to return if the property is not set or its value is not an array of doubles. @@ -652,6 +688,8 @@ CELIX_UTILS_EXPORT const celix_array_list_t* celix_properties_getDoubleArrayList * string is converted to an array of booleans if possible. If the property is not set, its value is not an array of * booleans or its value cannot be converted to a boolean array, the default value is returned as a copy. * + * An celix err is logged if the default value is needed and not an array list with boolean values. + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The default value to return if the property is not set or its value is not an array of @@ -659,8 +697,11 @@ CELIX_UTILS_EXPORT const celix_array_list_t* celix_properties_getDoubleArrayList * @param[out] list A copy of the found list, a new array list with boolean values or a copy of the default value if the * property is not set, its value is not an array of booleans or its value cannot be converted to an * array of booleans. - * @return CELIX_SUCCESS if the operation was successful, CELIX_ENOMEM if there was not enough memory to create the - * array list. Note if the key is not found, the return status is still CELIX_SUCCESS. + * @return CELIX_SUCCESS if the operation was successful. Note if the key is not found or the value cannot be converted + * to an array of booleans, the return status is still CELIX_SUCCESS. + * @returnval CELIX_ENOMEM if there was not enough memory to create the array list. + * @returnval CELIX_ILLEGAL_ARGUMENT if the provided default value is not NULL and not an array list with bool values. + * In this case an error message is also logged to celix_err. */ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsBoolArrayList(const celix_properties_t* properties, const char* key, @@ -670,10 +711,11 @@ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsBoolArrayList(const celi /** * @brief Get the property value as an array of booleans without copying. * - * This function provides a non-owning, read-only access to a property value interpreted as an array of booleans. + * This function provides a non-owning, read-only access to a array of booleans property value. * It returns a const pointer to the array. If the property is not set or its value is not an array of booleans, * the default value is returned. * + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The value to return if the property is not set or its value is not an array of booleans. @@ -694,15 +736,20 @@ CELIX_UTILS_EXPORT const celix_array_list_t* celix_properties_getBoolArrayList( * The returned array list is configured with a remove callback so that the destruction of the array list will also * free the strings in the array list. * + * An celix err is logged if the default value is needed and not an array list with string values. + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The default value to return if the property is not set or its value is not an array of * strings. * @param[out] list A copy of the found list, a new array list with string values or a copy of the default value if the * property is not set, its value is not an array of strings or its value cannot be converted to an - * array of strings. - * @return CELIX_SUCCESS if the operation was successful, CELIX_ENOMEM if there was not enough memory to create the - * array list. Note if the key is not found, the return status is still CELIX_SUCCESS. + * array of strings. + * @return CELIX_SUCCESS if the operation was successful. Note if the key is not found or the value cannot be converted + * to an array of strings, the return status is still CELIX_SUCCESS. + * @returnval CELIX_ENOMEM if there was not enough memory to create the array list. + * @returnval CELIX_ILLEGAL_ARGUMENT if the provided default value is not NULL and not an array list with string values. + * In this case an error message is also logged to celix_err. */ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsStringArrayList(const celix_properties_t* properties, const char* key, @@ -712,10 +759,11 @@ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsStringArrayList(const ce /** * @brief Get the property value as an array of strings without copying. * - * This function provides a non-owning, read-only access to a property value interpreted as an array of strings. + * This function provides a non-owning, read-only access to a array of string property value. * It returns a const pointer to the array. If the property is not set or its value is not an array of strings, * the default value is returned. * + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The value to return if the property is not set or its value is not an array of strings. @@ -738,6 +786,8 @@ CELIX_UTILS_EXPORT const celix_array_list_t* celix_properties_getStringArrayList * The returned array list is configured with a remove callback so that the destruction of the array list will also * free the celix_version_t entries in the array list. * + * An celix err is logged if the default value is needed and not an array list with celix_version_t values. + * * @param[in] properties The property set to search. * @param[in] key The key of the property to get. * @param[in] defaultValue The default value to return if the property is not set or its value is not an array of @@ -745,8 +795,11 @@ CELIX_UTILS_EXPORT const celix_array_list_t* celix_properties_getStringArrayList * @param[out] list A copy of the found list, a new array list with celix_version_t values or a copy of the default * value if the property is not set, its value is not an array of celix_version_t entries or its value cannot be * converted to an array of celix_version_t entries. - * @return CELIX_SUCCESS if the operation was successful, CELIX_ENOMEM if there was not enough memory to create the - * array list. Note if the key is not found, the return status is still CELIX_SUCCESS. + * @return CELIX_SUCCESS if the operation was successful. Note if the key is not found or the value cannot be converted + * to an array of celix_version_t, the return status is still CELIX_SUCCESS. + * @returnval CELIX_ENOMEM if there was not enough memory to create the array list. + * @returnval CELIX_ILLEGAL_ARGUMENT if the provided default value is not NULL and not an array list with + * celix_version_t values. In this case an error message is also logged to celix_err. */ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsVersionArrayList(const celix_properties_t* properties, const char* key, @@ -756,7 +809,7 @@ CELIX_UTILS_EXPORT celix_status_t celix_properties_getAsVersionArrayList(const c /** * @brief Get the property value as an array of celix_version_t entries without copying. * - * This function provides a non-owning, read-only access to a property value interpreted as an array of celix_version_t + * This function provides a non-owning, read-only access to a array of celix_version_t property value. * entries. It returns a const pointer to the array. If the property is not set or its value is not an array of * celix_version_t entries, the default value is returned. * diff --git a/libs/utils/src/array_list.c b/libs/utils/src/array_list.c index 85013da9c..f4cdcd36c 100644 --- a/libs/utils/src/array_list.c +++ b/libs/utils/src/array_list.c @@ -28,6 +28,14 @@ #include "celix_utils.h" #include "celix_version.h" +#define STRING_VALUE_UNDEFINED_EL_TYPE "CELIX_ARRAY_LIST_ELEMENT_TYPE_UNDEFINED" +#define STRING_VALUE_POINTER_EL_TYPE "CELIX_ARRAY_LIST_ELEMENT_TYPE_POINTER" +#define STRING_VALUE_STRING_EL_TYPE "CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING" +#define STRING_VALUE_LONG_EL_TYPE "CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG" +#define STRING_VALUE_DOUBLE_EL_TYPE "CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE" +#define STRING_VALUE_BOOL_EL_TYPE "CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL" +#define STRING_VALUE_VERSION_EL_TYPE "CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION" + struct celix_array_list { celix_array_list_element_type_t elementType; celix_array_list_entry_t* elementData; @@ -601,3 +609,24 @@ void celix_arrayList_sortEntries(celix_array_list_t *list, celix_array_list_comp qsort_r(list->elementData, list->size, sizeof(celix_array_list_entry_t), celix_arrayList_compareEntries, compare); #endif } + +const char* celix_arrayList_elementTypeToString(celix_array_list_element_type_t type) { + switch (type) { + case CELIX_ARRAY_LIST_ELEMENT_TYPE_UNDEFINED: + return STRING_VALUE_UNDEFINED_EL_TYPE; + case CELIX_ARRAY_LIST_ELEMENT_TYPE_POINTER: + return STRING_VALUE_POINTER_EL_TYPE; + case CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING: + return STRING_VALUE_STRING_EL_TYPE; + case CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG: + return STRING_VALUE_LONG_EL_TYPE; + case CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE: + return STRING_VALUE_DOUBLE_EL_TYPE; + case CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL: + return STRING_VALUE_BOOL_EL_TYPE; + case CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION: + return STRING_VALUE_VERSION_EL_TYPE; + default: + return STRING_VALUE_UNDEFINED_EL_TYPE; + } +} diff --git a/libs/utils/src/filter.c b/libs/utils/src/filter.c index fe776aa19..0ad1fd4aa 100644 --- a/libs/utils/src/filter.c +++ b/libs/utils/src/filter.c @@ -712,8 +712,14 @@ static bool celix_filter_matchSubStringForValue(const celix_filter_t* filter, co return true; } +static bool celix_filter_isPropertyEntryArrayWithElementType(const celix_properties_entry_t* entry, + celix_array_list_element_type_t elType) { + return entry && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST && + celix_arrayList_getElementType(entry->typed.arrayValue) == elType; +} + static bool celix_filter_matchSubString(const celix_filter_t* filter, const celix_properties_entry_t* entry) { - if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY) { + if (celix_filter_isPropertyEntryArrayWithElementType(entry, CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING)) { for (int i = 0; i < celix_arrayList_size(entry->typed.arrayValue); i++) { const char* substr = celix_arrayList_getString(entry->typed.arrayValue, i); if (celix_filter_matchSubStringForValue(filter, substr)) { @@ -726,7 +732,7 @@ static bool celix_filter_matchSubString(const celix_filter_t* filter, const celi } static bool celix_filter_matchApprox(const celix_filter_t* filter, const celix_properties_entry_t* entry) { - if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY) { + if (celix_filter_isPropertyEntryArrayWithElementType(entry, CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING)) { for (int i = 0; i < celix_arrayList_size(entry->typed.arrayValue); i++) { const char* substr = celix_arrayList_getString(entry->typed.arrayValue, i); if (strcasestr(substr, filter->value) != NULL) { @@ -751,15 +757,15 @@ static bool celix_filter_matchPropertyEntry(const celix_filter_t* filter, const //match for array types - if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY && filter->internal->convertedToLong) { + if (celix_filter_isPropertyEntryArrayWithElementType(entry, CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG)) { return celix_utils_matchLongArrays(filter->operand, entry->typed.arrayValue, filter->internal->longValue); - } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY && filter->internal->convertedToDouble) { + } else if (celix_filter_isPropertyEntryArrayWithElementType(entry, CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE)) { return celix_utils_matchDoubleArrays(filter->operand, entry->typed.arrayValue, filter->internal->doubleValue); - } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY && filter->internal->convertedToBool) { + } else if (celix_filter_isPropertyEntryArrayWithElementType(entry, CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL)) { return celix_utils_matchBoolArrays(filter->operand, entry->typed.arrayValue, filter->internal->boolValue); - } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY && filter->internal->convertedToVersion) { + } else if (celix_filter_isPropertyEntryArrayWithElementType(entry, CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION)) { return celix_utils_matchVersionArrays(filter->operand, entry->typed.arrayValue, filter->internal->versionValue); - } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY) { + } else if (celix_filter_isPropertyEntryArrayWithElementType(entry, CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING)) { return celix_utils_matchStringArrays(filter->operand, entry->typed.arrayValue, filter->value); } diff --git a/libs/utils/src/properties.c b/libs/utils/src/properties.c index 639afde97..1eda4d1d7 100644 --- a/libs/utils/src/properties.c +++ b/libs/utils/src/properties.c @@ -163,11 +163,7 @@ static celix_status_t celix_properties_fillEntry(celix_properties_t* properties, } } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_BOOL) { entry->value = entry->typed.boolValue ? CELIX_PROPERTIES_BOOL_TRUE_STRVAL : CELIX_PROPERTIES_BOOL_FALSE_STRVAL; - } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY) { + } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST) { entry->value = celix_utils_arrayListToString(entry->typed.arrayValue); } else /*string value*/ { assert(entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING); @@ -220,11 +216,7 @@ static void celix_properties_freeTypedEntry(celix_properties_t* properties, celi } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_VERSION) { celix_version_destroy((celix_version_t*)entry->typed.versionValue); entry->typed.versionValue = NULL; - } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY || - entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY) { + } else if (entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST) { celix_arrayList_destroy((celix_array_list_t*)entry->typed.arrayValue); entry->typed.arrayValue = NULL; } else { @@ -653,6 +645,22 @@ const celix_properties_entry_t* celix_properties_getEntry(const celix_properties return entry; } +static const bool celix_properties_isEntryArrayListWithElType(const celix_properties_entry_t* entry, + celix_array_list_element_type_t elType) { + return entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST && + celix_arrayList_getElementType(entry->typed.arrayValue) == elType; +} + +static const celix_properties_entry_t* celix_properties_getArrayListEntry(const celix_properties_t* properties, + const char* key, + celix_array_list_element_type_t elType) { + const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); + if (celix_properties_isEntryArrayListWithElType(entry, elType)) { + return entry; + } + return NULL; +} + celix_status_t celix_properties_set(celix_properties_t* properties, const char* key, const char* value) { return celix_properties_setString(properties, key, value); } @@ -916,55 +924,6 @@ celix_properties_assignVersion(celix_properties_t* properties, const char* key, return celix_properties_createAndSetEntry(properties, key, &prototype); } -celix_status_t celix_properties_getAsLongArrayList(const celix_properties_t* properties, - const char* key, - const celix_array_list_t* defaultValue, - celix_array_list_t** list) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY) { - celix_array_list_t* copy = celix_arrayList_copy(entry->typed.arrayValue); - if (!copy) { - return CELIX_ENOMEM; - } - *list = copy; - return CELIX_SUCCESS; - } - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING) { - celix_status_t convertStatus = celix_utils_convertStringToLongArrayList(entry->value, defaultValue, list); - if (convertStatus == CELIX_ILLEGAL_ARGUMENT) { - // conversion failed, but no memory error so defaultValue is copied and set - return CELIX_SUCCESS; - } - return convertStatus; - } - if (defaultValue) { - *list = celix_arrayList_copy(defaultValue); - return *list ? CELIX_SUCCESS : CELIX_ENOMEM; - } - *list = NULL; - return CELIX_SUCCESS; -} - -static celix_properties_value_type_e celix_properties_getPropertiesTypeFromArrayList(const celix_array_list_t* list) { - switch (celix_arrayList_getElementType(list)) { - case CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG: - return CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY; - case CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE: - return CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY; - case CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL: - return CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY; - case CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING: - return CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY; - case CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION: - return CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY; - default: - //LCOV_EXCL_START - assert(false); - abort(); - //LCOV_EXCL_STOP - } -} - celix_status_t celix_properties_setArrayList(celix_properties_t* properties, const char* key, const celix_array_list_t* values) { if (!key || !values) { @@ -977,7 +936,7 @@ celix_properties_setArrayList(celix_properties_t* properties, const char* key, c return CELIX_ENOMEM; } celix_properties_entry_t prototype = {0}; - prototype.valueType = celix_properties_getPropertiesTypeFromArrayList(values); + prototype.valueType = CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST; prototype.typed.arrayValue = copy; return celix_properties_createAndSetEntry(properties, key, &prototype); } @@ -991,27 +950,53 @@ celix_properties_assignArrayList(celix_properties_t* properties, const char* key assert(celix_arrayList_getElementType(values) != CELIX_ARRAY_LIST_ELEMENT_TYPE_UNDEFINED && celix_arrayList_getElementType(values) != CELIX_ARRAY_LIST_ELEMENT_TYPE_POINTER); //wrong array list type celix_properties_entry_t prototype = {0}; - prototype.valueType = celix_properties_getPropertiesTypeFromArrayList(values); + prototype.valueType = CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST; prototype.typed.arrayValue = values; return celix_properties_createAndSetEntry(properties, key, &prototype); } -const celix_array_list_t* celix_properties_getLongArrayList(const celix_properties_t* properties, - const char* key, - const celix_array_list_t* defaultValue) { +const celix_array_list_t* celix_properties_getArrayList(const celix_properties_t* properties, + const char* key, + const celix_array_list_t* defaultValue) { const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_LONG_ARRAY) { + if (entry && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_ARRAY_LIST) { return entry->typed.arrayValue; } return defaultValue; } -celix_status_t celix_properties_getAsDoubleArrayList(const celix_properties_t* properties, - const char* key, - const celix_array_list_t* defaultValue, - celix_array_list_t** list) { +static const celix_array_list_t* celix_properties_getTypedArrayList(const celix_properties_t* properties, + const char* key, + celix_array_list_element_type_t elType, + const celix_array_list_t* defaultValue) { + const celix_properties_entry_t* entry = celix_properties_getArrayListEntry(properties, key, elType); + if (entry) { + return entry->typed.arrayValue; + } + if (defaultValue) { + return celix_arrayList_getElementType(defaultValue) == elType ? defaultValue : NULL; + } + return NULL; +} + +static celix_status_t celix_properties_getAsTypedArrayList( + const celix_properties_t* properties, + const char* key, + const celix_array_list_t* defaultValue, + celix_array_list_element_type_t elType, + celix_status_t (*convertStringToArray)(const char*, const celix_array_list_t*, celix_array_list_t**), + celix_array_list_t** list) { + *list = NULL; + + if (defaultValue && celix_arrayList_getElementType(defaultValue) != elType) { + celix_err_pushf("Default value has wrong element type. Expected %s, but got %s", + celix_arrayList_elementTypeToString(elType), + celix_arrayList_elementTypeToString(celix_arrayList_getElementType(defaultValue))); + return CELIX_ILLEGAL_ARGUMENT; + } + const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY) { + if (entry && celix_properties_isEntryArrayListWithElType(entry, elType)) { celix_array_list_t* copy = celix_arrayList_copy(entry->typed.arrayValue); if (!copy) { return CELIX_ENOMEM; @@ -1019,10 +1004,10 @@ celix_status_t celix_properties_getAsDoubleArrayList(const celix_properties_t* p *list = copy; return CELIX_SUCCESS; } - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING) { - celix_status_t convertStatus = celix_utils_convertStringToDoubleArrayList(entry->value, defaultValue, list); + if (entry && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING) { + celix_status_t convertStatus = convertStringToArray(entry->value, defaultValue, list); if (convertStatus == CELIX_ILLEGAL_ARGUMENT) { - // conversion failed, but no memory error so defaultValue is copied and set + // conversion failed, but no memory error so defaultValue is used and no error is set return CELIX_SUCCESS; } return convertStatus; @@ -1031,127 +1016,77 @@ celix_status_t celix_properties_getAsDoubleArrayList(const celix_properties_t* p *list = celix_arrayList_copy(defaultValue); return *list ? CELIX_SUCCESS : CELIX_ENOMEM; } - *list = NULL; return CELIX_SUCCESS; } +celix_status_t celix_properties_getAsLongArrayList(const celix_properties_t* properties, + const char* key, + const celix_array_list_t* defaultValue, + celix_array_list_t** list) { + return celix_properties_getAsTypedArrayList(properties, key, defaultValue, CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG, + celix_utils_convertStringToLongArrayList, list); +} + +const celix_array_list_t* celix_properties_getLongArrayList(const celix_properties_t* properties, + const char* key, + const celix_array_list_t* defaultValue) { + return celix_properties_getTypedArrayList(properties, key, CELIX_ARRAY_LIST_ELEMENT_TYPE_LONG, defaultValue); +} + +celix_status_t celix_properties_getAsDoubleArrayList(const celix_properties_t* properties, + const char* key, + const celix_array_list_t* defaultValue, + celix_array_list_t** list) { + return celix_properties_getAsTypedArrayList(properties, key, defaultValue, CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE, + celix_utils_convertStringToDoubleArrayList, list); +} + const celix_array_list_t* celix_properties_getDoubleArrayList(const celix_properties_t* properties, const char* key, const celix_array_list_t* defaultValue) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_DOUBLE_ARRAY) { - return entry->typed.arrayValue; - } - return defaultValue; + return celix_properties_getTypedArrayList(properties, key, CELIX_ARRAY_LIST_ELEMENT_TYPE_DOUBLE, defaultValue); } celix_status_t celix_properties_getAsBoolArrayList(const celix_properties_t* properties, const char* key, const celix_array_list_t* defaultValue, celix_array_list_t** list) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY) { - celix_array_list_t* copy = celix_arrayList_copy(entry->typed.arrayValue); - if (!copy) { - return CELIX_ENOMEM; - } - *list = copy; - return CELIX_SUCCESS; - } - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING) { - celix_status_t convertStatus = celix_utils_convertStringToBoolArrayList(entry->value, defaultValue, list); - if (convertStatus == CELIX_ILLEGAL_ARGUMENT) { - // conversion failed, but no memory error so defaultValue is copied and set - return CELIX_SUCCESS; - } - return convertStatus; - } - if (defaultValue) { - *list = celix_arrayList_copy(defaultValue); - return *list ? CELIX_SUCCESS : CELIX_ENOMEM; - } - *list = NULL; - return CELIX_SUCCESS; + return celix_properties_getAsTypedArrayList(properties, key, defaultValue, CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL, + celix_utils_convertStringToBoolArrayList, list); } const celix_array_list_t* celix_properties_getBoolArrayList(const celix_properties_t* properties, const char* key, const celix_array_list_t* defaultValue) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_BOOL_ARRAY) { - return entry->typed.arrayValue; - } - return defaultValue; + return celix_properties_getTypedArrayList(properties, key, CELIX_ARRAY_LIST_ELEMENT_TYPE_BOOL, defaultValue); } celix_status_t celix_properties_getAsStringArrayList(const celix_properties_t* properties, const char* key, const celix_array_list_t* defaultValue, celix_array_list_t** list) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY) { - *list = celix_arrayList_copy(entry->typed.arrayValue); - return *list ? CELIX_SUCCESS : CELIX_ENOMEM; - } - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING) { - celix_status_t convertStatus = celix_utils_convertStringToStringArrayList(entry->value, defaultValue, list); - if (convertStatus == CELIX_ILLEGAL_ARGUMENT) { - // conversion failed, but no memory error so defaultValue is copied and set - return CELIX_SUCCESS; - } - return convertStatus; - } - if (defaultValue) { - *list = celix_arrayList_copy(defaultValue); - return *list ? CELIX_SUCCESS : CELIX_ENOMEM; - } - *list = NULL; - return CELIX_SUCCESS; + return celix_properties_getAsTypedArrayList(properties, key, defaultValue, CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING, + celix_utils_convertStringToStringArrayList, list); } const celix_array_list_t* celix_properties_getStringArrayList(const celix_properties_t* properties, const char* key, const celix_array_list_t* defaultValue) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING_ARRAY) { - return entry->typed.arrayValue; - } - return defaultValue; + return celix_properties_getTypedArrayList(properties, key, CELIX_ARRAY_LIST_ELEMENT_TYPE_STRING, defaultValue); } celix_status_t celix_properties_getAsVersionArrayList(const celix_properties_t* properties, const char* key, const celix_array_list_t* defaultValue, celix_array_list_t** list) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY) { - *list = celix_arrayList_copy(entry->typed.arrayValue); - return *list ? CELIX_SUCCESS : CELIX_ENOMEM; - } - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_STRING) { - celix_status_t convertStatus = celix_utils_convertStringToStringArrayList(entry->value, defaultValue, list); - if (convertStatus == CELIX_ILLEGAL_ARGUMENT) { - // conversion failed, but no memory error so defaultValue is copied and set - return CELIX_SUCCESS; - } - return convertStatus; - } - if (defaultValue) { - *list = celix_arrayList_copy(defaultValue); - return *list ? CELIX_SUCCESS : CELIX_ENOMEM; - } - *list = NULL; - return CELIX_SUCCESS; + return celix_properties_getAsTypedArrayList(properties, key, defaultValue, CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION, + celix_utils_convertStringToVersionArrayList, list); } const celix_array_list_t* celix_properties_getVersionArrayList(const celix_properties_t* properties, const char* key, const celix_array_list_t* defaultValue) { - const celix_properties_entry_t* entry = celix_properties_getEntry(properties, key); - if (entry != NULL && entry->valueType == CELIX_PROPERTIES_VALUE_TYPE_VERSION_ARRAY) { - return entry->typed.arrayValue; - } - return defaultValue; + return celix_properties_getTypedArrayList(properties, key, CELIX_ARRAY_LIST_ELEMENT_TYPE_VERSION, defaultValue); } size_t celix_properties_size(const celix_properties_t* properties) {