2 * Copyright 2016 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.
17 #include <gtest/gtest.h>
19 #include <folly/futures/Future.h>
20 #include <folly/Unit.h>
21 #include <folly/Memory.h>
22 #include <folly/Executor.h>
23 #include <folly/dynamic.h>
24 #include <folly/Baton.h>
25 #include <folly/portability/Unistd.h>
33 #include <type_traits>
35 using namespace folly;
37 #define EXPECT_TYPE(x, T) \
38 EXPECT_TRUE((std::is_same<decltype(x), T>::value))
40 typedef FutureException eggs_t;
41 static eggs_t eggs("eggs");
45 TEST(Future, futureDefaultCtor) {
49 TEST(Future, futureToUnit) {
50 Future<Unit> fu = makeFuture(42).unit();
52 EXPECT_TRUE(makeFuture<int>(eggs).unit().hasException());
55 TEST(Future, voidFutureToUnit) {
56 Future<Unit> fu = makeFuture().unit();
58 EXPECT_TRUE(makeFuture<Unit>(eggs).unit().hasException());
61 TEST(Future, unitFutureToUnitIdentity) {
62 Future<Unit> fu = makeFuture(Unit{}).unit();
64 EXPECT_TRUE(makeFuture<Unit>(eggs).unit().hasException());
67 TEST(Future, toUnitWhileInProgress) {
69 Future<Unit> fu = p.getFuture().unit();
70 EXPECT_FALSE(fu.isReady());
72 EXPECT_TRUE(fu.isReady());
75 TEST(Future, makeFutureWithUnit) {
77 Future<Unit> fu = makeFutureWith([&] { count++; });
81 TEST(Future, onError) {
83 auto flag = [&]{ theFlag = true; };
84 #define EXPECT_FLAG() \
86 EXPECT_TRUE(theFlag); \
90 #define EXPECT_NO_FLAG() \
92 EXPECT_FALSE(theFlag); \
98 auto f = makeFuture().then([] {
100 }).onError([&](eggs_t& /* e */) { flag(); });
102 EXPECT_NO_THROW(f.value());
106 auto f = makeFuture()
107 .then([] { throw eggs; })
108 .onError([&](eggs_t& /* e */) {
113 EXPECT_NO_THROW(f.value());
118 auto f = makeFuture().then([] {
120 }).onError([&](eggs_t /* e */) { flag(); });
122 EXPECT_NO_THROW(f.value());
126 auto f = makeFuture()
127 .then([] { throw eggs; })
128 .onError([&](eggs_t /* e */) {
133 EXPECT_NO_THROW(f.value());
138 auto f = makeFuture().then([] {
140 }).onError([&](std::exception& /* e */) { flag(); });
142 EXPECT_NO_THROW(f.value());
146 auto f = makeFuture()
147 .then([] { throw eggs; })
148 .onError([&](std::exception& /* e */) {
153 EXPECT_NO_THROW(f.value());
158 auto f = makeFuture().then([] {
160 }).onError([&](int /* e */) { flag(); });
162 EXPECT_NO_THROW(f.value());
166 auto f = makeFuture()
167 .then([] { throw - 1; })
168 .onError([&](int /* e */) {
173 EXPECT_NO_THROW(f.value());
178 auto f = makeFuture().then([] {
180 }).onError([&](eggs_t& /* e */) mutable { flag(); });
182 EXPECT_NO_THROW(f.value());
186 auto f = makeFuture()
187 .then([] { throw eggs; })
188 .onError([&](eggs_t& /* e */) mutable {
193 EXPECT_NO_THROW(f.value());
198 auto f = makeFuture()
199 .then([] { return 42; })
200 .onError([&](eggs_t& /* e */) {
205 EXPECT_EQ(42, f.value());
209 auto f = makeFuture()
210 .then([] { return 42; })
211 .onError([&](eggs_t& /* e */) {
213 return makeFuture<int>(-1);
216 EXPECT_EQ(42, f.value());
219 // Catch different exception
221 auto f = makeFuture().then([] {
223 }).onError([&](std::runtime_error& /* e */) { flag(); });
225 EXPECT_THROW(f.value(), eggs_t);
229 auto f = makeFuture()
230 .then([] { throw eggs; })
231 .onError([&](std::runtime_error& /* e */) {
236 EXPECT_THROW(f.value(), eggs_t);
239 // Returned value propagates
241 auto f = makeFuture().then([] {
244 }).onError([&](eggs_t& /* e */) { return 42; });
245 EXPECT_EQ(42, f.value());
248 // Returned future propagates
250 auto f = makeFuture().then([] {
253 }).onError([&](eggs_t& /* e */) { return makeFuture<int>(42); });
254 EXPECT_EQ(42, f.value());
259 auto f = makeFuture()
260 .then([] { throw eggs; return 0; })
261 .onError([&] (eggs_t& e) { throw e; return -1; });
262 EXPECT_THROW(f.value(), eggs_t);
266 auto f = makeFuture()
267 .then([] { throw eggs; return 0; })
268 .onError([&] (eggs_t& e) { throw e; return makeFuture<int>(-1); });
269 EXPECT_THROW(f.value(), eggs_t);
272 // exception_wrapper, return Future<T>
274 auto f = makeFuture()
275 .then([] { throw eggs; })
276 .onError([&](exception_wrapper /* e */) {
281 EXPECT_NO_THROW(f.value());
284 // exception_wrapper, return Future<T> but throw
286 auto f = makeFuture()
291 .onError([&](exception_wrapper /* e */) {
294 return makeFuture<int>(-1);
297 EXPECT_THROW(f.value(), eggs_t);
300 // exception_wrapper, return T
302 auto f = makeFuture()
307 .onError([&](exception_wrapper /* e */) {
312 EXPECT_EQ(-1, f.value());
315 // exception_wrapper, return T but throw
317 auto f = makeFuture()
322 .onError([&](exception_wrapper /* e */) {
328 EXPECT_THROW(f.value(), eggs_t);
331 // const exception_wrapper&
333 auto f = makeFuture()
334 .then([] { throw eggs; })
335 .onError([&](const exception_wrapper& /* e */) {
340 EXPECT_NO_THROW(f.value());
345 TEST(Future, special) {
346 EXPECT_FALSE(std::is_copy_constructible<Future<int>>::value);
347 EXPECT_FALSE(std::is_copy_assignable<Future<int>>::value);
348 EXPECT_TRUE(std::is_move_constructible<Future<int>>::value);
349 EXPECT_TRUE(std::is_move_assignable<Future<int>>::value);
353 auto f = makeFuture<std::string>("0")
355 return makeFuture<std::string>("1"); })
356 .then([](Try<std::string>&& t) {
357 return makeFuture(t.value() + ";2"); })
358 .then([](const Try<std::string>&& t) {
359 return makeFuture(t.value() + ";3"); })
360 .then([](Try<std::string>& t) {
361 return makeFuture(t.value() + ";4"); })
362 .then([](const Try<std::string>& t) {
363 return makeFuture(t.value() + ";5"); })
364 .then([](Try<std::string> t) {
365 return makeFuture(t.value() + ";6"); })
366 .then([](const Try<std::string> t) {
367 return makeFuture(t.value() + ";7"); })
368 .then([](std::string&& s) {
369 return makeFuture(s + ";8"); })
370 .then([](const std::string&& s) {
371 return makeFuture(s + ";9"); })
372 .then([](std::string& s) {
373 return makeFuture(s + ";10"); })
374 .then([](const std::string& s) {
375 return makeFuture(s + ";11"); })
376 .then([](std::string s) {
377 return makeFuture(s + ";12"); })
378 .then([](const std::string s) {
379 return makeFuture(s + ";13"); })
381 EXPECT_EQ(f.value(), "1;2;3;4;5;6;7;8;9;10;11;12;13");
384 TEST(Future, thenTry) {
387 makeFuture<int>(42).then([&](Try<int>&& t) {
389 EXPECT_EQ(42, t.value());
391 EXPECT_TRUE(flag); flag = false;
394 .then([](Try<int>&& t) { return t.value(); })
395 .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
396 EXPECT_TRUE(flag); flag = false;
398 makeFuture().then([&](Try<Unit>&& t) { flag = true; t.value(); });
399 EXPECT_TRUE(flag); flag = false;
402 auto f = p.getFuture().then([&](Try<Unit>&& /* t */) { flag = true; });
404 EXPECT_FALSE(f.isReady());
407 EXPECT_TRUE(f.isReady());
410 TEST(Future, thenValue) {
412 makeFuture<int>(42).then([&](int i){
416 EXPECT_TRUE(flag); flag = false;
419 .then([](int i){ return i; })
420 .then([&](int i) { flag = true; EXPECT_EQ(42, i); });
421 EXPECT_TRUE(flag); flag = false;
423 makeFuture().then([&]{
426 EXPECT_TRUE(flag); flag = false;
428 auto f = makeFuture<int>(eggs).then([&](int /* i */) {});
429 EXPECT_THROW(f.value(), eggs_t);
431 f = makeFuture<Unit>(eggs).then([&]{});
432 EXPECT_THROW(f.value(), eggs_t);
435 TEST(Future, thenValueFuture) {
438 .then([](int i){ return makeFuture<int>(std::move(i)); })
439 .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
440 EXPECT_TRUE(flag); flag = false;
442 makeFuture().then([] {
444 }).then([&](Try<Unit>&& /* t */) { flag = true; });
445 EXPECT_TRUE(flag); flag = false;
448 static std::string doWorkStatic(Try<std::string>&& t) {
449 return t.value() + ";static";
452 TEST(Future, thenFunction) {
454 std::string doWork(Try<std::string>&& t) {
455 return t.value() + ";class";
457 static std::string doWorkStatic(Try<std::string>&& t) {
458 return t.value() + ";class-static";
462 auto f = makeFuture<std::string>("start")
464 .then(Worker::doWorkStatic)
465 .then(&Worker::doWork, &w);
467 EXPECT_EQ(f.value(), "start;static;class-static;class");
470 static Future<std::string> doWorkStaticFuture(Try<std::string>&& t) {
471 return makeFuture(t.value() + ";static");
474 TEST(Future, thenFunctionFuture) {
476 Future<std::string> doWorkFuture(Try<std::string>&& t) {
477 return makeFuture(t.value() + ";class");
479 static Future<std::string> doWorkStaticFuture(Try<std::string>&& t) {
480 return makeFuture(t.value() + ";class-static");
484 auto f = makeFuture<std::string>("start")
485 .then(doWorkStaticFuture)
486 .then(Worker::doWorkStaticFuture)
487 .then(&Worker::doWorkFuture, &w);
489 EXPECT_EQ(f.value(), "start;static;class-static;class");
492 TEST(Future, thenStdFunction) {
494 std::function<int()> fn = [](){ return 42; };
495 auto f = makeFuture().then(std::move(fn));
496 EXPECT_EQ(f.value(), 42);
499 std::function<int(int)> fn = [](int i){ return i + 23; };
500 auto f = makeFuture(19).then(std::move(fn));
501 EXPECT_EQ(f.value(), 42);
504 std::function<int(Try<int>&)> fn = [](Try<int>& t){ return t.value() + 2; };
505 auto f = makeFuture(1).then(std::move(fn));
506 EXPECT_EQ(f.value(), 3);
510 std::function<void()> fn = [&flag](){ flag = true; };
511 auto f = makeFuture().then(std::move(fn));
512 EXPECT_TRUE(f.isReady());
517 TEST(Future, thenBind) {
519 return makeFuture("bind");
521 auto b = std::bind(l);
522 auto f = makeFuture().then(std::move(b));
523 EXPECT_EQ(f.value(), "bind");
526 TEST(Future, thenBindTry) {
527 auto l = [](Try<std::string>&& t) {
528 return makeFuture(t.value() + ";bind");
530 auto b = std::bind(l, std::placeholders::_1);
531 auto f = makeFuture<std::string>("start").then(std::move(b));
533 EXPECT_EQ(f.value(), "start;bind");
536 TEST(Future, value) {
537 auto f = makeFuture(std::unique_ptr<int>(new int(42)));
538 auto up = std::move(f.value());
541 EXPECT_THROW(makeFuture<int>(eggs).value(), eggs_t);
544 TEST(Future, isReady) {
546 auto f = p.getFuture();
547 EXPECT_FALSE(f.isReady());
549 EXPECT_TRUE(f.isReady());
552 TEST(Future, futureNotReady) {
554 Future<int> f = p.getFuture();
555 EXPECT_THROW(f.value(), eggs_t);
558 TEST(Future, hasException) {
559 EXPECT_TRUE(makeFuture<int>(eggs).getTry().hasException());
560 EXPECT_FALSE(makeFuture(42).getTry().hasException());
563 TEST(Future, hasValue) {
564 EXPECT_TRUE(makeFuture(42).getTry().hasValue());
565 EXPECT_FALSE(makeFuture<int>(eggs).getTry().hasValue());
568 TEST(Future, makeFuture) {
569 EXPECT_TYPE(makeFuture(42), Future<int>);
570 EXPECT_EQ(42, makeFuture(42).value());
572 EXPECT_TYPE(makeFuture<float>(42), Future<float>);
573 EXPECT_EQ(42, makeFuture<float>(42).value());
575 auto fun = [] { return 42; };
576 EXPECT_TYPE(makeFutureWith(fun), Future<int>);
577 EXPECT_EQ(42, makeFutureWith(fun).value());
579 auto funf = [] { return makeFuture<int>(43); };
580 EXPECT_TYPE(makeFutureWith(funf), Future<int>);
581 EXPECT_EQ(43, makeFutureWith(funf).value());
583 auto failfun = []() -> int { throw eggs; };
584 EXPECT_TYPE(makeFutureWith(failfun), Future<int>);
585 EXPECT_NO_THROW(makeFutureWith(failfun));
586 EXPECT_THROW(makeFutureWith(failfun).value(), eggs_t);
588 auto failfunf = []() -> Future<int> { throw eggs; };
589 EXPECT_TYPE(makeFutureWith(failfunf), Future<int>);
590 EXPECT_NO_THROW(makeFutureWith(failfunf));
591 EXPECT_THROW(makeFutureWith(failfunf).value(), eggs_t);
593 EXPECT_TYPE(makeFuture(), Future<Unit>);
596 TEST(Future, finish) {
597 auto x = std::make_shared<int>(0);
600 auto f = p.getFuture().then([x](Try<int>&& t) { *x = t.value(); });
602 // The callback hasn't executed
605 // The callback has a reference to x
606 EXPECT_EQ(2, x.use_count());
610 // the callback has executed
613 // the callback has been destructed
614 // and has released its reference to x
615 EXPECT_EQ(1, x.use_count());
618 TEST(Future, finishBigLambda) {
619 auto x = std::make_shared<int>(0);
621 // bulk_data, to be captured in the lambda passed to Future::then.
622 // This is meant to force that the lambda can't be stored inside
623 // the Future object.
624 std::array<char, sizeof(detail::Core<int>)> bulk_data = {0};
626 // suppress gcc warning about bulk_data not being used
627 EXPECT_EQ(bulk_data[0], 0);
630 auto f = p.getFuture().then([x, bulk_data](Try<int>&& t) { *x = t.value(); });
632 // The callback hasn't executed
635 // The callback has a reference to x
636 EXPECT_EQ(2, x.use_count());
640 // the callback has executed
643 // the callback has been destructed
644 // and has released its reference to x
645 EXPECT_EQ(1, x.use_count());
648 TEST(Future, unwrap) {
652 auto fa = a.getFuture();
653 auto fb = b.getFuture();
658 // do a, then do b, and get the result of a + b.
659 Future<int> f = fa.then([&](Try<int>&& ta) {
660 auto va = ta.value();
662 return fb.then([va, &flag2](Try<int>&& tb) {
664 return va + tb.value();
670 EXPECT_FALSE(f.isReady());
675 EXPECT_FALSE(f.isReady());
680 EXPECT_EQ(7, f.value());
683 TEST(Future, throwCaughtInImmediateThen) {
684 // Neither of these should throw "Promise already satisfied"
686 [=](Try<Unit>&&) -> int { throw std::exception(); });
688 [=](Try<Unit>&&) -> Future<int> { throw std::exception(); });
691 TEST(Future, throwIfFailed) {
692 makeFuture<Unit>(eggs)
693 .then([=](Try<Unit>&& t) {
694 EXPECT_THROW(t.throwIfFailed(), eggs_t);
697 .then([=](Try<Unit>&& t) {
698 EXPECT_NO_THROW(t.throwIfFailed());
701 makeFuture<int>(eggs)
702 .then([=](Try<int>&& t) {
703 EXPECT_THROW(t.throwIfFailed(), eggs_t);
706 .then([=](Try<int>&& t) {
707 EXPECT_NO_THROW(t.throwIfFailed());
711 TEST(Future, getFutureAfterSetValue) {
714 EXPECT_EQ(42, p.getFuture().value());
717 TEST(Future, getFutureAfterSetException) {
719 p.setWith([]() -> void { throw std::logic_error("foo"); });
720 EXPECT_THROW(p.getFuture().value(), std::logic_error);
723 TEST(Future, detachRace) {
725 // This test is designed to detect a race that was in Core::detachOne()
726 // where detached_ was incremented and then tested, and that
727 // allowed a race where both Promise and Future would think they were the
728 // second and both try to delete. This showed up at scale but was very
729 // difficult to reliably repro in a test. As it is, this only fails about
730 // once in every 1,000 executions. Doing this 1,000 times is going to make a
731 // slow test so I won't do that but if it ever fails, take it seriously, and
732 // run the test binary with "--gtest_repeat=10000 --gtest_filter=*detachRace"
733 // (Don't forget to enable ASAN)
734 auto p = folly::make_unique<Promise<bool>>();
735 auto f = folly::make_unique<Future<bool>>(p->getFuture());
736 folly::Baton<> baton;
746 // Test of handling of a circular dependency. It's never recommended
747 // to have one because of possible memory leaks. Here we test that
748 // we can handle freeing of the Future while it is running.
749 TEST(Future, CircularDependencySharedPtrSelfReset) {
750 Promise<int64_t> promise;
751 auto ptr = std::make_shared<Future<int64_t>>(promise.getFuture());
753 ptr->then([ptr](folly::Try<int64_t>&& /* uid */) mutable {
754 EXPECT_EQ(1, ptr.use_count());
756 // Leaving no references to ourselves.
758 EXPECT_EQ(0, ptr.use_count());
761 EXPECT_EQ(2, ptr.use_count());
768 TEST(Future, Constructor) {
769 auto f1 = []() -> Future<int> { return Future<int>(3); }();
770 EXPECT_EQ(f1.value(), 3);
771 auto f2 = []() -> Future<Unit> { return Future<Unit>(); }();
772 EXPECT_NO_THROW(f2.value());
775 TEST(Future, ImplicitConstructor) {
776 auto f1 = []() -> Future<int> { return 3; }();
777 EXPECT_EQ(f1.value(), 3);
778 // Unfortunately, the C++ standard does not allow the
779 // following implicit conversion to work:
780 //auto f2 = []() -> Future<Unit> { }();
783 TEST(Future, thenDynamic) {
784 // folly::dynamic has a constructor that takes any T, this test makes
785 // sure that we call the then lambda with folly::dynamic and not
786 // Try<folly::dynamic> because that then fails to compile
787 Promise<folly::dynamic> p;
788 Future<folly::dynamic> f = p.getFuture().then(
789 [](const folly::dynamic& d) {
790 return folly::dynamic(d.asInt() + 3);
794 EXPECT_EQ(f.get(), 5);
797 TEST(Future, RequestContext) {
798 class NewThreadExecutor : public Executor {
800 ~NewThreadExecutor() override {
801 std::for_each(v_.begin(), v_.end(), [](std::thread& t){ t.join(); });
803 void add(Func f) override {
804 if (throwsOnAdd_) { throw std::exception(); }
805 v_.emplace_back(std::move(f));
807 void addWithPriority(Func f, int8_t /* prio */) override {
810 uint8_t getNumPriorities() const override { return numPriorities_; }
812 void setHandlesPriorities() { numPriorities_ = 2; }
813 void setThrowsOnAdd() { throwsOnAdd_ = true; }
815 std::vector<std::thread> v_;
816 uint8_t numPriorities_ = 1;
817 bool throwsOnAdd_ = false;
820 struct MyRequestData : RequestData {
821 MyRequestData(bool value = false) : value(value) {}
828 folly::RequestContextScopeGuard rctx;
829 RequestContext::get()->setContextData(
830 "key", folly::make_unique<MyRequestData>(true));
831 auto checker = [](int lineno) {
832 return [lineno](Try<int>&& /* t */) {
833 auto d = static_cast<MyRequestData*>(
834 RequestContext::get()->getContextData("key"));
835 EXPECT_TRUE(d && d->value) << "on line " << lineno;
839 makeFuture(1).via(&e).then(checker(__LINE__));
841 e.setHandlesPriorities();
842 makeFuture(2).via(&e).then(checker(__LINE__));
844 p1.getFuture().then(checker(__LINE__));
847 p2.getFuture().via(&e).then(checker(__LINE__));
849 // Assert that no RequestContext is set
850 EXPECT_FALSE(RequestContext::saveContext());
855 TEST(Future, makeFutureNoThrow) {
856 makeFuture().value();