达梦基础命令,DM8 SQL语句,备份与恢复【数据库】

达梦:用户 User 即 模式 schema

复制代码
-- 模式就类似于mysql中的数据库
-- 创建用户达梦是默认创建同名的模式
DROP USER IF EXISTS app CASCADE;
-- with admin option:形同于 mysql中的 with grant option
-- 意思是:你创建的这个用户可以给别人继续赋值权限
create user app indentified by "ITcast888!" with admin option;
-- 密码:8位、大小写、数字、特殊字符

-- 给所有的权限
grant dba to app;

-- 切换模式
set schema 模式名称;
-- 在指定用户下创建模式 【可以不用】
create schema 名称 authorization 用户名;

在达梦里:

  • 创建用户 app,会自动生成一个同名的模式 app
  • 模式(SCHEMA)就是存放表、视图、索引的 "文件夹"。

切换模式之后,再建表,表自动创建到 app 用户自己的模式里。

不切模式,表自动创建到 app 用户自己的模式里。CREATE TABLE SYSDBA.student(id int);

字段类型对照

|------|----------------------|---------------------------|-----------------|
| 场景 | MySQL | 达梦 DM8 | 说明 |
| 整数 | INT/BIGINT | 同名支持 | 范围略有差异 |
| 定点数 | DECIMAL(p,s) | DECIMAL/NUMBER | 财务推荐 |
| 浮点数 | FLOAT/DOUBLE | FLOAT/DOUBLE | 非精确 |
| 字符 | VARCHARTEXT | VARCHAR2、VARCHAR、CLOB | TEXTCLOB |
| 二进制 | BLOB/VARBINARY | BLOB/RAW | 大对象用 BLOB |
| 日期时间 | DATETIME/TIMESTAMP | DATE/TIMESTAMP | DATE 含时分秒 |
| 布尔 | BOOLEAN | TINYINT/CHAR(1) | 用 0/1 或 Y/N |

varchar2 和 varchar 有什么区别?

varchar2 是 Oracle 当中主推的类型。

varchar和varchar2

varchar中 '' ≠ null

varchar2中 '' = null

登录

复制代码
# 写绝对路径执行脚本看状态
/home/dmdba/dmdbms/bin/DmServiceDMSERVER status

#登录
disql SYSDBA/Sysdba123@localhost:5236

建表示例

删表

复制代码
drop table if exists app.users;

建表

复制代码
create table app.users(
    id bigint primary key,
    username varchar2(50) not null,
    email varchar2(200) unique,
    status char(1) default 'a' check (status in ('a','d')),
    created_at timestamp default current_timestamp
);

看表

复制代码
select table_name from dba_tables where owner='APP';
select * from users;

创建序列(自增主键)

复制代码
create sequence app.auto_increments
start with 1
increment by 2
nocache
no cycle;
  • create sequence app.auto_incrementsapp模式下,创建名为auto_increments的序列。
  • start with 1序列初始值:从数字 1 开始。
  • increment by 2每次取值自增 2,取值依次为:1 → 3 → 5 → 7...... 只生成奇数。
  • nocache不缓存序列号。每次都从数据库读取最新值,避免并发场景下出现序号跳号。
  • no cycle序号达到最大值后不再循环,再次取值会直接报错。

删除序列

复制代码
drop sequence auto_increments;

插入数据

复制代码
insert into app.users(id,username,email)
values (app.seq_users.nextval,'alice','a@x.com');

insert into app.users(id,username,email)
values (app.seq_users.nextval,'bob','b@x.com');
  1. 第一次执行 app.seq_users.nextval拿到数字:1,序列内部计数器变成 2
  2. 第二次再执行 app.seq_users.nextval拿到数字:2,计数器变成 3

正好用来给主键 ID 自动生成 1、2、3、4...... 自增编号。

复制代码
select * from app.users;

select app.seq_users.currval as last_id from dual;
  • currval:读取当前会话里刚刚拿到的序列号,不会让序号继续增长。
  • as last_id:给查询结果列起别名。
  • from dual:达梦 / Oracle 必须带的虚拟空表。

用途:刚插入完一条数据,立刻拿到这条记录的自增主键 ID。

查询五子句

复制代码
#分组统计每个状态的人数
select status,count(*) as cnt
from app.users
group by status;

#只保留数量大于 1 的分组
select status,count(*) as cnt
from app.users
group by status
having count(*) >1;

#按创建时间倒序排列
select id,username,users.created_at
from app.users
order by created_at desc;

#分页查询:跳过前 10 条,再取出后面 5 条
select id,username,users.created_at
from app.users
order by created_at asc
offset 10 rows fetch next 5 rows only;
  • offset 10 rows:跳过前 10 行;

  • fetch next 5 row only:只读取接下来的 5 行;

    select * from users limit 0,2;
    select * from users limit 2,2;
    select * from users limit 3;
    select * from users offset 4 rows fetch next 3 rows only;
    select * from users order by id fetch next 3 rows only;

    select rownum from users;
    select rownum from stus;
    select rownum from users2;

    select * from (select *,rownum rn from users) w
    where w.rn between 1 and 2;

    select * from (select *,rownum rn from users) w
    where w.rn = 2;

rownum 是 Oracle / 达梦的伪列,会给每一行自动生成行号 1,2,3......

核心知识点(rownum 陷阱)

  1. rownum 是动态生成的,只能用:
    • rownum < N
    • rownum <= N
    • rownum = 1
  2. 直接写 rownum=2rownum>2 查不出结果,必须把行号放到子查询里变成普通字段,再在外层过滤。

多表查询

建表

复制代码
CREATE TABLE app.orders (
  id          INT PRIMARY KEY,             -- 订单ID
  user_id     INT NOT NULL,                -- 下单用户ID,外键关联 users.id
  amount      DECIMAL(12,2) NOT NULL,         -- 订单金额
  status      CHAR(1) , 
  -- N=新建, P=已支付, C=已取消
  created_at  TIMESTAMP,
  CONSTRAINT fk_orders_user FOREIGN KEY (user_id)
    REFERENCES app.users(id)
);

-- 插入一些订单
INSERT INTO app.orders (id, user_id, amount, status)
VALUES (1001, 1, 99.90, 'P');

INSERT INTO app.orders (id, user_id, amount, status)
VALUES (1002, 2, 199.50, 'N');               -- 用户必须存在

INSERT INTO app.orders (id, user_id, amount, status)
VALUES (1003, 2, 49.99, 'C');

内连接

复制代码
SELECT u.username, o.amount
FROM app.users u
INNER JOIN app.orders o ON u.id = o.user_id;
  • 效果:只查询同时存在用户和对应订单的数据;
  • 没有订单的用户,不会出现在结果集中。

左连接

复制代码
SELECT u.username, o.amount
FROM app.users u
LEFT JOIN app.orders o ON u.id = o.user_id;
  • 效果:以左表 users 为主,所有用户全部保留;
  • 没有订单的用户,订单字段会显示为 NULL

子查询

查出金额大于 100 元订单的用户 ID,再找出这些用户的姓名。

复制代码
SELECT username
FROM app.users
WHERE id IN (SELECT user_id FROM app.orders WHERE amount > 100);

自关联

自关联就是一张表自己和自己 JOIN,一张表起两个不同别名。以订单表举例:查询同一个用户下金额更大的订单记录

复制代码
SELECT o1.*, o2.amount
FROM app.orders o1
JOIN app.orders o2
  ON o1.user_id = o2.user_id
  AND o1.amount < o2.amount;

用户与权限

创建用户与授权

复制代码
-- 创建用户 report,密码带大小写+特殊字符,双引号严格保留格式
CREATE USER report IDENTIFIED BY "Report123!";

-- 授予登录数据库的会话权限
GRANT CREATE SESSION TO report;

-- 授予 report 用户只能查询 app.users 这张表,不能增删改
GRANT SELECT ON app.users TO report;
  • 系统权限(用户、角色、会话、建库建表权限)→ 用 with admin option
  • 表 / 视图的增删改查权限 → 用 with grant option

app 用户授予一系列开发常用权限,让该账号可以登录数据库、创建模式、建表、视图、序列、触发器,满足日常开发需求。

复制代码
-- 允许用户登录数据库,建立会话连接
GRANT CREATE SESSION TO app;

-- 允许用户创建自己的模式(schema)
GRANT CREATE SCHEMA TO app;

-- 允许创建数据表
GRANT CREATE TABLE TO app;
-- 允许创建视图
GRANT CREATE VIEW TO app;
-- 允许创建序列(自增主键用)
GRANT CREATE SEQUENCE TO app;
-- 允许创建触发器
GRANT CREATE TRIGGER TO app;
权限 作用
CREATE SESSION 核心登录权限,没有这条,用户无法连接数据库
CREATE SCHEMA 可以新建自定义模式
CREATE TABLE 在自己模式下建表
CREATE VIEW 基于数据表创建视图
CREATE SEQUENCE 创建自增序列,实现主键自增
CREATE TRIGGER 编写触发器,实现数据自动联动

系统权限统一使用 WITH ADMIN OPTION

复制代码
-- 允许创建存储过程、自定义函数
GRANT CREATE PROCEDURE TO app;

-- 允许在自己的表上创建索引
GRANT CREATE INDEX TO app;

-- 或
GRANT RESOURCE TO app;
GRANT CREATE SESSION TO app;
  • CREATE PROCEDURE:系统权限,用来编写存储过程、函数,封装复杂业务逻辑。
  • CREATE INDEX:允许给数据表建立索引,优化查询速度。

角色

角色(role)就是权限打包容器:把一堆权限先放进角色里,再把角色分配给多个用户,不用一条条给每个用户单独授权,批量管理权限。

复制代码
-- 1. 创建角色
create role app_dev;

-- 2. 给角色授予权限(把权限打包进角色)
grant create session, create table, create sequence to app_dev;
grant select on app.users to app_dev;

-- 3. 把角色分配给用户,用户自动继承角色内所有权限
grant app_dev to app;
grant app_dev to report;
  • 权限 → 授予给角色

  • 角色 → 授予给用户

  • 用户 = 自身直接权限 + 所有被分配角色的权限

    -- 回收用户身上的角色
    revoke app_dev from report;

    -- 删除角色
    drop role app_dev;

回收权限

回收 report 用户对 app.users 这张表的查询(SELECT)对象权限

复制代码
REVOKE SELECT ON app.users FROM report;

对象权限 + WITH GRANT OPTION,回收时会连带级联回收

执行后:

  • report 自身权限被收回
  • test 从 report 获得的同一张表查询权限也会自动消失

对比:系统权限 WITH ADMIN OPTION 回收不会级联下级权限。

查询这条权限是否生效

复制代码
-- 管理员查看
select grantee,table_name,privilege,grantable
from dba_tab_privs
where table_owner='APP' and table_name='USERS';

GRANTABLE 字段会显示为 YES,代表支持转授。

查看权限

user_tab_privs 是数据字典视图,用来查看当前登录用户自己拥有的所有表对象权限(SELECT、INSERT、UPDATE、DELETE 等

复制代码
-- 查看所有的
select  * from user_tab_privs;

三条同类字典视图区别

  1. user_tab_privs只看当前自己账号拥有的表权限。

  2. all_tab_privs查看当前用户自己 + 被授予角色带来的所有表权限。

  3. dba_tab_privs管理员视图,查看全库所有用户的表权限(需要 DBA 权限才能查询)

修改权限

复制代码
grant 新权限 on 模式.表名 to 用户名
grant 新权限 to 用户名;

限定用户信息

复制代码
-- 允许哪些ip使用app用户登录
ALTER USER APP ALLOW_IP '192.168.1.10','192.168.1.11';
-- 用户只能查,不能增删改任何表
ALTER USER APP READ ONLY;
-- 恢复正常读写
ALTER USER APP NOT READ ONLY;

备份与恢复

导出命令:/home/dmdba/dmdbms/bin/dexp

导入命令:/home/dmdba/dmdbms/bin/dimp

备份存放:/home/dmdba/backup/

dexp导出工具(逻辑备份)

复制代码
mkdir -p /home/dmdba/backup
chown dmdba:dmdba /home/dmdba/backup
chmod 700 /home/dmdba/backup

su - dmdba
# 注意:密码中千万别带@
/home/dmdba/dmdbms/bin/dexp app/'ITcast888!'@127.0.0.1:5236 \
  FILE=/home/dmdba/backup/app_$(date +%F).dmp \
  LOG=/home/dmdba/backup/app_$(date +%F).log

-- 如果只导出某个模式,可以添加 schemas=模式名称

  • -p:多级目录自动创建,不报错
  • chown:把文件夹归属改为数据库运行用户 dmdba
  • 700:仅 dmdba 可读写,安全权限

必须 dmdba 用户执行导出工具,root 会环境异常。

  • SCHEMAS=APP:只导出 APP 这一个模式(用户)
  • $(date +%F):自动拼接当天日期
  • 注意:密码里不能包含@,会被 Shell 截断

dimp导入

复制代码
/home/dmdba/dmdbms/bin/dimp app/'ITcast888!'@127.0.0.1:5236 FILE=/home/dmdba/backup/备份生成的文件名.dmp LOG=/home/dmdba/backup/备份生成的文件名.log FULL=y

FULL=Y 全量完全导入:把 dmp 里所有对象(用户、表、数据、视图、序列、存储过程)全部恢复到库中