You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

150 line
5.4 KiB

  1. %%% File : ibrowse_functional_tests.erl
  2. %%% Authors : Benjamin Lee <http://github.com/benjaminplee>
  3. %%% Dan Schwabe <http://github.com/dfschwabe>
  4. %%% Brian Richards <http://github.com/richbria>
  5. %%% Description : Functional tests of the ibrowse library using a live test HTTP server
  6. %%% Created : 18 November 2014 by Benjamin Lee <yardspoon@gmail.com>
  7. -module(ibrowse_functional_tests).
  8. -include_lib("eunit/include/eunit.hrl").
  9. -define(PER_TEST_TIMEOUT_SEC, 60).
  10. -define(TIMEDTEST(Desc, Fun), {Desc, {timeout, ?PER_TEST_TIMEOUT_SEC, fun Fun/0}}).
  11. -define(SERVER_PORT, 8181).
  12. -define(BASE_URL, "http://localhost:" ++ integer_to_list(?SERVER_PORT)).
  13. -define(SHORT_TIMEOUT_MS, 5000).
  14. -define(LONG_TIMEOUT_MS, 30000).
  15. -define(PAUSE_FOR_CONNECTIONS_MS, 2000).
  16. setup() ->
  17. application:start(crypto),
  18. application:start(public_key),
  19. application:start(ssl),
  20. ibrowse_test_server:start_server(?SERVER_PORT, tcp),
  21. ibrowse:start(),
  22. ok.
  23. teardown(_) ->
  24. ibrowse:stop(),
  25. ibrowse_test_server:stop_server(?SERVER_PORT),
  26. ok.
  27. running_server_fixture_test_() ->
  28. {foreach,
  29. fun setup/0,
  30. fun teardown/1,
  31. [
  32. ?TIMEDTEST("Simple request can be honored", simple_request),
  33. ?TIMEDTEST("Slow server causes timeout", slow_server_timeout),
  34. ?TIMEDTEST("Pipeline depth goes down with responses", pipeline_depth),
  35. ?TIMEDTEST("Timeout closes pipe", closing_pipes),
  36. ?TIMEDTEST("Requests are balanced over connections", balanced_connections),
  37. ?TIMEDTEST("Pipeline too small signals retries", small_pipeline),
  38. ?TIMEDTEST("Dest status can be gathered", status)
  39. ]
  40. }.
  41. simple_request() ->
  42. ?assertMatch({ok, "200", _, _}, ibrowse:send_req(?BASE_URL, [], get, [], [])).
  43. slow_server_timeout() ->
  44. ?assertMatch({error, req_timedout}, ibrowse:send_req(?BASE_URL ++ "/never_respond", [], get, [], [], 5000)).
  45. pipeline_depth() ->
  46. MaxSessions = 2,
  47. MaxPipeline = 2,
  48. RequestsSent = 2,
  49. EmptyPipelineDepth = 0,
  50. ?assertEqual([], ibrowse_test_server:get_conn_pipeline_depth()),
  51. Fun = fun() -> ibrowse:send_req(?BASE_URL, [], get, [], [{max_sessions, MaxSessions}, {max_pipeline_size, MaxPipeline}], ?SHORT_TIMEOUT_MS) end,
  52. times(RequestsSent, fun() -> spawn_link(Fun) end),
  53. timer:sleep(?PAUSE_FOR_CONNECTIONS_MS),
  54. Counts = [Count || {_Pid, Count} <- ibrowse_test_server:get_conn_pipeline_depth()],
  55. ?assertEqual(MaxSessions, length(Counts)),
  56. ?assertEqual(lists:duplicate(MaxSessions, EmptyPipelineDepth), Counts).
  57. closing_pipes() ->
  58. MaxSessions = 2,
  59. MaxPipeline = 2,
  60. RequestsSent = 2,
  61. BalancedNumberOfRequestsPerConnection = 1,
  62. ?assertEqual([], ibrowse_test_server:get_conn_pipeline_depth()),
  63. Fun = fun() -> ibrowse:send_req(?BASE_URL ++ "/never_respond", [], get, [], [{max_sessions, MaxSessions}, {max_pipeline_size, MaxPipeline}], ?SHORT_TIMEOUT_MS) end,
  64. times(RequestsSent, fun() -> spawn_link(Fun) end),
  65. timer:sleep(?PAUSE_FOR_CONNECTIONS_MS),
  66. Counts = [Count || {_Pid, Count} <- ibrowse_test_server:get_conn_pipeline_depth()],
  67. ?assertEqual(MaxSessions, length(Counts)),
  68. ?assertEqual(lists:duplicate(MaxSessions, BalancedNumberOfRequestsPerConnection), Counts),
  69. timer:sleep(?SHORT_TIMEOUT_MS),
  70. ?assertEqual([], ibrowse_test_server:get_conn_pipeline_depth()).
  71. balanced_connections() ->
  72. MaxSessions = 4,
  73. MaxPipeline = 100,
  74. RequestsSent = 80,
  75. BalancedNumberOfRequestsPerConnection = 20,
  76. ?assertEqual([], ibrowse_test_server:get_conn_pipeline_depth()),
  77. Fun = fun() -> ibrowse:send_req(?BASE_URL ++ "/never_respond", [], get, [], [{max_sessions, MaxSessions}, {max_pipeline_size, MaxPipeline}], ?LONG_TIMEOUT_MS) end,
  78. times(RequestsSent, fun() -> spawn_link(Fun) end),
  79. timer:sleep(?PAUSE_FOR_CONNECTIONS_MS),
  80. Counts = [Count || {_Pid, Count} <- ibrowse_test_server:get_conn_pipeline_depth()],
  81. ?assertEqual(MaxSessions, length(Counts)),
  82. ?assertEqual(lists:duplicate(MaxSessions, BalancedNumberOfRequestsPerConnection), Counts).
  83. small_pipeline() ->
  84. MaxSessions = 10,
  85. MaxPipeline = 10,
  86. RequestsSent = 100,
  87. FullRequestsPerConnection = 10,
  88. ?assertEqual([], ibrowse_test_server:get_conn_pipeline_depth()),
  89. Fun = fun() -> ibrowse:send_req(?BASE_URL ++ "/never_respond", [], get, [], [{max_sessions, MaxSessions}, {max_pipeline_size, MaxPipeline}], ?SHORT_TIMEOUT_MS) end,
  90. times(RequestsSent, fun() -> spawn(Fun) end),
  91. timer:sleep(?PAUSE_FOR_CONNECTIONS_MS), %% Wait for everyone to get in line
  92. Counts = [Count || {_Pid, Count} <- ibrowse_test_server:get_conn_pipeline_depth()],
  93. ?assertEqual(MaxSessions, length(Counts)),
  94. ?assertEqual(lists:duplicate(MaxSessions, FullRequestsPerConnection), Counts),
  95. Response = ibrowse:send_req(?BASE_URL ++ "/never_respond", [], get, [], [{max_sessions, MaxSessions}, {max_pipeline_size, MaxPipeline}], ?SHORT_TIMEOUT_MS),
  96. ?assertEqual({error, retry_later}, Response).
  97. status() ->
  98. MaxSessions = 10,
  99. MaxPipeline = 10,
  100. RequestsSent = 100,
  101. Fun = fun() -> ibrowse:send_req(?BASE_URL ++ "/never_respond", [], get, [], [{max_sessions, MaxSessions}, {max_pipeline_size, MaxPipeline}], ?SHORT_TIMEOUT_MS) end,
  102. times(RequestsSent, fun() -> spawn(Fun) end),
  103. timer:sleep(?PAUSE_FOR_CONNECTIONS_MS), %% Wait for everyone to get in line
  104. ibrowse:show_dest_status(),
  105. ibrowse:show_dest_status("http://localhost:8181").
  106. times(0, _) ->
  107. ok;
  108. times(X, Fun) ->
  109. Fun(),
  110. times(X - 1, Fun).