{
    "mode": "info",
    "parameter": "test",
    "section": "",
    "url": "https://www.chedong.com/phpMan.php/info/test/json",
    "generated": "2026-07-30T17:07:50Z",
    "sections": {
        "File: coreutils.info,  Node: test invocation,  Next: expr invocation,  Prev: true invocation,  Up: Conditions": {
            "content": "",
            "subsections": [
                {
                    "name": "16.3 'test': Check file types and compare values",
                    "content": "'test' returns a status of 0 (true) or 1 (false) depending on the\nevaluation of the conditional expression EXPR.  Each part of the\nexpression must be a separate argument.\n\n'test' has file status checks, string operators, and numeric\ncomparison operators.\n\n'test' has an alternate form that uses opening and closing square\nbrackets instead a leading 'test'.  For example, instead of 'test -d /',\nyou can write '[ -d / ]'.  The square brackets must be separate\narguments; for example, '[-d /]' does not have the desired effect.\nSince 'test EXPR' and '[ EXPR ]' have the same meaning, only the former\nform is discussed below.\n\nSynopses:\n\ntest EXPRESSION\ntest\n[ EXPRESSION ]\n[ ]\n[ OPTION\n\nDue to shell aliases and built-in 'test' functions, using an\nunadorned 'test' interactively or in a script may get you different\nfunctionality than that described here.  Invoke it via 'env' (i.e., 'env\ntest ...') to avoid interference from the shell.\n\nIf EXPRESSION is omitted, 'test' returns false.  If EXPRESSION is a\nsingle argument, 'test' returns false if the argument is null and true\notherwise.  The argument can be any string, including strings like '-d',\n'-1', '--', '--help', and '--version' that most other programs would\ntreat as options.  To get help and version information, invoke the\ncommands '[ --help' and '[ --version', without the usual closing\nbrackets.  *Note Common options::.\n\nExit status:\n\n0 if the expression is true,\n1 if the expression is false,\n2 if an error occurred.\n\n* Menu:\n\n* File type tests::             -[bcdfhLpSt]\n* Access permission tests::     -[gkruwxOG]\n* File characteristic tests::   -e -s -nt -ot -ef\n* String tests::                -z -n = == !=\n* Numeric tests::               -eq -ne -lt -le -gt -ge\n* Connectives for test::        ! -a -o\n"
                }
            ]
        },
        "File: coreutils.info,  Node: File type tests,  Next: Access permission tests,  Up: test invocation": {
            "content": "",
            "subsections": []
        },
        "These options test for particular types of files.  (Everything's a file,": {
            "content": "but not all files are the same!)\n\n'-b FILE'\nTrue if FILE exists and is a block special device.\n\n'-c FILE'\nTrue if FILE exists and is a character special device.\n\n'-d FILE'\nTrue if FILE exists and is a directory.\n\n'-f FILE'\nTrue if FILE exists and is a regular file.\n\n'-h FILE'\n'-L FILE'\nTrue if FILE exists and is a symbolic link.  Unlike all other\nfile-related tests, this test does not dereference FILE if it is a\nsymbolic link.\n\n'-p FILE'\nTrue if FILE exists and is a named pipe.\n\n'-S FILE'\nTrue if FILE exists and is a socket.\n\n'-t FD'\nTrue if FD is a file descriptor that is associated with a terminal.\n",
            "subsections": []
        },
        "File: coreutils.info,  Node: Access permission tests,  Next: File characteristic tests,  Prev: File type tests,  Up: test invocation": {
            "content": "These options test for particular access permissions.\n\n'-g FILE'\nTrue if FILE exists and has its set-group-ID bit set.\n\n'-k FILE'\nTrue if FILE exists and has its \"sticky\" bit set.\n\n'-r FILE'\nTrue if FILE exists and read permission is granted.\n\n'-u FILE'\nTrue if FILE exists and has its set-user-ID bit set.\n\n'-w FILE'\nTrue if FILE exists and write permission is granted.\n\n'-x FILE'\nTrue if FILE exists and execute permission is granted (or search\npermission, if it is a directory).\n\n'-O FILE'\nTrue if FILE exists and is owned by the current effective user ID.\n\n'-G FILE'\nTrue if FILE exists and is owned by the current effective group ID.\n",
            "subsections": []
        },
        "File: coreutils.info,  Node: File characteristic tests,  Next: String tests,  Prev: Access permission tests,  Up: test invocation": {
            "content": "These options test other file characteristics.\n\n'-e FILE'\nTrue if FILE exists.\n\n'-s FILE'\nTrue if FILE exists and has a size greater than zero.\n\n'FILE1 -nt FILE2'\nTrue if FILE1 is newer (according to modification date) than FILE2,\nor if FILE1 exists and FILE2 does not.\n\n'FILE1 -ot FILE2'\nTrue if FILE1 is older (according to modification date) than FILE2,\nor if FILE2 exists and FILE1 does not.\n\n'FILE1 -ef FILE2'\nTrue if FILE1 and FILE2 have the same device and inode numbers,\ni.e., if they are hard links to each other.\n\n'-N FILE'\nTrue if FILE exists and has been modified (mtime) since it was last\nread (atime).\n",
            "subsections": []
        },
        "File: coreutils.info,  Node: String tests,  Next: Numeric tests,  Prev: File characteristic tests,  Up: test invocation": {
            "content": "",
            "subsections": []
        },
        "These options test string characteristics.  You may need to quote STRING": {
            "content": "arguments for the shell.  For example:\n\ntest -n \"$V\"\n\nThe quotes here prevent the wrong arguments from being passed to\n'test' if '$V' is empty or contains special characters.\n\n'-z STRING'\nTrue if the length of STRING is zero.\n\n'-n STRING'\n'STRING'\nTrue if the length of STRING is nonzero.\n\n'STRING1 = STRING2'\nTrue if the strings are equal.\n\n'STRING1 == STRING2'\nTrue if the strings are equal (synonym for =).\n\n'STRING1 != STRING2'\nTrue if the strings are not equal.\n",
            "subsections": []
        },
        "File: coreutils.info,  Node: Numeric tests,  Next: Connectives for test,  Prev: String tests,  Up: test invocation": {
            "content": "",
            "subsections": []
        },
        "Numeric relational operators.  The arguments must be entirely numeric": {
            "content": "(possibly negative), or the special expression '-l STRING', which\nevaluates to the length of STRING.\n\n'ARG1 -eq ARG2'\n'ARG1 -ne ARG2'\n'ARG1 -lt ARG2'\n'ARG1 -le ARG2'\n'ARG1 -gt ARG2'\n'ARG1 -ge ARG2'\nThese arithmetic binary operators return true if ARG1 is equal,\nnot-equal, less-than, less-than-or-equal, greater-than, or\ngreater-than-or-equal than ARG2, respectively.\n\nFor example:\n\ntest -1 -gt -2 && echo yes\n=> yes\ntest -l abc -gt 1 && echo yes\n=> yes\ntest 0x100 -eq 1\nerror-> test: integer expression expected before -eq\n",
            "subsections": []
        },
        "File: coreutils.info,  Node: Connectives for test,  Prev: Numeric tests,  Up: test invocation": {
            "content": "",
            "subsections": []
        },
        "Note it's preferred to use shell logical primitives rather than these": {
            "content": "logical connectives internal to 'test', because an expression may become\nambiguous depending on the expansion of its parameters.\n\nFor example, this becomes ambiguous when '$1' is set to ''!'' and\n'$2' to the empty string '''':\n\ntest \"$1\" -a \"$2\"\n\nand should be written as:\n\ntest \"$1\" && test \"$2\"\n\nNote the shell logical primitives also benefit from short circuit\noperation, which can be significant for file attribute tests.\n\n'! EXPR'\nTrue if EXPR is false.  '!' has lower precedence than all parts of\nEXPR.  Note '!' needs to be specified to the left of a binary\nexpression, I.e., ''!' 1 -gt 2' rather than '1 '!' -gt 2'.  Also\n'!' is often a shell special character and is best used quoted.\n\n'EXPR1 -a EXPR2'\nTrue if both EXPR1 and EXPR2 are true.  '-a' is left associative,\nand has a higher precedence than '-o'.\n\n'EXPR1 -o EXPR2'\nTrue if either EXPR1 or EXPR2 is true.  '-o' is left associative.\n",
            "subsections": []
        }
    },
    "flags": [],
    "examples": [],
    "see_also": []
}