Go to main content

man pages section 1: User Commands

Exit Print View

Updated: July 2017
 
 

escript (1)

Name

escript - Erlang scripting support

Synopsis

Please see following description for synopsis

Description

escript(1)                       User Commands                      escript(1)



NAME
       escript - Erlang scripting support

DESCRIPTION
       escript provides support for running short Erlang programs without hav-
       ing to compile them first and an easy way to retrieve the command  line
       arguments.

EXPORTS
       script-name script-arg1 script-arg2...
       escript escript-flags script-name script-arg1 script-arg2...

              escript runs a script written in Erlang.

              Here follows an example.

              $ chmod u+x factorial
              $ cat factorial
              #!/usr/bin/env escript
              %% -*- erlang -*-
              %%! -smp enable -sname factorial -mnesia debug verbose
              main([String]) ->
                  try
                      N = list_to_integer(String),
                      F = fac(N),
                      io:format("factorial ~w = ~w\n", [N,F])
                  catch
                      _:_ ->
                          usage()
                  end;
              main(_) ->
                  usage().

              usage() ->
                  io:format("usage: factorial integer\n"),
                  halt(1).

              fac(0) -> 1;
              fac(N) -> N * fac(N-1).
              $ ./factorial 5
              factorial 5 = 120
              $ ./factorial
              usage: factorial integer
              $ ./factorial five
              usage: factorial integer


              The  header  of  the Erlang script in the example differs from a
              normal Erlang module. The first  line  is  intended  to  be  the
              interpreter  line,  which invokes escript. However if you invoke
              the escript like this

              $ escript factorial 5

              the contents of the first line does not matter,  but  it  cannot
              contain Erlang code as it will be ignored.

              The  second  line in the example, contains an optional directive
              to the Emacs editor which causes it to enter the major mode  for
              editing Erlang source files. If the directive is present it must
              be located on the second line.

              If there is a comment selecting the encoding it can  be  located
              on the second line.

          Note:
              The encoding specified by the above mentioned comment applies to
              the script itself. The encoding of the I/O-server, however,  has
              to be set explicitly like this:

              io:setopts([{encoding, unicode}])

              The default encoding of the I/O-server for standard_io is latin1
              since the script runs in a non-interactive terminal (see   Using
              Unicode in Erlang).


              On  the  third line (or second line depending on the presence of
              the Emacs directive), it is possible to give  arguments  to  the
              emulator, such as

              %%! -smp enable -sname factorial -mnesia debug verbose

              Such  an  argument  line must start with %%! and the rest of the
              line will interpreted as arguments to the emulator.

              If you know the location of the escript  executable,  the  first
              line can directly give the path to escript. For instance:

              #!/usr/local/bin/escript

              As  any  other  kind of scripts, Erlang scripts will not work on
              Unix platforms if the execution bit for the script file  is  not
              set. (Use chmod +x script-name to turn on the execution bit.)

              The  rest  of  the  Erlang script file may either contain Erlang
              source code, an inlined beam file or an inlined archive file.

              An Erlang script file must always contain the  function  main/1.
              When  the script is run, the main/1 function will be called with
              a list of strings representing the arguments given to the script
              (not changed or interpreted in any way).

              If  the  main/1 function in the script returns successfully, the
              exit status for the script will be 0. If an exception is  gener-
              ated  during  execution, a short message will be printed and the
              script terminated with exit status 127.

              To return your own non-zero exit code, call halt(ExitCode);  for
              instance:

              halt(1).

              Call  escript:script_name()  from your to script to retrieve the
              pathname of the script (the pathname is usually, but not always,
              absolute).

              If  the  file contains source code (as in the example above), it
              will be processed by the preprocessor epp. This means  that  you
              for example may use pre-defined macros (such as ?MODULE) as well
              as include  directives  like  the  -include_lib  directive.  For
              instance, use

              -include_lib("kernel/include/file.hrl").

              to  include  the  record definitions for the records used by the
              file:read_link_info/1 function. You can also select encoding  by
              including  a  encoding  comment  here,  but  if there is a valid
              encoding comment on the second line it takes precedence.

              The script will be checked for syntactic and  semantic  correct-
              ness  before  being  run.  If there are warnings (such as unused
              variables), they will be printed and the script  will  still  be
              run.  If  there  are errors, they will be printed and the script
              will not be run and its exit status will be 127.

              Both the module declaration and the export  declaration  of  the
              main/1 function are optional.

              By  default, the script will be interpreted. You can force it to
              be compiled by including the following  line  somewhere  in  the
              script file:

              -mode(compile).

              Execution  of  interpreted code is slower than compiled code. If
              much of the execution takes place in interpreted code it may  be
              worthwhile  to  compile  it,  even though the compilation itself
              will take a little while. It is also possible to  supply  native
              instead  of  compile,  this  will  compile  the script using the
              native flag, again  depending  on  the  characteristics  of  the
              escript this could or could not be worth while.

              As mentioned earlier, it is possible to have a script which con-
              tains precompiled beam code. In a precompiled script, the inter-
              pretation  of  the  script  header  is  exactly the same as in a
              script containing source code. That means that you  can  make  a
              beam  file  executable  by  prepending  the  file with the lines
              starting with #! and  %%!  mentioned  above.  In  a  precompiled
              script, the function main/1 must be exported.

              As  yet  another  option it is possible to have an entire Erlang
              archive in the script. In a archive script,  the  interpretation
              of the script header is exactly the same as in a script contain-
              ing source code. That means that you can make  an  archive  file
              executable  by  prepending the file with the lines starting with
              #! and %%! mentioned above. In an archive script,  the  function
              main/1  must  be exported. By default the main/1 function in the
              module with the same name as the basename of  the  escript  file
              will  be invoked. This behavior can be overridden by setting the
              flag -escript main Module as one of the emulator flags. The Mod-
              ule  must  be  the name of a module which has an exported main/1
              function. See code(3) for more information  about  archives  and
              code loading.

              In  many  cases  it  is  very convenient to have a header in the
              escript, especially on Unix platforms. But the header is in fact
              optional.  This  means that you directly can "execute" an Erlang
              module, beam file or archive file without adding any  header  to
              them. But then you have to invoke the script like this:

              $ escript factorial.erl 5
              factorial 5 = 120
              $ escript factorial.beam 5
              factorial 5 = 120
              $ escript factorial.zip 5
              factorial 5 = 120


       escript:create(FileOrBin,  Sections)  ->  ok | {ok, binary()} | {error,
       term()}

              Types:

                 FileOrBin = filename() | 'binary'
                 Sections = [Header] Body | Body
                 Header = shebang | {shebang, Shebang} | comment  |  {comment,
                 Comment} | {emu_args, EmuArgs}
                 Shebang = string() | 'default' | 'undefined'
                 Comment = string() | 'default' | 'undefined'
                 EmuArgs = string() | 'undefined'
                 Body  =  {source,  SourceCode} | {beam, BeamCode} | {archive,
                 ZipArchive} | {archive, ZipFiles, ZipOptions}
                 SourceCode = BeamCode = file:filename() | binary()
                 ZipArchive = zip:filename() | binary()
                 ZipFiles = [ZipFile]
                 ZipFile = file:filename()  |  {file:filename(),  binary()}  |
                 {file:filename(), binary(), file:file_info()}
                 ZipOptions = [zip:create_option()]

              The  create/2  function  creates  an escript from a list of sec-
              tions. The sections can be given in any order. An escript begins
              with  an  optional  Header  followed by a mandatory Body. If the
              header is present, it does always begin with a shebang, possibly
              followed  by  a  comment  and  emu_args. The shebang defaults to
              "/usr/bin/env escript". The comment defaults to "This is an  -*-
              erlang  -*- file". The created escript can either be returned as
              a binary or written to file.

              As an example of how the function can  be  used,  we  create  an
              interpreted  escript  which  uses  emu_args to set some emulator
              flag. In this case it happens to disable the smp_support. We  do
              also  extract  the  different  sections  from  the newly created
              script:

              > Source = "%% Demo\nmain(_Args) ->\n io:format(erlang:system_info(smp_support)).\n".
              "%% Demo\nmain(_Args) ->\n    io:format(erlang:system_info(smp_support)).\n"
              > io:format("~s\n", [Source]).
              %% Demo
              main(_Args) ->
                  io:format(erlang:system_info(smp_support)).

              ok
              > {ok, Bin} = escript:create(binary, [shebang, comment, {emu_args, "-smp disable"}, {source, list_to_binary(Source)}]).
              {ok,<<"#!/usr/bin/env escript\n%% This is an -*- erlang -*- file\n%%!-smp disabl"...>>}
              > file:write_file("demo.escript", Bin).
              ok
              > os:cmd("escript demo.escript").
              "false"
              > escript:extract("demo.escript", []).
              {ok,[{shebang,default}, {comment,default}, {emu_args,"-smp disable"},
                   {source,<<"%% Demo\nmain(_Args) ->\n    io:format(erlang:system_info(smp_su"...>>}]}


              An escript without header can be created like this:

              > file:write_file("demo.erl", ["%% demo.erl\n-module(demo).\n-export([main/1]).\n\n", Source]).
              ok
              > {ok, _, BeamCode} = compile:file("demo.erl", [binary, debug_info]).
              {ok,demo,
                  <<70,79,82,49,0,0,2,208,66,69,65,77,65,116,111,109,0,0,0,
                    79,0,0,0,9,4,100,...>>}
              > escript:create("demo.beam", [{beam, BeamCode}]).
              ok
              > escript:extract("demo.beam", []).
              {ok,[{shebang,undefined}, {comment,undefined}, {emu_args,undefined},
                   {beam,<<70,79,82,49,0,0,3,68,66,69,65,77,65,116,
                           111,109,0,0,0,83,0,0,0,9,...>>}]}
              > os:cmd("escript demo.beam").
              "true"


              Here we create an archive script containing both Erlang code  as
              well as beam code. Then we iterate over all files in the archive
              and collect their contents and some info about them.

              > {ok, SourceCode} = file:read_file("demo.erl").
              {ok,<<"%% demo.erl\n-module(demo).\n-export([main/1]).\n\n%% Demo\nmain(_Arg"...>>}
              > escript:create("demo.escript", [shebang, {archive, [{"demo.erl", SourceCode}, {"demo.beam", BeamCode}], []}]).
              ok
              > {ok, [{shebang,default}, {comment,undefined}, {emu_args,undefined}, {archive, ArchiveBin}]} = escript:extract("demo.escript", []).
              {ok,[{shebang,default}, {comment,undefined}, {emu_args,undefined},
                   {{archive,<<80,75,3,4,20,0,0,0,8,0,118,7,98,60,105,
                              152,61,93,107,0,0,0,118,0,...>>}]}
              > file:write_file("demo.zip", ArchiveBin).
              ok
              > zip:foldl(fun(N, I, B, A) -> [{N, I(), B()} | A] end, [], "demo.zip").
              {ok,[{"demo.beam",
                    {file_info,748,regular,read_write,
                               {{2010,3,2},{0,59,22}},
                               {{2010,3,2},{0,59,22}},
                               {{2010,3,2},{0,59,22}},
                               54,1,0,0,0,0,0},
                    <<70,79,82,49,0,0,2,228,66,69,65,77,65,116,111,109,0,0,0,
                      83,0,0,...>>},
                   {"demo.erl",
                    {file_info,118,regular,read_write,
                               {{2010,3,2},{0,59,22}},
                               {{2010,3,2},{0,59,22}},
                               {{2010,3,2},{0,59,22}},
                               54,1,0,0,0,0,0},
                    <<"%% demo.erl\n-module(demo).\n-export([main/1]).\n\n%% Demo\nmain(_Arg"...>>}]}

       escript:extract(File, Options) -> {ok, Sections} | {error, term()}

              Types:

                 File = filename()
                 Options = [] | [compile_source]
                 Sections = Headers Body
                 Headers = {shebang, Shebang}  {comment,  Comment}  {emu_args,
                 EmuArgs}
                 Shebang = string() | 'default' | 'undefined'
                 Comment = string() | 'default' | 'undefined'
                 EmuArgs = string() | 'undefined'
                 Body  =  {source,  SourceCode}  | {source, BeamCode} | {beam,
                 BeamCode} | {archive, ZipArchive}
                 SourceCode = BeamCode = ZipArchive = binary()

              The extract/2 function parses an escript and extracts  its  sec-
              tions. This is the reverse of create/2.

              All  sections  are  returned  even  if  they do not exist in the
              escript. If a particular section happens to have the same  value
              as  the  default  value,  the extracted value is set to the atom
              default. If a section is missing, the extracted value is set  to
              the atom undefined.

              The compile_source option only affects the result if the escript
              contains source code. In that case the Erlang code is  automati-
              cally  compiled  and  {source,  BeamCode} is returned instead of
              {source, SourceCode}.

              > escript:create("demo.escript", [shebang, {archive, [{"demo.erl", SourceCode}, {"demo.beam", BeamCode}], []}]).
              ok
              > {ok, [{shebang,default}, {comment,undefined}, {emu_args,undefined}, {archive, ArchiveBin}]} = escript:extract("demo.escript", []).
              {ok,[{{archive,<<80,75,3,4,20,0,0,0,8,0,118,7,98,60,105,
                              152,61,93,107,0,0,0,118,0,...>>}
                   {emu_args,undefined}]}


       escript:script_name() -> File

              Types:

                 File = filename()

              The script_name/0 function returns the name of the escript being
              executed.  If  the function is invoked outside the context of an
              escript, the behavior is undefined.

OPTIONS ACCEPTED BY ESCRIPT
         -c:
           Compile the escript regardless of the value of the mode attribute.

         -d:
           Debug the escript. Starts the debugger, loads the module containing
           the  main/1 function into the debugger, sets a breakpoint in main/1
           and invokes main/1. If  the  module  is  precompiled,  it  must  be
           explicitly compiled with the debug_info option.

         -i:
           Interpret   the  escript  regardless  of  the  value  of  the  mode
           attribute.

         -s:
           Only perform a syntactic and semantic check  of  the  script  file.
           Warnings  and  errors  (if any) are written to the standard output,
           but the script will not be run. The exit status will be 0 if  there
           were no errors, and 127 otherwise.

         -n:
           Compile the escript using the +native flag.


ATTRIBUTES
       See attributes(5) for descriptions of the following attributes:


       +---------------+------------------+
       |ATTRIBUTE TYPE | ATTRIBUTE VALUE  |
       +---------------+------------------+
       |Availability   | runtime/erlang   |
       +---------------+------------------+
       |Stability      | Uncommitted      |
       +---------------+------------------+
NOTES
       This     software     was    built    from    source    available    at
       https://java.net/projects/solaris-userland.   The  original   community
       source     was     downloaded     from      http://www.erlang.org/down-
       load/otp_src_17.5.tar.gz

       Further information about this software can be found on the open source
       community website at http://www.erlang.org/.



Ericsson AB                        erts 6.4                         escript(1)