aboutsummaryrefslogtreecommitdiffstats
path: root/lib/stdlib/test/stdlib_SUITE.erl
diff options
context:
space:
mode:
Diffstat (limited to 'lib/stdlib/test/stdlib_SUITE.erl')
-rw-r--r--lib/stdlib/test/stdlib_SUITE.erl255
1 files changed, 185 insertions, 70 deletions
diff --git a/lib/stdlib/test/stdlib_SUITE.erl b/lib/stdlib/test/stdlib_SUITE.erl
index 8a2cb5ea6b..a586729b30 100644
--- a/lib/stdlib/test/stdlib_SUITE.erl
+++ b/lib/stdlib/test/stdlib_SUITE.erl
@@ -1,18 +1,19 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 1997-2011. All Rights Reserved.
+%% Copyright Ericsson AB 1997-2015. All Rights Reserved.
%%
-%% The contents of this file are subject to the Erlang Public License,
-%% Version 1.1, (the "License"); you may not use this file except in
-%% compliance with the License. You should have received a copy of the
-%% Erlang Public License along with this software. If not, it can be
-%% retrieved online at http://www.erlang.org/.
-%%
-%% Software distributed under the License is distributed on an "AS IS"
-%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
-%% the License for the specific language governing rights and limitations
-%% under the License.
+%% Licensed under the Apache License, Version 2.0 (the "License");
+%% you may not use this file except in compliance with the License.
+%% You may obtain a copy of the License at
+%%
+%% http://www.apache.org/licenses/LICENSE-2.0
+%%
+%% Unless required by applicable law or agreed to in writing, software
+%% distributed under the License is distributed on an "AS IS" BASIS,
+%% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+%% See the License for the specific language governing permissions and
+%% limitations under the License.
%%
%% %CopyrightEnd%
%%
@@ -22,18 +23,7 @@
-module(stdlib_SUITE).
-include_lib("test_server/include/test_server.hrl").
-
-% Default timetrap timeout (set in init_per_testcase).
--define(default_timeout, ?t:minutes(1)).
--define(application, stdlib).
-
-% Test server specific exports
--export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1,
- init_per_group/2,end_per_group/2]).
--export([init_per_testcase/2, end_per_testcase/2]).
-
-% Test cases must be exported.
--export([app_test/1, appup_test/1]).
+-compile(export_all).
%%
%% all/1
@@ -41,10 +31,10 @@
suite() -> [{ct_hooks,[ts_install_cth]}].
all() ->
- [app_test, appup_test].
+ [app_test, appup_test, assert_test, {group,upgrade}].
groups() ->
- [].
+ [{upgrade,[minor_upgrade,major_upgrade]}].
init_per_suite(Config) ->
Config.
@@ -52,19 +42,20 @@ init_per_suite(Config) ->
end_per_suite(_Config) ->
ok.
+init_per_group(upgrade, Config) ->
+ ct_release_test:init(Config);
init_per_group(_GroupName, Config) ->
Config.
+end_per_group(upgrade, Config) ->
+ ct_release_test:cleanup(Config);
end_per_group(_GroupName, Config) ->
Config.
init_per_testcase(_Case, Config) ->
- ?line Dog=test_server:timetrap(?default_timeout),
- [{watchdog, Dog}|Config].
-end_per_testcase(_Case, Config) ->
- Dog=?config(watchdog, Config),
- test_server:timetrap_cancel(Dog),
+ Config.
+end_per_testcase(_Case, _Config) ->
ok.
%
@@ -78,56 +69,92 @@ app_test(Config) when is_list(Config) ->
?t:app_test(stdlib),
ok.
-%% Test that appup allows upgrade from/downgrade to a maximum of two
-%% major releases back.
+%% Test that appup allows upgrade from/downgrade to a maximum of one
+%% major release back.
appup_test(_Config) ->
- application:load(stdlib),
- {_,_,Vsn} = lists:keyfind(stdlib,1,application:loaded_applications()),
- AppupFile = filename:join([code:lib_dir(stdlib),ebin,"stdlib.appup"]),
+ appup_tests(stdlib,create_test_vsns(stdlib)).
+
+appup_tests(_App,{[],[]}) ->
+ {skip,"no previous releases available"};
+appup_tests(App,{OkVsns0,NokVsns}) ->
+ application:load(App),
+ {_,_,Vsn} = lists:keyfind(App,1,application:loaded_applications()),
+ AppupFileName = atom_to_list(App) ++ ".appup",
+ AppupFile = filename:join([code:lib_dir(App),ebin,AppupFileName]),
{ok,[{Vsn,UpFrom,DownTo}=AppupScript]} = file:consult(AppupFile),
ct:log("~p~n",[AppupScript]),
- {OkVsns,NokVsns} = create_test_vsns(Vsn),
+ OkVsns =
+ case OkVsns0 -- [Vsn] of
+ OkVsns0 ->
+ OkVsns0;
+ Ok ->
+ ct:log("Current version, ~p, is same as in previous release.~n"
+ "Removing this from the list of ok versions.",
+ [Vsn]),
+ Ok
+ end,
+ ct:log("Testing that appup allows upgrade from these versions: ~p~n",
+ [OkVsns]),
check_appup(OkVsns,UpFrom,{ok,[restart_new_emulator]}),
check_appup(OkVsns,DownTo,{ok,[restart_new_emulator]}),
+ ct:log("Testing that appup does not allow upgrade from these versions: ~p~n",
+ [NokVsns]),
check_appup(NokVsns,UpFrom,error),
check_appup(NokVsns,DownTo,error),
ok.
-create_test_vsns(Current) ->
- [XStr,YStr|Rest] = string:tokens(Current,"."),
- X = list_to_integer(XStr),
- Y = list_to_integer(YStr),
- SecondMajor = vsn(X,Y-2),
- SecondMinor = SecondMajor ++ ".1.3",
- FirstMajor = vsn(X,Y-1),
- FirstMinor = FirstMajor ++ ".57",
- ThisMajor = vsn(X,Y),
- This =
- case Rest of
- [] ->
- [];
- ["1"] ->
- [ThisMajor];
- _ ->
- ThisMinor = ThisMajor ++ ".1",
- [ThisMajor,ThisMinor]
+create_test_vsns(App) ->
+ ThisMajor = erlang:system_info(otp_release),
+ FirstMajor = previous_major(ThisMajor),
+ SecondMajor = previous_major(FirstMajor),
+ Ok = app_vsn(App,[ThisMajor,FirstMajor]),
+ Nok0 = app_vsn(App,[SecondMajor]),
+ Nok = case Ok of
+ [Ok1|_] ->
+ [Ok1 ++ ",1" | Nok0]; % illegal
+ _ ->
+ Nok0
+ end,
+ {Ok,Nok}.
+
+previous_major("17") ->
+ "r16b";
+previous_major("r16b") ->
+ "r15b";
+previous_major(Rel) ->
+ integer_to_list(list_to_integer(Rel)-1).
+
+app_vsn(App,[R|Rs]) ->
+ OldRel =
+ case test_server:is_release_available(R) of
+ true ->
+ {release,R};
+ false ->
+ case ct:get_config({otp_releases,list_to_atom(R)}) of
+ undefined ->
+ false;
+ Prog0 ->
+ case os:find_executable(Prog0) of
+ false ->
+ false;
+ Prog ->
+ {prog,Prog}
+ end
+ end
end,
- OkVsns = This ++ [FirstMajor, FirstMinor, SecondMajor, SecondMinor],
-
- ThirdMajor = vsn(X,Y-3),
- ThirdMinor = ThirdMajor ++ ".10.12",
- Illegal = ThisMajor ++ ",1",
- Newer1Major = vsn(X,Y+1),
- Newer1Minor = Newer1Major ++ ".1",
- Newer2Major = ThisMajor ++ "1",
- NokVsns = [ThirdMajor,ThirdMinor,
- Illegal,
- Newer1Major,Newer1Minor,
- Newer2Major],
- {OkVsns,NokVsns}.
-
-vsn(X,Y) ->
- integer_to_list(X) ++ "." ++ integer_to_list(Y).
+ case OldRel of
+ false ->
+ app_vsn(App,Rs);
+ _ ->
+ {ok,N} = test_server:start_node(prevrel,peer,[{erl,[OldRel]}]),
+ _ = rpc:call(N,application,load,[App]),
+ As = rpc:call(N,application,loaded_applications,[]),
+ {_,_,V} = lists:keyfind(App,1,As),
+ test_server:stop_node(N),
+ [V|app_vsn(App,Rs)]
+ end;
+app_vsn(_App,[]) ->
+ [].
check_appup([Vsn|Vsns],Instrs,Expected) ->
case systools_relup:appup_search_for_version(Vsn, Instrs) of
@@ -136,3 +163,91 @@ check_appup([Vsn|Vsns],Instrs,Expected) ->
end;
check_appup([],_,_) ->
ok.
+
+
+minor_upgrade(Config) ->
+ ct_release_test:upgrade(stdlib,minor,{?MODULE,[]},Config).
+
+major_upgrade(Config) ->
+ ct_release_test:upgrade(stdlib,major,{?MODULE,[]},Config).
+
+%% Version numbers are checked by ct_release_test, so there is nothing
+%% more to check here...
+upgrade_init(CtData,State) ->
+ {ok,{FromVsn,ToVsn}} = ct_release_test:get_app_vsns(CtData,stdlib),
+ case ct_release_test:get_appup(CtData,stdlib) of
+ {ok,{FromVsn,ToVsn,[restart_new_emulator],[restart_new_emulator]}} ->
+ io:format("Upgrade/downgrade ~p <--> ~p",[FromVsn,ToVsn]);
+ {error,{vsn_not_found,_}} when FromVsn==ToVsn ->
+ io:format("No upgrade test for stdlib, same version")
+ end,
+ State.
+upgrade_upgraded(_CtData,State) ->
+ State.
+upgrade_downgraded(_CtData,State) ->
+ State.
+
+
+-include_lib("stdlib/include/assert.hrl").
+-include_lib("stdlib/include/assert.hrl"). % test repeated inclusion
+assert_test(suite) ->
+ [];
+assert_test(doc) ->
+ ["Assert macros test."];
+assert_test(_Config) ->
+ ok = ?assert(true),
+ {'EXIT',{{assert, _},_}} = (catch ?assert(false)),
+ {'EXIT',{{assert, Info1},_}} = (catch ?assert(0)),
+ {not_boolean,0} = lists:keyfind(not_boolean,1,Info1),
+
+ ok = ?assertNot(false),
+ {'EXIT',{{assert, _},_}} = (catch ?assertNot(true)),
+ {'EXIT',{{assert, Info2},_}} = (catch ?assertNot(0)),
+ {not_boolean,0} = lists:keyfind(not_boolean,1,Info2),
+
+ ok = ?assertMatch({foo,_}, {foo,bar}),
+ {'EXIT',{{assertMatch,_},_}} =
+ (catch ?assertMatch({foo,_}, {foo})),
+
+ ok = ?assertMatch({foo,N} when N > 0, {foo,1}),
+ {'EXIT',{{assertMatch,_},_}} =
+ (catch ?assertMatch({foo,N} when N > 0, {foo,0})),
+
+ ok = ?assertNotMatch({foo,_}, {foo,bar,baz}),
+ {'EXIT',{{assertNotMatch,_},_}} =
+ (catch ?assertNotMatch({foo,_}, {foo,baz})),
+
+ ok = ?assertNotMatch({foo,N} when N > 0, {foo,0}),
+ {'EXIT',{{assertNotMatch,_},_}} =
+ (catch ?assertNotMatch({foo,N} when N > 0, {foo,1})),
+
+ ok = ?assertEqual(1.0, 1.0),
+ {'EXIT',{{assertEqual,_},_}} = (catch ?assertEqual(1, 1.0)),
+
+ ok = ?assertNotEqual(1, 1.0),
+ {'EXIT',{{assertNotEqual,_},_}} = (catch ?assertNotEqual(1.0, 1.0)),
+
+ ok = ?assertException(error, badarith, 1/0),
+ ok = ?assertException(exit, foo, exit(foo)),
+ ok = ?assertException(throw, foo, throw(foo)),
+ ok = ?assertException(throw, {foo,_}, throw({foo,bar})),
+ ok = ?assertException(throw, {foo,N} when N > 0, throw({foo,1})),
+ {'EXIT',{{assertException,Why1},_}} =
+ (catch ?assertException(error, badarith, 0/1)),
+ true = lists:keymember(unexpected_success,1,Why1),
+ {'EXIT',{{assertException,Why2},_}} =
+ (catch ?assertException(error, badarith, 1/length(0))),
+ true = lists:keymember(unexpected_exception,1,Why2),
+ {'EXIT',{{assertException,Why3},_}} =
+ (catch ?assertException(throw, {foo,N} when N > 0, throw({foo,0}))),
+ true = lists:keymember(unexpected_exception,1,Why3),
+
+ ok = ?assertNotException(throw, {foo,baz}, throw({foo,bar})),
+ {'EXIT',{{assertNotException,Why4},_}} =
+ (catch ?assertNotException(throw, {foo,bar}, throw({foo,bar}))),
+ true = lists:keymember(unexpected_exception,1,Why4),
+
+ ok = ?assertError(badarith, 1/0),
+ ok = ?assertExit(foo, exit(foo)),
+ ok = ?assertThrow(foo, throw(foo)),
+ ok.