系统 | System
系统
该System
模块提供了与VM或主机系统直接交互的功能。
时间
该System
模块还提供随时间工作的功能,返回系统保存的不同时间,支持不同的时间单位。
依靠系统时间的一个复杂因素是它们可能会被调整。例如,当您进入和离开夏令时时,系统时钟将被调整,通常会增加或删除一个小时。我们称这种变化为“时间扭曲”。为了理解这种变化可能是有害的,请想象下面的代码:
## DO NOT DO THIS
prev = System.os_time()
# ... execute some code ...
next = System.os_time()
diff = next - prev
如果在代码执行期间系统时钟发生改变,那么在1秒内执行的代码可能会被报告为超过1小时!为了解决这些问题,虚拟机提供了一个单调的时间System.monotonic_time/0
,永远不会减少,也不会跳跃:
## DO THIS
prev = System.monotonic_time()
# ... execute some code ...
next = System.monotonic_time()
diff = next - prev
一般来说,虚拟机提供三种时间测量:
os_time/0
- 操作系统报告的时间。这个时间可以及时向前或向后调整,没有限制;
system_time/0
-os_time/0
的VM视图。尽管虚拟机工作在对齐它们,但在时间扭曲的情况下,系统时间和操作系统时间可能不匹配。这个时间不是单调的(即它可能会减少),因为它的行为是由VM时间扭曲模式配置的 ;
monotonic_time/0
-Erlang VM提供的单调增加的时间。
- 环境变量不会被内嵌
- 通配符扩展不会发生(除非
Path.wildcard/2
明确使用)
- 为确保shell安全,不需要转义或引用参数。
此函数返回包含收集的结果和命令退出状态的元组。
在内部,这个功能使用一个Port
与外部世界进行交互。但是,如果您打算运行一个长时间运行的程序,端口保证stdin / stdout设备将被关闭,但不会自动终止程序。该Port
模块的文档描述了这个问题以及“僵尸进程”部分下的可能解决方案。
实例
iex> System.cmd "echo", ["hello"]
{"hello\n", 0}
iex> System.cmd "echo", ["hello"], env: [{"MIX_ENV", "test"}]
{"hello\n", 0}
iex> System.cmd "echo", ["hello"], into: IO.stream(:stdio, :line)
hello
{%IO.Stream{}, 0}
备选方案
:into
-将结果注入给定的可收集性中,默认为""
:cd
- 运行命令的目录
:env
-包含环境键值为二进制的元组的枚举。
:arg0
-设置命令arg0
:stderr_to_stdout
-将stderr重定向到stdouttrue
:parallelism
-如果属实,VM将安排端口任务以改善系统中的并行性。 如果设置为false,VM将尝试立即执行命令,以牺牲并行性为代价来提高延迟。 通过将“+ spp”参数传递给--erl,可以在系统启动时设置默认值。
错误原因
如果给出无效论据,ArgumentError
则由...提出System.cmd/3
。System.cmd/3
也期望有一套严格的选项,如果给出未知或无效的选项,将会提高。
此外,System.cmd/3
可能失败的原因之一,POSIX详述如下:
:system_limit
-Erlang模拟器中的所有可用端口都在使用中
:enomem
-内存不足,无法创建端口
:eagain
-没有更多可用的操作系统进程
:enametoolong
-发出的外部命令太长
:emfile
- 没有更多可用的文件描述符(对于运行Erlang模拟器的操作系统进程)
:enfile
- 文件表已满(针对整个操作系统)
:eacces
-命令不指向可执行文件
:enoent
-命令不指向现有文件
shell命令
如果您希望在shell中执行受信任的命令,使用管道,重定向等,请检查:os.cmd/1
。
compiled_endianness()
返回系统编译时使用的Endianness。
convert_time_unit(time, from_unit, to_unit)
convert_time_unit(integer, time_unit | :native, time_unit | :native) :: integer
将时间单位从单位时间转换为单位时间。
结果通过发言功能四舍五入。
convert_time_unit/3
接受一个额外的时间单位(除了那个time_unit/0
类型的):native
。:native
是Erlang运行时系统使用的时间单位。它确定运行时何时启动并保持不变,直到运行时停止。要确定:native
系统中单位的含义,可以调用此函数将1秒转换为:native
时间单位(即System.convert_time_unit(1, :second, :native)
)。
cwd()
当前工作目录。
返回当前工作目录,如果不存在,则返回nil。
cwd!()
当前工作目录,错误异常。
返回当前工作目录或引发RuntimeError
。
delete_env(varname)
delete_env(String.t) :: :ok
删除环境变量。
从环境中移除变量varname。
endianness()
返回Endianness。
find_executable(program)
find_executable(binary) :: binary | nil
在系统上定位可执行文件。
该函数在Unix和Windows上使用环境变量PATH查找可执行程序。它还考虑为每个操作系统正确的可执行文件的扩展,所以对于Windows,它会尝试查找与文件.com
,.cmd
或者类似的扩展。
get_env()
get_env() :: %{optional(String.t) => String.t}
返回所有系统环境变量。
返回的值是包含名称-值对的映射。变量名及其值是字符串。
get_env(varname)
get_env(String.t) :: String.t | nil
返回给定环境变量的值。
环境变量varname的返回值是一个字符串,如果环境变量未定义,则返回nil。
get_pid()
get_pid() :: binary
ErlangVM进程标识符。
以操作系统环境最常用的格式返回当前Erlang模拟器的进程标识符。
有关更多信息,请参阅:os.getpid/0
。
halt(status \ 0)
halt(non_neg_integer | binary | :abort) :: no_return
立即停止Erlang运行时系统。
在没有正确关闭应用程序和端口的情况下终止Erlang运行时系统。请stop/1
仔细关闭系统。
status
必须是一个非负整数,原子:abort
或二进制。
- 如果是整数,则运行时系统以返回给操作系统的整数值退出。
- 如果
:abort
,如果在操作系统中启用了核心转储,则运行时系统将中止生成核心转储。
- 由TMPDIR环境变量命名的目录。
- 由temp环境变量命名的目录。
- 由tmp环境变量命名的目录。
C:\TMP
在Windows或/tmp
Unix上
- 作为最后的手段,当前的工作目录
如果以上都不可写,则返回nil
。
tmp_dir!()
可写临时目录,出现错误时出现异常。
同tmp_dir/0
而引起RuntimeError
的,而不是返回nil
,如果没有临时目录设置。
unique_integer(modifiers \ [])
unique_integer([:positive | :monotonic]) :: integer
生成并返回当前运行时实例中唯一的整数。
“Unique”意味着此函数使用相同的列表调用modifiers
,将不会在当前运行时实例上多次返回相同的整数。
如果modifiers
是[]
,则返回唯一的整数(可以是正值或负值)。可以传递其他修饰符来更改返回的整数的属性:
:positive
-返回的整数保证为正整数。
:monotonic
- 返回的整数单调递增。这意味着,在相同的运行时实例上(但即使在不同的进程上),使用:monotonic
修饰符返回的整数总是严格小于连续调用返回值的整数:monotonic
。
上面列出的所有修饰符都可以组合; 重复的修饰符modifiers
将被忽略。
由编译器插入:erlang.unique_integer/1
。
user_home()
用户主目录。
返回用户主目录(独立于平台)。
user_home!()
用户主目录,出现错误异常。
同user_home/0
而引起RuntimeError
的,而不是返回nil
,如果没有用户家里设置。
version()
version() :: String.t
Elixir版本信息。
以二进制形式返回Elixir的版本。