1/*
2 * Copyright (C) 2014 Apple Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 *
13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
14 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
15 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
17 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
18 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
19 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
20 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
21 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
22 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
23 * THE POSSIBILITY OF SUCH DAMAGE.
24 */
25
26#include "config.h"
27
28#include <wtf/text/StringBuilder.h>
29#include <wtf/text/StringView.h>
30
31namespace TestWebKitAPI {
32
33StringView stringViewFromLiteral(const char* characters)
34{
35 return StringView(reinterpret_cast<const LChar*>(characters), strlen(characters));
36}
37
38StringView stringViewFromUTF8(String &ref, const char* characters)
39{
40 ref = String::fromUTF8(characters);
41 return ref;
42}
43
44TEST(WTF, StringViewEmptyVsNull)
45{
46 StringView nullView;
47 EXPECT_TRUE(nullView.isNull());
48 EXPECT_TRUE(nullView.isEmpty());
49
50 // Test in a boolean context to test operator bool().
51 if (nullView)
52 FAIL();
53 else
54 SUCCEED();
55
56 if (!nullView)
57 SUCCEED();
58 else
59 FAIL();
60
61 StringView emptyView = StringView::empty();
62 EXPECT_FALSE(emptyView.isNull());
63 EXPECT_TRUE(emptyView.isEmpty());
64
65 // Test in a boolean context to test operator bool().
66 if (emptyView)
67 SUCCEED();
68 else
69 FAIL();
70
71 if (!emptyView)
72 FAIL();
73 else
74 SUCCEED();
75
76 StringView viewWithCharacters(String("hello"));
77 EXPECT_FALSE(viewWithCharacters.isNull());
78 EXPECT_FALSE(viewWithCharacters.isEmpty());
79
80 // Test in a boolean context to test operator bool().
81 if (viewWithCharacters)
82 SUCCEED();
83 else
84 FAIL();
85
86 if (!viewWithCharacters)
87 FAIL();
88 else
89 SUCCEED();
90}
91
92bool compareLoopIterations(StringView::GraphemeClusters graphemeClusters, std::vector<StringView> expected)
93{
94 std::vector<StringView> actual;
95 for (auto graphemeCluster : graphemeClusters)
96 actual.push_back(graphemeCluster);
97 return actual == expected;
98}
99
100bool compareLoopIterations(StringView::CodePoints codePoints, std::vector<UChar32> expected)
101{
102 std::vector<UChar32> actual;
103 for (auto codePoint : codePoints)
104 actual.push_back(codePoint);
105 return actual == expected;
106}
107
108static bool compareLoopIterations(StringView::CodeUnits codeUnits, std::vector<UChar> expected)
109{
110 std::vector<UChar> actual;
111 for (auto codeUnit : codeUnits)
112 actual.push_back(codeUnit);
113 return actual == expected;
114}
115
116static void build(StringBuilder& builder, std::vector<UChar> input)
117{
118 builder.clear();
119 for (auto codeUnit : input)
120 builder.append(codeUnit);
121}
122
123TEST(WTF, StringViewIterators)
124{
125 EXPECT_TRUE(compareLoopIterations(StringView().codePoints(), { }));
126 EXPECT_TRUE(compareLoopIterations(StringView().codeUnits(), { }));
127 EXPECT_TRUE(compareLoopIterations(StringView().graphemeClusters(), { }));
128
129 EXPECT_TRUE(compareLoopIterations(StringView::empty().codePoints(), { }));
130 EXPECT_TRUE(compareLoopIterations(StringView::empty().codeUnits(), { }));
131 EXPECT_TRUE(compareLoopIterations(StringView::empty().graphemeClusters(), { }));
132
133 String helo("helo");
134 StringView heloView(helo);
135
136 auto codePoints = heloView.codePoints();
137 auto codePointsIterator = codePoints.begin();
138 EXPECT_EQ(*codePointsIterator, 'h');
139 EXPECT_EQ(*codePointsIterator, 'h');
140 ++codePointsIterator;
141 ++codePointsIterator;
142 EXPECT_EQ(*codePointsIterator, 'l');
143 auto savedIterator = codePointsIterator;
144 codePointsIterator = codePoints.begin();
145 EXPECT_EQ(*codePointsIterator, 'h');
146 codePointsIterator = savedIterator;
147 EXPECT_EQ(*codePointsIterator, 'l');
148 String webkit("webkit");
149 auto webkitCodePoints = StringView(webkit).codePoints();
150 codePointsIterator = webkitCodePoints.begin();
151 ++codePointsIterator;
152 ++codePointsIterator;
153 EXPECT_EQ(*codePointsIterator, 'b');
154 while (codePointsIterator != webkitCodePoints.end())
155 ++codePointsIterator;
156
157 EXPECT_TRUE(compareLoopIterations(heloView.codePoints(), {'h', 'e', 'l', 'o'}));
158 EXPECT_TRUE(compareLoopIterations(heloView.codeUnits(), {'h', 'e', 'l', 'o'}));
159 EXPECT_TRUE(compareLoopIterations(heloView.graphemeClusters(), {
160 StringView(heloView.characters8(), 1),
161 StringView(heloView.characters8() + 1, 1),
162 StringView(heloView.characters8() + 2, 1),
163 StringView(heloView.characters8() + 3, 1)}));
164
165 StringBuilder b;
166 build(b, {0xD800, 0xDD55}); // Surrogates for unicode code point U+10155
167 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0x10155}));
168 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0xD800, 0xDD55}));
169 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {StringView(b.toString())}));
170
171 build(b, {0xD800}); // Leading surrogate only
172 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0xD800}));
173 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0xD800}));
174 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {StringView(b.toString())}));
175
176 build(b, {0xD800, 0xD801}); // Two leading surrogates
177 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0xD800, 0xD801}));
178 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0xD800, 0xD801}));
179 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {StringView(b.characters16(), 1), StringView(b.characters16() + 1, 1)}));
180
181 build(b, {0xDD55}); // Trailing surrogate only
182 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0xDD55}));
183 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0xDD55}));
184 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {StringView(b.toString())}));
185
186 build(b, {0xD800, 'h'}); // Leading surrogate followed by non-surrogate
187 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0xD800, 'h'}));
188 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0xD800, 'h'}));
189 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {StringView(b.characters16(), 1), StringView(b.characters16() + 1, 1)}));
190
191 build(b, {0x0306}); // "COMBINING BREVE"
192 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0x0306}));
193 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0x0306}));
194 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {StringView(b.toString())}));
195
196 build(b, {0x0306, 0xD800, 0xDD55, 'h', 'e', 'l', 'o'}); // Mix of single code unit and multi code unit code points
197 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0x0306, 0x10155, 'h', 'e', 'l', 'o'}));
198 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0x0306, 0xD800, 0xDD55, 'h', 'e', 'l', 'o'}));
199 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {
200 StringView(b.characters16(), 1),
201 StringView(b.characters16() + 1, 2),
202 StringView(b.characters16() + 3, 1),
203 StringView(b.characters16() + 4, 1),
204 StringView(b.characters16() + 5, 1),
205 StringView(b.characters16() + 6, 1)}));
206
207 build(b, {'e', 0x0301}); // "COMBINING ACUTE"
208 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {'e', 0x0301}));
209 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {'e', 0x0301}));
210 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {StringView(b.toString())}));
211
212 build(b, {'e', 0x0301, 0x0306, 'a'}); // "COMBINING ACUTE" "COMBINING BREVE"
213 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {'e', 0x0301, 0x0306, 'a'}));
214 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {'e', 0x0301, 0x0306, 'a'}));
215 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {
216 StringView(b.characters16(), 3),
217 StringView(b.characters16() + 3, 1),
218 }));
219
220 build(b, {0x1112, 0x116f, 0x11b6, 0x1107, 0x1161, 0x11B8}); // Korean combining Jamo
221 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codePoints(), {0x1112, 0x116f, 0x11b6, 0x1107, 0x1161, 0x11B8}));
222 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).codeUnits(), {0x1112, 0x116f, 0x11b6, 0x1107, 0x1161, 0x11B8}));
223 EXPECT_TRUE(compareLoopIterations(StringView(b.toString()).graphemeClusters(), {
224 StringView(b.characters16(), 3),
225 StringView(b.characters16() + 3, 3)}));
226}
227
228static Vector<String> vectorFromSplitResult(const StringView::SplitResult& substrings)
229{
230 Vector<String> result;
231 for (StringView substring : substrings)
232 result.append(substring.toString());
233 return result;
234}
235
236TEST(WTF, StringViewSplitEmptyAndNullStrings)
237{
238 StringView a = emptyString();
239 auto splitResult = a.split('b');
240 EXPECT_TRUE(splitResult.begin() == splitResult.end());
241
242 a = { String { } };
243 splitResult = a.split('b');
244 EXPECT_TRUE(splitResult.begin() == splitResult.end());
245
246 a = { };
247 splitResult = a.split('b');
248 EXPECT_TRUE(splitResult.begin() == splitResult.end());
249}
250
251TEST(WTF, StringViewSplitBasic)
252{
253 String referenceHolder;
254 StringView a = stringViewFromUTF8(referenceHolder, "This is a sentence.");
255
256 // Simple
257 Vector<String> actual = vectorFromSplitResult(a.split('T'));
258 Vector<String> expected({ "his is a sentence." });
259 ASSERT_EQ(expected.size(), actual.size());
260 for (size_t i = 0; i < actual.size(); ++i)
261 EXPECT_STREQ(expected[i].utf8().data(), actual[i].utf8().data()) << "Vectors differ at index " << i;
262
263 actual = vectorFromSplitResult(a.split('.'));
264 expected = { "This is a sentence" };
265 ASSERT_EQ(expected.size(), actual.size());
266 for (size_t i = 0; i < actual.size(); ++i)
267 EXPECT_STREQ(expected[i].utf8().data(), actual[i].utf8().data()) << "Vectors differ at index " << i;
268
269 actual = vectorFromSplitResult(a.split('a'));
270 expected = { "This is ", " sentence." };
271 ASSERT_EQ(expected.size(), actual.size());
272 for (size_t i = 0; i < actual.size(); ++i)
273 EXPECT_STREQ(expected[i].utf8().data(), actual[i].utf8().data()) << "Vectors differ at index " << i;
274
275 actual = vectorFromSplitResult(a.split(' '));
276 expected = { "This", "is", "a", "sentence." };
277 ASSERT_EQ(expected.size(), actual.size());
278 for (size_t i = 0; i < actual.size(); ++i)
279 EXPECT_STREQ(expected[i].utf8().data(), actual[i].utf8().data()) << "Vectors differ at index " << i;
280
281 // Non-existent separator
282 actual = vectorFromSplitResult(a.split('z'));
283 expected = { "This is a sentence." };
284 ASSERT_EQ(expected.size(), actual.size());
285 for (size_t i = 0; i < actual.size(); ++i)
286 EXPECT_STREQ(expected[i].utf8().data(), actual[i].utf8().data()) << "Vectors differ at index " << i;
287}
288
289TEST(WTF, StringViewSplitWithConsecutiveSeparators)
290{
291 String referenceHolder;
292 StringView a = stringViewFromUTF8(referenceHolder, " This is a sentence. ");
293
294 Vector<String> actual = vectorFromSplitResult(a.split(' '));
295 Vector<String> expected({ "This", "is", "a", "sentence." });
296 ASSERT_EQ(expected.size(), actual.size());
297 for (size_t i = 0; i < actual.size(); ++i)
298 EXPECT_STREQ(expected[i].utf8().data(), actual[i].utf8().data()) << "Vectors differ at index " << i;
299
300 actual = vectorFromSplitResult(a.splitAllowingEmptyEntries(' '));
301 expected = { "", "This", "", "", "", "", "is", "", "a", "", "", "", "", "", "", "sentence.", "" };
302 ASSERT_EQ(expected.size(), actual.size());
303 for (size_t i = 0; i < actual.size(); ++i)
304 EXPECT_STREQ(expected[i].utf8().data(), actual[i].utf8().data()) << "Vectors differ at index " << i;
305}
306
307TEST(WTF, StringViewEqualBasic)
308{
309 String referenceHolder;
310 StringView a = stringViewFromUTF8(referenceHolder, "Hello World!");
311 EXPECT_TRUE(a == "Hello World!");
312 EXPECT_FALSE(a == "Hello World");
313 EXPECT_FALSE(a == "Hello World!!");
314
315 auto test = "Hell\0";
316 a = StringView { (const LChar*)test, 5 };
317 EXPECT_FALSE(a == "Hell\0");
318 EXPECT_FALSE(a == "Hell");
319
320 StringView test3 = "Hello";
321 EXPECT_TRUE(test3 == "Hello\0");
322 EXPECT_TRUE(test3 == "Hello");
323}
324
325TEST(WTF, StringViewEqualIgnoringASCIICaseBasic)
326{
327 RefPtr<StringImpl> a = StringImpl::createFromLiteral("aBcDeFG");
328 RefPtr<StringImpl> b = StringImpl::createFromLiteral("ABCDEFG");
329 RefPtr<StringImpl> c = StringImpl::createFromLiteral("abcdefg");
330 const char d[] = "aBcDeFG";
331 RefPtr<StringImpl> empty = StringImpl::create(reinterpret_cast<const LChar*>(""));
332 RefPtr<StringImpl> shorter = StringImpl::createFromLiteral("abcdef");
333 RefPtr<StringImpl> different = StringImpl::createFromLiteral("abcrefg");
334
335 StringView stringViewA(*a.get());
336 StringView stringViewB(*b.get());
337 StringView stringViewC(*c.get());
338 StringView emptyStringView(*empty.get());
339 StringView shorterStringView(*shorter.get());
340 StringView differentStringView(*different.get());
341
342 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewB));
343 ASSERT_TRUE(equalIgnoringASCIICase(stringViewB, stringViewC));
344 ASSERT_TRUE(equalIgnoringASCIICase(stringViewB, stringViewC));
345 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, d));
346 ASSERT_TRUE(equalIgnoringASCIICase(stringViewB, d));
347 ASSERT_TRUE(equalIgnoringASCIICase(stringViewC, d));
348
349 // Identity.
350 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewA));
351 ASSERT_TRUE(equalIgnoringASCIICase(stringViewB, stringViewB));
352 ASSERT_TRUE(equalIgnoringASCIICase(stringViewC, stringViewC));
353
354 // Transitivity.
355 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewB));
356 ASSERT_TRUE(equalIgnoringASCIICase(stringViewB, stringViewC));
357 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewC));
358
359 // Negative cases.
360 ASSERT_FALSE(equalIgnoringASCIICase(stringViewA, emptyStringView));
361 ASSERT_FALSE(equalIgnoringASCIICase(stringViewB, emptyStringView));
362 ASSERT_FALSE(equalIgnoringASCIICase(stringViewC, emptyStringView));
363 ASSERT_FALSE(equalIgnoringASCIICase(stringViewA, shorterStringView));
364 ASSERT_FALSE(equalIgnoringASCIICase(stringViewB, shorterStringView));
365 ASSERT_FALSE(equalIgnoringASCIICase(stringViewC, shorterStringView));
366 ASSERT_FALSE(equalIgnoringASCIICase(stringViewA, differentStringView));
367 ASSERT_FALSE(equalIgnoringASCIICase(stringViewB, differentStringView));
368 ASSERT_FALSE(equalIgnoringASCIICase(stringViewC, differentStringView));
369 ASSERT_FALSE(equalIgnoringASCIICase(emptyStringView, d));
370 ASSERT_FALSE(equalIgnoringASCIICase(shorterStringView, d));
371 ASSERT_FALSE(equalIgnoringASCIICase(differentStringView, d));
372}
373
374TEST(WTF, StringViewEqualIgnoringASCIICaseWithEmpty)
375{
376 RefPtr<StringImpl> a = StringImpl::create(reinterpret_cast<const LChar*>(""));
377 RefPtr<StringImpl> b = StringImpl::create(reinterpret_cast<const LChar*>(""));
378 StringView stringViewA(*a.get());
379 StringView stringViewB(*b.get());
380 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewB));
381 ASSERT_TRUE(equalIgnoringASCIICase(stringViewB, stringViewA));
382}
383
384TEST(WTF, StringViewEqualIgnoringASCIICaseWithLatin1Characters)
385{
386 RefPtr<StringImpl> a = StringImpl::create(reinterpret_cast<const LChar*>("aBcéeFG"));
387 RefPtr<StringImpl> b = StringImpl::create(reinterpret_cast<const LChar*>("ABCÉEFG"));
388 RefPtr<StringImpl> c = StringImpl::create(reinterpret_cast<const LChar*>("ABCéEFG"));
389 RefPtr<StringImpl> d = StringImpl::create(reinterpret_cast<const LChar*>("abcéefg"));
390 const char e[] = "aBcéeFG";
391 StringView stringViewA(*a.get());
392 StringView stringViewB(*b.get());
393 StringView stringViewC(*c.get());
394 StringView stringViewD(*d.get());
395
396 // Identity.
397 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewA));
398 ASSERT_TRUE(equalIgnoringASCIICase(stringViewB, stringViewB));
399 ASSERT_TRUE(equalIgnoringASCIICase(stringViewC, stringViewC));
400 ASSERT_TRUE(equalIgnoringASCIICase(stringViewD, stringViewD));
401
402 // All combination.
403 ASSERT_FALSE(equalIgnoringASCIICase(stringViewA, stringViewB));
404 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewC));
405 ASSERT_TRUE(equalIgnoringASCIICase(stringViewA, stringViewD));
406 ASSERT_FALSE(equalIgnoringASCIICase(stringViewB, stringViewC));
407 ASSERT_FALSE(equalIgnoringASCIICase(stringViewB, stringViewD));
408 ASSERT_TRUE(equalIgnoringASCIICase(stringViewC, stringViewD));
409 ASSERT_FALSE(equalIgnoringASCIICase(stringViewA, e));
410 ASSERT_FALSE(equalIgnoringASCIICase(stringViewB, e));
411 ASSERT_FALSE(equalIgnoringASCIICase(stringViewC, e));
412 ASSERT_FALSE(equalIgnoringASCIICase(stringViewD, e));
413}
414
415TEST(WTF, StringViewFindIgnoringASCIICaseBasic)
416{
417 String referenceAHolder;
418 StringView referenceA = stringViewFromUTF8(referenceAHolder, "aBcéeFG");
419 String referenceBHolder;
420 StringView referenceB = stringViewFromUTF8(referenceBHolder, "ABCÉEFG");
421
422 // Search the exact string.
423 EXPECT_EQ(static_cast<size_t>(0), referenceA.findIgnoringASCIICase(referenceA));
424 EXPECT_EQ(static_cast<size_t>(0), referenceB.findIgnoringASCIICase(referenceB));
425
426 // A and B are distinct by the non-ascii character é/É.
427 EXPECT_EQ(static_cast<size_t>(notFound), referenceA.findIgnoringASCIICase(referenceB));
428 EXPECT_EQ(static_cast<size_t>(notFound), referenceB.findIgnoringASCIICase(referenceA));
429
430 String tempStringHolder;
431 // Find the prefix.
432 EXPECT_EQ(static_cast<size_t>(0), referenceA.findIgnoringASCIICase(stringViewFromLiteral("a")));
433 EXPECT_EQ(static_cast<size_t>(0), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "abcé")));
434 EXPECT_EQ(static_cast<size_t>(0), referenceA.findIgnoringASCIICase(stringViewFromLiteral("A")));
435 EXPECT_EQ(static_cast<size_t>(0), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCé")));
436 EXPECT_EQ(static_cast<size_t>(0), referenceB.findIgnoringASCIICase(stringViewFromLiteral("a")));
437 EXPECT_EQ(static_cast<size_t>(0), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "abcÉ")));
438 EXPECT_EQ(static_cast<size_t>(0), referenceB.findIgnoringASCIICase(stringViewFromLiteral("A")));
439 EXPECT_EQ(static_cast<size_t>(0), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCÉ")));
440
441 // Not a prefix.
442 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromLiteral("x")));
443 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "accé")));
444 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "abcÉ")));
445 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromLiteral("X")));
446 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABDé")));
447 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCÉ")));
448 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromLiteral("y")));
449 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "accÉ")));
450 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "abcé")));
451 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromLiteral("Y")));
452 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABdÉ")));
453 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCé")));
454
455 // Find the infix.
456 EXPECT_EQ(static_cast<size_t>(2), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "cée")));
457 EXPECT_EQ(static_cast<size_t>(3), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ée")));
458 EXPECT_EQ(static_cast<size_t>(2), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "cé")));
459 EXPECT_EQ(static_cast<size_t>(2), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "c")));
460 EXPECT_EQ(static_cast<size_t>(3), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "é")));
461 EXPECT_EQ(static_cast<size_t>(2), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Cée")));
462 EXPECT_EQ(static_cast<size_t>(3), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "éE")));
463 EXPECT_EQ(static_cast<size_t>(2), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Cé")));
464 EXPECT_EQ(static_cast<size_t>(2), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "C")));
465
466 EXPECT_EQ(static_cast<size_t>(2), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "cÉe")));
467 EXPECT_EQ(static_cast<size_t>(3), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Ée")));
468 EXPECT_EQ(static_cast<size_t>(2), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "cÉ")));
469 EXPECT_EQ(static_cast<size_t>(2), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "c")));
470 EXPECT_EQ(static_cast<size_t>(3), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "É")));
471 EXPECT_EQ(static_cast<size_t>(2), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "CÉe")));
472 EXPECT_EQ(static_cast<size_t>(3), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ÉE")));
473 EXPECT_EQ(static_cast<size_t>(2), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "CÉ")));
474 EXPECT_EQ(static_cast<size_t>(2), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "C")));
475
476 // Not an infix.
477 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "céd")));
478 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Ée")));
479 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "bé")));
480 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "x")));
481 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "É")));
482 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "CÉe")));
483 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "éd")));
484 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "CÉ")));
485 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Y")));
486
487 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "cée")));
488 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Éc")));
489 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "cé")));
490 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "W")));
491 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "é")));
492 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "bÉe")));
493 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "éE")));
494 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "BÉ")));
495 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "z")));
496
497 // Find the suffix.
498 EXPECT_EQ(static_cast<size_t>(6), referenceA.findIgnoringASCIICase(stringViewFromLiteral("g")));
499 EXPECT_EQ(static_cast<size_t>(4), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "efg")));
500 EXPECT_EQ(static_cast<size_t>(3), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "éefg")));
501 EXPECT_EQ(static_cast<size_t>(6), referenceA.findIgnoringASCIICase(stringViewFromLiteral("G")));
502 EXPECT_EQ(static_cast<size_t>(4), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "EFG")));
503 EXPECT_EQ(static_cast<size_t>(3), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "éEFG")));
504
505 EXPECT_EQ(static_cast<size_t>(6), referenceB.findIgnoringASCIICase(stringViewFromLiteral("g")));
506 EXPECT_EQ(static_cast<size_t>(4), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "efg")));
507 EXPECT_EQ(static_cast<size_t>(3), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Éefg")));
508 EXPECT_EQ(static_cast<size_t>(6), referenceB.findIgnoringASCIICase(stringViewFromLiteral("G")));
509 EXPECT_EQ(static_cast<size_t>(4), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "EFG")));
510 EXPECT_EQ(static_cast<size_t>(3), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ÉEFG")));
511
512 // Not a suffix.
513 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromLiteral("X")));
514 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "edg")));
515 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "Éefg")));
516 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromLiteral("w")));
517 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "dFG")));
518 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceA.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ÉEFG")));
519
520 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromLiteral("Z")));
521 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ffg")));
522 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "éefg")));
523 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromLiteral("r")));
524 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "EgG")));
525 EXPECT_EQ(static_cast<size_t>(WTF::notFound), referenceB.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "éEFG")));
526}
527
528TEST(WTF, StringViewFindIgnoringASCIICaseWithValidOffset)
529{
530 String referenceHolder;
531 StringView reference = stringViewFromUTF8(referenceHolder, "ABCÉEFGaBcéeFG");
532 String tempStringHolder;
533
534 EXPECT_EQ(static_cast<size_t>(0), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABC"), 0));
535 EXPECT_EQ(static_cast<size_t>(7), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABC"), 1));
536 EXPECT_EQ(static_cast<size_t>(0), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCÉ"), 0));
537 EXPECT_EQ(static_cast<size_t>(WTF::notFound), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCÉ"), 1));
538 EXPECT_EQ(static_cast<size_t>(7), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCé"), 0));
539 EXPECT_EQ(static_cast<size_t>(7), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCé"), 1));
540}
541
542TEST(WTF, StringViewFindIgnoringASCIICaseWithInvalidOffset)
543{
544 String referenceHolder;
545 StringView reference = stringViewFromUTF8(referenceHolder, "ABCÉEFGaBcéeFG");
546 String tempStringHolder;
547
548 EXPECT_EQ(static_cast<size_t>(WTF::notFound), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABC"), 15));
549 EXPECT_EQ(static_cast<size_t>(WTF::notFound), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABC"), 16));
550 EXPECT_EQ(static_cast<size_t>(WTF::notFound), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCÉ"), 17));
551 EXPECT_EQ(static_cast<size_t>(WTF::notFound), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCÉ"), 42));
552 EXPECT_EQ(static_cast<size_t>(WTF::notFound), reference.findIgnoringASCIICase(stringViewFromUTF8(tempStringHolder, "ABCÉ"), std::numeric_limits<unsigned>::max()));
553}
554
555TEST(WTF, StringViewFindIgnoringASCIICaseOnEmpty)
556{
557 String referenceHolder;
558 StringView reference = stringViewFromUTF8(referenceHolder, "ABCÉEFG");
559 StringView empty = stringViewFromLiteral("");
560 EXPECT_EQ(static_cast<size_t>(0), reference.findIgnoringASCIICase(empty));
561 EXPECT_EQ(static_cast<size_t>(0), reference.findIgnoringASCIICase(empty, 0));
562 EXPECT_EQ(static_cast<size_t>(3), reference.findIgnoringASCIICase(empty, 3));
563 EXPECT_EQ(static_cast<size_t>(7), reference.findIgnoringASCIICase(empty, 7));
564 EXPECT_EQ(static_cast<size_t>(7), reference.findIgnoringASCIICase(empty, 8));
565 EXPECT_EQ(static_cast<size_t>(7), reference.findIgnoringASCIICase(empty, 42));
566 EXPECT_EQ(static_cast<size_t>(7), reference.findIgnoringASCIICase(empty, std::numeric_limits<unsigned>::max()));
567}
568
569TEST(WTF, StringViewFindIgnoringASCIICaseWithPatternLongerThanReference)
570{
571 String referenceHolder;
572 StringView reference = stringViewFromUTF8(referenceHolder, "ABCÉEFG");
573 String patternHolder;
574 StringView pattern = stringViewFromUTF8(patternHolder, "ABCÉEFGA");
575
576 EXPECT_EQ(static_cast<size_t>(WTF::notFound), reference.findIgnoringASCIICase(pattern));
577 EXPECT_EQ(static_cast<size_t>(0), pattern.findIgnoringASCIICase(reference));
578}
579
580TEST(WTF, StringViewStartsWithBasic)
581{
582 StringView reference = stringViewFromLiteral("abcdefg");
583 String referenceUTF8Ref;
584 StringView referenceUTF8 = stringViewFromUTF8(referenceUTF8Ref, "àîûèô");
585
586 StringView oneLetterPrefix = stringViewFromLiteral("a");
587 StringView shortPrefix = stringViewFromLiteral("abc");
588 StringView longPrefix = stringViewFromLiteral("abcdef");
589 StringView upperCasePrefix = stringViewFromLiteral("ABC");
590 StringView empty = stringViewFromLiteral("");
591 StringView notPrefix = stringViewFromLiteral("bc");
592
593 String oneLetterPrefixUTF8Ref;
594 StringView oneLetterPrefixUTF8 = stringViewFromUTF8(oneLetterPrefixUTF8Ref, "à");
595 String shortPrefixUTF8Ref;
596 StringView shortPrefixUTF8 = stringViewFromUTF8(shortPrefixUTF8Ref, "àî");
597 String longPrefixUTF8Ref;
598 StringView longPrefixUTF8 = stringViewFromUTF8(longPrefixUTF8Ref, "àîûè");
599 String upperCasePrefixUTF8Ref;
600 StringView upperCasePrefixUTF8 = stringViewFromUTF8(upperCasePrefixUTF8Ref, "ÀÎ");
601 String notPrefixUTF8Ref;
602 StringView notPrefixUTF8 = stringViewFromUTF8(notPrefixUTF8Ref, "îû");
603
604 EXPECT_TRUE(reference.startsWith(reference));
605 EXPECT_TRUE(reference.startsWith(oneLetterPrefix));
606 EXPECT_TRUE(reference.startsWith(shortPrefix));
607 EXPECT_TRUE(reference.startsWith(longPrefix));
608 EXPECT_TRUE(reference.startsWith(empty));
609
610 EXPECT_TRUE(referenceUTF8.startsWith(referenceUTF8));
611 EXPECT_TRUE(referenceUTF8.startsWith(oneLetterPrefixUTF8));
612 EXPECT_TRUE(referenceUTF8.startsWith(shortPrefixUTF8));
613 EXPECT_TRUE(referenceUTF8.startsWith(longPrefixUTF8));
614 EXPECT_TRUE(referenceUTF8.startsWith(empty));
615
616 EXPECT_FALSE(reference.startsWith(notPrefix));
617 EXPECT_FALSE(reference.startsWith(upperCasePrefix));
618 EXPECT_FALSE(reference.startsWith(notPrefixUTF8));
619 EXPECT_FALSE(reference.startsWith(upperCasePrefixUTF8));
620 EXPECT_FALSE(referenceUTF8.startsWith(notPrefix));
621 EXPECT_FALSE(referenceUTF8.startsWith(upperCasePrefix));
622 EXPECT_FALSE(referenceUTF8.startsWith(notPrefixUTF8));
623 EXPECT_FALSE(referenceUTF8.startsWith(upperCasePrefixUTF8));
624}
625
626TEST(WTF, StringViewStartsWithEmpty)
627{
628 StringView a = stringViewFromLiteral("");
629 String refB;
630 StringView b = stringViewFromUTF8(refB, "");
631
632 EXPECT_TRUE(a.startsWith(a));
633 EXPECT_TRUE(a.startsWith(b));
634 EXPECT_TRUE(b.startsWith(a));
635 EXPECT_TRUE(b.startsWith(b));
636}
637
638TEST(WTF, StringViewStartsWithIgnoringASCIICaseBasic)
639{
640 StringView reference = stringViewFromLiteral("abcdefg");
641
642 String referenceUTF8Ref;
643 StringView referenceUTF8 = stringViewFromUTF8(referenceUTF8Ref, "àîûèô");
644
645 StringView oneLetterPrefix = stringViewFromLiteral("a");
646 StringView shortPrefix = stringViewFromLiteral("abc");
647 StringView longPrefix = stringViewFromLiteral("abcdef");
648 StringView upperCasePrefix = stringViewFromLiteral("ABC");
649 StringView mixedCasePrefix = stringViewFromLiteral("aBcDe");
650 StringView empty = stringViewFromLiteral("");
651 StringView notPrefix = stringViewFromLiteral("bc");
652
653 String oneLetterPrefixUTF8Ref;
654 StringView oneLetterPrefixUTF8 = stringViewFromUTF8(oneLetterPrefixUTF8Ref, "à");
655 String shortPrefixUTF8Ref;
656 StringView shortPrefixUTF8 = stringViewFromUTF8(shortPrefixUTF8Ref, "àî");
657 String longPrefixUTF8Ref;
658 StringView longPrefixUTF8 = stringViewFromUTF8(longPrefixUTF8Ref, "àîûè");
659 String upperCasePrefixUTF8Ref;
660 StringView upperCasePrefixUTF8 = stringViewFromUTF8(upperCasePrefixUTF8Ref, "ÀÎ");
661 String notPrefixUTF8Ref;
662 StringView notPrefixUTF8 = stringViewFromUTF8(notPrefixUTF8Ref, "îû");
663
664 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(reference));
665 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(oneLetterPrefix));
666 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(shortPrefix));
667 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(longPrefix));
668 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(empty));
669 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(upperCasePrefix));
670 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(mixedCasePrefix));
671
672 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(referenceUTF8));
673 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(oneLetterPrefixUTF8));
674 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(shortPrefixUTF8));
675 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(longPrefixUTF8));
676 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(empty));
677
678 EXPECT_FALSE(reference.startsWithIgnoringASCIICase(notPrefix));
679 EXPECT_FALSE(reference.startsWithIgnoringASCIICase(notPrefixUTF8));
680 EXPECT_FALSE(reference.startsWithIgnoringASCIICase(upperCasePrefixUTF8));
681 EXPECT_FALSE(referenceUTF8.startsWithIgnoringASCIICase(notPrefix));
682 EXPECT_FALSE(referenceUTF8.startsWithIgnoringASCIICase(notPrefixUTF8));
683 EXPECT_FALSE(referenceUTF8.startsWithIgnoringASCIICase(upperCasePrefix));
684 EXPECT_FALSE(referenceUTF8.startsWithIgnoringASCIICase(upperCasePrefixUTF8));
685}
686
687
688TEST(WTF, StringViewStartsWithIgnoringASCIICaseEmpty)
689{
690 StringView a = stringViewFromLiteral("");
691 String refB;
692 StringView b = stringViewFromUTF8(refB, "");
693
694 EXPECT_TRUE(a.startsWithIgnoringASCIICase(a));
695 EXPECT_TRUE(a.startsWithIgnoringASCIICase(b));
696 EXPECT_TRUE(b.startsWithIgnoringASCIICase(a));
697 EXPECT_TRUE(b.startsWithIgnoringASCIICase(b));
698}
699
700TEST(WTF, StringViewStartsWithIgnoringASCIICaseWithLatin1Characters)
701{
702 StringView reference = stringViewFromLiteral("aBcéeFG");
703 String referenceUTF8Ref;
704 StringView referenceUTF8 = stringViewFromUTF8(referenceUTF8Ref, "aBcéeFG");
705
706 StringView a = stringViewFromLiteral("aBcéeF");
707 StringView b = stringViewFromLiteral("ABCéEF");
708 StringView c = stringViewFromLiteral("abcéef");
709 StringView d = stringViewFromLiteral("Abcéef");
710
711 String refE;
712 StringView e = stringViewFromUTF8(refE, "aBcéeF");
713 String refF;
714 StringView f = stringViewFromUTF8(refF, "ABCéEF");
715 String refG;
716 StringView g = stringViewFromUTF8(refG, "abcéef");
717 String refH;
718 StringView h = stringViewFromUTF8(refH, "Abcéef");
719
720 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(a));
721 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(b));
722 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(c));
723 EXPECT_TRUE(reference.startsWithIgnoringASCIICase(d));
724
725 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(e));
726 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(f));
727 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(g));
728 EXPECT_TRUE(referenceUTF8.startsWithIgnoringASCIICase(h));
729
730 EXPECT_FALSE(reference.endsWithIgnoringASCIICase(referenceUTF8));
731 EXPECT_FALSE(referenceUTF8.endsWithIgnoringASCIICase(reference));
732}
733
734TEST(WTF, StringViewEndsWithBasic)
735{
736 StringView reference = stringViewFromLiteral("abcdefg");
737 String referenceUTF8Ref;
738 StringView referenceUTF8 = stringViewFromUTF8(referenceUTF8Ref, "àîûèô");
739
740 StringView oneLetterSuffix = stringViewFromLiteral("g");
741 StringView shortSuffix = stringViewFromLiteral("efg");
742 StringView longSuffix = stringViewFromLiteral("cdefg");
743 StringView upperCaseSuffix = stringViewFromLiteral("EFG");
744 StringView empty = stringViewFromLiteral("");
745 StringView notSuffix = stringViewFromLiteral("bc");
746
747 String oneLetterSuffixUTF8Ref;
748 StringView oneLetterSuffixUTF8 = stringViewFromUTF8(oneLetterSuffixUTF8Ref, "ô");
749 String shortSuffixUTF8Ref;
750 StringView shortSuffixUTF8 = stringViewFromUTF8(shortSuffixUTF8Ref, "èô");
751 String longSuffixUTF8Ref;
752 StringView longSuffixUTF8 = stringViewFromUTF8(longSuffixUTF8Ref, "îûèô");
753 String upperCaseSuffixUTF8Ref;
754 StringView upperCaseSuffixUTF8 = stringViewFromUTF8(upperCaseSuffixUTF8Ref, "ÈÔ");
755 String notSuffixUTF8Ref;
756 StringView notSuffixUTF8 = stringViewFromUTF8(notSuffixUTF8Ref, "îû");
757
758 EXPECT_TRUE(reference.endsWith(reference));
759 EXPECT_TRUE(reference.endsWith(oneLetterSuffix));
760 EXPECT_TRUE(reference.endsWith(shortSuffix));
761 EXPECT_TRUE(reference.endsWith(longSuffix));
762 EXPECT_TRUE(reference.endsWith(empty));
763
764 EXPECT_TRUE(referenceUTF8.endsWith(referenceUTF8));
765 EXPECT_TRUE(referenceUTF8.endsWith(oneLetterSuffixUTF8));
766 EXPECT_TRUE(referenceUTF8.endsWith(shortSuffixUTF8));
767 EXPECT_TRUE(referenceUTF8.endsWith(longSuffixUTF8));
768 EXPECT_TRUE(referenceUTF8.endsWith(empty));
769
770 EXPECT_FALSE(reference.endsWith(notSuffix));
771 EXPECT_FALSE(reference.endsWith(upperCaseSuffix));
772 EXPECT_FALSE(reference.endsWith(notSuffixUTF8));
773 EXPECT_FALSE(reference.endsWith(upperCaseSuffixUTF8));
774 EXPECT_FALSE(referenceUTF8.endsWith(notSuffix));
775 EXPECT_FALSE(referenceUTF8.endsWith(upperCaseSuffix));
776 EXPECT_FALSE(referenceUTF8.endsWith(notSuffixUTF8));
777 EXPECT_FALSE(referenceUTF8.endsWith(upperCaseSuffixUTF8));
778}
779
780TEST(WTF, StringViewEndsWithEmpty)
781{
782 StringView a = stringViewFromLiteral("");
783 String refB;
784 StringView b = stringViewFromUTF8(refB, "");
785
786 EXPECT_TRUE(a.endsWith(a));
787 EXPECT_TRUE(a.endsWith(b));
788 EXPECT_TRUE(b.endsWith(a));
789 EXPECT_TRUE(b.endsWith(b));
790}
791
792TEST(WTF, StringViewEndsWithIgnoringASCIICaseBasic)
793{
794 StringView reference = stringViewFromLiteral("abcdefg");
795 String referenceUTF8Ref;
796 StringView referenceUTF8 = stringViewFromUTF8(referenceUTF8Ref, "àîûèô");
797
798 StringView oneLetterSuffix = stringViewFromLiteral("g");
799 StringView shortSuffix = stringViewFromLiteral("efg");
800 StringView longSuffix = stringViewFromLiteral("bcdefg");
801 StringView upperCaseSuffix = stringViewFromLiteral("EFG");
802 StringView mixedCaseSuffix = stringViewFromLiteral("bCdeFg");
803 StringView empty = stringViewFromLiteral("");
804 StringView notSuffix = stringViewFromLiteral("bc");
805
806 String oneLetterSuffixUTF8Ref;
807 StringView oneLetterSuffixUTF8 = stringViewFromUTF8(oneLetterSuffixUTF8Ref, "ô");
808 String shortSuffixUTF8Ref;
809 StringView shortSuffixUTF8 = stringViewFromUTF8(shortSuffixUTF8Ref, "èô");
810 String longSuffixUTF8Ref;
811 StringView longSuffixUTF8 = stringViewFromUTF8(longSuffixUTF8Ref, "îûèô");
812 String upperCaseSuffixUTF8Ref;
813 StringView upperCaseSuffixUTF8 = stringViewFromUTF8(upperCaseSuffixUTF8Ref, "ÈÔ");
814 String notSuffixUTF8Ref;
815 StringView notSuffixUTF8 = stringViewFromUTF8(notSuffixUTF8Ref, "îû");
816
817 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(reference));
818 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(oneLetterSuffix));
819 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(shortSuffix));
820 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(longSuffix));
821 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(empty));
822 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(upperCaseSuffix));
823 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(mixedCaseSuffix));
824
825 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(referenceUTF8));
826 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(oneLetterSuffixUTF8));
827 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(shortSuffixUTF8));
828 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(longSuffixUTF8));
829 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(empty));
830
831 EXPECT_FALSE(reference.endsWithIgnoringASCIICase(notSuffix));
832 EXPECT_FALSE(reference.endsWithIgnoringASCIICase(notSuffixUTF8));
833 EXPECT_FALSE(reference.endsWithIgnoringASCIICase(upperCaseSuffixUTF8));
834 EXPECT_FALSE(referenceUTF8.endsWithIgnoringASCIICase(notSuffix));
835 EXPECT_FALSE(referenceUTF8.endsWithIgnoringASCIICase(notSuffixUTF8));
836 EXPECT_FALSE(referenceUTF8.endsWithIgnoringASCIICase(upperCaseSuffix));
837 EXPECT_FALSE(referenceUTF8.endsWithIgnoringASCIICase(upperCaseSuffixUTF8));
838}
839
840TEST(WTF, StringViewEndsWithIgnoringASCIICaseEmpty)
841{
842 StringView a = stringViewFromLiteral("");
843 String refB;
844 StringView b = stringViewFromUTF8(refB, "");
845
846 EXPECT_TRUE(a.endsWithIgnoringASCIICase(a));
847 EXPECT_TRUE(a.endsWithIgnoringASCIICase(b));
848 EXPECT_TRUE(b.endsWithIgnoringASCIICase(a));
849 EXPECT_TRUE(b.endsWithIgnoringASCIICase(b));
850}
851
852TEST(WTF, StringViewEndsWithIgnoringASCIICaseWithLatin1Characters)
853{
854 StringView reference = stringViewFromLiteral("aBcéeFG");
855 String referenceUTF8Ref;
856 StringView referenceUTF8 = stringViewFromUTF8(referenceUTF8Ref, "aBcéeFG");
857
858 StringView a = stringViewFromLiteral("BcéeFG");
859 StringView b = stringViewFromLiteral("BCéEFG");
860 StringView c = stringViewFromLiteral("bcéefG");
861 StringView d = stringViewFromLiteral("bcéefg");
862
863 String refE;
864 StringView e = stringViewFromUTF8(refE, "bcéefG");
865 String refF;
866 StringView f = stringViewFromUTF8(refF, "BCéEFG");
867 String refG;
868 StringView g = stringViewFromUTF8(refG, "bcéefG");
869 String refH;
870 StringView h = stringViewFromUTF8(refH, "bcéefg");
871
872 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(a));
873 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(b));
874 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(c));
875 EXPECT_TRUE(reference.endsWithIgnoringASCIICase(d));
876
877 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(e));
878 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(f));
879 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(g));
880 EXPECT_TRUE(referenceUTF8.endsWithIgnoringASCIICase(h));
881
882 EXPECT_FALSE(reference.endsWithIgnoringASCIICase(referenceUTF8));
883 EXPECT_FALSE(referenceUTF8.endsWithIgnoringASCIICase(reference));
884}
885
886TEST(WTF, StringView8Bit)
887{
888 StringView nullView;
889 EXPECT_TRUE(StringView().is8Bit());
890 EXPECT_TRUE(StringView::empty().is8Bit());
891
892 LChar* lcharPtr = nullptr;
893 UChar* ucharPtr = nullptr;
894 EXPECT_TRUE(StringView(lcharPtr, 0).is8Bit());
895 EXPECT_FALSE(StringView(ucharPtr, 0).is8Bit());
896
897 EXPECT_TRUE(StringView(String(lcharPtr, 0)).is8Bit());
898 EXPECT_TRUE(StringView(String(ucharPtr, 0)).is8Bit());
899
900 EXPECT_TRUE(StringView(String().impl()).is8Bit());
901 EXPECT_TRUE(StringView(emptyString().impl()).is8Bit());
902}
903
904TEST(WTF, StringViewRightBasic)
905{
906 auto reference = stringViewFromLiteral("Cappuccino");
907 EXPECT_TRUE(reference.right(0) == stringViewFromLiteral(""));
908 EXPECT_TRUE(reference.right(1) == stringViewFromLiteral("o"));
909 EXPECT_TRUE(reference.right(2) == stringViewFromLiteral("no"));
910 EXPECT_TRUE(reference.right(3) == stringViewFromLiteral("ino"));
911 EXPECT_TRUE(reference.right(4) == stringViewFromLiteral("cino"));
912 EXPECT_TRUE(reference.right(5) == stringViewFromLiteral("ccino"));
913 EXPECT_TRUE(reference.right(6) == stringViewFromLiteral("uccino"));
914 EXPECT_TRUE(reference.right(7) == stringViewFromLiteral("puccino"));
915 EXPECT_TRUE(reference.right(8) == stringViewFromLiteral("ppuccino"));
916 EXPECT_TRUE(reference.right(9) == stringViewFromLiteral("appuccino"));
917 EXPECT_TRUE(reference.right(10) == stringViewFromLiteral("Cappuccino"));
918}
919
920TEST(WTF, StringViewLeftBasic)
921{
922 auto reference = stringViewFromLiteral("Cappuccino");
923 EXPECT_TRUE(reference.left(0) == stringViewFromLiteral(""));
924 EXPECT_TRUE(reference.left(1) == stringViewFromLiteral("C"));
925 EXPECT_TRUE(reference.left(2) == stringViewFromLiteral("Ca"));
926 EXPECT_TRUE(reference.left(3) == stringViewFromLiteral("Cap"));
927 EXPECT_TRUE(reference.left(4) == stringViewFromLiteral("Capp"));
928 EXPECT_TRUE(reference.left(5) == stringViewFromLiteral("Cappu"));
929 EXPECT_TRUE(reference.left(6) == stringViewFromLiteral("Cappuc"));
930 EXPECT_TRUE(reference.left(7) == stringViewFromLiteral("Cappucc"));
931 EXPECT_TRUE(reference.left(8) == stringViewFromLiteral("Cappucci"));
932 EXPECT_TRUE(reference.left(9) == stringViewFromLiteral("Cappuccin"));
933 EXPECT_TRUE(reference.left(10) == stringViewFromLiteral("Cappuccino"));
934}
935
936TEST(WTF, StringViewReverseFindBasic)
937{
938 auto reference = stringViewFromLiteral("Cappuccino");
939 EXPECT_EQ(reference.reverseFind('o'), 9U);
940 EXPECT_EQ(reference.reverseFind('n'), 8U);
941 EXPECT_EQ(reference.reverseFind('c'), 6U);
942 EXPECT_EQ(reference.reverseFind('p'), 3U);
943 EXPECT_EQ(reference.reverseFind('k'), notFound);
944
945 EXPECT_EQ(reference.reverseFind('o', 8), notFound);
946 EXPECT_EQ(reference.reverseFind('c', 8), 6U);
947 EXPECT_EQ(reference.reverseFind('c', 6), 6U);
948 EXPECT_EQ(reference.reverseFind('c', 5), 5U);
949 EXPECT_EQ(reference.reverseFind('c', 4), notFound);
950}
951
952TEST(WTF, StringViewStripLeadingAndTrailingMatchedCharacters)
953{
954 auto isA = [] (UChar c) {
955 return c == 'A';
956 };
957
958 EXPECT_TRUE(stringViewFromLiteral("AAABBBAAA").stripLeadingAndTrailingMatchedCharacters(isA) == stringViewFromLiteral("BBB"));
959 EXPECT_TRUE(stringViewFromLiteral("AAABBBCCC").stripLeadingAndTrailingMatchedCharacters(isA) == stringViewFromLiteral("BBBCCC"));
960 EXPECT_TRUE(stringViewFromLiteral("CCCBBBAAA").stripLeadingAndTrailingMatchedCharacters(isA) == stringViewFromLiteral("CCCBBB"));
961 EXPECT_TRUE(stringViewFromLiteral("CCCBBBCCC").stripLeadingAndTrailingMatchedCharacters(isA) == stringViewFromLiteral("CCCBBBCCC"));
962 EXPECT_TRUE(stringViewFromLiteral("AAAAAACCC").stripLeadingAndTrailingMatchedCharacters(isA) == stringViewFromLiteral("CCC"));
963 EXPECT_TRUE(stringViewFromLiteral("BBBAAAAAA").stripLeadingAndTrailingMatchedCharacters(isA) == stringViewFromLiteral("BBB"));
964 EXPECT_TRUE(stringViewFromLiteral("CCCAAABBB").stripLeadingAndTrailingMatchedCharacters(isA) == stringViewFromLiteral("CCCAAABBB"));
965 EXPECT_TRUE(stringViewFromLiteral("AAAAAAAAA").stripLeadingAndTrailingMatchedCharacters(isA) == StringView::empty());
966
967 StringView emptyView = StringView::empty();
968 EXPECT_TRUE(emptyView.stripLeadingAndTrailingMatchedCharacters(isA) == emptyView);
969
970 StringView nullView;
971 EXPECT_TRUE(nullView.stripLeadingAndTrailingMatchedCharacters(isA) == nullView);
972}
973
974} // namespace TestWebKitAPI
975