summaryrefslogtreecommitdiff
path: root/tests/unit/test_fgla.c
blob: 60f4e7b6be56d821938a67ddece5834900216a98 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
/**
 * test_fgla.c - Unit tests for fgla utility functions
 *
 * Copyright (C) 2025 https://optics-design.com
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License as
 * published by the Free Software Foundation, either version 3 of the
 * License, or (at your option) any later version.
 */

#include "../test_framework.h"
#include "../../include/glautils/fgla.h"

// Test string validation
int test_search_term_validation() {
    TEST_START("Search Term Validation");
    
    // Valid search terms
    TEST_ASSERT(fgla_validate_search_term("BK7"), "BK7 should be valid");
    TEST_ASSERT(fgla_validate_search_term("N-SF6"), "N-SF6 should be valid");
    TEST_ASSERT(fgla_validate_search_term("517642"), "517642 should be valid");
    TEST_ASSERT(fgla_validate_search_term("51x64x"), "51x64x should be valid");
    TEST_ASSERT(fgla_validate_search_term("FK51A"), "FK51A should be valid");
    
    // Invalid search terms
    TEST_ASSERT(!fgla_validate_search_term(NULL), "NULL should be invalid");
    TEST_ASSERT(!fgla_validate_search_term(""), "Empty string should be invalid");
    TEST_ASSERT(!fgla_validate_search_term("test@#$"), "Special characters should be invalid");
    TEST_ASSERT(!fgla_validate_search_term("test|pipe"), "Pipe character should be invalid");
    
    // Test boundary conditions
    char long_term[300];
    memset(long_term, 'A', sizeof(long_term) - 1);
    long_term[sizeof(long_term) - 1] = '\0';
    TEST_ASSERT(!fgla_validate_search_term(long_term), "Overly long term should be invalid");
    
    TEST_END();
}

// Test glass code pattern recognition
int test_glass_code_pattern() {
    TEST_START("Glass Code Pattern Recognition");
    
    // Valid glass code patterns
    TEST_ASSERT(fgla_is_glass_code_pattern("517642"), "517642 should be glass code pattern");
    TEST_ASSERT(fgla_is_glass_code_pattern("123456"), "123456 should be glass code pattern");
    TEST_ASSERT(fgla_is_glass_code_pattern("51x64x"), "51x64x should be glass code pattern");
    TEST_ASSERT(fgla_is_glass_code_pattern("x12345"), "x12345 should be glass code pattern");
    TEST_ASSERT(fgla_is_glass_code_pattern("xxxxxx"), "xxxxxx should be glass code pattern");
    
    // Invalid patterns
    TEST_ASSERT(!fgla_is_glass_code_pattern("51764"), "51764 (5 digits) should not be glass code pattern");
    TEST_ASSERT(!fgla_is_glass_code_pattern("5176420"), "5176420 (7 digits) should not be glass code pattern");
    TEST_ASSERT(!fgla_is_glass_code_pattern("BK7123"), "BK7123 (letters) should not be glass code pattern");
    TEST_ASSERT(!fgla_is_glass_code_pattern("51-642"), "51-642 (dash) should not be glass code pattern");
    TEST_ASSERT(!fgla_is_glass_code_pattern(NULL), "NULL should not be glass code pattern");
    
    TEST_END();
}

// Test glass code pattern matching
int test_glass_code_matching() {
    TEST_START("Glass Code Pattern Matching");
    
    // Exact matches
    TEST_ASSERT(fgla_matches_glass_code_pattern_safe("517642", "517642"), 
               "Exact match should work");
    
    // Wildcard matches
    TEST_ASSERT(fgla_matches_glass_code_pattern_safe("517642", "51x64x"), 
               "Wildcard pattern should match");
    TEST_ASSERT(fgla_matches_glass_code_pattern_safe("517642", "x17642"), 
               "Leading wildcard should match");
    TEST_ASSERT(fgla_matches_glass_code_pattern_safe("517642", "51764x"), 
               "Trailing wildcard should match");
    
    // Non-matches
    TEST_ASSERT(!fgla_matches_glass_code_pattern_safe("517642", "518642"), 
               "Different digit should not match");
    TEST_ASSERT(!fgla_matches_glass_code_pattern_safe("517642", "51x63x"), 
               "Wrong wildcard pattern should not match");
    
    // Handle longer glass codes (should extract first 6 digits)
    TEST_ASSERT(fgla_matches_glass_code_pattern_safe("5176420123", "517642"), 
               "Should match first 6 digits of longer code");
    
    // Edge cases
    TEST_ASSERT(!fgla_matches_glass_code_pattern_safe(NULL, "517642"), 
               "NULL glass code should not match");
    TEST_ASSERT(!fgla_matches_glass_code_pattern_safe("517642", NULL), 
               "NULL pattern should not match");
    
    TEST_END();
}

// Test string normalization
int test_string_normalization() {
    TEST_START("String Normalization");
    
    char output[100];
    
    // Test basic normalization
    int result = fgla_normalize_string_safe("N-BK7", output, sizeof(output));
    TEST_ASSERT_EQ(0, result, "Normalization should succeed");
    TEST_ASSERT_STR_EQ("nbk7", output, "Should remove dash and convert to lowercase");
    
    // Test with multiple dashes
    result = fgla_normalize_string_safe("N-SF-6", output, sizeof(output));
    TEST_ASSERT_EQ(0, result, "Multi-dash normalization should succeed");
    TEST_ASSERT_STR_EQ("nsf6", output, "Should remove all dashes");
    
    // Test with no dashes
    result = fgla_normalize_string_safe("BK7", output, sizeof(output));
    TEST_ASSERT_EQ(0, result, "No-dash normalization should succeed");
    TEST_ASSERT_STR_EQ("bk7", output, "Should just convert to lowercase");
    
    // Test error conditions
    result = fgla_normalize_string_safe(NULL, output, sizeof(output));
    TEST_ASSERT_EQ(-1, result, "NULL input should return error");
    
    result = fgla_normalize_string_safe("test", NULL, sizeof(output));
    TEST_ASSERT_EQ(-1, result, "NULL output should return error");
    
    result = fgla_normalize_string_safe("test", output, 0);
    TEST_ASSERT_EQ(-1, result, "Zero-size output should return error");
    
    TEST_END();
}

// Test substring search
int test_substring_search() {
    TEST_START("Substring Search");
    
    // Case-insensitive search
    TEST_ASSERT(fgla_contains_substring_safe("N-BK7", "bk"), 
               "Should find 'bk' in 'N-BK7' (case insensitive)");
    TEST_ASSERT(fgla_contains_substring_safe("N-BK7", "BK"), 
               "Should find 'BK' in 'N-BK7'");
    
    // Dash-insensitive search
    TEST_ASSERT(fgla_contains_substring_safe("N-BK7", "nbk"), 
               "Should find 'nbk' in 'N-BK7' (dash insensitive)");
    TEST_ASSERT(fgla_contains_substring_safe("NBK7", "n-bk"), 
               "Should find 'n-bk' in 'NBK7' (dash insensitive)");
    
    // Non-matches
    TEST_ASSERT(!fgla_contains_substring_safe("N-BK7", "sf"), 
               "Should not find 'sf' in 'N-BK7'");
    
    // Edge cases
    TEST_ASSERT(!fgla_contains_substring_safe(NULL, "test"), 
               "NULL haystack should return false");
    TEST_ASSERT(!fgla_contains_substring_safe("test", NULL), 
               "NULL needle should return false");
    TEST_ASSERT(!fgla_contains_substring_safe("", "test"), 
               "Empty haystack should return false");
    TEST_ASSERT(!fgla_contains_substring_safe("test", ""), 
               "Empty needle should return false");
    
    TEST_END();
}

// Test catalog matching
int test_catalog_matching() {
    TEST_START("Catalog Matching");
    
    const char* catalogs[] = {"SCHOTT", "HOYA", "CDGM"};
    
    // Should match
    TEST_ASSERT(fgla_matches_catalog("SCHOTT", catalogs, 3), 
               "Should match SCHOTT");
    TEST_ASSERT(fgla_matches_catalog("schott", catalogs, 3), 
               "Should match schott (case insensitive)");
    TEST_ASSERT(fgla_matches_catalog("HOYA", catalogs, 3), 
               "Should match HOYA");
    
    // Should not match
    TEST_ASSERT(!fgla_matches_catalog("Ohara", catalogs, 3), 
               "Should not match Ohara (not in list)");
    
    // Empty catalog list should match all
    TEST_ASSERT(fgla_matches_catalog("SCHOTT", NULL, 0), 
               "Empty catalog list should match anything");
    TEST_ASSERT(fgla_matches_catalog("Unknown", NULL, 0), 
               "Empty catalog list should match anything");
    
    TEST_END();
}

// Test lowercase conversion
int test_lowercase_conversion() {
    TEST_START("Lowercase Conversion");
    
    char test_str[20];
    
    // Test normal case
    strcpy(test_str, "BK7");
    fgla_to_lowercase_safe(test_str, sizeof(test_str));
    TEST_ASSERT_STR_EQ("bk7", test_str, "Should convert BK7 to bk7");
    
    // Test mixed case
    strcpy(test_str, "N-SF6");
    fgla_to_lowercase_safe(test_str, sizeof(test_str));
    TEST_ASSERT_STR_EQ("n-sf6", test_str, "Should convert N-SF6 to n-sf6");
    
    // Test already lowercase
    strcpy(test_str, "already");
    fgla_to_lowercase_safe(test_str, sizeof(test_str));
    TEST_ASSERT_STR_EQ("already", test_str, "Should not change already lowercase");
    
    // Test with NULL (should not crash)
    fgla_to_lowercase_safe(NULL, 10);  // Should not crash
    
    TEST_END();
}

// Main test runner
int main() {
    printf(BLUE "=== FGLA Utility Unit Tests ===" RESET "\n\n");
    
    RUN_TEST(test_search_term_validation);
    RUN_TEST(test_glass_code_pattern);
    RUN_TEST(test_glass_code_matching);
    RUN_TEST(test_string_normalization);
    RUN_TEST(test_substring_search);
    RUN_TEST(test_catalog_matching);
    RUN_TEST(test_lowercase_conversion);
    
    TEST_SUMMARY();
}
Back to https://optics-design.com