test.js 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538
  1. var ifAsync = require('./index.js')
  2. var should = require('should')
  3. describe('ifAsync', function() {
  4. it('requires at least one predicate', function () {
  5. (function () {
  6. ifAsync()
  7. }).should.throw('at least one predicate and one consequent are required')
  8. })
  9. it('throws an error if at least one consequent is not provided', function () {
  10. (function () {
  11. ifAsync(function (callback) { callback(null, true) })(function () {
  12. })
  13. }).should.throw('missing at least one consequent, you forgot to call then() ?')
  14. })
  15. it('invokes the predicate', function (done) {
  16. var predicateInvoked = false
  17. var functor = ifAsync(
  18. function predicate(callback) {
  19. predicateInvoked = true
  20. callback(null, 1)
  21. },
  22. function consequent(callback) {
  23. callback()
  24. }
  25. )
  26. functor(function callback(err) {
  27. predicateInvoked.should.be.true
  28. done()
  29. })
  30. })
  31. it('invokes the consequent if the predicate evaluates to "true"', function (done) {
  32. var consequentInvoked = false
  33. var functor = ifAsync(
  34. function predicate(callback) {
  35. callback(null, 1)
  36. },
  37. function consequent(callback) {
  38. consequentInvoked = true
  39. callback()
  40. }
  41. )
  42. functor(function callback(err) {
  43. consequentInvoked.should.be.true
  44. done()
  45. })
  46. })
  47. it('invokes the default consequent if predicate evaluates to "false"', function (done) {
  48. var consequentInvoked = false
  49. var defaultConsequentInvoked = false
  50. var functor = ifAsync(
  51. function predicate(callback) {
  52. callback(null, 0)
  53. },
  54. function consequent(callback) {
  55. consequentInvoked = true
  56. callback()
  57. },
  58. function defaultConsequent(callback) {
  59. defaultConsequentInvoked = true
  60. callback()
  61. }
  62. )
  63. functor(function callback(err) {
  64. consequentInvoked.should.be.false
  65. defaultConsequentInvoked.should.be.true
  66. done()
  67. })
  68. })
  69. it('invokes a second predicate if it is provided when the first predicate does not evaluate to true', function (done) {
  70. var p1Invoked = false
  71. var p2Invoked = false
  72. var c1Invoked = false
  73. var c2Invoked = false
  74. var functor = ifAsync(
  75. function predicate1(callback) {
  76. p1Invoked = true
  77. callback(null, 0)
  78. },
  79. function consequent1(callback) {
  80. c1Invoked = true
  81. callback()
  82. },
  83. function predicate2(callback) {
  84. p2Invoked = true
  85. callback(null, 1)
  86. },
  87. function consequent2(callback) {
  88. c2Invoked = true
  89. callback()
  90. }
  91. )
  92. functor(function (err) {
  93. p1Invoked.should.be.true
  94. c1Invoked.should.be.false
  95. p2Invoked.should.be.true
  96. c2Invoked.should.be.true
  97. done()
  98. })
  99. })
  100. it('has fluent interface', function (done) {
  101. var p1Invoked = false
  102. var p2Invoked = false
  103. var c1Invoked = false
  104. var c2Invoked = false
  105. var functor = ifAsync(function predicate1(callback) {
  106. p1Invoked = true
  107. callback(null, 0)
  108. })
  109. .then(function consequent1(callback) {
  110. c1Invoked = true
  111. callback()
  112. })
  113. .elseIf(function predicate2(callback) {
  114. p2Invoked = true
  115. callback(null, 1)
  116. })
  117. .then(function consequent2(callback) {
  118. c2Invoked = true
  119. callback()
  120. })
  121. functor(function (err) {
  122. p1Invoked.should.be.true
  123. c1Invoked.should.be.false
  124. p2Invoked.should.be.true
  125. c2Invoked.should.be.true
  126. done()
  127. })
  128. })
  129. it('cannot call elseIf() after elseIf()', function () {
  130. (function () {
  131. ifAsync(pFalse).then(foo).elseIf(pFalse).elseIf(pFalse)
  132. }).should.throw('only then() may be called after elseIf()')
  133. })
  134. describe('has an and() operator', function () {
  135. it('ifAsync(true).and(false) should invoke both predicates and the else consequent', function (done) {
  136. var p1Invoked = false
  137. var p2Invoked = false
  138. var c1Invoked = false
  139. var c2Invoked = false
  140. ifAsync(function(callback) {
  141. p1Invoked = true
  142. callback(null, true)
  143. })
  144. .and(function (callback) {
  145. p2Invoked = true
  146. callback(null, false)
  147. }).then(function(cb) {
  148. c1Invoked = true
  149. cb()
  150. }).else(function (cb) {
  151. c2Invoked = true
  152. cb()
  153. })(function (err) {
  154. p1Invoked.should.be.true
  155. p2Invoked.should.be.true
  156. c1Invoked.should.be.false
  157. c2Invoked.should.be.true
  158. done()
  159. })
  160. })
  161. it('ifAsync(false).and(*) should invoke the first predicate and the second (else) consequent, it should not invoke the second predicate', function(done) {
  162. var p1Invoked = false
  163. var p2Invoked = false
  164. var c1Invoked = false
  165. var c2Invoked = false
  166. ifAsync(function(callback) {
  167. p1Invoked = true
  168. callback(null, false)
  169. })
  170. .and(function (callback) {
  171. p2Invoked = true
  172. callback(null, true)
  173. }).then(function(cb) {
  174. c1Invoked = true
  175. cb()
  176. }).else(function (cb) {
  177. c2Invoked = true
  178. cb()
  179. })(function (err) {
  180. p1Invoked.should.be.true
  181. p2Invoked.should.be.false
  182. c1Invoked.should.be.false
  183. c2Invoked.should.be.true
  184. done()
  185. })
  186. })
  187. it('ifAsync(true).and(true) should invoke both predicates and the first (then) consequent', function(done) {
  188. var p1Invoked = false
  189. var p2Invoked = false
  190. var c1Invoked = false
  191. var c2Invoked = false
  192. ifAsync(function(callback) {
  193. p1Invoked = true
  194. callback(null, true)
  195. })
  196. .and(function (callback) {
  197. p2Invoked = true
  198. callback(null, true)
  199. }).then(function(cb) {
  200. c1Invoked = true
  201. cb()
  202. }).else(function (cb) {
  203. c2Invoked = true
  204. cb()
  205. })(function (err) {
  206. p1Invoked.should.be.true
  207. p2Invoked.should.be.true
  208. c1Invoked.should.be.true
  209. c2Invoked.should.be.false
  210. done()
  211. })
  212. })
  213. it('ifAsync(p1 = false).then(c1).elseif(p2 = true).and(p3 = true).then(c2) should not invoke c1 and should invoke p1, p2 and p3', function(done) {
  214. var c1Invoked = false
  215. var c2Invoked = false
  216. var p1Invoked = false
  217. var p2Invoked = false
  218. var p3Invoked = false
  219. ifAsync(function p1(callback) {
  220. p1Invoked = true
  221. callback(null, false)
  222. }).then(function c1(callback) {
  223. c1Invoked = true
  224. callback()
  225. }).elseif(function p2(callback) {
  226. p2Invoked = true
  227. callback(null, true)
  228. }).and(function p3(callback) {
  229. p3Invoked = true
  230. callback(null, true)
  231. }).then(function c2(callback) {
  232. c2Invoked = true
  233. callback()
  234. })(function(err) {
  235. p1Invoked.should.be.true
  236. c1Invoked.should.be.false
  237. p2Invoked.should.be.true
  238. p3Invoked.should.be.true
  239. c2Invoked.should.be.true
  240. done()
  241. })
  242. })
  243. it('ifAsync(p1 = true).and.not(p2 = false).then(c1), should invoke p1 and p2 and c1 and not c2', function (done) {
  244. var c1Invoked = false
  245. var c2Invoked = false
  246. var p1Invoked = false
  247. var p2Invoked = false
  248. ifAsync(function p1(callback) {
  249. p1Invoked = true
  250. callback(null, true)
  251. }).and.not(function p2(callback) {
  252. p2Invoked = true
  253. callback(null, false)
  254. }).then(function c1(callback) {
  255. c1Invoked = true
  256. callback()
  257. }).else(function c2 (callback) {
  258. c2Invoked = true
  259. callback()
  260. })(function(err) {
  261. p1Invoked.should.be.true
  262. p2Invoked.should.be.true
  263. c1Invoked.should.be.true
  264. c2Invoked.should.be.false
  265. done()
  266. })
  267. })
  268. })
  269. describe('has an or() operator', function () {
  270. it('ifAsync(true).or(*) should invoke the first predicate and the first (then) consequent, it should not invoke the second predicate', function (done) {
  271. var p1Invoked = false
  272. var p2Invoked = false
  273. var c1Invoked = false
  274. var c2Invoked = false
  275. ifAsync(function(callback) {
  276. p1Invoked = true
  277. callback(null, true)
  278. })
  279. .or(function (callback) {
  280. p2Invoked = true
  281. callback(null, true)
  282. }).then(function(cb) {
  283. c1Invoked = true
  284. cb()
  285. }).else(function (cb) {
  286. c2Invoked = true
  287. cb()
  288. })(function (err) {
  289. p1Invoked.should.be.true
  290. p2Invoked.should.be.false
  291. c1Invoked.should.be.true
  292. c2Invoked.should.be.false
  293. done()
  294. })
  295. })
  296. it('ifAsync(false).or(true) should invoke both predicates and the first (then) consequent', function (done) {
  297. var p1Invoked = false
  298. var p2Invoked = false
  299. var c1Invoked = false
  300. var c2Invoked = false
  301. ifAsync(function(callback) {
  302. p1Invoked = true
  303. callback(null, false)
  304. })
  305. .or(function (callback) {
  306. p2Invoked = true
  307. callback(null, true)
  308. }).then(function(cb) {
  309. c1Invoked = true
  310. cb()
  311. }).else(function (cb) {
  312. c2Invoked = true
  313. cb()
  314. })(function (err) {
  315. p1Invoked.should.be.true
  316. p2Invoked.should.be.true
  317. c1Invoked.should.be.true
  318. c2Invoked.should.be.false
  319. done()
  320. })
  321. })
  322. it('ifAsync(false).or(false) should invoke both predicates and the second (else) consequent', function (done) {
  323. var p1Invoked = false
  324. var p2Invoked = false
  325. var c1Invoked = false
  326. var c2Invoked = false
  327. ifAsync(function(callback) {
  328. p1Invoked = true
  329. callback(null, false)
  330. })
  331. .or(function (callback) {
  332. p2Invoked = true
  333. callback(null, false)
  334. }).then(function(cb) {
  335. c1Invoked = true
  336. cb()
  337. }).else(function (cb) {
  338. c2Invoked = true
  339. cb()
  340. })(function (err) {
  341. p1Invoked.should.be.true
  342. p2Invoked.should.be.true
  343. c1Invoked.should.be.false
  344. c2Invoked.should.be.true
  345. done()
  346. })
  347. })
  348. it('ifAsync(p1 = false).then(c1).elseif(p2 = false).or(p3 = true).then(c2) should not invoke c1 and should invoke p1, p2 and p3', function(done) {
  349. var c1Invoked = false
  350. var c2Invoked = false
  351. var p1Invoked = false
  352. var p2Invoked = false
  353. var p3Invoked = false
  354. ifAsync(function p1(callback) {
  355. p1Invoked = true
  356. callback(null, false)
  357. }).then(function c1(callback) {
  358. c1Invoked = true
  359. callback()
  360. }).elseif(function p2(callback) {
  361. p2Invoked = true
  362. callback(null, false)
  363. }).or(function p3(callback) {
  364. p3Invoked = true
  365. callback(null, true)
  366. }).then(function c2(callback) {
  367. c2Invoked = true
  368. callback()
  369. })(function(err) {
  370. p1Invoked.should.be.true
  371. c1Invoked.should.be.false
  372. p2Invoked.should.be.true
  373. p3Invoked.should.be.true
  374. c2Invoked.should.be.true
  375. done()
  376. })
  377. })
  378. it('ifAsync(p1 = false).or.not(p2 = false).then(c1), should invoke p1 and p2 and c1 and not c2', function (done) {
  379. var c1Invoked = false
  380. var c2Invoked = false
  381. var p1Invoked = false
  382. var p2Invoked = false
  383. ifAsync(function p1(callback) {
  384. p1Invoked = true
  385. callback(null, false)
  386. }).or.not(function p2(callback) {
  387. p2Invoked = true
  388. callback(null, false)
  389. }).then(function c1(callback) {
  390. c1Invoked = true
  391. callback()
  392. }).else(function c2 (callback) {
  393. c2Invoked = true
  394. callback()
  395. })(function(err) {
  396. p1Invoked.should.be.true
  397. p2Invoked.should.be.true
  398. c1Invoked.should.be.true
  399. c2Invoked.should.be.false
  400. done()
  401. })
  402. })
  403. })
  404. it('carry arguments from "then" consequent', function (done) {
  405. ifAsync(function(a, b, callback) {
  406. a.should.eql(1)
  407. b.should.eql(2)
  408. callback(null, true)
  409. })
  410. .then(function(a, b, callback) {
  411. a.should.eql(1)
  412. b.should.eql(2)
  413. callback(null, 3)
  414. })(1, 2, function (err, a) {
  415. a.should.eql(3)
  416. done()
  417. })
  418. })
  419. it('carry arguments from default "else" consequent', function (done) {
  420. ifAsync(function(a, b, callback) {
  421. a.should.eql(1)
  422. b.should.eql(2)
  423. callback(null, false)
  424. })
  425. .then(function(a, b, callback) {
  426. a.should.eql(1)
  427. b.should.eql(2)
  428. callback(null, 3)
  429. })(1, 2, function (err, a, b) {
  430. a.should.eql(1)
  431. b.should.eql(2)
  432. done()
  433. })
  434. })
  435. it('has a negation operator for predicates', function (done) {
  436. var p1Invoked = false
  437. var c1Invoked = false
  438. var c2Invoked = false
  439. ifAsync.not(function p1(callback) {
  440. p1Invoked = true
  441. callback(null, true)
  442. }).then(function c1(callback) {
  443. c1Invoked = true
  444. callback()
  445. }).else(function c2(callback) {
  446. c2Invoked = true
  447. callback()
  448. })(function(err) {
  449. p1Invoked.should.be.true
  450. c1Invoked.should.be.false
  451. c2Invoked.should.be.true
  452. done()
  453. })
  454. })
  455. it('has a negation operator for predicates 2', function (done) {
  456. var p1Invoked = false
  457. var p2Invoked = false
  458. var c1Invoked = false
  459. var c2Invoked = false
  460. ifAsync(function p1(callback) {
  461. p1Invoked = true
  462. callback(null, false)
  463. }).then(function c1(callback) {
  464. c1Invoked = true
  465. callback()
  466. }).elseIf.not(function p2(callback) {
  467. p2Invoked = true
  468. callback(null, false)
  469. }).then(function c2(callback) {
  470. c2Invoked = true
  471. callback()
  472. })(function(err) {
  473. p1Invoked.should.be.true
  474. c1Invoked.should.be.false
  475. p2Invoked.should.be.true
  476. c2Invoked.should.be.true
  477. done()
  478. })
  479. })
  480. function pTrue (callback) {
  481. callback(null, true)
  482. }
  483. function pFalse (callback) {
  484. callback(null, false)
  485. }
  486. function foo (callback) {
  487. callback()
  488. }
  489. })