Last active
August 23, 2019 14:54
-
-
Save hcs42/775b414943b156a98b98 to your computer and use it in GitHub Desktop.
Erlang notes
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Loading modules | |
--------------- | |
Purging = removing the old version of the module (so that it will only have a new | |
version). | |
erlang:check_old_code(mymodule). | |
Return if the module has an old version loaded. | |
code:load_file(mymodule). | |
code:load_abs("/home/me/mymodule"). % no ".beam" | |
Load mymodule (and mark the currently loaded version of the module as "old"). | |
code:purge(mymodule). | |
Purge mymodule: if there are any processes using the old code, they are | |
killed. | |
code:soft_purge(mymodule). | |
Purge mymodule only if there are no processes using the old code. | |
code:delete(mymodule). | |
Mark the new version of the module as "old". | |
Shortcuts that work only from the Erlang shell: | |
l(mymodule), nl(mymodule) | |
Load mymodule to this or all nodes. | |
c("/home/me/mymodule"). % no ".beam" | |
Compile and load (an purge) mymodule. | |
m() | |
Show loaded modules. | |
Manual pages: erl, erlang, shell, code, c | |
http://learnyousomeerlang.com/designing-a-concurrent-application#hot-code-loving | |
Processes | |
--------- | |
processes() | |
pid(A, B, C) | |
process_info(Pid) | |
process_info(Pid, backtrace) | |
> f(TMP1), {backtrace,TMP1} = process_info(list_to_pid("PIDSTR"), backtrace), io:format("~s~n",[TMP1]). | |
is_pid() | |
is_process_alive(Pid) | |
exit(Pid, kill) | |
pid_to_list() | |
erlang:process_display(LocalPid, backtrace) | |
rpc:pinfo(Pid), rpc:pinfo(Pid, Item) | |
registered(), whereis() | |
global:registered_names(), global:whereis_name(Name). | |
Upgrade gen_server | |
------------------ | |
Up = fun(Mod) -> [sys:suspend(Mod), code:purge(Mod), code:load_file(Mod), sys:change_code(Mod,Mod,"0",[]), sys:resume(Mod)] end. | |
Ports | |
----- | |
erlang:ports() | |
erlang:port_info(Port), erlang:port_info(Port, Item) | |
is_port() | |
erlang:port_to_list(Port) | |
Nodes | |
----- | |
is_alive() | |
Returns true if the local node is alive | |
node(), nodes() | |
node(Arg) | |
Returns the node where Arg is located. Arg can be a pid, a reference, or a | |
port | |
nodes(Arg | [Arg]), Arg = visible | hidden | connected | this | known | |
net_adm:ping(Node) | |
dbg | |
--- | |
Quick start: | |
dbg:tracer(). | |
dbg:p(all, call). | |
dbg:tpl(Module, []). | |
dbg:tpl(Module, Function, Arity, [{'_', [], [{return_trace}]}]). | |
http://stackoverflow.com/questions/1954894/using-trace-and-dbg-in-erlang | |
dbg:tracer(). | |
dbg:tracer(port, dbg:trace_port(file, os:getenv("HOME") ++ "/myfile.dbg")). | |
dbg:tracer(process, {fun (_,100) -> dbg:stop_clear(); | |
(Msg, N) -> io:format("~p~n", [Msg]), N+1 end, 0 | |
}). | |
dbg:p(all, call). | |
dbg:p(all, [call, timestamp]). | |
dbg:tpl(Module, []). | |
dbg:tpl(Module, Function, Arity, [{'_', [], [{return_trace}]}]). | |
Print all calls to the functions of Module. | |
dbg:tp(...) | |
Same as tpl, but only for exported functions. | |
dbg:stop_clear(). | |
Redbug | |
------ | |
application:start(eper). | |
redbug:start(["mymod->return"],[{msgs,100},{time,20000},print_pid]). | |
redbug:start(["erlang:demonitor->return"],[{msgs,100},{time,20000},print_pid]). | |
Diagnostic | |
---------- | |
toolbar:start() | |
erlang:get_stacktrace() | |
Get the stacktrace of the last exception in the calling process | |
dtop:start, timer:sleep(5000). | |
top | |
dtop:sort(mem) | |
Sort by memory usage | |
sys:get_status(pid(0,187,0)) | |
Get the gen_server's state | |
ets:i() | |
Connecting to erlang nodes | |
-------------------------- | |
(See also my connect2beam script which is wrapper around the call below.) | |
erl -name <name of new node> \ | |
-setcookie <same as the original node's cookie> \ | |
-kernel <same kernel options as the original node> \ | |
-remsh <name of the original node> | |
name of the original node: | |
short names: node@host | |
Compiling an OTP module | |
----------------------- | |
erlc +debug_info -o ../ebin -I ../include ssl_manager.erl | |
Regular expressions | |
------------------- | |
re:run(Text, Pattern, [{capture, none}]) -> | |
match | nomatch | |
re:run(Text, Pattern, [{capture, all, list}]) -> | |
{match, [Group0, Group1, Group2, ...]} | | |
nomatch | |
re:replace(Text, Pattern, Replacement, [global, {return, list}]) | |
Records in the shell | |
-------------------- | |
rd(RecordName, RecordDefinition) | |
Defines a record in the shell. | |
rl() | |
rl(RecordName) | |
rl(RecordNames) | |
Prints record definitions. | |
rp(Term) | |
Prints a term using the record definitions known to the shell. | |
Shell | |
----- | |
catch_exception(true). | |
Date, time (before Erlang/OTP 18) | |
---------- | |
Datetime representations: | |
erlang:timestamp() = {MegaSecs, Secs, MicroSecs} -- time since the epoch (tz independent) | |
gregorian_seconds() = integer() -- number of seconds since year 0 (tz naive) | |
datetime() = {{Year, Month, Day}, {Hour, Minute, Seconds}} (tz naive) | |
Functions for getting the current datetime: | |
os:timestamp() -> erlang:timestamp() | |
erlang:now() -> erlang:timestamp() | |
calendar:local_time() -> current datetime() in local time | |
calendar:universal_time() -> current datetime() in UTC | |
Conversion functions: | |
calendar:datetime_to_gregorian_seconds(datetime()) -> gregorian_seconds() in same time zone | |
calendar:gregorian_seconds_to_datetime(gregorian_seconds()) -> datetime() in same time zone | |
calendar:local_time_to_universal_time(datetime()) in local time -> datetime() in UTC | |
calendar:universal_time_to_local_time(datetime()) in UTC -> datetime() in local time | |
calendar:now_to_local_time(erlang:timestamp()) -> datetime() in local time | |
calendar:now_to_universal_time(erlang:timestamp()) -> datetime() in UTC | |
Crash dumps | |
----------- | |
> crashdump_viewer:start(). | |
Mnesia | |
------ | |
Print all tables | |
[io:format("~p~n", [T]) || T <- lists:sort(mnesia:system_info(tables))], ok. | |
ST = fun(TableName) -> | |
Iterator = fun(Rec,_)-> | |
io:format("~p~n",[Rec]), | |
[] | |
end, | |
case mnesia:is_transaction() of | |
true -> mnesia:foldl(Iterator,[],TableName); | |
false -> | |
Exec = fun({Fun,Tab}) -> mnesia:foldl(Fun, [],Tab) end, | |
mnesia:activity(transaction,Exec,[{Iterator,TableName}],mnesia_frag) | |
end | |
end. | |
Files | |
----- | |
abspath, basename, pathname: | |
filename:absname(path) | |
filename:basename(path) | |
filename:dirname(path) | |
Tests: | |
-e: filelib:is_regular() | |
-d: filelib:is_dir() | |
-f: filelib:is_file() | |
Unix commands: | |
mkdir -p filelib:ensure_dir(Path++File) | |
pwd file:get_cwd() | |
cd file:set_cwd() | |
ls file:list_dir(Dir) | |
find filelib:fold_files() | |
rm file:delete(File) | |
mv file:rename(Src, Dst) | |
Etc | |
--- | |
Convert number from base <from> to base <to> | |
io:format("~.<to>B", [<from>#Number]). |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment