Linux环境变量名中允许的字符

时间:2010-05-12 17:03:58

标签: linux syntax environment-variables

Linux环境变量名称中允许使用哪些字符?我粗略地搜索手册页和网页只会产生有关如何使用变量的信息,但不会产生允许使用哪些名称的信息。

我有一个Java程序,它需要一个包含点的已定义环境变量,如com.example.fancyproperty。使用Windows我可以设置该变量,但我没有运气在linux中设置它(在SuSE和Ubuntu中尝试过)。这个变量名是否允许?

7 个答案:

答案 0 :(得分:173)

来自The Open Group

  

这些字符串具有表格   名称=值; 名称不得包含   字符'='。对于值   便携式跨系统符合   IEEE Std 1003.1-2001,值为   由来自的人物组成   便携式字符集(除了NUL   如下所示)。

因此名称可以包含除=和NUL之外的任何字符,但是:

  

Shell中的实用程序使用的环境变量名称   IEEE标准的实用程序量   1003.1-2001仅由大写字母,数字和'_'组成   (下划线)来自人物   在便携式字符集中定义   不要以数字开头。其他   字符可能被允许   实施;申请书   容忍这些名字的存在。

因此虽然名称可能有效,但除了字母,数字和下划线之外,shell可能不支持任何内容。

答案 1 :(得分:31)

关于shell的POSIX标准 IEEE Std 1003.1-2008 / IEEE POSIX P1003.2/ISO 9945.2 Shell和Tools标准没有定义变量名的词法约定,但是粗略 look at the source显示它使用与

类似的内容

[a-zA-Z_]+[a-zA-Z0-9_]*

(编辑:在第二个字符类中添加了缺少的下划线。)

快速说明,因为有些shell不支持正则表达式中的+,可能是更具可移植性的正则表达式:

[a-zA-Z_]{1,}[a-zA-Z0-9_]{0,}

答案 2 :(得分:10)

我的快速测试显示它们基本上遵循与C变量名称相同的规则,即

  1. a-z,A-Z,_和0-9
  2. 不能以数字开头
  3. 所以这会将.排除在其中。任何非法变量名称都记入unknown command

    这是在ZSH中测试的,它主要与BASH兼容。

答案 3 :(得分:4)

取决于'允许'的含义。

忽略现有的Windows:

环境是一个字符串数组,传递给程序的主函数。如果您阅读execve(2),除了空终止之外,您将看不到这些字符串的要求或限制。

按照惯例,每个字符串由NAME = value组成。没有引用约定,因此在此约定中名称中不能包含“=”。

普通人通过与shell讨论这些字符串来设置这些字符串。每个shell都有自己关于什么是有效变量NAME的想法,所以你必须阅读关于它的内容的手册页,看看它的想法。

通常,像com.baseball.spit = fleagh这样的东西都是Java系统属性,不管某个Java程序是否愿意回退到环境中,最好用-D指定它们。

答案 4 :(得分:2)

这取决于shell。我猜你默认使用bash,在这种情况下允许使用字母,数字和下划线,但你不能用数字启动变量名。截至Bash v.3,periods are not allowed within variable names

答案 5 :(得分:0)

尽管大多数Shell都不允许设置环境变量(如其他答案所述),但是如果需要,您可以使用env(1)使用非标准环境变量执行其他程序。

例如,擦除所有环境并将Strange.Env:Var设置为值foo,然后执行将其打印的perl程序:

env -i Strange.Env:Var=foo perl -MData::Dumper -E 'say Dumper(\%ENV)'

将打印

$VAR1 = {
          'Strange.Env:Var' => 'foo'
        };

答案 6 :(得分:0)

是的,您可以做到。

使用execenv命令实现这一场景。

Docker中的测试治具

docker run -it --rm alpine:3.10

在容器中运行命令:

exec env spring.application_name=happy-variable-name ${SHELL:-/bin/sh}

验证环境变量:

HOSTNAME=bd0bccfdc53b
SHLVL=2
HOME=/root
spring.application_name=happy-variable-name
TERM=xterm
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
PWD=/

使用ps aux验证PID是否更改

PID   USER     TIME  COMMAND
    1 root      0:00 /bin/sh
   12 root      0:00 ps aux

使用python验证环境变量

apk add python
python -c 'import os; print(os.environ["spring.application_name"])'

OUTPUT是happy-variable-name

会发生什么?

  1. Shell调用内置的exec
  2. shell内置exec调用syscall.exec创建进程'env'来替换当前的shell
  3. env进程调用syscall.execvp创建进程'/ bin / sh'来替换env进程

另一种方式

  • Docker映像

如果使用的是docker,则可以在Dockerfile中设置变量

FROM busybox
ENV xx.f%^&*()$#ff=1234
  • Kubernetes配置图

如果您使用的是Kubernetes,则可以通过ConfigMap设置变量

test.yaml

apiVersion: v1
kind: ConfigMap
metadata:
  name: foo-config
data:
  "xx.ff-bar": "1234"

---
apiVersion: v1
kind: Pod
metadata:
  name: foobar
spec:
  containers:
    - name: test-container
      image: k8s.gcr.io/busybox
      command: [ "/bin/sh", "-c", "env" ]
      envFrom:
      - configMapRef:
          name: foo-config
  restartPolicy: Never

部署pod kubectl apply -f test.yaml

验证kubectl logs foobar输出:

xx.ff-bar=1234

ConfigMap允许'-','_'或'。'