ORACLE、MySQL、PostgreSQL 客户端 sqlplus,mysql,psql 常用命令对比(二)

上接:ORACLE、MySQL、PostgreSQL 客户端 sqlplus,mysql,psql 常用命令对比(一),在对比了客户端的安装以及连接数据库区别。现在连接上数据库之后就是进一步的操作了,然而连上数据库之后首先看到的就是提示符,那本篇就从定制提示符开始吧。本来之前都是通过一种方式来配置提示符,没想到提示符的配置也比较复杂,mysql 竟然可以通过3种方式来实现。那这篇文章就讲一下三种数据库的提示符相关的知识。

默认提示符

默认情况下 sqlplus、mysql、psql 的提示符都很简单,如下:

image-20240120193039196

sqlplus 默认提示符为: SQL>

mysql 默认提示符为:mysql>

psql 默认提示:[dbname]=# 默认的数据库是postgrespostgres=#

既然要定制提示符,那我们就得知道提示符的配置在哪里,下面是三种数据库的提示符的配置。

提示符配置

sqlplus 提示符配置

sqlplus 提示符配置可以通过配置文件或者通过命令直接修改

配置文件有两种:

一个是全局配置文件(Site Profile) :$ORACLE_HOME/sqlplus/admin/glogin.sql,从任意位置登录sqlplus 都生效

一个是用户配置文件(User Profile):ORACLE_PATH 环境变量下的 login.sql,Note:SQL*Plus will no longer search for login.sql in the current directory. 通过查询官方手册 发现在11g的版本是当前目录下查找 login.sql,12c之后是依赖ORACLE_PATH 环境变量。但是我在11204版本的时候测试也是依赖ORACLE_PATH 环境变量的。

参考Configuring SQL*Plus 手册 [^1]

可以看到 ORACLE 官方写 SQL*Plus User’s Guide and Reference 洋洋洒洒竟然有300多页。

sqlplus 除了修改配置文件之外,也可以通过 SET SQLPROMPT 命令直接指定当前的提示符。

1
2
SQL> SET SQLPROMPT "_USER'@'_CONNECT_IDENTIFIER _DATE> "
SYS@ora19cl 2024-01-20 06:24:13>

mysql 提示符配置

mysql 提示符配置文件为:MySQL 配置文件的[mysql]标签,MySQL的配置文件可以存在多个位置依次为:/etc/my.cnf/etc/mysql/my.cnf/usr/local/mysql/etc/my.cnf~/.my.cnf

同样 mysql 除了通过参数文件设置 提示符之外,也可以直接通过prompt set \u@\d \r:\m:\s> 直接设置,他跟参数文件的配置有一点区别,配置文件是 key = value 的形式,比如:prompt = "\u@mysqldb \R:\m:\s [\d]> "但是通过命令行设置是 prompt set \u@\d \r:\m:\s>

mysql 除了通过配置参数文件、命令行直接修改之外也可以通过 mysql --prompt 来指定,类似如下:

1
mysql --prompt="\u@iasmmysql currentdb is [\d]> "

实际上在写这篇文章的时候,我只知道是通过参数文件来进行配置的,但是为了这篇文章,我又重新查看了官方手册,发现是可以通过3 种方式实现的:

You can set the prompt in several ways:

  • Use an environment variable. You can set the MYSQL_PS1 environment variable to a prompt string. For example:

    1
    2
    export MYSQL_PS1="(\u@\h) [\d]> "
    (liups@127.0.0.1) [mesdb]>
  • Use a command-line option. You can set the --prompt option on the command line to mysql. For example:

    1
    2
    $> mysql --prompt="(\u@\h) [\d]> "
    (liups@127.0.0.1) [mesdb]>
  • Use an option file. You can set the prompt option in the [mysql] group of any MySQL option file, such as /etc/my.cnf or the .my.cnffile in your home directory. For example:

    1
    2
    [mysql]
    prompt=(\\u@\\h) [\\d]>\\_

    参考 mysql Client Commands 官方手册 [^2]

其中 mysql 的提示符竟然可以通过 OS 的 MYSQL_PS1 变量来设置。

psql 提示符配置

psql 提示符配置文件:~/.psqlrc 也就是当前用户的家目录下 .psqlrc 文件。

定制提示符

定制 sqlplus 提示符

ORACLE 的 sqlplus 提示符是由 SQLPROMPT 控制的,通过 show SQLPROMPT 可以查看当前的默认配置,

1
2
SQL> show SQLPROMPT
sqlprompt "SQL> "

可以看到目前的提示符就是SQL> ,可以通过define可以查看当前的提示符的系统变量。

1
2
3
4
5
6
7
8
9
10
SQL> define
DEFINE _DATE = "2024-01-19 20:18:24" (CHAR)
DEFINE _CONNECT_IDENTIFIER = "dbo19c_high" (CHAR)
DEFINE _USER = "ADMIN" (CHAR)
DEFINE _PRIVILEGE = "" (CHAR)
DEFINE _SQLPLUS_RELEASE = "1918000000" (CHAR)
DEFINE _EDITOR = "vi" (CHAR)
DEFINE _O_VERSION = "Oracle Database 19c Enterprise Edition Release 19.0.0.0.0 - Production
Version 19.22.0.1.0" (CHAR)
DEFINE _O_RELEASE = "1922000100" (CHAR)

也就是上面的 _DATE_CONNECT_IDENTIFIER 等信息是可以直接拿来使用的,可以直接写到配置文件中,首先那我们先看下默认的配置文件的模样。使用cat 命令进行查看。

cat $ORACLE_HOME/sqlplus/admin/glogin.sql

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
--
-- Copyright (c) 1988, 2005, Oracle. All Rights Reserved.
--
-- NAME
-- glogin.sql
--
-- DESCRIPTION
-- SQL*Plus global login "site profile" file
--
-- Add any SQL*Plus commands here that are to be executed when a
-- user starts SQL*Plus, or uses the SQL*Plus CONNECT command.
--
-- USAGE
-- This script is automatically run
--

可以看到这里都是注释,描述的用途和用法,也就是这里的内容会自动运行。

比如最简单的配置:SET SQLPROMPT "_USER'@'_CONNECT_IDENTIFIER _DATE> "

_DATE :当前时间、_CONNECT_IDENTIFIER 连接标识、_USER:用户名

可以在 sqlplus 直接 通过 set SQLPROMPT 设置对当前session生效,也可以修改配置文件永久生效。

1
SET SQLPROMPT "_USER'@'_CONNECT_IDENTIFIER _DATE> "

美化后的效果如下:

1
SYS@ora19cl 2024-01-19 22:02:13>

可以能当前时间太长,可以去掉,就使用SET SQLPROMPT "_USER'@'_CONNECT_IDENTIFIER> "

美化效果如下:

1
2
SQL> SET SQLPROMPT "_USER'@'_CONNECT_IDENTIFIER> "
SYS@ora19cl>

其中配置文件和通过命令直接设置的语法是一致的。都是 set SQLPROMPT

以上是通过拼接系统自带的变量来进行定制,实际上 还支持通过 sql 语句进行拼接。

以下定制提示符是转自:OracleBlog – 笑看数据库江湖的那些事儿……的 12c的sqlplus提示符,就是根据sql 语句查询出当前的数据库是PDB还是PDB等信息。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
define_editor=vi
set timing on
set serveroutput on size 100000
set linesize 100
set trimspool on
set long 5000
set termout off
default gname=idle
column global_name new_value gname
SELECT lower(USER) || '@' ||
case (select cdb from v$database)
when 'NO' then
(select upper(instance_name) from v$instance) || '[NON-CDB]'
when 'YES' then
decode(sys_Context('userenv', 'con_Name'),
'CDB$ROOT',
(select upper(instance_name) from v$instance) || '[CDB]',
sys_Context('userenv', 'con_Name') || '[PDB]')
end || '(' ||
nvl(UTL_INADDR.GET_HOST_ADDRESS,
SYS_CONTEXT('userenv', 'ip_address')) || ')' GLOBAL_NAME
FROM v$instance;
set sqlprompt '&gname> '
set termout on

效果如下:

CDB

1
sys@ORCL1[CDB](172.20.22.127)>

PDB

1
sys@PDBMES[PDB](172.20.22.127)>

可以显示用户,登录的PDB/CDB 数据库,并且增加了 CDB/PDB的标识,并且还显示当前的ip信息。可以说是非常完善了。

定制 mysql 提示符

prompt 命令用于重新配置默认的 mysql> 提示符,可用于定义提示符的字符串可以包含以下特殊序列。

下面表格引用自 mysql Client Commands 官方手册 [2] 。

Option Description
\C The current connection identifier
\c A counter that increments for each statement you issue
\D The full current date
\d The default database
\h The server host
\l The current delimiter
\m Minutes of the current time
\n A newline character
\O The current month in three-letter format (Jan, Feb, …)
\o The current month in numeric format
\P am/pm
\p The current TCP/IP port or socket file
\R The current time, in 24-hour military time (0–23)
\r The current time, standard 12-hour time (1–12)
\S Semicolon
\s Seconds of the current time
\T Print an asterisk (*) if the current session is inside a transaction block (from MySQL 8.0.28)
\t A tab character
\U Your full *user_name*@*host_name* account name
\u Your user name
\v The server version
\w The current day of the week in three-letter format (Mon, Tue, …)
\Y The current year, four digits
\y The current year, two digits
\_ A space
\ A space (a space follows the backslash)
\' Single quote
\" Double quote
\\ A literal \ backslash character
\*x* x, for any “*x*” not listed above

虽然 mysql 的提示符支持30个选项,其实真正需要的就那么几个比如,用户、数据库、时间、主机等。

用户区分 /U/u ,其中 /U :完整的用户名@hostname形式。

1
mes@iasmmysql currentdb is [mesdb] mes@localhost >
1
prompt = "\u@mysqldb \R:\m:\s [\d]> "

mysql 通过配置文件和命令行设置是有区别的,上面有写,这个需要注意。

这里单独看一下 export MYSQL_PS1="(\u@\h) [\d]> ",这是操作系统一个变量,可以用来配置mysql 客户端的提示符,这个跟 OS 的 PS1 类似。

定制 psql 提示符

psql 是通过配置.psqlrc文件(linux平台)来定制 psql 提示符。

.psqlrc文件
cd
vi .psqlrc 对配置文件进行编辑,有3个变量 PROMPT1PROMPT2PROMPT3 进行控制。

PROMPT1 是 psql 请求一个新命令时的使用的正常提示符。
PROMPT2 是在一个命令输入期待更多输入时(因为查询没有用一个分号结束或者引号没有关闭)显示的提示符。
PROMPT3 在你运行一个 SQL COPY 命令和等待你在终端上键入记录时使用。

常用的选项有下面几个,来自官方手册 [^3]

  • %M The full host name (with domain name) of the database server, or [local] if the connection is over a Unix domain socket, or [local:/dir/name], if the Unix domain socket is not at the compiled in default location.
  • %> The port number at which the database server is listening.
  • %n The database session user name. (The expansion of this value might change during a database session as the result of the command SET SESSION AUTHORIZATION.)
  • %/ The name of the current database.
  • %# If the session user is a database superuser, then a #, otherwise a >. (The expansion of this value might change during a database session as the result of the command SET SESSION AUTHORIZATION.)
  • %x Transaction status: an empty string when not in a transaction block, or * when in a transaction block, or ! when in a failed transaction block, or ? when the transaction state is indeterminate (for example, because there is no connection).
1
2
3
\set PROMPT1 '%`date +%H:%M:%S` (%n@%M:%>)%/%R%#%x'
\set PROMPT2 '%M %n@%/%R %# '
20:38:04 (postgres@[local]:5432)postgres=#

psql 与众不同的一点是可以设置颜色

1
2
\set PROMPT1 '%M:%[%033[1;31m%]%>%[%033[0m%] %n@%[%033[1;33m%]%/%[%033[0m%]%R%#%x '
\set PROMPT2 '%M %n@%[%033[1;33m%]%/%[%033[0m%] %[%033[1;31m%]%R %[%033[0m%]%# '

效果如下图所示:

image-20240120210103253

其中端口号设置红色,数据库的名称设置为黄色,PROMPT2 未完成的查询有红色的 - 代替了原来的 =

总结:

三种数据库的提示符都可以通过在当前session 进行设置,其中 :

sqlplus 是SET SQLPROMPT

mysql 是:prompt set \u@\d \r:\m:\s>

psql 是:\set PROMPT1 '%date +%H:%M:%S (%n@%M:%>)%/%R%#%x'

注意⚠️: sqlplus 是 SET SQLPROMPT ,mysql 是 prompt set,关键词一个是 SQLPROMPT 一个是 prompt,其中 sqlplus 是 set 在前,mysql 是 set在后,而psql 呢,又不一样,他set的时候需要前面有一个 \ 然后 set PROMPT1/PROMPT3/PROMPT3`,有3个关键词。

提示符的格式基本上是:用户、库名、时间、连接方式等的拼接,oracle 的sqlplus 提示又比较复杂支持通过sql语句进行拼接。

plsql 是支持设置不同的颜色,目前没有发现 sqlplus 和mysql 支持定制颜色。

参考资料

[1]:https://docs.oracle.com/en/database/oracle/oracle-database/12.2/sqpug/configuring-SQL-Plus.html “configuring-SQL-Plus”
[2]:https://www.postgresql.org/docs/current/app-psql.html#APP-PSQL-PROMPTING “psql PROMPTING “
[3]:https://dev.mysql.com/doc/refman/8.0/en/mysql-commands.html “mysql-commands “