via and activate/deactivate chaining
[folly.git] / folly / wangle / test / FutureTest.cpp
1 /*
2  * Copyright 2014 Facebook, Inc.
3  *
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
7  *
8  *   http://www.apache.org/licenses/LICENSE-2.0
9  *
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.
15  */
16
17 #include <algorithm>
18 #include <atomic>
19 #include <folly/small_vector.h>
20 #include <gtest/gtest.h>
21 #include <memory>
22 #include <string>
23 #include <thread>
24 #include <type_traits>
25 #include <unistd.h>
26 #include <folly/Memory.h>
27 #include <folly/wangle/Executor.h>
28 #include <folly/wangle/Future.h>
29 #include <folly/wangle/ManualExecutor.h>
30 #include <folly/MPMCQueue.h>
31
32 #include <folly/io/async/Request.h>
33
34 using namespace folly;
35 using namespace folly::wangle;
36 using std::pair;
37 using std::string;
38 using std::unique_ptr;
39 using std::vector;
40
41 #define EXPECT_TYPE(x, T) \
42   EXPECT_TRUE((std::is_same<decltype(x), T>::value))
43
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};
48   std::thread worker;
49   folly::Baton<> baton;
50
51   void work() {
52     baton.post();
53     Func fn;
54     while (!done) {
55       while (!funcs.isEmpty()) {
56         funcs.blockingRead(fn);
57         fn();
58       }
59     }
60   }
61
62  public:
63   ThreadExecutor(size_t n = 1024)
64     : funcs(n), worker(std::bind(&ThreadExecutor::work, this)) {}
65
66   ~ThreadExecutor() {
67     done = true;
68     funcs.write([]{});
69     worker.join();
70   }
71
72   void add(Func fn) override {
73     funcs.blockingWrite(std::move(fn));
74   }
75
76   void waitForStartup() {
77     baton.wait();
78   }
79 };
80
81 typedef WangleException eggs_t;
82 static eggs_t eggs("eggs");
83
84 // Future
85
86 TEST(Future, try) {
87   class A {
88    public:
89     A(int x) : x_(x) {}
90
91     int x() const {
92       return x_;
93     }
94    private:
95     int x_;
96   };
97
98   A a(5);
99   Try<A> t_a(std::move(a));
100
101   Try<void> t_void;
102
103   EXPECT_EQ(5, t_a.value().x());
104 }
105
106 TEST(Future, special) {
107   EXPECT_FALSE(std::is_copy_constructible<Future<int>>::value);
108   EXPECT_FALSE(std::is_copy_assignable<Future<int>>::value);
109   EXPECT_TRUE(std::is_move_constructible<Future<int>>::value);
110   EXPECT_TRUE(std::is_move_assignable<Future<int>>::value);
111 }
112
113 TEST(Future, thenTry) {
114   bool flag = false;
115
116   makeFuture<int>(42).then([&](Try<int>&& t) {
117                               flag = true;
118                               EXPECT_EQ(42, t.value());
119                             });
120   EXPECT_TRUE(flag); flag = false;
121
122   makeFuture<int>(42)
123     .then([](Try<int>&& t) { return t.value(); })
124     .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
125   EXPECT_TRUE(flag); flag = false;
126
127   makeFuture().then([&](Try<void>&& t) { flag = true; t.value(); });
128   EXPECT_TRUE(flag); flag = false;
129
130   Promise<void> p;
131   auto f = p.getFuture().then([&](Try<void>&& t) { flag = true; });
132   EXPECT_FALSE(flag);
133   EXPECT_FALSE(f.isReady());
134   p.setValue();
135   EXPECT_TRUE(flag);
136   EXPECT_TRUE(f.isReady());
137 }
138
139 TEST(Future, thenValue) {
140   bool flag = false;
141   makeFuture<int>(42).then([&](int i){
142     EXPECT_EQ(42, i);
143     flag = true;
144   });
145   EXPECT_TRUE(flag); flag = false;
146
147   makeFuture<int>(42)
148     .then([](int i){ return i; })
149     .then([&](int i) { flag = true; EXPECT_EQ(42, i); });
150   EXPECT_TRUE(flag); flag = false;
151
152   makeFuture().then([&]{
153     flag = true;
154   });
155   EXPECT_TRUE(flag); flag = false;
156
157   auto f = makeFuture<int>(eggs).then([&](int i){});
158   EXPECT_THROW(f.value(), eggs_t);
159
160   f = makeFuture<void>(eggs).then([&]{});
161   EXPECT_THROW(f.value(), eggs_t);
162 }
163
164 TEST(Future, thenValueFuture) {
165   bool flag = false;
166   makeFuture<int>(42)
167     .then([](int i){ return makeFuture<int>(std::move(i)); })
168     .then([&](Try<int>&& t) { flag = true; EXPECT_EQ(42, t.value()); });
169   EXPECT_TRUE(flag); flag = false;
170
171   makeFuture()
172     .then([]{ return makeFuture(); })
173     .then([&](Try<void>&& t) { flag = true; });
174   EXPECT_TRUE(flag); flag = false;
175 }
176
177 static string doWorkStatic(Try<string>&& t) {
178   return t.value() + ";static";
179 }
180
181 TEST(Future, thenFunction) {
182   struct Worker {
183     string doWork(Try<string>&& t) {
184       return t.value() + ";class";
185     }
186     static string doWorkStatic(Try<string>&& t) {
187       return t.value() + ";class-static";
188     }
189   } w;
190
191   auto f = makeFuture<string>("start")
192     .then(doWorkStatic)
193     .then(Worker::doWorkStatic)
194     .then(&w, &Worker::doWork);
195
196   EXPECT_EQ(f.value(), "start;static;class-static;class");
197 }
198
199 static Future<string> doWorkStaticFuture(Try<string>&& t) {
200   return makeFuture(t.value() + ";static");
201 }
202
203 TEST(Future, thenFunctionFuture) {
204   struct Worker {
205     Future<string> doWorkFuture(Try<string>&& t) {
206       return makeFuture(t.value() + ";class");
207     }
208     static Future<string> doWorkStaticFuture(Try<string>&& t) {
209       return makeFuture(t.value() + ";class-static");
210     }
211   } w;
212
213   auto f = makeFuture<string>("start")
214     .then(doWorkStaticFuture)
215     .then(Worker::doWorkStaticFuture)
216     .then(&w, &Worker::doWorkFuture);
217
218   EXPECT_EQ(f.value(), "start;static;class-static;class");
219 }
220
221 TEST(Future, value) {
222   auto f = makeFuture(unique_ptr<int>(new int(42)));
223   auto up = std::move(f.value());
224   EXPECT_EQ(42, *up);
225
226   EXPECT_THROW(makeFuture<int>(eggs).value(), eggs_t);
227 }
228
229 TEST(Future, isReady) {
230   Promise<int> p;
231   auto f = p.getFuture();
232   EXPECT_FALSE(f.isReady());
233   p.setValue(42);
234   EXPECT_TRUE(f.isReady());
235   }
236
237 TEST(Future, futureNotReady) {
238   Promise<int> p;
239   Future<int> f = p.getFuture();
240   EXPECT_THROW(f.value(), eggs_t);
241 }
242
243 TEST(Future, hasException) {
244   EXPECT_TRUE(makeFuture<int>(eggs).getTry().hasException());
245   EXPECT_FALSE(makeFuture(42).getTry().hasException());
246 }
247
248 TEST(Future, hasValue) {
249   EXPECT_TRUE(makeFuture(42).getTry().hasValue());
250   EXPECT_FALSE(makeFuture<int>(eggs).getTry().hasValue());
251 }
252
253 TEST(Future, makeFuture) {
254   EXPECT_TYPE(makeFuture(42), Future<int>);
255   EXPECT_EQ(42, makeFuture(42).value());
256
257   EXPECT_TYPE(makeFuture<float>(42), Future<float>);
258   EXPECT_EQ(42, makeFuture<float>(42).value());
259
260   auto fun = [] { return 42; };
261   EXPECT_TYPE(makeFutureTry(fun), Future<int>);
262   EXPECT_EQ(42, makeFutureTry(fun).value());
263
264   auto failfun = []() -> int { throw eggs; };
265   EXPECT_TYPE(makeFutureTry(failfun), Future<int>);
266   EXPECT_THROW(makeFutureTry(failfun).value(), eggs_t);
267
268   EXPECT_TYPE(makeFuture(), Future<void>);
269 }
270
271 // Promise
272
273 TEST(Promise, special) {
274   EXPECT_FALSE(std::is_copy_constructible<Promise<int>>::value);
275   EXPECT_FALSE(std::is_copy_assignable<Promise<int>>::value);
276   EXPECT_TRUE(std::is_move_constructible<Promise<int>>::value);
277   EXPECT_TRUE(std::is_move_assignable<Promise<int>>::value);
278 }
279
280 TEST(Promise, getFuture) {
281   Promise<int> p;
282   Future<int> f = p.getFuture();
283   EXPECT_FALSE(f.isReady());
284 }
285
286 TEST(Promise, setValue) {
287   Promise<int> fund;
288   auto ffund = fund.getFuture();
289   fund.setValue(42);
290   EXPECT_EQ(42, ffund.value());
291
292   struct Foo {
293     string name;
294     int value;
295   };
296
297   Promise<Foo> pod;
298   auto fpod = pod.getFuture();
299   Foo f = {"the answer", 42};
300   pod.setValue(f);
301   Foo f2 = fpod.value();
302   EXPECT_EQ(f.name, f2.name);
303   EXPECT_EQ(f.value, f2.value);
304
305   pod = Promise<Foo>();
306   fpod = pod.getFuture();
307   pod.setValue(std::move(f2));
308   Foo f3 = fpod.value();
309   EXPECT_EQ(f.name, f3.name);
310   EXPECT_EQ(f.value, f3.value);
311
312   Promise<unique_ptr<int>> mov;
313   auto fmov = mov.getFuture();
314   mov.setValue(unique_ptr<int>(new int(42)));
315   unique_ptr<int> ptr = std::move(fmov.value());
316   EXPECT_EQ(42, *ptr);
317
318   Promise<void> v;
319   auto fv = v.getFuture();
320   v.setValue();
321   EXPECT_TRUE(fv.isReady());
322 }
323
324 TEST(Promise, setException) {
325   {
326     Promise<void> p;
327     auto f = p.getFuture();
328     p.setException(eggs);
329     EXPECT_THROW(f.value(), eggs_t);
330   }
331   {
332     Promise<void> p;
333     auto f = p.getFuture();
334     try {
335       throw eggs;
336     } catch (...) {
337       p.setException(std::current_exception());
338     }
339     EXPECT_THROW(f.value(), eggs_t);
340   }
341 }
342
343 TEST(Promise, fulfil) {
344   {
345     Promise<int> p;
346     auto f = p.getFuture();
347     p.fulfil([] { return 42; });
348     EXPECT_EQ(42, f.value());
349   }
350   {
351     Promise<int> p;
352     auto f = p.getFuture();
353     p.fulfil([]() -> int { throw eggs; });
354     EXPECT_THROW(f.value(), eggs_t);
355   }
356 }
357
358 TEST(Future, finish) {
359   auto x = std::make_shared<int>(0);
360   {
361     Promise<int> p;
362     auto f = p.getFuture().then([x](Try<int>&& t) { *x = t.value(); });
363
364     // The callback hasn't executed
365     EXPECT_EQ(0, *x);
366
367     // The callback has a reference to x
368     EXPECT_EQ(2, x.use_count());
369
370     p.setValue(42);
371
372     // the callback has executed
373     EXPECT_EQ(42, *x);
374   }
375   // the callback has been destructed
376   // and has released its reference to x
377   EXPECT_EQ(1, x.use_count());
378 }
379
380 TEST(Future, unwrap) {
381   Promise<int> a;
382   Promise<int> b;
383
384   auto fa = a.getFuture();
385   auto fb = b.getFuture();
386
387   bool flag1 = false;
388   bool flag2 = false;
389
390   // do a, then do b, and get the result of a + b.
391   Future<int> f = fa.then([&](Try<int>&& ta) {
392     auto va = ta.value();
393     flag1 = true;
394     return fb.then([va, &flag2](Try<int>&& tb) {
395       flag2 = true;
396       return va + tb.value();
397     });
398   });
399
400   EXPECT_FALSE(flag1);
401   EXPECT_FALSE(flag2);
402   EXPECT_FALSE(f.isReady());
403
404   a.setValue(3);
405   EXPECT_TRUE(flag1);
406   EXPECT_FALSE(flag2);
407   EXPECT_FALSE(f.isReady());
408
409   b.setValue(4);
410   EXPECT_TRUE(flag1);
411   EXPECT_TRUE(flag2);
412   EXPECT_EQ(7, f.value());
413 }
414
415 TEST(Future, whenAll) {
416   // returns a vector variant
417   {
418     vector<Promise<int>> promises(10);
419     vector<Future<int>> futures;
420
421     for (auto& p : promises)
422       futures.push_back(p.getFuture());
423
424     auto allf = whenAll(futures.begin(), futures.end());
425
426     random_shuffle(promises.begin(), promises.end());
427     for (auto& p : promises) {
428       EXPECT_FALSE(allf.isReady());
429       p.setValue(42);
430     }
431
432     EXPECT_TRUE(allf.isReady());
433     auto& results = allf.value();
434     for (auto& t : results) {
435       EXPECT_EQ(42, t.value());
436     }
437   }
438
439   // check error semantics
440   {
441     vector<Promise<int>> promises(4);
442     vector<Future<int>> futures;
443
444     for (auto& p : promises)
445       futures.push_back(p.getFuture());
446
447     auto allf = whenAll(futures.begin(), futures.end());
448
449
450     promises[0].setValue(42);
451     promises[1].setException(eggs);
452
453     EXPECT_FALSE(allf.isReady());
454
455     promises[2].setValue(42);
456
457     EXPECT_FALSE(allf.isReady());
458
459     promises[3].setException(eggs);
460
461     EXPECT_TRUE(allf.isReady());
462     EXPECT_FALSE(allf.getTry().hasException());
463
464     auto& results = allf.value();
465     EXPECT_EQ(42, results[0].value());
466     EXPECT_TRUE(results[1].hasException());
467     EXPECT_EQ(42, results[2].value());
468     EXPECT_TRUE(results[3].hasException());
469   }
470
471   // check that futures are ready in then()
472   {
473     vector<Promise<void>> promises(10);
474     vector<Future<void>> futures;
475
476     for (auto& p : promises)
477       futures.push_back(p.getFuture());
478
479     auto allf = whenAll(futures.begin(), futures.end())
480       .then([](Try<vector<Try<void>>>&& ts) {
481         for (auto& f : ts.value())
482           f.value();
483       });
484
485     random_shuffle(promises.begin(), promises.end());
486     for (auto& p : promises)
487       p.setValue();
488     EXPECT_TRUE(allf.isReady());
489   }
490 }
491
492
493 TEST(Future, whenAny) {
494   {
495     vector<Promise<int>> promises(10);
496     vector<Future<int>> futures;
497
498     for (auto& p : promises)
499       futures.push_back(p.getFuture());
500
501     for (auto& f : futures) {
502       EXPECT_FALSE(f.isReady());
503     }
504
505     auto anyf = whenAny(futures.begin(), futures.end());
506
507     /* futures were moved in, so these are invalid now */
508     EXPECT_FALSE(anyf.isReady());
509
510     promises[7].setValue(42);
511     EXPECT_TRUE(anyf.isReady());
512     auto& idx_fut = anyf.value();
513
514     auto i = idx_fut.first;
515     EXPECT_EQ(7, i);
516
517     auto& f = idx_fut.second;
518     EXPECT_EQ(42, f.value());
519   }
520
521   // error
522   {
523     vector<Promise<void>> promises(10);
524     vector<Future<void>> futures;
525
526     for (auto& p : promises)
527       futures.push_back(p.getFuture());
528
529     for (auto& f : futures) {
530       EXPECT_FALSE(f.isReady());
531     }
532
533     auto anyf = whenAny(futures.begin(), futures.end());
534
535     EXPECT_FALSE(anyf.isReady());
536
537     promises[3].setException(eggs);
538     EXPECT_TRUE(anyf.isReady());
539     EXPECT_TRUE(anyf.value().second.hasException());
540   }
541
542   // then()
543   {
544     vector<Promise<int>> promises(10);
545     vector<Future<int>> futures;
546
547     for (auto& p : promises)
548       futures.push_back(p.getFuture());
549
550     auto anyf = whenAny(futures.begin(), futures.end())
551       .then([](Try<pair<size_t, Try<int>>>&& f) {
552         EXPECT_EQ(42, f.value().second.value());
553       });
554
555     promises[3].setValue(42);
556     EXPECT_TRUE(anyf.isReady());
557   }
558 }
559
560
561 TEST(when, already_completed) {
562   {
563     vector<Future<void>> fs;
564     for (int i = 0; i < 10; i++)
565       fs.push_back(makeFuture());
566
567     whenAll(fs.begin(), fs.end())
568       .then([&](Try<vector<Try<void>>>&& t) {
569         EXPECT_EQ(fs.size(), t.value().size());
570       });
571   }
572   {
573     vector<Future<int>> fs;
574     for (int i = 0; i < 10; i++)
575       fs.push_back(makeFuture(i));
576
577     whenAny(fs.begin(), fs.end())
578       .then([&](Try<pair<size_t, Try<int>>>&& t) {
579         auto& p = t.value();
580         EXPECT_EQ(p.first, p.second.value());
581       });
582   }
583 }
584
585 TEST(when, whenN) {
586   vector<Promise<void>> promises(10);
587   vector<Future<void>> futures;
588
589   for (auto& p : promises)
590     futures.push_back(p.getFuture());
591
592   bool flag = false;
593   size_t n = 3;
594   whenN(futures.begin(), futures.end(), n)
595     .then([&](Try<vector<pair<size_t, Try<void>>>>&& t) {
596       flag = true;
597       auto v = t.value();
598       EXPECT_EQ(n, v.size());
599       for (auto& tt : v)
600         EXPECT_TRUE(tt.second.hasValue());
601     });
602
603   promises[0].setValue();
604   EXPECT_FALSE(flag);
605   promises[1].setValue();
606   EXPECT_FALSE(flag);
607   promises[2].setValue();
608   EXPECT_TRUE(flag);
609 }
610
611 /* Ensure that we can compile when_{all,any} with folly::small_vector */
612 TEST(when, small_vector) {
613
614   static_assert(!FOLLY_IS_TRIVIALLY_COPYABLE(Future<void>),
615                 "Futures should not be trivially copyable");
616   static_assert(!FOLLY_IS_TRIVIALLY_COPYABLE(Future<int>),
617                 "Futures should not be trivially copyable");
618
619   using folly::small_vector;
620   {
621     small_vector<Future<void>> futures;
622
623     for (int i = 0; i < 10; i++)
624       futures.push_back(makeFuture());
625
626     auto anyf = whenAny(futures.begin(), futures.end());
627   }
628
629   {
630     small_vector<Future<void>> futures;
631
632     for (int i = 0; i < 10; i++)
633       futures.push_back(makeFuture());
634
635     auto allf = whenAll(futures.begin(), futures.end());
636   }
637 }
638
639 TEST(Future, whenAllVariadic) {
640   Promise<bool> pb;
641   Promise<int> pi;
642   Future<bool> fb = pb.getFuture();
643   Future<int> fi = pi.getFuture();
644   bool flag = false;
645   whenAll(std::move(fb), std::move(fi))
646     .then([&](Try<std::tuple<Try<bool>, Try<int>>>&& t) {
647       flag = true;
648       EXPECT_TRUE(t.hasValue());
649       EXPECT_TRUE(std::get<0>(t.value()).hasValue());
650       EXPECT_EQ(std::get<0>(t.value()).value(), true);
651       EXPECT_TRUE(std::get<1>(t.value()).hasValue());
652       EXPECT_EQ(std::get<1>(t.value()).value(), 42);
653     });
654   pb.setValue(true);
655   EXPECT_FALSE(flag);
656   pi.setValue(42);
657   EXPECT_TRUE(flag);
658 }
659
660 TEST(Future, whenAllVariadicReferences) {
661   Promise<bool> pb;
662   Promise<int> pi;
663   Future<bool> fb = pb.getFuture();
664   Future<int> fi = pi.getFuture();
665   bool flag = false;
666   whenAll(fb, fi)
667     .then([&](Try<std::tuple<Try<bool>, Try<int>>>&& t) {
668       flag = true;
669       EXPECT_TRUE(t.hasValue());
670       EXPECT_TRUE(std::get<0>(t.value()).hasValue());
671       EXPECT_EQ(std::get<0>(t.value()).value(), true);
672       EXPECT_TRUE(std::get<1>(t.value()).hasValue());
673       EXPECT_EQ(std::get<1>(t.value()).value(), 42);
674     });
675   pb.setValue(true);
676   EXPECT_FALSE(flag);
677   pi.setValue(42);
678   EXPECT_TRUE(flag);
679 }
680
681 TEST(Future, whenAll_none) {
682   vector<Future<int>> fs;
683   auto f = whenAll(fs.begin(), fs.end());
684   EXPECT_TRUE(f.isReady());
685 }
686
687 TEST(Future, throwCaughtInImmediateThen) {
688   // Neither of these should throw "Promise already satisfied"
689   makeFuture().then(
690     [=](Try<void>&&) -> int { throw std::exception(); });
691   makeFuture().then(
692     [=](Try<void>&&) -> Future<int> { throw std::exception(); });
693 }
694
695 TEST(Future, throwIfFailed) {
696   makeFuture<void>(eggs)
697     .then([=](Try<void>&& t) {
698       EXPECT_THROW(t.throwIfFailed(), eggs_t);
699     });
700   makeFuture()
701     .then([=](Try<void>&& t) {
702       EXPECT_NO_THROW(t.throwIfFailed());
703     });
704
705   makeFuture<int>(eggs)
706     .then([=](Try<int>&& t) {
707       EXPECT_THROW(t.throwIfFailed(), eggs_t);
708     });
709   makeFuture<int>(42)
710     .then([=](Try<int>&& t) {
711       EXPECT_NO_THROW(t.throwIfFailed());
712     });
713 }
714
715 TEST(Future, waitWithSemaphoreImmediate) {
716   waitWithSemaphore(makeFuture());
717   auto done = waitWithSemaphore(makeFuture(42)).value();
718   EXPECT_EQ(42, done);
719
720   vector<int> v{1,2,3};
721   auto done_v = waitWithSemaphore(makeFuture(v)).value();
722   EXPECT_EQ(v.size(), done_v.size());
723   EXPECT_EQ(v, done_v);
724
725   vector<Future<void>> v_f;
726   v_f.push_back(makeFuture());
727   v_f.push_back(makeFuture());
728   auto done_v_f = waitWithSemaphore(whenAll(v_f.begin(), v_f.end())).value();
729   EXPECT_EQ(2, done_v_f.size());
730
731   vector<Future<bool>> v_fb;
732   v_fb.push_back(makeFuture(true));
733   v_fb.push_back(makeFuture(false));
734   auto fut = whenAll(v_fb.begin(), v_fb.end());
735   auto done_v_fb = std::move(waitWithSemaphore(std::move(fut)).value());
736   EXPECT_EQ(2, done_v_fb.size());
737 }
738
739 TEST(Future, waitWithSemaphore) {
740   Promise<int> p;
741   Future<int> f = p.getFuture();
742   std::atomic<bool> flag{false};
743   std::atomic<int> result{1};
744   std::atomic<std::thread::id> id;
745
746   std::thread t([&](Future<int>&& tf){
747       auto n = tf.then([&](Try<int> && t) {
748           id = std::this_thread::get_id();
749           return t.value();
750         });
751       flag = true;
752       result.store(waitWithSemaphore(std::move(n)).value());
753     },
754     std::move(f)
755     );
756   while(!flag){}
757   EXPECT_EQ(result.load(), 1);
758   p.setValue(42);
759   t.join();
760   // validate that the callback ended up executing in this thread, which
761   // is more to ensure that this test actually tests what it should
762   EXPECT_EQ(id, std::this_thread::get_id());
763   EXPECT_EQ(result.load(), 42);
764 }
765
766 TEST(Future, waitWithSemaphoreForTime) {
767  {
768   Promise<int> p;
769   Future<int> f = p.getFuture();
770   auto t = waitWithSemaphore(std::move(f),
771     std::chrono::microseconds(1));
772   EXPECT_FALSE(t.isReady());
773   p.setValue(1);
774   EXPECT_TRUE(t.isReady());
775  }
776  {
777   Promise<int> p;
778   Future<int> f = p.getFuture();
779   p.setValue(1);
780   auto t = waitWithSemaphore(std::move(f),
781     std::chrono::milliseconds(1));
782   EXPECT_TRUE(t.isReady());
783  }
784  {
785   vector<Future<bool>> v_fb;
786   v_fb.push_back(makeFuture(true));
787   v_fb.push_back(makeFuture(false));
788   auto f = whenAll(v_fb.begin(), v_fb.end());
789   auto t = waitWithSemaphore(std::move(f),
790     std::chrono::milliseconds(1));
791   EXPECT_TRUE(t.isReady());
792   EXPECT_EQ(2, t.value().size());
793  }
794  {
795   vector<Future<bool>> v_fb;
796   Promise<bool> p1;
797   Promise<bool> p2;
798   v_fb.push_back(p1.getFuture());
799   v_fb.push_back(p2.getFuture());
800   auto f = whenAll(v_fb.begin(), v_fb.end());
801   auto t = waitWithSemaphore(std::move(f),
802     std::chrono::milliseconds(1));
803   EXPECT_FALSE(t.isReady());
804   p1.setValue(true);
805   EXPECT_FALSE(t.isReady());
806   p2.setValue(true);
807   EXPECT_TRUE(t.isReady());
808  }
809  {
810   auto t = waitWithSemaphore(makeFuture(),
811     std::chrono::milliseconds(1));
812   EXPECT_TRUE(t.isReady());
813  }
814 }
815
816 TEST(Future, callbackAfterActivate) {
817   Promise<void> p;
818   auto f = p.getFuture();
819   f.deactivate();
820
821   size_t count = 0;
822   f.then([&](Try<void>&&) { count++; });
823
824   p.setValue();
825   EXPECT_EQ(0, count);
826
827   f.activate();
828   EXPECT_EQ(1, count);
829 }
830
831 TEST(Future, activateOnDestruct) {
832   auto f = std::make_shared<Future<void>>(makeFuture());
833   f->deactivate();
834
835   size_t count = 0;
836   f->then([&](Try<void>&&) { count++; });
837   EXPECT_EQ(0, count);
838
839   f.reset();
840   EXPECT_EQ(1, count);
841 }
842
843 TEST(Future, viaActsCold) {
844   ManualExecutor x;
845   size_t count = 0;
846
847   auto fv = makeFuture().via(&x);
848   fv.then([&](Try<void>&&) { count++; });
849
850   EXPECT_EQ(0, count);
851
852   fv.activate();
853
854   EXPECT_EQ(1, x.run());
855   EXPECT_EQ(1, count);
856 }
857
858 TEST(Future, viaIsCold) {
859   ManualExecutor x;
860   EXPECT_FALSE(makeFuture().via(&x).isActive());
861 }
862
863 TEST(Future, viaRaces) {
864   ManualExecutor x;
865   Promise<void> p;
866   auto tid = std::this_thread::get_id();
867   bool done = false;
868
869   std::thread t1([&] {
870     p.getFuture()
871       .via(&x)
872       .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
873       .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
874       .then([&](Try<void>&&) { done = true; });
875   });
876
877   std::thread t2([&] {
878     p.setValue();
879   });
880
881   while (!done) x.run();
882   t1.join();
883   t2.join();
884 }
885
886 // TODO(#4920689)
887 TEST(Future, viaRaces_2stage) {
888   ManualExecutor x;
889   Promise<void> p;
890   auto tid = std::this_thread::get_id();
891   bool done = false;
892
893   std::thread t1([&] {
894     auto f2 = p.getFuture().via(&x);
895     f2.then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
896       .then([&](Try<void>&&) { EXPECT_EQ(tid, std::this_thread::get_id()); })
897       .then([&](Try<void>&&) { done = true; });
898
899     // the bug was in the promise being fulfilled before f2 is reactivated. we
900     // could sleep, but yielding should cause this to fail with reasonable
901     // probability
902     std::this_thread::yield();
903     f2.activate();
904   });
905
906   std::thread t2([&] {
907     p.setValue();
908   });
909
910   while (!done) x.run();
911   t1.join();
912   t2.join();
913 }
914
915 TEST(Future, getFuture_after_setValue) {
916   Promise<int> p;
917   p.setValue(42);
918   EXPECT_EQ(42, p.getFuture().value());
919 }
920
921 TEST(Future, getFuture_after_setException) {
922   Promise<void> p;
923   p.fulfil([]() -> void { throw std::logic_error("foo"); });
924   EXPECT_THROW(p.getFuture().value(), std::logic_error);
925 }
926
927 TEST(Future, detachRace) {
928   // Task #5438209
929   // This test is designed to detect a race that was in Core::detachOne()
930   // where detached_ was incremented and then tested, and that
931   // allowed a race where both Promise and Future would think they were the
932   // second and both try to delete. This showed up at scale but was very
933   // difficult to reliably repro in a test. As it is, this only fails about
934   // once in every 1,000 executions. Doing this 1,000 times is going to make a
935   // slow test so I won't do that but if it ever fails, take it seriously, and
936   // run the test binary with "--gtest_repeat=10000 --gtest_filter=*detachRace"
937   // (Don't forget to enable ASAN)
938   auto p = folly::make_unique<Promise<bool>>();
939   auto f = folly::make_unique<Future<bool>>(p->getFuture());
940   folly::Baton<> baton;
941   std::thread t1([&]{
942     baton.post();
943     p.reset();
944   });
945   baton.wait();
946   f.reset();
947   t1.join();
948 }
949
950 class TestData : public RequestData {
951  public:
952   explicit TestData(int data) : data_(data) {}
953   virtual ~TestData() {}
954   int data_;
955 };
956
957 TEST(Future, context) {
958
959   // Start a new context
960   RequestContext::create();
961
962   EXPECT_EQ(nullptr, RequestContext::get()->getContextData("test"));
963
964   // Set some test data
965   RequestContext::get()->setContextData(
966     "test",
967     std::unique_ptr<TestData>(new TestData(10)));
968
969   // Start a future
970   Promise<void> p;
971   auto future = p.getFuture().then([&]{
972     // Check that the context followed the future
973     EXPECT_TRUE(RequestContext::get() != nullptr);
974     auto a = dynamic_cast<TestData*>(
975       RequestContext::get()->getContextData("test"));
976     auto data = a->data_;
977     EXPECT_EQ(10, data);
978   });
979
980   // Clear the context
981   RequestContext::setContext(nullptr);
982
983   EXPECT_EQ(nullptr, RequestContext::get()->getContextData("test"));
984
985   // Fulfil the promise
986   p.setValue();
987 }
988
989
990 // This only fails about 1 in 1k times when the bug is present :(
991 TEST(Future, t5506504) {
992   ThreadExecutor x;
993
994   auto fn = [&x]{
995     auto promises = std::make_shared<vector<Promise<void>>>(4);
996     vector<Future<void>> futures;
997
998     for (auto& p : *promises) {
999       futures.emplace_back(
1000         p.getFuture()
1001         .via(&x)
1002         .then([](Try<void>&&){}));
1003     }
1004
1005     x.waitForStartup();
1006     x.add([promises]{
1007       for (auto& p : *promises) p.setValue();
1008     });
1009
1010     return whenAll(futures.begin(), futures.end());
1011   };
1012
1013   waitWithSemaphore(fn());
1014 }