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/EventBase.h>
34 #include <folly/io/async/Request.h>
36 using namespace folly;
39 using std::unique_ptr;
41 using std::chrono::milliseconds;
43 #define EXPECT_TYPE(x, T) \
44 EXPECT_TRUE((std::is_same<decltype(x), T>::value))
46 /// Simple executor that does work in another thread
47 class ThreadExecutor : public Executor {
48 folly::MPMCQueue<Func> funcs;
49 std::atomic<bool> done {false};
57 while (!funcs.isEmpty()) {
58 funcs.blockingRead(fn);
65 explicit ThreadExecutor(size_t n = 1024)
66 : funcs(n), worker(std::bind(&ThreadExecutor::work, this)) {}
74 void add(Func fn) override {
75 funcs.blockingWrite(std::move(fn));
78 void waitForStartup() {
83 typedef FutureException eggs_t;
84 static eggs_t eggs("eggs");
88 TEST(Future, onError) {
90 auto flag = [&]{ theFlag = true; };
91 #define EXPECT_FLAG() \
93 EXPECT_TRUE(theFlag); \
97 #define EXPECT_NO_FLAG() \
99 EXPECT_FALSE(theFlag); \
105 auto f = makeFuture()
106 .then([] { throw eggs; })
107 .onError([&] (eggs_t& e) { flag(); });
109 EXPECT_NO_THROW(f.value());
113 auto f = makeFuture()
114 .then([] { throw eggs; })
115 .onError([&] (eggs_t& e) { flag(); return makeFuture(); });
117 EXPECT_NO_THROW(f.value());
122 auto f = makeFuture()
123 .then([] { throw eggs; })
124 .onError([&] (eggs_t e) { flag(); });
126 EXPECT_NO_THROW(f.value());
130 auto f = makeFuture()
131 .then([] { throw eggs; })
132 .onError([&] (eggs_t e) { flag(); return makeFuture(); });
134 EXPECT_NO_THROW(f.value());
139 auto f = makeFuture()
140 .then([] { throw eggs; })
141 .onError([&] (std::exception& e) { flag(); });
143 EXPECT_NO_THROW(f.value());
147 auto f = makeFuture()
148 .then([] { throw eggs; })
149 .onError([&] (std::exception& e) { flag(); return makeFuture(); });
151 EXPECT_NO_THROW(f.value());
156 auto f = makeFuture()
157 .then([] { throw -1; })
158 .onError([&] (int e) { flag(); });
160 EXPECT_NO_THROW(f.value());
164 auto f = makeFuture()
165 .then([] { throw -1; })
166 .onError([&] (int e) { flag(); return makeFuture(); });
168 EXPECT_NO_THROW(f.value());
173 auto f = makeFuture()
174 .then([] { throw eggs; })
175 .onError([&] (eggs_t& e) mutable { flag(); });
177 EXPECT_NO_THROW(f.value());
181 auto f = makeFuture()
182 .then([] { throw eggs; })
183 .onError([&] (eggs_t& e) mutable { flag(); return makeFuture(); });
185 EXPECT_NO_THROW(f.value());
190 auto f = makeFuture()
191 .then([] { return 42; })
192 .onError([&] (eggs_t& e) { flag(); return -1; });
194 EXPECT_EQ(42, f.value());
198 auto f = makeFuture()
199 .then([] { return 42; })
200 .onError([&] (eggs_t& e) { flag(); return makeFuture<int>(-1); });
202 EXPECT_EQ(42, f.value());
205 // Catch different exception
207 auto f = makeFuture()
208 .then([] { throw eggs; })
209 .onError([&] (std::runtime_error& e) { flag(); });
211 EXPECT_THROW(f.value(), eggs_t);
215 auto f = makeFuture()
216 .then([] { throw eggs; })
217 .onError([&] (std::runtime_error& e) { flag(); return makeFuture(); });
219 EXPECT_THROW(f.value(), eggs_t);
222 // Returned value propagates
224 auto f = makeFuture()
225 .then([] { throw eggs; return 0; })
226 .onError([&] (eggs_t& e) { return 42; });
227 EXPECT_EQ(42, f.value());
230 // Returned future propagates
232 auto f = makeFuture()
233 .then([] { throw eggs; return 0; })
234 .onError([&] (eggs_t& e) { return makeFuture<int>(42); });
235 EXPECT_EQ(42, f.value());
240 auto f = makeFuture()
241 .then([] { throw eggs; return 0; })
242 .onError([&] (eggs_t& e) { throw e; return -1; });
243 EXPECT_THROW(f.value(), eggs_t);
247 auto f = makeFuture()
248 .then([] { throw eggs; return 0; })
249 .onError([&] (eggs_t& e) { throw e; return makeFuture<int>(-1); });
250 EXPECT_THROW(f.value(), eggs_t);
267 Try<A> t_a(std::move(a));
271 EXPECT_EQ(5, t_a.value().x());
274 TEST(Future, special) {
275 EXPECT_FALSE(std::is_copy_constructible<Future<int>>::value);
276 EXPECT_FALSE(std::is_copy_assignable<Future<int>>::value);
277 EXPECT_TRUE(std::is_move_constructible<Future<int>>::value);
278 EXPECT_TRUE(std::is_move_assignable<Future<int>>::value);
282 auto f = makeFuture<string>("0")
283 .then([](){ return makeFuture<string>("1"); })
284 .then([](Try<string>&& t) { return makeFuture(t.value() + ";2"); })
285 .then([](const Try<string>&& t) { return makeFuture(t.value() + ";3"); })
286 .then([](Try<string>& t) { return makeFuture(t.value() + ";4"); })
287 .then([](const Try<string>& t) { return makeFuture(t.value() + ";5"); })
288 .then([](Try<string> t) { return makeFuture(t.value() + ";6"); })
289 .then([](const Try<string> t) { return makeFuture(t.value() + ";7"); })
290 .then([](string&& s) { return makeFuture(s + ";8"); })
291 .then([](const string&& s) { return makeFuture(s + ";9"); })
292 .then([](string& s) { return makeFuture(s + ";10"); })
293 .then([](const string& s) { return makeFuture(s + ";11"); })
294 .then([](string s) { return makeFuture(s + ";12"); })
295 .then([](const string s) { return makeFuture(s + ";13"); })
297 EXPECT_EQ(f.value(), "1;2;3;4;5;6;7;8;9;10;11;12;13");
300 TEST(Future, thenTry) {
303 makeFuture<int>(42).then([&](Try<int>&& t) {
305 EXPECT_EQ(42, t.value());
307 EXPECT_TRUE(flag); flag = false;
310 .then([](Try<int>&& t) { return t.value(); })
311 .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
312 EXPECT_TRUE(flag); flag = false;
314 makeFuture().then([&](Try<void>&& t) { flag = true; t.value(); });
315 EXPECT_TRUE(flag); flag = false;
318 auto f = p.getFuture().then([&](Try<void>&& t) { flag = true; });
320 EXPECT_FALSE(f.isReady());
323 EXPECT_TRUE(f.isReady());
326 TEST(Future, thenValue) {
328 makeFuture<int>(42).then([&](int i){
332 EXPECT_TRUE(flag); flag = false;
335 .then([](int i){ return i; })
336 .then([&](int i) { flag = true; EXPECT_EQ(42, i); });
337 EXPECT_TRUE(flag); flag = false;
339 makeFuture().then([&]{
342 EXPECT_TRUE(flag); flag = false;
344 auto f = makeFuture<int>(eggs).then([&](int i){});
345 EXPECT_THROW(f.value(), eggs_t);
347 f = makeFuture<void>(eggs).then([&]{});
348 EXPECT_THROW(f.value(), eggs_t);
351 TEST(Future, thenValueFuture) {
354 .then([](int i){ return makeFuture<int>(std::move(i)); })
355 .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
356 EXPECT_TRUE(flag); flag = false;
359 .then([]{ return makeFuture(); })
360 .then([&](Try<void>&& t) { flag = true; });
361 EXPECT_TRUE(flag); flag = false;
364 static string doWorkStatic(Try<string>&& t) {
365 return t.value() + ";static";
368 TEST(Future, thenFunction) {
370 string doWork(Try<string>&& t) {
371 return t.value() + ";class";
373 static string doWorkStatic(Try<string>&& t) {
374 return t.value() + ";class-static";
378 auto f = makeFuture<string>("start")
380 .then(Worker::doWorkStatic)
381 .then(&w, &Worker::doWork);
383 EXPECT_EQ(f.value(), "start;static;class-static;class");
386 static Future<string> doWorkStaticFuture(Try<string>&& t) {
387 return makeFuture(t.value() + ";static");
390 TEST(Future, thenFunctionFuture) {
392 Future<string> doWorkFuture(Try<string>&& t) {
393 return makeFuture(t.value() + ";class");
395 static Future<string> doWorkStaticFuture(Try<string>&& t) {
396 return makeFuture(t.value() + ";class-static");
400 auto f = makeFuture<string>("start")
401 .then(doWorkStaticFuture)
402 .then(Worker::doWorkStaticFuture)
403 .then(&w, &Worker::doWorkFuture);
405 EXPECT_EQ(f.value(), "start;static;class-static;class");
408 TEST(Future, thenBind) {
410 return makeFuture("bind");
412 auto b = std::bind(l);
413 auto f = makeFuture().then(std::move(b));
414 EXPECT_EQ(f.value(), "bind");
417 TEST(Future, thenBindTry) {
418 auto l = [](Try<string>&& t) {
419 return makeFuture(t.value() + ";bind");
421 auto b = std::bind(l, std::placeholders::_1);
422 auto f = makeFuture<string>("start").then(std::move(b));
424 EXPECT_EQ(f.value(), "start;bind");
427 TEST(Future, value) {
428 auto f = makeFuture(unique_ptr<int>(new int(42)));
429 auto up = std::move(f.value());
432 EXPECT_THROW(makeFuture<int>(eggs).value(), eggs_t);
435 TEST(Future, isReady) {
437 auto f = p.getFuture();
438 EXPECT_FALSE(f.isReady());
440 EXPECT_TRUE(f.isReady());
443 TEST(Future, futureNotReady) {
445 Future<int> f = p.getFuture();
446 EXPECT_THROW(f.value(), eggs_t);
449 TEST(Future, hasException) {
450 EXPECT_TRUE(makeFuture<int>(eggs).getTry().hasException());
451 EXPECT_FALSE(makeFuture(42).getTry().hasException());
454 TEST(Future, hasValue) {
455 EXPECT_TRUE(makeFuture(42).getTry().hasValue());
456 EXPECT_FALSE(makeFuture<int>(eggs).getTry().hasValue());
459 TEST(Future, makeFuture) {
460 EXPECT_TYPE(makeFuture(42), Future<int>);
461 EXPECT_EQ(42, makeFuture(42).value());
463 EXPECT_TYPE(makeFuture<float>(42), Future<float>);
464 EXPECT_EQ(42, makeFuture<float>(42).value());
466 auto fun = [] { return 42; };
467 EXPECT_TYPE(makeFutureTry(fun), Future<int>);
468 EXPECT_EQ(42, makeFutureTry(fun).value());
470 auto failfun = []() -> int { throw eggs; };
471 EXPECT_TYPE(makeFutureTry(failfun), Future<int>);
472 EXPECT_THROW(makeFutureTry(failfun).value(), eggs_t);
474 EXPECT_TYPE(makeFuture(), Future<void>);
479 TEST(Promise, special) {
480 EXPECT_FALSE(std::is_copy_constructible<Promise<int>>::value);
481 EXPECT_FALSE(std::is_copy_assignable<Promise<int>>::value);
482 EXPECT_TRUE(std::is_move_constructible<Promise<int>>::value);
483 EXPECT_TRUE(std::is_move_assignable<Promise<int>>::value);
486 TEST(Promise, getFuture) {
488 Future<int> f = p.getFuture();
489 EXPECT_FALSE(f.isReady());
492 TEST(Promise, setValue) {
494 auto ffund = fund.getFuture();
496 EXPECT_EQ(42, ffund.value());
504 auto fpod = pod.getFuture();
505 Foo f = {"the answer", 42};
507 Foo f2 = fpod.value();
508 EXPECT_EQ(f.name, f2.name);
509 EXPECT_EQ(f.value, f2.value);
511 pod = Promise<Foo>();
512 fpod = pod.getFuture();
513 pod.setValue(std::move(f2));
514 Foo f3 = fpod.value();
515 EXPECT_EQ(f.name, f3.name);
516 EXPECT_EQ(f.value, f3.value);
518 Promise<unique_ptr<int>> mov;
519 auto fmov = mov.getFuture();
520 mov.setValue(unique_ptr<int>(new int(42)));
521 unique_ptr<int> ptr = std::move(fmov.value());
525 auto fv = v.getFuture();
527 EXPECT_TRUE(fv.isReady());
530 TEST(Promise, setException) {
533 auto f = p.getFuture();
534 p.setException(eggs);
535 EXPECT_THROW(f.value(), eggs_t);
539 auto f = p.getFuture();
543 p.setException(exception_wrapper(std::current_exception()));
545 EXPECT_THROW(f.value(), eggs_t);
549 TEST(Promise, fulfil) {
552 auto f = p.getFuture();
553 p.fulfil([] { return 42; });
554 EXPECT_EQ(42, f.value());
558 auto f = p.getFuture();
559 p.fulfil([]() -> int { throw eggs; });
560 EXPECT_THROW(f.value(), eggs_t);
564 TEST(Future, finish) {
565 auto x = std::make_shared<int>(0);
568 auto f = p.getFuture().then([x](Try<int>&& t) { *x = t.value(); });
570 // The callback hasn't executed
573 // The callback has a reference to x
574 EXPECT_EQ(2, x.use_count());
578 // the callback has executed
581 // the callback has been destructed
582 // and has released its reference to x
583 EXPECT_EQ(1, x.use_count());
586 TEST(Future, unwrap) {
590 auto fa = a.getFuture();
591 auto fb = b.getFuture();
596 // do a, then do b, and get the result of a + b.
597 Future<int> f = fa.then([&](Try<int>&& ta) {
598 auto va = ta.value();
600 return fb.then([va, &flag2](Try<int>&& tb) {
602 return va + tb.value();
608 EXPECT_FALSE(f.isReady());
613 EXPECT_FALSE(f.isReady());
618 EXPECT_EQ(7, f.value());
621 TEST(Future, whenAll) {
622 // returns a vector variant
624 vector<Promise<int>> promises(10);
625 vector<Future<int>> futures;
627 for (auto& p : promises)
628 futures.push_back(p.getFuture());
630 auto allf = whenAll(futures.begin(), futures.end());
632 random_shuffle(promises.begin(), promises.end());
633 for (auto& p : promises) {
634 EXPECT_FALSE(allf.isReady());
638 EXPECT_TRUE(allf.isReady());
639 auto& results = allf.value();
640 for (auto& t : results) {
641 EXPECT_EQ(42, t.value());
645 // check error semantics
647 vector<Promise<int>> promises(4);
648 vector<Future<int>> futures;
650 for (auto& p : promises)
651 futures.push_back(p.getFuture());
653 auto allf = whenAll(futures.begin(), futures.end());
656 promises[0].setValue(42);
657 promises[1].setException(eggs);
659 EXPECT_FALSE(allf.isReady());
661 promises[2].setValue(42);
663 EXPECT_FALSE(allf.isReady());
665 promises[3].setException(eggs);
667 EXPECT_TRUE(allf.isReady());
668 EXPECT_FALSE(allf.getTry().hasException());
670 auto& results = allf.value();
671 EXPECT_EQ(42, results[0].value());
672 EXPECT_TRUE(results[1].hasException());
673 EXPECT_EQ(42, results[2].value());
674 EXPECT_TRUE(results[3].hasException());
677 // check that futures are ready in then()
679 vector<Promise<void>> promises(10);
680 vector<Future<void>> futures;
682 for (auto& p : promises)
683 futures.push_back(p.getFuture());
685 auto allf = whenAll(futures.begin(), futures.end())
686 .then([](Try<vector<Try<void>>>&& ts) {
687 for (auto& f : ts.value())
691 random_shuffle(promises.begin(), promises.end());
692 for (auto& p : promises)
694 EXPECT_TRUE(allf.isReady());
699 TEST(Future, whenAny) {
701 vector<Promise<int>> promises(10);
702 vector<Future<int>> futures;
704 for (auto& p : promises)
705 futures.push_back(p.getFuture());
707 for (auto& f : futures) {
708 EXPECT_FALSE(f.isReady());
711 auto anyf = whenAny(futures.begin(), futures.end());
713 /* futures were moved in, so these are invalid now */
714 EXPECT_FALSE(anyf.isReady());
716 promises[7].setValue(42);
717 EXPECT_TRUE(anyf.isReady());
718 auto& idx_fut = anyf.value();
720 auto i = idx_fut.first;
723 auto& f = idx_fut.second;
724 EXPECT_EQ(42, f.value());
729 vector<Promise<void>> promises(10);
730 vector<Future<void>> futures;
732 for (auto& p : promises)
733 futures.push_back(p.getFuture());
735 for (auto& f : futures) {
736 EXPECT_FALSE(f.isReady());
739 auto anyf = whenAny(futures.begin(), futures.end());
741 EXPECT_FALSE(anyf.isReady());
743 promises[3].setException(eggs);
744 EXPECT_TRUE(anyf.isReady());
745 EXPECT_TRUE(anyf.value().second.hasException());
750 vector<Promise<int>> promises(10);
751 vector<Future<int>> futures;
753 for (auto& p : promises)
754 futures.push_back(p.getFuture());
756 auto anyf = whenAny(futures.begin(), futures.end())
757 .then([](pair<size_t, Try<int>> p) {
758 EXPECT_EQ(42, p.second.value());
761 promises[3].setValue(42);
762 EXPECT_TRUE(anyf.isReady());
767 TEST(when, already_completed) {
769 vector<Future<void>> fs;
770 for (int i = 0; i < 10; i++)
771 fs.push_back(makeFuture());
773 whenAll(fs.begin(), fs.end())
774 .then([&](vector<Try<void>> ts) {
775 EXPECT_EQ(fs.size(), ts.size());
779 vector<Future<int>> fs;
780 for (int i = 0; i < 10; i++)
781 fs.push_back(makeFuture(i));
783 whenAny(fs.begin(), fs.end())
784 .then([&](pair<size_t, Try<int>> p) {
785 EXPECT_EQ(p.first, p.second.value());
791 vector<Promise<void>> promises(10);
792 vector<Future<void>> futures;
794 for (auto& p : promises)
795 futures.push_back(p.getFuture());
799 whenN(futures.begin(), futures.end(), n)
800 .then([&](vector<pair<size_t, Try<void>>> v) {
802 EXPECT_EQ(n, v.size());
804 EXPECT_TRUE(tt.second.hasValue());
807 promises[0].setValue();
809 promises[1].setValue();
811 promises[2].setValue();
815 /* Ensure that we can compile when_{all,any} with folly::small_vector */
816 TEST(when, small_vector) {
818 static_assert(!FOLLY_IS_TRIVIALLY_COPYABLE(Future<void>),
819 "Futures should not be trivially copyable");
820 static_assert(!FOLLY_IS_TRIVIALLY_COPYABLE(Future<int>),
821 "Futures should not be trivially copyable");
823 using folly::small_vector;
825 small_vector<Future<void>> futures;
827 for (int i = 0; i < 10; i++)
828 futures.push_back(makeFuture());
830 auto anyf = whenAny(futures.begin(), futures.end());
834 small_vector<Future<void>> futures;
836 for (int i = 0; i < 10; i++)
837 futures.push_back(makeFuture());
839 auto allf = whenAll(futures.begin(), futures.end());
843 TEST(Future, whenAllVariadic) {
846 Future<bool> fb = pb.getFuture();
847 Future<int> fi = pi.getFuture();
849 whenAll(std::move(fb), std::move(fi))
850 .then([&](std::tuple<Try<bool>, Try<int>> tup) {
852 EXPECT_TRUE(std::get<0>(tup).hasValue());
853 EXPECT_EQ(std::get<0>(tup).value(), true);
854 EXPECT_TRUE(std::get<1>(tup).hasValue());
855 EXPECT_EQ(std::get<1>(tup).value(), 42);
863 TEST(Future, whenAllVariadicReferences) {
866 Future<bool> fb = pb.getFuture();
867 Future<int> fi = pi.getFuture();
870 .then([&](std::tuple<Try<bool>, Try<int>> tup) {
872 EXPECT_TRUE(std::get<0>(tup).hasValue());
873 EXPECT_EQ(std::get<0>(tup).value(), true);
874 EXPECT_TRUE(std::get<1>(tup).hasValue());
875 EXPECT_EQ(std::get<1>(tup).value(), 42);
883 TEST(Future, whenAll_none) {
884 vector<Future<int>> fs;
885 auto f = whenAll(fs.begin(), fs.end());
886 EXPECT_TRUE(f.isReady());
889 TEST(Future, throwCaughtInImmediateThen) {
890 // Neither of these should throw "Promise already satisfied"
892 [=](Try<void>&&) -> int { throw std::exception(); });
894 [=](Try<void>&&) -> Future<int> { throw std::exception(); });
897 TEST(Future, throwIfFailed) {
898 makeFuture<void>(eggs)
899 .then([=](Try<void>&& t) {
900 EXPECT_THROW(t.throwIfFailed(), eggs_t);
903 .then([=](Try<void>&& t) {
904 EXPECT_NO_THROW(t.throwIfFailed());
907 makeFuture<int>(eggs)
908 .then([=](Try<int>&& t) {
909 EXPECT_THROW(t.throwIfFailed(), eggs_t);
912 .then([=](Try<int>&& t) {
913 EXPECT_NO_THROW(t.throwIfFailed());
917 TEST(Future, waitImmediate) {
919 auto done = makeFuture(42).wait().value();
922 vector<int> v{1,2,3};
923 auto done_v = makeFuture(v).wait().value();
924 EXPECT_EQ(v.size(), done_v.size());
925 EXPECT_EQ(v, done_v);
927 vector<Future<void>> v_f;
928 v_f.push_back(makeFuture());
929 v_f.push_back(makeFuture());
930 auto done_v_f = whenAll(v_f.begin(), v_f.end()).wait().value();
931 EXPECT_EQ(2, done_v_f.size());
933 vector<Future<bool>> v_fb;
934 v_fb.push_back(makeFuture(true));
935 v_fb.push_back(makeFuture(false));
936 auto fut = whenAll(v_fb.begin(), v_fb.end());
937 auto done_v_fb = std::move(fut.wait().value());
938 EXPECT_EQ(2, done_v_fb.size());
943 Future<int> f = p.getFuture();
944 std::atomic<bool> flag{false};
945 std::atomic<int> result{1};
946 std::atomic<std::thread::id> id;
948 std::thread t([&](Future<int>&& tf){
949 auto n = tf.then([&](Try<int> && t) {
950 id = std::this_thread::get_id();
954 result.store(n.wait().value());
959 EXPECT_EQ(result.load(), 1);
962 // validate that the callback ended up executing in this thread, which
963 // is more to ensure that this test actually tests what it should
964 EXPECT_EQ(id, std::this_thread::get_id());
965 EXPECT_EQ(result.load(), 42);
969 MoveFlag() = default;
970 MoveFlag(const MoveFlag&) = delete;
971 MoveFlag(MoveFlag&& other) noexcept {
977 TEST(Future, waitReplacesSelf) {
981 auto f1 = makeFuture(MoveFlag());
983 EXPECT_FALSE(f1.value().moved);
986 auto f2 = makeFuture(MoveFlag()).wait();
987 EXPECT_FALSE(f2.value().moved);
993 auto f1 = makeFuture(MoveFlag());
994 f1.wait(milliseconds(1));
995 EXPECT_FALSE(f1.value().moved);
998 auto f2 = makeFuture(MoveFlag()).wait(milliseconds(1));
999 EXPECT_FALSE(f2.value().moved);
1004 folly::EventBase eb;
1006 auto f1 = makeFuture(MoveFlag());
1008 EXPECT_FALSE(f1.value().moved);
1011 auto f2 = makeFuture(MoveFlag()).waitVia(&eb);
1012 EXPECT_FALSE(f2.value().moved);
1016 TEST(Future, waitWithDuration) {
1019 Future<int> f = p.getFuture();
1020 f.wait(milliseconds(1));
1021 EXPECT_FALSE(f.isReady());
1023 EXPECT_TRUE(f.isReady());
1027 Future<int> f = p.getFuture();
1029 f.wait(milliseconds(1));
1030 EXPECT_TRUE(f.isReady());
1033 vector<Future<bool>> v_fb;
1034 v_fb.push_back(makeFuture(true));
1035 v_fb.push_back(makeFuture(false));
1036 auto f = whenAll(v_fb.begin(), v_fb.end());
1037 f.wait(milliseconds(1));
1038 EXPECT_TRUE(f.isReady());
1039 EXPECT_EQ(2, f.value().size());
1042 vector<Future<bool>> v_fb;
1045 v_fb.push_back(p1.getFuture());
1046 v_fb.push_back(p2.getFuture());
1047 auto f = whenAll(v_fb.begin(), v_fb.end());
1048 f.wait(milliseconds(1));
1049 EXPECT_FALSE(f.isReady());
1051 EXPECT_FALSE(f.isReady());
1053 EXPECT_TRUE(f.isReady());
1056 auto f = makeFuture().wait(milliseconds(1));
1057 EXPECT_TRUE(f.isReady());
1062 auto start = std::chrono::steady_clock::now();
1063 auto f = p.getFuture().wait(milliseconds(100));
1064 auto elapsed = std::chrono::steady_clock::now() - start;
1065 EXPECT_GE(elapsed, milliseconds(100));
1066 EXPECT_FALSE(f.isReady());
1068 EXPECT_TRUE(f.isReady());
1072 // Try to trigger the race where the resultant Future is not yet complete
1073 // even if we didn't hit the timeout, and make sure we deal with it properly
1076 auto t = std::thread([&]{
1078 std::this_thread::sleep_for(milliseconds(100));
1082 auto f = p.getFuture().wait(std::chrono::seconds(3600));
1083 EXPECT_TRUE(f.isReady());
1088 class DummyDrivableExecutor : public DrivableExecutor {
1090 void add(Func f) override {}
1091 void drive() override { ran = true; }
1095 TEST(Future, getVia) {
1099 auto f = via(&x).then([]{ return true; });
1100 EXPECT_TRUE(f.getVia(&x));
1106 auto f = via(&x).then();
1111 DummyDrivableExecutor x;
1112 auto f = makeFuture(true);
1113 EXPECT_TRUE(f.getVia(&x));
1114 EXPECT_FALSE(x.ran);
1118 TEST(Future, waitVia) {
1121 auto f = via(&x).then();
1122 EXPECT_FALSE(f.isReady());
1124 EXPECT_TRUE(f.isReady());
1128 // try rvalue as well
1130 auto f = via(&x).activate().then().waitVia(&x);
1131 EXPECT_TRUE(f.isReady());
1135 DummyDrivableExecutor x;
1136 makeFuture(true).waitVia(&x);
1137 EXPECT_FALSE(x.ran);
1141 TEST(Future, callbackAfterActivate) {
1143 auto f = p.getFuture();
1147 f.then([&](Try<void>&&) { count++; });
1150 EXPECT_EQ(0, count);
1153 EXPECT_EQ(1, count);
1156 TEST(Future, activateOnDestruct) {
1157 auto f = std::make_shared<Future<void>>(makeFuture());
1161 f->then([&](Try<void>&&) { count++; });
1162 EXPECT_EQ(0, count);
1165 EXPECT_EQ(1, count);
1168 TEST(Future, viaActsCold) {
1173 fv.then([&](Try<void>&&) { count++; });
1175 EXPECT_EQ(0, count);
1179 EXPECT_EQ(1, x.run());
1180 EXPECT_EQ(1, count);
1183 TEST(Future, viaIsCold) {
1185 EXPECT_FALSE(via(&x).isActive());
1188 TEST(Future, viaRaces) {
1191 auto tid = std::this_thread::get_id();
1194 std::thread t1([&] {
1197 .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1198 .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1199 .then([&](Try<void>&&) { done = true; });
1202 std::thread t2([&] {
1206 while (!done) x.run();
1212 TEST(Future, viaRaces_2stage) {
1215 auto tid = std::this_thread::get_id();
1218 std::thread t1([&] {
1219 auto f2 = p.getFuture().via(&x);
1220 f2.then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1221 .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
1222 .then([&](Try<void>&&) { done = true; });
1224 // the bug was in the promise being fulfilled before f2 is reactivated. we
1225 // could sleep, but yielding should cause this to fail with reasonable
1227 std::this_thread::yield();
1231 std::thread t2([&] {
1235 while (!done) x.run();
1240 TEST(Future, getFuture_after_setValue) {
1243 EXPECT_EQ(42, p.getFuture().value());
1246 TEST(Future, getFuture_after_setException) {
1248 p.fulfil([]() -> void { throw std::logic_error("foo"); });
1249 EXPECT_THROW(p.getFuture().value(), std::logic_error);
1252 TEST(Future, detachRace) {
1254 // This test is designed to detect a race that was in Core::detachOne()
1255 // where detached_ was incremented and then tested, and that
1256 // allowed a race where both Promise and Future would think they were the
1257 // second and both try to delete. This showed up at scale but was very
1258 // difficult to reliably repro in a test. As it is, this only fails about
1259 // once in every 1,000 executions. Doing this 1,000 times is going to make a
1260 // slow test so I won't do that but if it ever fails, take it seriously, and
1261 // run the test binary with "--gtest_repeat=10000 --gtest_filter=*detachRace"
1262 // (Don't forget to enable ASAN)
1263 auto p = folly::make_unique<Promise<bool>>();
1264 auto f = folly::make_unique<Future<bool>>(p->getFuture());
1265 folly::Baton<> baton;
1275 class TestData : public RequestData {
1277 explicit TestData(int data) : data_(data) {}
1278 virtual ~TestData() {}
1282 TEST(Future, context) {
1284 // Start a new context
1285 RequestContext::create();
1287 EXPECT_EQ(nullptr, RequestContext::get()->getContextData("test"));
1289 // Set some test data
1290 RequestContext::get()->setContextData(
1292 std::unique_ptr<TestData>(new TestData(10)));
1296 auto future = p.getFuture().then([&]{
1297 // Check that the context followed the future
1298 EXPECT_TRUE(RequestContext::get() != nullptr);
1299 auto a = dynamic_cast<TestData*>(
1300 RequestContext::get()->getContextData("test"));
1301 auto data = a->data_;
1302 EXPECT_EQ(10, data);
1305 // Clear the context
1306 RequestContext::setContext(nullptr);
1308 EXPECT_EQ(nullptr, RequestContext::get()->getContextData("test"));
1310 // Fulfil the promise
1315 // This only fails about 1 in 1k times when the bug is present :(
1316 TEST(Future, t5506504) {
1320 auto promises = std::make_shared<vector<Promise<void>>>(4);
1321 vector<Future<void>> futures;
1323 for (auto& p : *promises) {
1324 futures.emplace_back(
1327 .then([](Try<void>&&){}));
1332 for (auto& p : *promises) p.setValue();
1335 return whenAll(futures.begin(), futures.end());
1341 // Test of handling of a circular dependency. It's never recommended
1342 // to have one because of possible memory leaks. Here we test that
1343 // we can handle freeing of the Future while it is running.
1344 TEST(Future, CircularDependencySharedPtrSelfReset) {
1345 Promise<int64_t> promise;
1346 auto ptr = std::make_shared<Future<int64_t>>(promise.getFuture());
1349 [ptr] (folly::Try<int64_t>&& uid) mutable {
1350 EXPECT_EQ(1, ptr.use_count());
1352 // Leaving no references to ourselves.
1354 EXPECT_EQ(0, ptr.use_count());
1358 EXPECT_EQ(2, ptr.use_count());
1362 promise.fulfil([]{return 1l;});
1365 TEST(Future, Constructor) {
1366 auto f1 = []() -> Future<int> { return Future<int>(3); }();
1367 EXPECT_EQ(f1.value(), 3);
1368 auto f2 = []() -> Future<void> { return Future<void>(); }();
1369 EXPECT_NO_THROW(f2.value());
1372 TEST(Future, ImplicitConstructor) {
1373 auto f1 = []() -> Future<int> { return 3; }();
1374 EXPECT_EQ(f1.value(), 3);
1375 // Unfortunately, the C++ standard does not allow the
1376 // following implicit conversion to work:
1377 //auto f2 = []() -> Future<void> { }();