Vous ne pouvez pas sélectionner plus de 25 sujets Les noms de sujets doivent commencer par une lettre ou un nombre, peuvent contenir des tirets ('-') et peuvent comporter jusqu'à 35 caractères.

674 lignes
32 KiB

il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
il y a 14 ans
  1. %% Copyright (c) 2011 Basho Technologies, Inc. All Rights Reserved.
  2. %%
  3. %% This file is provided to you under the Apache License,
  4. %% Version 2.0 (the "License"); you may not use this file
  5. %% except in compliance with the License. You may obtain
  6. %% 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,
  11. %% software distributed under the License is distributed on an
  12. %% "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  13. %% KIND, either express or implied. See the License for the
  14. %% specific language governing permissions and limitations
  15. %% under the License.
  16. -module(lager_test_backend).
  17. -include("lager.hrl").
  18. -behaviour(gen_event).
  19. -export([init/1, handle_call/2, handle_event/2, handle_info/2, terminate/2,
  20. code_change/3]).
  21. -record(state, {level, buffer, ignored}).
  22. -compile([{parse_transform, lager_transform}]).
  23. -ifdef(TEST).
  24. -include_lib("eunit/include/eunit.hrl").
  25. -export([pop/0, count/0, count_ignored/0]).
  26. -endif.
  27. init(Level) ->
  28. {ok, #state{level=lager_util:level_to_num(Level), buffer=[], ignored=[]}}.
  29. handle_call(count, #state{buffer=Buffer} = State) ->
  30. {ok, length(Buffer), State};
  31. handle_call(count_ignored, #state{ignored=Ignored} = State) ->
  32. {ok, length(Ignored), State};
  33. handle_call(flush, State) ->
  34. {ok, ok, State#state{buffer=[], ignored=[]}};
  35. handle_call(pop, #state{buffer=Buffer} = State) ->
  36. case Buffer of
  37. [] ->
  38. {ok, undefined, State};
  39. [H|T] ->
  40. {ok, H, State#state{buffer=T}}
  41. end;
  42. handle_call(get_loglevel, #state{level=Level} = State) ->
  43. {ok, Level, State};
  44. handle_call({set_loglevel, Level}, State) ->
  45. {ok, ok, State#state{level=lager_util:level_to_num(Level)}};
  46. handle_call(_Request, State) ->
  47. {ok, ok, State}.
  48. handle_event({log, Level, Time, Message}, #state{level=LogLevel,
  49. buffer=Buffer} = State) when Level =< LogLevel ->
  50. {ok, State#state{buffer=Buffer ++ [{Level, Time, Message}]}};
  51. handle_event({log, _Level, _Time, _Message}, #state{ignored=Ignored} = State) ->
  52. {ok, State#state{ignored=Ignored ++ [ignored]}};
  53. handle_event(_Event, State) ->
  54. {ok, State}.
  55. handle_info(_Info, State) ->
  56. {ok, State}.
  57. terminate(_Reason, _State) ->
  58. ok.
  59. code_change(_OldVsn, State, _Extra) ->
  60. {ok, State}.
  61. -ifdef(TEST).
  62. pop() ->
  63. gen_event:call(lager_event, ?MODULE, pop).
  64. count() ->
  65. gen_event:call(lager_event, ?MODULE, count).
  66. count_ignored() ->
  67. gen_event:call(lager_event, ?MODULE, count_ignored).
  68. not_running_test() ->
  69. ?assertEqual({error, lager_not_running}, lager:log(info, self(), "not running")).
  70. lager_test_() ->
  71. {foreach,
  72. fun setup/0,
  73. fun cleanup/1,
  74. [
  75. {"observe that there is nothing up my sleeve",
  76. fun() ->
  77. ?assertEqual(undefined, pop()),
  78. ?assertEqual(0, count())
  79. end
  80. },
  81. {"logging works",
  82. fun() ->
  83. lager:warning("test message"),
  84. ?assertEqual(1, count()),
  85. {Level, _Time, Message} = pop(),
  86. ?assertMatch(Level, lager_util:level_to_num(warning)),
  87. [LevelStr, _LocStr, MsgStr] = re:split(Message, " ", [{return, list}, {parts, 3}]),
  88. ?assertEqual("[warning]", LevelStr),
  89. ?assertEqual("test message", MsgStr),
  90. ok
  91. end
  92. },
  93. {"logging with arguments works",
  94. fun() ->
  95. lager:warning("test message ~p", [self()]),
  96. ?assertEqual(1, count()),
  97. {Level, _Time, Message} = pop(),
  98. ?assertMatch(Level, lager_util:level_to_num(warning)),
  99. [LevelStr, _LocStr, MsgStr] = re:split(Message, " ", [{return, list}, {parts, 3}]),
  100. ?assertEqual("[warning]", LevelStr),
  101. ?assertEqual(lists:flatten(io_lib:format("test message ~p", [self()])), MsgStr),
  102. ok
  103. end
  104. },
  105. {"logging works from inside a begin/end block",
  106. fun() ->
  107. ?assertEqual(0, count()),
  108. begin
  109. lager:warning("test message 2")
  110. end,
  111. ?assertEqual(1, count()),
  112. ok
  113. end
  114. },
  115. {"logging works from inside a list comprehension",
  116. fun() ->
  117. ?assertEqual(0, count()),
  118. [lager:warning("test message") || _N <- lists:seq(1, 10)],
  119. ?assertEqual(10, count()),
  120. ok
  121. end
  122. },
  123. {"logging works from a begin/end block inside a list comprehension",
  124. fun() ->
  125. ?assertEqual(0, count()),
  126. [ begin lager:warning("test message") end || _N <- lists:seq(1, 10)],
  127. ?assertEqual(10, count()),
  128. ok
  129. end
  130. },
  131. {"logging works from a nested list comprehension",
  132. fun() ->
  133. ?assertEqual(0, count()),
  134. [ [lager:warning("test message") || _N <- lists:seq(1, 10)] ||
  135. _I <- lists:seq(1, 10)],
  136. ?assertEqual(100, count()),
  137. ok
  138. end
  139. },
  140. {"log messages below the threshold are ignored",
  141. fun() ->
  142. ?assertEqual(0, count()),
  143. lager:debug("this message will be ignored"),
  144. ?assertEqual(0, count()),
  145. ?assertEqual(0, count_ignored()),
  146. lager_mochiglobal:put(loglevel, ?DEBUG),
  147. lager:debug("this message should be ignored"),
  148. ?assertEqual(0, count()),
  149. ?assertEqual(1, count_ignored()),
  150. lager:set_loglevel(?MODULE, debug),
  151. lager:debug("this message should be logged"),
  152. ?assertEqual(1, count()),
  153. ?assertEqual(1, count_ignored()),
  154. ?assertEqual(debug, lager:get_loglevel(?MODULE)),
  155. ok
  156. end
  157. }
  158. ]
  159. }.
  160. setup() ->
  161. error_logger:tty(false),
  162. application:load(lager),
  163. application:set_env(lager, handlers, [{?MODULE, info}]),
  164. application:set_env(lager, error_logger_redirect, false),
  165. application:start(lager),
  166. gen_event:call(lager_event, ?MODULE, flush).
  167. cleanup(_) ->
  168. application:stop(lager),
  169. application:unload(lager),
  170. error_logger:tty(true).
  171. crash(Type) ->
  172. spawn(fun() -> gen_server:call(crash, Type) end),
  173. timer:sleep(100).
  174. error_logger_redirect_crash_test_() ->
  175. {foreach,
  176. fun() ->
  177. error_logger:tty(false),
  178. application:load(lager),
  179. application:set_env(lager, error_logger_redirect, true),
  180. application:set_env(lager, handlers, [{?MODULE, error}]),
  181. application:start(lager),
  182. crash:start()
  183. end,
  184. fun(_) ->
  185. application:stop(lager),
  186. application:unload(lager),
  187. case whereis(crash) of
  188. undefined -> ok;
  189. Pid -> exit(Pid, kill)
  190. end,
  191. error_logger:tty(true)
  192. end,
  193. [
  194. {"again, there is nothing up my sleeve",
  195. fun() ->
  196. ?assertEqual(undefined, pop()),
  197. ?assertEqual(0, count())
  198. end
  199. },
  200. {"bad return value",
  201. fun() ->
  202. Pid = whereis(crash),
  203. crash(bad_return),
  204. {_, _, Msg} = pop(),
  205. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: bad return value: bleh", [Pid])),
  206. ?assertEqual(Expected, lists:flatten(Msg))
  207. end
  208. },
  209. {"case clause",
  210. fun() ->
  211. Pid = whereis(crash),
  212. crash(case_clause),
  213. {_, _, Msg} = pop(),
  214. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: no case clause matching {} in crash:handle_call/3", [Pid])),
  215. ?assertEqual(Expected, lists:flatten(Msg))
  216. end
  217. },
  218. {"function clause",
  219. fun() ->
  220. Pid = whereis(crash),
  221. crash(function_clause),
  222. {_, _, Msg} = pop(),
  223. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: no function clause matching crash:function({})", [Pid])),
  224. ?assertEqual(Expected, lists:flatten(Msg))
  225. end
  226. },
  227. {"if clause",
  228. fun() ->
  229. Pid = whereis(crash),
  230. crash(if_clause),
  231. {_, _, Msg} = pop(),
  232. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: no true branch found while evaluating if expression in crash:handle_call/3", [Pid])),
  233. ?assertEqual(Expected, lists:flatten(Msg))
  234. end
  235. },
  236. {"try clause",
  237. fun() ->
  238. Pid = whereis(crash),
  239. crash(try_clause),
  240. {_, _, Msg} = pop(),
  241. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: no try clause matching [] in crash:handle_call/3", [Pid])),
  242. ?assertEqual(Expected, lists:flatten(Msg))
  243. end
  244. },
  245. {"undefined function",
  246. fun() ->
  247. Pid = whereis(crash),
  248. crash(undef),
  249. {_, _, Msg} = pop(),
  250. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: call to undefined function crash:booger/0 from crash:handle_call/3", [Pid])),
  251. ?assertEqual(Expected, lists:flatten(Msg))
  252. end
  253. },
  254. {"bad math",
  255. fun() ->
  256. Pid = whereis(crash),
  257. crash(badarith),
  258. {_, _, Msg} = pop(),
  259. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: bad arithmetic expression in crash:handle_call/3", [Pid])),
  260. ?assertEqual(Expected, lists:flatten(Msg))
  261. end
  262. },
  263. {"bad match",
  264. fun() ->
  265. Pid = whereis(crash),
  266. crash(badmatch),
  267. {_, _, Msg} = pop(),
  268. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: no match of right hand value {} in crash:handle_call/3", [Pid])),
  269. ?assertEqual(Expected, lists:flatten(Msg))
  270. end
  271. },
  272. {"bad arity",
  273. fun() ->
  274. Pid = whereis(crash),
  275. crash(badarity),
  276. {_, _, Msg} = pop(),
  277. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: fun called with wrong arity of 1 instead of 3 in crash:handle_call/3", [Pid])),
  278. ?assertEqual(Expected, lists:flatten(Msg))
  279. end
  280. },
  281. {"bad arg1",
  282. fun() ->
  283. Pid = whereis(crash),
  284. crash(badarg1),
  285. {_, _, Msg} = pop(),
  286. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: bad argument in crash:handle_call/3", [Pid])),
  287. ?assertEqual(Expected, lists:flatten(Msg))
  288. end
  289. },
  290. {"bad arg2",
  291. fun() ->
  292. Pid = whereis(crash),
  293. crash(badarg2),
  294. {_, _, Msg} = pop(),
  295. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: bad argument in call to erlang:iolist_to_binary([[102,111,111],bar]) in crash:handle_call/3", [Pid])),
  296. ?assertEqual(Expected, lists:flatten(Msg))
  297. end
  298. },
  299. {"noproc",
  300. fun() ->
  301. Pid = whereis(crash),
  302. crash(noproc),
  303. {_, _, Msg} = pop(),
  304. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: no such process or port in call to gen_event:call(foo, bar, baz)", [Pid])),
  305. ?assertEqual(Expected, lists:flatten(Msg))
  306. end
  307. },
  308. {"badfun",
  309. fun() ->
  310. Pid = whereis(crash),
  311. crash(badfun),
  312. {_, _, Msg} = pop(),
  313. Expected = lists:flatten(io_lib:format("[error] ~w gen_server crash terminated with reason: bad function booger in crash:handle_call/3", [Pid])),
  314. ?assertEqual(Expected, lists:flatten(Msg))
  315. end
  316. }
  317. ]
  318. }.
  319. error_logger_redirect_test_() ->
  320. {foreach,
  321. fun() ->
  322. error_logger:tty(false),
  323. application:load(lager),
  324. application:set_env(lager, error_logger_redirect, true),
  325. application:set_env(lager, handlers, [{?MODULE, info}]),
  326. application:start(lager),
  327. timer:sleep(100),
  328. gen_event:call(lager_event, ?MODULE, flush)
  329. end,
  330. fun(_) ->
  331. application:stop(lager),
  332. application:unload(lager),
  333. error_logger:tty(true)
  334. end,
  335. [
  336. {"error reports are printed",
  337. fun() ->
  338. error_logger:error_report([{this, is}, a, {silly, format}]),
  339. _ = gen_event:which_handlers(error_logger),
  340. timer:sleep(100),
  341. {_, _, Msg} = pop(),
  342. Expected = lists:flatten(io_lib:format("[error] ~w this: is, a, silly: format", [self()])),
  343. ?assertEqual(Expected, lists:flatten(Msg))
  344. end
  345. },
  346. {"string error reports are printed",
  347. fun() ->
  348. error_logger:error_report("this is less silly"),
  349. _ = gen_event:which_handlers(error_logger),
  350. timer:sleep(100),
  351. {_, _, Msg} = pop(),
  352. Expected = lists:flatten(io_lib:format("[error] ~w this is less silly", [self()])),
  353. ?assertEqual(Expected, lists:flatten(Msg))
  354. end
  355. },
  356. {"error messages are printed",
  357. fun() ->
  358. error_logger:error_msg("doom, doom has come upon you all"),
  359. _ = gen_event:which_handlers(error_logger),
  360. timer:sleep(100),
  361. {_, _, Msg} = pop(),
  362. Expected = lists:flatten(io_lib:format("[error] ~w doom, doom has come upon you all", [self()])),
  363. ?assertEqual(Expected, lists:flatten(Msg))
  364. end
  365. },
  366. {"error messages are truncated at 4096 characters",
  367. fun() ->
  368. error_logger:error_msg("doom, doom has come upon you all ~p", [string:copies("doom", 10000)]),
  369. _ = gen_event:which_handlers(error_logger),
  370. timer:sleep(1000),
  371. {_, _, Msg} = pop(),
  372. ?assert(length(lists:flatten(Msg)) < 5100)
  373. end
  374. },
  375. {"info reports are printed",
  376. fun() ->
  377. error_logger:info_report([{this, is}, a, {silly, format}]),
  378. _ = gen_event:which_handlers(error_logger),
  379. timer:sleep(100),
  380. {_, _, Msg} = pop(),
  381. Expected = lists:flatten(io_lib:format("[info] ~w this: is, a, silly: format", [self()])),
  382. ?assertEqual(Expected, lists:flatten(Msg))
  383. end
  384. },
  385. {"info reports are truncated at 4096 characters",
  386. fun() ->
  387. error_logger:info_report([[{this, is}, a, {silly, format}] || _ <- lists:seq(0, 600)]),
  388. _ = gen_event:which_handlers(error_logger),
  389. timer:sleep(1000),
  390. {_, _, Msg} = pop(),
  391. ?assert(length(lists:flatten(Msg)) < 5000)
  392. end
  393. },
  394. {"single term info reports are printed",
  395. fun() ->
  396. error_logger:info_report({foolish, bees}),
  397. _ = gen_event:which_handlers(error_logger),
  398. timer:sleep(100),
  399. {_, _, Msg} = pop(),
  400. Expected = lists:flatten(io_lib:format("[info] ~w {foolish,bees}", [self()])),
  401. ?assertEqual(Expected, lists:flatten(Msg))
  402. end
  403. },
  404. {"single term error reports are printed",
  405. fun() ->
  406. error_logger:error_report({foolish, bees}),
  407. _ = gen_event:which_handlers(error_logger),
  408. timer:sleep(100),
  409. {_, _, Msg} = pop(),
  410. Expected = lists:flatten(io_lib:format("[error] ~w {foolish,bees}", [self()])),
  411. ?assertEqual(Expected, lists:flatten(Msg))
  412. end
  413. },
  414. {"string info reports are printed",
  415. fun() ->
  416. error_logger:info_report("this is less silly"),
  417. _ = gen_event:which_handlers(error_logger),
  418. timer:sleep(100),
  419. {_, _, Msg} = pop(),
  420. Expected = lists:flatten(io_lib:format("[info] ~w this is less silly", [self()])),
  421. ?assertEqual(Expected, lists:flatten(Msg))
  422. end
  423. },
  424. {"string info reports are truncated at 4096 characters",
  425. fun() ->
  426. error_logger:info_report(string:copies("this is less silly", 1000)),
  427. _ = gen_event:which_handlers(error_logger),
  428. timer:sleep(1000),
  429. {_, _, Msg} = pop(),
  430. ?assert(length(lists:flatten(Msg)) < 5100)
  431. end
  432. },
  433. {"info messages are printed",
  434. fun() ->
  435. error_logger:info_msg("doom, doom has come upon you all"),
  436. _ = gen_event:which_handlers(error_logger),
  437. timer:sleep(100),
  438. {_, _, Msg} = pop(),
  439. Expected = lists:flatten(io_lib:format("[info] ~w doom, doom has come upon you all", [self()])),
  440. ?assertEqual(Expected, lists:flatten(Msg))
  441. end
  442. },
  443. {"info messages are truncated at 4096 characters",
  444. fun() ->
  445. error_logger:info_msg("doom, doom has come upon you all ~p", [string:copies("doom", 10000)]),
  446. _ = gen_event:which_handlers(error_logger),
  447. timer:sleep(1000),
  448. {_, _, Msg} = pop(),
  449. ?assert(length(lists:flatten(Msg)) < 5100)
  450. end
  451. },
  452. {"warning messages are printed at the correct level",
  453. fun() ->
  454. error_logger:warning_msg("doom, doom has come upon you all"),
  455. Map = error_logger:warning_map(),
  456. _ = gen_event:which_handlers(error_logger),
  457. timer:sleep(100),
  458. {_, _, Msg} = pop(),
  459. Expected = lists:flatten(io_lib:format("[~w] ~w doom, doom has come upon you all", [Map, self()])),
  460. ?assertEqual(Expected, lists:flatten(Msg))
  461. end
  462. },
  463. {"warning reports are printed at the correct level",
  464. fun() ->
  465. error_logger:warning_report([{i, like}, pie]),
  466. Map = error_logger:warning_map(),
  467. _ = gen_event:which_handlers(error_logger),
  468. timer:sleep(100),
  469. {_, _, Msg} = pop(),
  470. Expected = lists:flatten(io_lib:format("[~w] ~w i: like, pie", [Map, self()])),
  471. ?assertEqual(Expected, lists:flatten(Msg))
  472. end
  473. },
  474. {"single term warning reports are printed at the correct level",
  475. fun() ->
  476. error_logger:warning_report({foolish, bees}),
  477. Map = error_logger:warning_map(),
  478. _ = gen_event:which_handlers(error_logger),
  479. timer:sleep(100),
  480. {_, _, Msg} = pop(),
  481. Expected = lists:flatten(io_lib:format("[~w] ~w {foolish,bees}", [Map, self()])),
  482. ?assertEqual(Expected, lists:flatten(Msg))
  483. end
  484. },
  485. {"application stop reports",
  486. fun() ->
  487. error_logger:info_report([{application, foo}, {exited, quittin_time}, {type, lazy}]),
  488. _ = gen_event:which_handlers(error_logger),
  489. timer:sleep(100),
  490. {_, _, Msg} = pop(),
  491. Expected = lists:flatten(io_lib:format("[info] ~w Application foo exited with reason: quittin_time", [self()])),
  492. ?assertEqual(Expected, lists:flatten(Msg))
  493. end
  494. },
  495. {"supervisor reports",
  496. fun() ->
  497. error_logger:error_report(supervisor_report, [{errorContext, france}, {offender, [{name, mini_steve}, {mfargs, {a, b, [c]}}, {pid, bleh}]}, {reason, fired}, {supervisor, {local, steve}}]),
  498. _ = gen_event:which_handlers(error_logger),
  499. timer:sleep(100),
  500. {_, _, Msg} = pop(),
  501. Expected = lists:flatten(io_lib:format("[error] ~w Supervisor steve had child mini_steve started with a:b(c) at bleh exit with reason fired in context france", [self()])),
  502. ?assertEqual(Expected, lists:flatten(Msg))
  503. end
  504. },
  505. {"supervisor reports with real error",
  506. fun() ->
  507. error_logger:error_report(supervisor_report, [{errorContext, france}, {offender, [{name, mini_steve}, {mfargs, {a, b, [c]}}, {pid, bleh}]}, {reason, {function_clause,[{crash,handle_info,[foo]}]}}, {supervisor, {local, steve}}]),
  508. _ = gen_event:which_handlers(error_logger),
  509. timer:sleep(100),
  510. {_, _, Msg} = pop(),
  511. Expected = lists:flatten(io_lib:format("[error] ~w Supervisor steve had child mini_steve started with a:b(c) at bleh exit with reason no function clause matching crash:handle_info(foo) in context france", [self()])),
  512. ?assertEqual(Expected, lists:flatten(Msg))
  513. end
  514. },
  515. {"supervisor_bridge reports",
  516. fun() ->
  517. error_logger:error_report(supervisor_report, [{errorContext, france}, {offender, [{mod, mini_steve}, {pid, bleh}]}, {reason, fired}, {supervisor, {local, steve}}]),
  518. _ = gen_event:which_handlers(error_logger),
  519. timer:sleep(100),
  520. {_, _, Msg} = pop(),
  521. Expected = lists:flatten(io_lib:format("[error] ~w Supervisor steve had child at module mini_steve at bleh exit with reason fired in context france", [self()])),
  522. ?assertEqual(Expected, lists:flatten(Msg))
  523. end
  524. },
  525. {"application progress report",
  526. fun() ->
  527. error_logger:info_report(progress, [{application, foo}, {started_at, node()}]),
  528. _ = gen_event:which_handlers(error_logger),
  529. timer:sleep(100),
  530. {_, _, Msg} = pop(),
  531. Expected = lists:flatten(io_lib:format("[info] ~w Application foo started on node ~w", [self(), node()])),
  532. ?assertEqual(Expected, lists:flatten(Msg))
  533. end
  534. },
  535. {"supervisor progress report",
  536. fun() ->
  537. lager:set_loglevel(?MODULE, debug),
  538. error_logger:info_report(progress, [{supervisor, {local, foo}}, {started, [{mfargs, {foo, bar, 1}}, {pid, baz}]}]),
  539. _ = gen_event:which_handlers(error_logger),
  540. timer:sleep(100),
  541. {_, _, Msg} = pop(),
  542. Expected = lists:flatten(io_lib:format("[debug] ~w Supervisor foo started foo:bar/1 at pid baz", [self()])),
  543. ?assertEqual(Expected, lists:flatten(Msg))
  544. end
  545. },
  546. {"crash report for emfile",
  547. fun() ->
  548. error_logger:error_report(crash_report, [[{pid, self()}, {error_info, {error, {emfile, [{stack, trace, 1}]}, []}}], []]),
  549. _ = gen_event:which_handlers(error_logger),
  550. timer:sleep(100),
  551. {_, _, Msg} = pop(),
  552. Expected = lists:flatten(io_lib:format("[error] ~w CRASH REPORT Process ~w with 0 neighbours crashed with reason: maximum number of file descriptors exhausted, check ulimit -n", [self(), self()])),
  553. ?assertEqual(Expected, lists:flatten(Msg))
  554. end
  555. },
  556. {"crash report for system process limit",
  557. fun() ->
  558. error_logger:error_report(crash_report, [[{pid, self()}, {error_info, {error, {system_limit, [{erlang, spawn, 1}]}, []}}], []]),
  559. _ = gen_event:which_handlers(error_logger),
  560. timer:sleep(100),
  561. {_, _, Msg} = pop(),
  562. Expected = lists:flatten(io_lib:format("[error] ~w CRASH REPORT Process ~w with 0 neighbours crashed with reason: system limit: maximum number of processes exceeded", [self(), self()])),
  563. ?assertEqual(Expected, lists:flatten(Msg))
  564. end
  565. },
  566. {"crash report for system process limit2",
  567. fun() ->
  568. error_logger:error_report(crash_report, [[{pid, self()}, {error_info, {error, {system_limit, [{erlang, spawn_opt, 1}]}, []}}], []]),
  569. _ = gen_event:which_handlers(error_logger),
  570. timer:sleep(100),
  571. {_, _, Msg} = pop(),
  572. Expected = lists:flatten(io_lib:format("[error] ~w CRASH REPORT Process ~w with 0 neighbours crashed with reason: system limit: maximum number of processes exceeded", [self(), self()])),
  573. ?assertEqual(Expected, lists:flatten(Msg))
  574. end
  575. },
  576. {"crash report for system port limit",
  577. fun() ->
  578. error_logger:error_report(crash_report, [[{pid, self()}, {error_info, {error, {system_limit, [{erlang, open_port, 1}]}, []}}], []]),
  579. _ = gen_event:which_handlers(error_logger),
  580. timer:sleep(100),
  581. {_, _, Msg} = pop(),
  582. Expected = lists:flatten(io_lib:format("[error] ~w CRASH REPORT Process ~w with 0 neighbours crashed with reason: system limit: maximum number of ports exceeded", [self(), self()])),
  583. ?assertEqual(Expected, lists:flatten(Msg))
  584. end
  585. },
  586. {"crash report for system port limit",
  587. fun() ->
  588. error_logger:error_report(crash_report, [[{pid, self()}, {error_info, {error, {system_limit, [{erlang, list_to_atom, 1}]}, []}}], []]),
  589. _ = gen_event:which_handlers(error_logger),
  590. timer:sleep(100),
  591. {_, _, Msg} = pop(),
  592. Expected = lists:flatten(io_lib:format("[error] ~w CRASH REPORT Process ~w with 0 neighbours crashed with reason: system limit: tried to create an atom larger than 255, or maximum atom count exceeded", [self(), self()])),
  593. ?assertEqual(Expected, lists:flatten(Msg))
  594. end
  595. },
  596. {"crash report for system ets table limit",
  597. fun() ->
  598. error_logger:error_report(crash_report, [[{pid, self()}, {error_info, {error, {system_limit,[{ets,new,[segment_offsets,[ordered_set,public]]},{mi_segment,open_write,1},{mi_buffer_converter,handle_cast,2},{gen_server,handle_msg,5},{proc_lib,init_p_do_apply,3}]}, []}}], []]),
  599. _ = gen_event:which_handlers(error_logger),
  600. timer:sleep(100),
  601. {_, _, Msg} = pop(),
  602. Expected = lists:flatten(io_lib:format("[error] ~w CRASH REPORT Process ~w with 0 neighbours crashed with reason: system limit: maximum number of ETS tables exceeded", [self(), self()])),
  603. ?assertEqual(Expected, lists:flatten(Msg))
  604. end
  605. },
  606. {"crash report for unknown system limit should be truncated at 500 characters",
  607. fun() ->
  608. error_logger:error_report(crash_report, [[{pid, self()}, {error_info, {error, {system_limit,[{wtf,boom,[string:copies("aaaa", 4096)]}]}, []}}], []]),
  609. _ = gen_event:which_handlers(error_logger),
  610. timer:sleep(1000),
  611. {_, _, Msg} = pop(),
  612. ?assert(length(lists:flatten(Msg)) > 500),
  613. ?assert(length(lists:flatten(Msg)) < 700)
  614. end
  615. },
  616. {"messages should not be generated if they don't satisfy the threshold",
  617. fun() ->
  618. lager:set_loglevel(?MODULE, error),
  619. error_logger:info_report([hello, world]),
  620. _ = gen_event:which_handlers(error_logger),
  621. timer:sleep(100),
  622. ?assertEqual(0, count()),
  623. ?assertEqual(0, count_ignored()),
  624. lager:set_loglevel(?MODULE, info),
  625. error_logger:info_report([hello, world]),
  626. _ = gen_event:which_handlers(error_logger),
  627. timer:sleep(100),
  628. ?assertEqual(1, count()),
  629. ?assertEqual(0, count_ignored()),
  630. lager:set_loglevel(?MODULE, error),
  631. lager_mochiglobal:put(loglevel, ?DEBUG),
  632. error_logger:info_report([hello, world]),
  633. _ = gen_event:which_handlers(error_logger),
  634. timer:sleep(100),
  635. ?assertEqual(1, count()),
  636. ?assertEqual(1, count_ignored())
  637. end
  638. }
  639. ]
  640. }.
  641. -endif.