2 * Copyright 2014 Facebook, Inc.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
19 #include <folly/small_vector.h>
20 #include <gtest/gtest.h>
24 #include <type_traits>
26 #include <folly/Memory.h>
27 #include <folly/Executor.h>
28 #include <folly/futures/Future.h>
29 #include <folly/futures/ManualExecutor.h>
30 #include <folly/futures/DrivableExecutor.h>
31 #include <folly/MPMCQueue.h>
33 #include <folly/io/async/Request.h>
35 using namespace folly;
38 using std::unique_ptr;
41 #define EXPECT_TYPE(x, T) \
42 EXPECT_TRUE((std::is_same<decltype(x), T>::value))
44 /// Simple executor that does work in another thread
45 class ThreadExecutor : public Executor {
46 folly::MPMCQueue<Func> funcs;
47 std::atomic<bool> done {false};
55 while (!funcs.isEmpty()) {
56 funcs.blockingRead(fn);
63 explicit ThreadExecutor(size_t n = 1024)
64 : funcs(n), worker(std::bind(&ThreadExecutor::work, this)) {}
72 void add(Func fn) override {
73 funcs.blockingWrite(std::move(fn));
76 void waitForStartup() {
81 typedef FutureException eggs_t;
82 static eggs_t eggs("eggs");
86 TEST(Future, onError) {
88 auto flag = [&]{ theFlag = true; };
89 #define EXPECT_FLAG() \
91 EXPECT_TRUE(theFlag); \
95 #define EXPECT_NO_FLAG() \
97 EXPECT_FALSE(theFlag); \
103 auto f = makeFuture()
104 .then([] { throw eggs; })
105 .onError([&] (eggs_t& e) { flag(); });
107 EXPECT_NO_THROW(f.value());
111 auto f = makeFuture()
112 .then([] { throw eggs; })
113 .onError([&] (eggs_t& e) { flag(); return makeFuture(); });
115 EXPECT_NO_THROW(f.value());
120 auto f = makeFuture()
121 .then([] { throw eggs; })
122 .onError([&] (eggs_t e) { flag(); });
124 EXPECT_NO_THROW(f.value());
128 auto f = makeFuture()
129 .then([] { throw eggs; })
130 .onError([&] (eggs_t e) { flag(); return makeFuture(); });
132 EXPECT_NO_THROW(f.value());
137 auto f = makeFuture()
138 .then([] { throw eggs; })
139 .onError([&] (std::exception& e) { flag(); });
141 EXPECT_NO_THROW(f.value());
145 auto f = makeFuture()
146 .then([] { throw eggs; })
147 .onError([&] (std::exception& e) { flag(); return makeFuture(); });
149 EXPECT_NO_THROW(f.value());
154 auto f = makeFuture()
155 .then([] { throw -1; })
156 .onError([&] (int e) { flag(); });
158 EXPECT_NO_THROW(f.value());
162 auto f = makeFuture()
163 .then([] { throw -1; })
164 .onError([&] (int e) { flag(); return makeFuture(); });
166 EXPECT_NO_THROW(f.value());
171 auto f = makeFuture()
172 .then([] { throw eggs; })
173 .onError([&] (eggs_t& e) mutable { flag(); });
175 EXPECT_NO_THROW(f.value());
179 auto f = makeFuture()
180 .then([] { throw eggs; })
181 .onError([&] (eggs_t& e) mutable { flag(); return makeFuture(); });
183 EXPECT_NO_THROW(f.value());
188 auto f = makeFuture()
189 .then([] { return 42; })
190 .onError([&] (eggs_t& e) { flag(); return -1; });
192 EXPECT_EQ(42, f.value());
196 auto f = makeFuture()
197 .then([] { return 42; })
198 .onError([&] (eggs_t& e) { flag(); return makeFuture<int>(-1); });
200 EXPECT_EQ(42, f.value());
203 // Catch different exception
205 auto f = makeFuture()
206 .then([] { throw eggs; })
207 .onError([&] (std::runtime_error& e) { flag(); });
209 EXPECT_THROW(f.value(), eggs_t);
213 auto f = makeFuture()
214 .then([] { throw eggs; })
215 .onError([&] (std::runtime_error& e) { flag(); return makeFuture(); });
217 EXPECT_THROW(f.value(), eggs_t);
220 // Returned value propagates
222 auto f = makeFuture()
223 .then([] { throw eggs; return 0; })
224 .onError([&] (eggs_t& e) { return 42; });
225 EXPECT_EQ(42, f.value());
228 // Returned future propagates
230 auto f = makeFuture()
231 .then([] { throw eggs; return 0; })
232 .onError([&] (eggs_t& e) { return makeFuture<int>(42); });
233 EXPECT_EQ(42, f.value());
238 auto f = makeFuture()
239 .then([] { throw eggs; return 0; })
240 .onError([&] (eggs_t& e) { throw e; return -1; });
241 EXPECT_THROW(f.value(), eggs_t);
245 auto f = makeFuture()
246 .then([] { throw eggs; return 0; })
247 .onError([&] (eggs_t& e) { throw e; return makeFuture<int>(-1); });
248 EXPECT_THROW(f.value(), eggs_t);
265 Try<A> t_a(std::move(a));
269 EXPECT_EQ(5, t_a.value().x());
272 TEST(Future, special) {
273 EXPECT_FALSE(std::is_copy_constructible<Future<int>>::value);
274 EXPECT_FALSE(std::is_copy_assignable<Future<int>>::value);
275 EXPECT_TRUE(std::is_move_constructible<Future<int>>::value);
276 EXPECT_TRUE(std::is_move_assignable<Future<int>>::value);
280 auto f = makeFuture<string>("0")
281 .then([](){ return makeFuture<string>("1"); })
282 .then([](Try<string>&& t) { return makeFuture(t.value() + ";2"); })
283 .then([](const Try<string>&& t) { return makeFuture(t.value() + ";3"); })
284 .then([](Try<string>& t) { return makeFuture(t.value() + ";4"); })
285 .then([](const Try<string>& t) { return makeFuture(t.value() + ";5"); })
286 .then([](Try<string> t) { return makeFuture(t.value() + ";6"); })
287 .then([](const Try<string> t) { return makeFuture(t.value() + ";7"); })
288 .then([](string&& s) { return makeFuture(s + ";8"); })
289 .then([](const string&& s) { return makeFuture(s + ";9"); })
290 .then([](string& s) { return makeFuture(s + ";10"); })
291 .then([](const string& s) { return makeFuture(s + ";11"); })
292 .then([](string s) { return makeFuture(s + ";12"); })
293 .then([](const string s) { return makeFuture(s + ";13"); })
295 EXPECT_EQ(f.value(), "1;2;3;4;5;6;7;8;9;10;11;12;13");
298 TEST(Future, thenTry) {
301 makeFuture<int>(42).then([&](Try<int>&& t) {
303 EXPECT_EQ(42, t.value());
305 EXPECT_TRUE(flag); flag = false;
308 .then([](Try<int>&& t) { return t.value(); })
309 .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
310 EXPECT_TRUE(flag); flag = false;
312 makeFuture().then([&](Try<void>&& t) { flag = true; t.value(); });
313 EXPECT_TRUE(flag); flag = false;
316 auto f = p.getFuture().then([&](Try<void>&& t) { flag = true; });
318 EXPECT_FALSE(f.isReady());
321 EXPECT_TRUE(f.isReady());
324 TEST(Future, thenValue) {
326 makeFuture<int>(42).then([&](int i){
330 EXPECT_TRUE(flag); flag = false;
333 .then([](int i){ return i; })
334 .then([&](int i) { flag = true; EXPECT_EQ(42, i); });
335 EXPECT_TRUE(flag); flag = false;
337 makeFuture().then([&]{
340 EXPECT_TRUE(flag); flag = false;
342 auto f = makeFuture<int>(eggs).then([&](int i){});
343 EXPECT_THROW(f.value(), eggs_t);
345 f = makeFuture<void>(eggs).then([&]{});
346 EXPECT_THROW(f.value(), eggs_t);
349 TEST(Future, thenValueFuture) {
352 .then([](int i){ return makeFuture<int>(std::move(i)); })
353 .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
354 EXPECT_TRUE(flag); flag = false;
357 .then([]{ return makeFuture(); })
358 .then([&](Try<void>&& t) { flag = true; });
359 EXPECT_TRUE(flag); flag = false;
362 static string doWorkStatic(Try<string>&& t) {
363 return t.value() + ";static";
366 TEST(Future, thenFunction) {
368 string doWork(Try<string>&& t) {
369 return t.value() + ";class";
371 static string doWorkStatic(Try<string>&& t) {
372 return t.value() + ";class-static";
376 auto f = makeFuture<string>("start")
378 .then(Worker::doWorkStatic)
379 .then(&w, &Worker::doWork);
381 EXPECT_EQ(f.value(), "start;static;class-static;class");
384 static Future<string> doWorkStaticFuture(Try<string>&& t) {
385 return makeFuture(t.value() + ";static");
388 TEST(Future, thenFunctionFuture) {
390 Future<string> doWorkFuture(Try<string>&& t) {
391 return makeFuture(t.value() + ";class");
393 static Future<string> doWorkStaticFuture(Try<string>&& t) {
394 return makeFuture(t.value() + ";class-static");
398 auto f = makeFuture<string>("start")
399 .then(doWorkStaticFuture)
400 .then(Worker::doWorkStaticFuture)
401 .then(&w, &Worker::doWorkFuture);
403 EXPECT_EQ(f.value(), "start;static;class-static;class");
406 TEST(Future, thenBind) {
408 return makeFuture("bind");
410 auto b = std::bind(l);
411 auto f = makeFuture().then(std::move(b));
412 EXPECT_EQ(f.value(), "bind");
415 TEST(Future, thenBindTry) {
416 auto l = [](Try<string>&& t) {
417 return makeFuture(t.value() + ";bind");
419 auto b = std::bind(l, std::placeholders::_1);
420 auto f = makeFuture<string>("start").then(std::move(b));
422 EXPECT_EQ(f.value(), "start;bind");
425 TEST(Future, value) {
426 auto f = makeFuture(unique_ptr<int>(new int(42)));
427 auto up = std::move(f.value());
430 EXPECT_THROW(makeFuture<int>(eggs).value(), eggs_t);
433 TEST(Future, isReady) {
435 auto f = p.getFuture();
436 EXPECT_FALSE(f.isReady());
438 EXPECT_TRUE(f.isReady());
441 TEST(Future, futureNotReady) {
443 Future<int> f = p.getFuture();
444 EXPECT_THROW(f.value(), eggs_t);
447 TEST(Future, hasException) {
448 EXPECT_TRUE(makeFuture<int>(eggs).getTry().hasException());
449 EXPECT_FALSE(makeFuture(42).getTry().hasException());
452 TEST(Future, hasValue) {
453 EXPECT_TRUE(makeFuture(42).getTry().hasValue());
454 EXPECT_FALSE(makeFuture<int>(eggs).getTry().hasValue());
457 TEST(Future, makeFuture) {
458 EXPECT_TYPE(makeFuture(42), Future<int>);
459 EXPECT_EQ(42, makeFuture(42).value());
461 EXPECT_TYPE(makeFuture<float>(42), Future<float>);
462 EXPECT_EQ(42, makeFuture<float>(42).value());
464 auto fun = [] { return 42; };
465 EXPECT_TYPE(makeFutureTry(fun), Future<int>);
466 EXPECT_EQ(42, makeFutureTry(fun).value());
468 auto failfun = []() -> int { throw eggs; };
469 EXPECT_TYPE(makeFutureTry(failfun), Future<int>);
470 EXPECT_THROW(makeFutureTry(failfun).value(), eggs_t);
472 EXPECT_TYPE(makeFuture(), Future<void>);
477 TEST(Promise, special) {
478 EXPECT_FALSE(std::is_copy_constructible<Promise<int>>::value);
479 EXPECT_FALSE(std::is_copy_assignable<Promise<int>>::value);
480 EXPECT_TRUE(std::is_move_constructible<Promise<int>>::value);
481 EXPECT_TRUE(std::is_move_assignable<Promise<int>>::value);
484 TEST(Promise, getFuture) {
486 Future<int> f = p.getFuture();
487 EXPECT_FALSE(f.isReady());
490 TEST(Promise, setValue) {
492 auto ffund = fund.getFuture();
494 EXPECT_EQ(42, ffund.value());
502 auto fpod = pod.getFuture();
503 Foo f = {"the answer", 42};
505 Foo f2 = fpod.value();
506 EXPECT_EQ(f.name, f2.name);
507 EXPECT_EQ(f.value, f2.value);
509 pod = Promise<Foo>();
510 fpod = pod.getFuture();
511 pod.setValue(std::move(f2));
512 Foo f3 = fpod.value();
513 EXPECT_EQ(f.name, f3.name);
514 EXPECT_EQ(f.value, f3.value);
516 Promise<unique_ptr<int>> mov;
517 auto fmov = mov.getFuture();
518 mov.setValue(unique_ptr<int>(new int(42)));
519 unique_ptr<int> ptr = std::move(fmov.value());
523 auto fv = v.getFuture();
525 EXPECT_TRUE(fv.isReady());
528 TEST(Promise, setException) {
531 auto f = p.getFuture();
532 p.setException(eggs);
533 EXPECT_THROW(f.value(), eggs_t);
537 auto f = p.getFuture();
541 p.setException(exception_wrapper(std::current_exception()));
543 EXPECT_THROW(f.value(), eggs_t);
547 TEST(Promise, fulfil) {
550 auto f = p.getFuture();
551 p.fulfil([] { return 42; });
552 EXPECT_EQ(42, f.value());
556 auto f = p.getFuture();
557 p.fulfil([]() -> int { throw eggs; });
558 EXPECT_THROW(f.value(), eggs_t);
562 TEST(Future, finish) {
563 auto x = std::make_shared<int>(0);
566 auto f = p.getFuture().then([x](Try<int>&& t) { *x = t.value(); });
568 // The callback hasn't executed
571 // The callback has a reference to x
572 EXPECT_EQ(2, x.use_count());
576 // the callback has executed
579 // the callback has been destructed
580 // and has released its reference to x
581 EXPECT_EQ(1, x.use_count());
584 TEST(Future, unwrap) {
588 auto fa = a.getFuture();
589 auto fb = b.getFuture();
594 // do a, then do b, and get the result of a + b.
595 Future<int> f = fa.then([&](Try<int>&& ta) {
596 auto va = ta.value();
598 return fb.then([va, &flag2](Try<int>&& tb) {
600 return va + tb.value();
606 EXPECT_FALSE(f.isReady());
611 EXPECT_FALSE(f.isReady());
616 EXPECT_EQ(7, f.value());
619 TEST(Future, whenAll) {
620 // returns a vector variant
622 vector<Promise<int>> promises(10);
623 vector<Future<int>> futures;
625 for (auto& p : promises)
626 futures.push_back(p.getFuture());
628 auto allf = whenAll(futures.begin(), futures.end());
630 random_shuffle(promises.begin(), promises.end());
631 for (auto& p : promises) {
632 EXPECT_FALSE(allf.isReady());
636 EXPECT_TRUE(allf.isReady());
637 auto& results = allf.value();
638 for (auto& t : results) {
639 EXPECT_EQ(42, t.value());
643 // check error semantics
645 vector<Promise<int>> promises(4);
646 vector<Future<int>> futures;
648 for (auto& p : promises)
649 futures.push_back(p.getFuture());
651 auto allf = whenAll(futures.begin(), futures.end());
654 promises[0].setValue(42);
655 promises[1].setException(eggs);
657 EXPECT_FALSE(allf.isReady());
659 promises[2].setValue(42);
661 EXPECT_FALSE(allf.isReady());
663 promises[3].setException(eggs);
665 EXPECT_TRUE(allf.isReady());
666 EXPECT_FALSE(allf.getTry().hasException());
668 auto& results = allf.value();
669 EXPECT_EQ(42, results[0].value());
670 EXPECT_TRUE(results[1].hasException());
671 EXPECT_EQ(42, results[2].value());
672 EXPECT_TRUE(results[3].hasException());
675 // check that futures are ready in then()
677 vector<Promise<void>> promises(10);
678 vector<Future<void>> futures;
680 for (auto& p : promises)
681 futures.push_back(p.getFuture());
683 auto allf = whenAll(futures.begin(), futures.end())
684 .then([](Try<vector<Try<void>>>&& ts) {
685 for (auto& f : ts.value())
689 random_shuffle(promises.begin(), promises.end());
690 for (auto& p : promises)
692 EXPECT_TRUE(allf.isReady());
697 TEST(Future, whenAny) {
699 vector<Promise<int>> promises(10);
700 vector<Future<int>> futures;
702 for (auto& p : promises)
703 futures.push_back(p.getFuture());
705 for (auto& f : futures) {
706 EXPECT_FALSE(f.isReady());
709 auto anyf = whenAny(futures.begin(), futures.end());
711 /* futures were moved in, so these are invalid now */
712 EXPECT_FALSE(anyf.isReady());
714 promises[7].setValue(42);
715 EXPECT_TRUE(anyf.isReady());
716 auto& idx_fut = anyf.value();
718 auto i = idx_fut.first;
721 auto& f = idx_fut.second;
722 EXPECT_EQ(42, f.value());
727 vector<Promise<void>> promises(10);
728 vector<Future<void>> futures;
730 for (auto& p : promises)
731 futures.push_back(p.getFuture());
733 for (auto& f : futures) {
734 EXPECT_FALSE(f.isReady());
737 auto anyf = whenAny(futures.begin(), futures.end());
739 EXPECT_FALSE(anyf.isReady());
741 promises[3].setException(eggs);
742 EXPECT_TRUE(anyf.isReady());
743 EXPECT_TRUE(anyf.value().second.hasException());
748 vector<Promise<int>> promises(10);
749 vector<Future<int>> futures;
751 for (auto& p : promises)
752 futures.push_back(p.getFuture());
754 auto anyf = whenAny(futures.begin(), futures.end())
755 .then([](pair<size_t, Try<int>> p) {
756 EXPECT_EQ(42, p.second.value());
759 promises[3].setValue(42);
760 EXPECT_TRUE(anyf.isReady());
765 TEST(when, already_completed) {
767 vector<Future<void>> fs;
768 for (int i = 0; i < 10; i++)
769 fs.push_back(makeFuture());
771 whenAll(fs.begin(), fs.end())
772 .then([&](vector<Try<void>> ts) {
773 EXPECT_EQ(fs.size(), ts.size());
777 vector<Future<int>> fs;
778 for (int i = 0; i < 10; i++)
779 fs.push_back(makeFuture(i));
781 whenAny(fs.begin(), fs.end())
782 .then([&](pair<size_t, Try<int>> p) {
783 EXPECT_EQ(p.first, p.second.value());
789 vector<Promise<void>> promises(10);
790 vector<Future<void>> futures;
792 for (auto& p : promises)
793 futures.push_back(p.getFuture());
797 whenN(futures.begin(), futures.end(), n)
798 .then([&](vector<pair<size_t, Try<void>>> v) {
800 EXPECT_EQ(n, v.size());
802 EXPECT_TRUE(tt.second.hasValue());
805 promises[0].setValue();
807 promises[1].setValue();
809 promises[2].setValue();
813 /* Ensure that we can compile when_{all,any} with folly::small_vector */
814 TEST(when, small_vector) {
816 static_assert(!FOLLY_IS_TRIVIALLY_COPYABLE(Future<void>),
817 "Futures should not be trivially copyable");
818 static_assert(!FOLLY_IS_TRIVIALLY_COPYABLE(Future<int>),
819 "Futures should not be trivially copyable");
821 using folly::small_vector;
823 small_vector<Future<void>> futures;
825 for (int i = 0; i < 10; i++)
826 futures.push_back(makeFuture());
828 auto anyf = whenAny(futures.begin(), futures.end());
832 small_vector<Future<void>> futures;
834 for (int i = 0; i < 10; i++)
835 futures.push_back(makeFuture());
837 auto allf = whenAll(futures.begin(), futures.end());
841 TEST(Future, whenAllVariadic) {
844 Future<bool> fb = pb.getFuture();
845 Future<int> fi = pi.getFuture();
847 whenAll(std::move(fb), std::move(fi))
848 .then([&](std::tuple<Try<bool>, Try<int>> tup) {
850 EXPECT_TRUE(std::get<0>(tup).hasValue());
851 EXPECT_EQ(std::get<0>(tup).value(), true);
852 EXPECT_TRUE(std::get<1>(tup).hasValue());
853 EXPECT_EQ(std::get<1>(tup).value(), 42);
861 TEST(Future, whenAllVariadicReferences) {
864 Future<bool> fb = pb.getFuture();
865 Future<int> fi = pi.getFuture();
868 .then([&](std::tuple<Try<bool>, Try<int>> tup) {
870 EXPECT_TRUE(std::get<0>(tup).hasValue());
871 EXPECT_EQ(std::get<0>(tup).value(), true);
872 EXPECT_TRUE(std::get<1>(tup).hasValue());
873 EXPECT_EQ(std::get<1>(tup).value(), 42);
881 TEST(Future, whenAll_none) {
882 vector<Future<int>> fs;
883 auto f = whenAll(fs.begin(), fs.end());
884 EXPECT_TRUE(f.isReady());
887 TEST(Future, throwCaughtInImmediateThen) {
888 // Neither of these should throw "Promise already satisfied"
890 [=](Try<void>&&) -> int { throw std::exception(); });
892 [=](Try<void>&&) -> Future<int> { throw std::exception(); });
895 TEST(Future, throwIfFailed) {
896 makeFuture<void>(eggs)
897 .then([=](Try<void>&& t) {
898 EXPECT_THROW(t.throwIfFailed(), eggs_t);
901 .then([=](Try<void>&& t) {
902 EXPECT_NO_THROW(t.throwIfFailed());
905 makeFuture<int>(eggs)
906 .then([=](Try<int>&& t) {
907 EXPECT_THROW(t.throwIfFailed(), eggs_t);
910 .then([=](Try<int>&& t) {
911 EXPECT_NO_THROW(t.throwIfFailed());
915 TEST(Future, waitImmediate) {
917 auto done = makeFuture(42).wait().value();
920 vector<int> v{1,2,3};
921 auto done_v = makeFuture(v).wait().value();
922 EXPECT_EQ(v.size(), done_v.size());
923 EXPECT_EQ(v, done_v);
925 vector<Future<void>> v_f;
926 v_f.push_back(makeFuture());
927 v_f.push_back(makeFuture());
928 auto done_v_f = whenAll(v_f.begin(), v_f.end()).wait().value();
929 EXPECT_EQ(2, done_v_f.size());
931 vector<Future<bool>> v_fb;
932 v_fb.push_back(makeFuture(true));
933 v_fb.push_back(makeFuture(false));
934 auto fut = whenAll(v_fb.begin(), v_fb.end());
935 auto done_v_fb = std::move(fut.wait().value());
936 EXPECT_EQ(2, done_v_fb.size());
941 Future<int> f = p.getFuture();
942 std::atomic<bool> flag{false};
943 std::atomic<int> result{1};
944 std::atomic<std::thread::id> id;
946 std::thread t([&](Future<int>&& tf){
947 auto n = tf.then([&](Try<int> && t) {
948 id = std::this_thread::get_id();
952 result.store(n.wait().value());
957 EXPECT_EQ(result.load(), 1);
960 // validate that the callback ended up executing in this thread, which
961 // is more to ensure that this test actually tests what it should
962 EXPECT_EQ(id, std::this_thread::get_id());
963 EXPECT_EQ(result.load(), 42);
966 TEST(Future, waitWithDuration) {
969 Future<int> f = p.getFuture();
970 auto t = f.wait(std::chrono::milliseconds(1));
971 EXPECT_FALSE(t.isReady());
973 EXPECT_TRUE(t.isReady());
977 Future<int> f = p.getFuture();
979 auto t = f.wait(std::chrono::milliseconds(1));
980 EXPECT_TRUE(t.isReady());
983 vector<Future<bool>> v_fb;
984 v_fb.push_back(makeFuture(true));
985 v_fb.push_back(makeFuture(false));
986 auto f = whenAll(v_fb.begin(), v_fb.end());
987 auto t = f.wait(std::chrono::milliseconds(1));
988 EXPECT_TRUE(t.isReady());
989 EXPECT_EQ(2, t.value().size());
992 vector<Future<bool>> v_fb;
995 v_fb.push_back(p1.getFuture());
996 v_fb.push_back(p2.getFuture());
997 auto f = whenAll(v_fb.begin(), v_fb.end());
998 auto t = f.wait(std::chrono::milliseconds(1));
999 EXPECT_FALSE(t.isReady());
1001 EXPECT_FALSE(t.isReady());
1003 EXPECT_TRUE(t.isReady());
1006 auto t = makeFuture().wait(std::chrono::milliseconds(1));
1007 EXPECT_TRUE(t.isReady());
1012 auto start = std::chrono::steady_clock::now();
1013 auto f = p.getFuture().wait(std::chrono::milliseconds(100));
1014 auto elapsed = std::chrono::steady_clock::now() - start;
1015 EXPECT_GE(elapsed, std::chrono::milliseconds(100));
1016 EXPECT_FALSE(f.isReady());
1018 EXPECT_TRUE(f.isReady());
1022 // Try to trigger the race where the resultant Future is not yet complete
1023 // even if we didn't hit the timeout, and make sure we deal with it properly
1026 auto t = std::thread([&]{
1028 std::this_thread::sleep_for(std::chrono::milliseconds(100));
1032 auto f = p.getFuture().wait(std::chrono::seconds(3600));
1033 EXPECT_TRUE(f.isReady());
1038 class DummyDrivableExecutor : public DrivableExecutor {
1040 void add(Func f) override {}
1041 void drive() override { ran = true; }
1045 TEST(Future, getVia) {
1049 auto f = via(&x).then([]{ return true; });
1050 EXPECT_TRUE(f.getVia(&x));
1056 auto f = via(&x).then();
1061 DummyDrivableExecutor x;
1062 auto f = makeFuture(true);
1063 EXPECT_TRUE(f.getVia(&x));
1064 EXPECT_FALSE(x.ran);
1068 TEST(Future, waitVia) {
1071 auto f = via(&x).then();
1072 EXPECT_FALSE(f.isReady());
1074 EXPECT_TRUE(f.isReady());
1078 // try rvalue as well
1080 auto f = via(&x).activate().then().waitVia(&x);
1081 EXPECT_TRUE(f.isReady());
1085 DummyDrivableExecutor x;
1086 makeFuture(true).waitVia(&x);
1087 EXPECT_FALSE(x.ran);
1091 TEST(Future, callbackAfterActivate) {
1093 auto f = p.getFuture();
1097 f.then([&](Try<void>&&) { count++; });
1100 EXPECT_EQ(0, count);
1103 EXPECT_EQ(1, count);
1106 TEST(Future, activateOnDestruct) {
1107 auto f = std::make_shared<Future<void>>(makeFuture());
1111 f->then([&](Try<void>&&) { count++; });
1112 EXPECT_EQ(0, count);
1115 EXPECT_EQ(1, count);
1118 TEST(Future, viaActsCold) {
1123 fv.then([&](Try<void>&&) { count++; });
1125 EXPECT_EQ(0, count);
1129 EXPECT_EQ(1, x.run());
1130 EXPECT_EQ(1, count);
1133 TEST(Future, viaIsCold) {
1135 EXPECT_FALSE(via(&x).isActive());
1138 TEST(Future, viaRaces) {
1141 auto tid = std::this_thread::get_id();
1144 std::thread t1([&] {
1147 .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1148 .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1149 .then([&](Try<void>&&) { done = true; });
1152 std::thread t2([&] {
1156 while (!done) x.run();
1162 TEST(Future, viaRaces_2stage) {
1165 auto tid = std::this_thread::get_id();
1168 std::thread t1([&] {
1169 auto f2 = p.getFuture().via(&x);
1170 f2.then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1171 .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1172 .then([&](Try<void>&&) { done = true; });
1174 // the bug was in the promise being fulfilled before f2 is reactivated. we
1175 // could sleep, but yielding should cause this to fail with reasonable
1177 std::this_thread::yield();
1181 std::thread t2([&] {
1185 while (!done) x.run();
1190 TEST(Future, getFuture_after_setValue) {
1193 EXPECT_EQ(42, p.getFuture().value());
1196 TEST(Future, getFuture_after_setException) {
1198 p.fulfil([]() -> void { throw std::logic_error("foo"); });
1199 EXPECT_THROW(p.getFuture().value(), std::logic_error);
1202 TEST(Future, detachRace) {
1204 // This test is designed to detect a race that was in Core::detachOne()
1205 // where detached_ was incremented and then tested, and that
1206 // allowed a race where both Promise and Future would think they were the
1207 // second and both try to delete. This showed up at scale but was very
1208 // difficult to reliably repro in a test. As it is, this only fails about
1209 // once in every 1,000 executions. Doing this 1,000 times is going to make a
1210 // slow test so I won't do that but if it ever fails, take it seriously, and
1211 // run the test binary with "--gtest_repeat=10000 --gtest_filter=*detachRace"
1212 // (Don't forget to enable ASAN)
1213 auto p = folly::make_unique<Promise<bool>>();
1214 auto f = folly::make_unique<Future<bool>>(p->getFuture());
1215 folly::Baton<> baton;
1225 class TestData : public RequestData {
1227 explicit TestData(int data) : data_(data) {}
1228 virtual ~TestData() {}
1232 TEST(Future, context) {
1234 // Start a new context
1235 RequestContext::create();
1237 EXPECT_EQ(nullptr, RequestContext::get()->getContextData("test"));
1239 // Set some test data
1240 RequestContext::get()->setContextData(
1242 std::unique_ptr<TestData>(new TestData(10)));
1246 auto future = p.getFuture().then([&]{
1247 // Check that the context followed the future
1248 EXPECT_TRUE(RequestContext::get() != nullptr);
1249 auto a = dynamic_cast<TestData*>(
1250 RequestContext::get()->getContextData("test"));
1251 auto data = a->data_;
1252 EXPECT_EQ(10, data);
1255 // Clear the context
1256 RequestContext::setContext(nullptr);
1258 EXPECT_EQ(nullptr, RequestContext::get()->getContextData("test"));
1260 // Fulfil the promise
1265 // This only fails about 1 in 1k times when the bug is present :(
1266 TEST(Future, t5506504) {
1270 auto promises = std::make_shared<vector<Promise<void>>>(4);
1271 vector<Future<void>> futures;
1273 for (auto& p : *promises) {
1274 futures.emplace_back(
1277 .then([](Try<void>&&){}));
1282 for (auto& p : *promises) p.setValue();
1285 return whenAll(futures.begin(), futures.end());
1291 // Test of handling of a circular dependency. It's never recommended
1292 // to have one because of possible memory leaks. Here we test that
1293 // we can handle freeing of the Future while it is running.
1294 TEST(Future, CircularDependencySharedPtrSelfReset) {
1295 Promise<int64_t> promise;
1296 auto ptr = std::make_shared<Future<int64_t>>(promise.getFuture());
1299 [ptr] (folly::Try<int64_t>&& uid) mutable {
1300 EXPECT_EQ(1, ptr.use_count());
1302 // Leaving no references to ourselves.
1304 EXPECT_EQ(0, ptr.use_count());
1308 EXPECT_EQ(2, ptr.use_count());
1312 promise.fulfil([]{return 1l;});
1315 TEST(Future, Constructor) {
1316 auto f1 = []() -> Future<int> { return Future<int>(3); }();
1317 EXPECT_EQ(f1.value(), 3);
1318 auto f2 = []() -> Future<void> { return Future<void>(); }();
1319 EXPECT_NO_THROW(f2.value());
1322 TEST(Future, ImplicitConstructor) {
1323 auto f1 = []() -> Future<int> { return 3; }();
1324 EXPECT_EQ(f1.value(), 3);
1325 // Unfortunately, the C++ standard does not allow the
1326 // following implicit conversion to work:
1327 //auto f2 = []() -> Future<void> { }();