From b43796334088f772a8c834eeef3b36305a053d7d Mon Sep 17 00:00:00 2001 From: Midoria7 Date: Tue, 24 Dec 2024 23:45:31 +0800 Subject: [PATCH] feat(lab7-transaction): implement transaction management This commit finalizes the implementation of lab 7, which is focused on transaction management within the database. The following files have been created to demonstrate and manage various aspects of transaction control and recovery: - run.sh: A shell script to execute the SQL statements for transaction management. - sql/1-1-check_violation.sql: SQL statement to check for transaction violations. - sql/1-2-commit_and_rollback.sql: SQL statement to demonstrate commit and rollback operations. - sql/1-3-schema_modification.sql: SQL statement for schema modifications within transactions. - sql/1-4-data_modifications.sql: SQL statement for data modifications within transactions. - sql/1-5-savepoint.sql: SQL statement to set and manage savepoints within transactions. - sql/1-6-failure.sql: SQL statement to simulate transaction failures. - sql/2-1-read_committed.sql: SQL statement to demonstrate the read committed isolation level. - sql/2-2-repeatable_read.sql: SQL statement to demonstrate the repeatable read isolation level. - sql/3-deadlock.sql: SQL statement to simulate and handle deadlock situations. - sql/init.sql: SQL statement to initialize the database for transaction management experiments. - 4-1-backup.sh: Shell script to perform database backup operations. - 4-2-recover.sh: Shell script to recover the database from a backup in case of failure. These scripts and configurations are essential for ensuring data integrity and consistency through proper transaction handling. --- lab7-transaction/4-1-backup.sh | 11 +++++ lab7-transaction/4-2-recover.sh | 13 ++++++ lab7-transaction/run.sh | 46 +++++++++++++++++++ lab7-transaction/sql/1-1-check_violation.sql | 5 ++ .../sql/1-2-commit_and_rollback.sql | 17 +++++++ .../sql/1-3-schema_modification.sql | 27 +++++++++++ .../sql/1-4-data_modifications.sql | 13 ++++++ lab7-transaction/sql/1-5-savepoint.sql | 13 ++++++ lab7-transaction/sql/1-6-failure.sql | 7 +++ lab7-transaction/sql/2-1-read_committed.sql | 34 ++++++++++++++ lab7-transaction/sql/2-2-repeatable_read.sql | 34 ++++++++++++++ lab7-transaction/sql/3-deadlock.sql | 22 +++++++++ lab7-transaction/sql/init.sql | 24 ++++++++++ 13 files changed, 266 insertions(+) create mode 100644 lab7-transaction/4-1-backup.sh create mode 100644 lab7-transaction/4-2-recover.sh create mode 100644 lab7-transaction/run.sh create mode 100644 lab7-transaction/sql/1-1-check_violation.sql create mode 100644 lab7-transaction/sql/1-2-commit_and_rollback.sql create mode 100644 lab7-transaction/sql/1-3-schema_modification.sql create mode 100644 lab7-transaction/sql/1-4-data_modifications.sql create mode 100644 lab7-transaction/sql/1-5-savepoint.sql create mode 100644 lab7-transaction/sql/1-6-failure.sql create mode 100644 lab7-transaction/sql/2-1-read_committed.sql create mode 100644 lab7-transaction/sql/2-2-repeatable_read.sql create mode 100644 lab7-transaction/sql/3-deadlock.sql create mode 100644 lab7-transaction/sql/init.sql diff --git a/lab7-transaction/4-1-backup.sh b/lab7-transaction/4-1-backup.sh new file mode 100644 index 0000000..3c21879 --- /dev/null +++ b/lab7-transaction/4-1-backup.sh @@ -0,0 +1,11 @@ +#!/bin/sh + +sudo su - opengauss + +gs_ctl start + +mkdir -p ~/backup +gs_basebackup -D ~/backup -p 7654 + +cd ~/backup || exit 1 +ls diff --git a/lab7-transaction/4-2-recover.sh b/lab7-transaction/4-2-recover.sh new file mode 100644 index 0000000..292836e --- /dev/null +++ b/lab7-transaction/4-2-recover.sh @@ -0,0 +1,13 @@ +#!/bin/sh + +sudo su - opengauss + +gs_ctl stop + +cd ~/data || exit 1 +ls + +rm -rf ./* +ls + +cp -r ~/backup/. . diff --git a/lab7-transaction/run.sh b/lab7-transaction/run.sh new file mode 100644 index 0000000..ec32ced --- /dev/null +++ b/lab7-transaction/run.sh @@ -0,0 +1,46 @@ +#!/bin/sh + +# config +db_hostname=127.0.0.1 +db_port=7654 +db_name="buptlab_database" +db_user="bupt_dba" +db_password="i_am_from_bupt666" +sql_dir="./lab7-transaction/sql" + +# check arguments +if [ $# -ne 1 ]; then + echo "Usage: $0 " + exit 1 +fi +task_id=$1 + +# get the sql filepath +sql_filepath="${sql_dir}/${task_id}.sql" + +# check if the file exists +if [ ! -f "${sql_filepath}" ]; then + echo "Error: File does not exist - ${sql_filepath}" + exit 1 +fi + +# create two copy +gsql \ + --host="${db_hostname}" \ + --port="${db_port}" \ + -d "${db_name}" \ + --username="${db_user}" \ + --password="${db_password}" \ + -echo-all \ + -f "./lab7-transaction/sql/init.sql" \ + >/dev/null + +# execute the sql +gsql \ + --host="${db_hostname}" \ + --port="${db_port}" \ + -d "${db_name}" \ + --username="${db_user}" \ + --password="${db_password}" \ + -echo-all \ + -f "${sql_filepath}" diff --git a/lab7-transaction/sql/1-1-check_violation.sql b/lab7-transaction/sql/1-1-check_violation.sql new file mode 100644 index 0000000..6a7cd4b --- /dev/null +++ b/lab7-transaction/sql/1-1-check_violation.sql @@ -0,0 +1,5 @@ +select * from partsupp_1 where ps_availqty < 10; + +update partsupp_1 set ps_availqty = ps_availqty - 8 where ps_availqty < 10; + +select * from partsupp_1 where ps_availqty < 10; diff --git a/lab7-transaction/sql/1-2-commit_and_rollback.sql b/lab7-transaction/sql/1-2-commit_and_rollback.sql new file mode 100644 index 0000000..667ebd7 --- /dev/null +++ b/lab7-transaction/sql/1-2-commit_and_rollback.sql @@ -0,0 +1,17 @@ +-- commit +begin transaction; + select ps_partkey, ps_supplycost from partsupp_1 where ps_partkey between '2020' and '2022'; + update partsupp_1 set ps_supplycost = 200 where ps_partkey between '2020' and '2022'; + select ps_partkey, ps_supplycost from partsupp_1 where ps_partkey between '2020' and '2022'; +commit transaction; + +select ps_partkey, ps_supplycost from partsupp_1 where ps_partkey between '2020' and '2022'; + +-- rollback +begin transaction; + select ps_partkey, ps_supplycost from partsupp_2 where ps_partkey between '2020' and '2022'; + update partsupp_2 set ps_supplycost = 200 where ps_partkey between '2020' and '2022'; + select ps_partkey, ps_supplycost from partsupp_2 where ps_partkey between '2020' and '2022'; +rollback transaction; + +select ps_partkey, ps_supplycost from partsupp_2 where ps_partkey between '2020' and '2022'; diff --git a/lab7-transaction/sql/1-3-schema_modification.sql b/lab7-transaction/sql/1-3-schema_modification.sql new file mode 100644 index 0000000..8eb6eab --- /dev/null +++ b/lab7-transaction/sql/1-3-schema_modification.sql @@ -0,0 +1,27 @@ +-- delete column os_availqty from partsupp_1 with commit +begin transaction; + alter table partsupp_1 drop column ps_availqty; +commit transaction; + +select ps_availqty from partsupp_1; + +-- delete column os_availqty to partsupp_2 with rollback +begin transaction; + alter table partsupp_2 drop column ps_availqty; +rollback transaction; + +select ps_availqty from partsupp_2; + +-- add column ps_availqty to partsupp_1 with commit +begin transaction; + alter table partsupp_1 add column ps_availqty_new integer; +commit transaction; + +select ps_availqty_new from partsupp_1; + +-- add column ps_availqty to partsupp_2 with rollback +begin transaction; + alter table partsupp_2 add column ps_availqty_new integer; +rollback transaction; + +select ps_availqty_new from partsupp_2; diff --git a/lab7-transaction/sql/1-4-data_modifications.sql b/lab7-transaction/sql/1-4-data_modifications.sql new file mode 100644 index 0000000..a9e5904 --- /dev/null +++ b/lab7-transaction/sql/1-4-data_modifications.sql @@ -0,0 +1,13 @@ +-- simple sql +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_availqty < 10; +insert into partsupp_1 values (2022, 2022, 7, 0, 'comment'); +delete from partsupp_1 where ps_partkey = '2022' and ps_suppkey = '2022'; +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_availqty < 10; + +-- run as transaction +begin transaction; + select ps_partkey, ps_suppkey, ps_availqty from partsupp_2 where ps_availqty < 10; + insert into partsupp_2 values (2022, 2022, 7, 0, 'comment'); + delete from partsupp_2 where ps_partkey = '2022' and ps_suppkey = '2022'; + select ps_partkey, ps_suppkey, ps_availqty from partsupp_2 where ps_availqty < 10; +commit transaction; diff --git a/lab7-transaction/sql/1-5-savepoint.sql b/lab7-transaction/sql/1-5-savepoint.sql new file mode 100644 index 0000000..b5528ed --- /dev/null +++ b/lab7-transaction/sql/1-5-savepoint.sql @@ -0,0 +1,13 @@ +begin transaction; + select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_availqty < 10; + insert into partsupp_1 values (2022, 2022, 7, 0, 'comment'); + + savepoint sp; + + delete from partsupp_1 where ps_partkey = '2022' and ps_suppkey = '2022'; + + rollback to sp; + +commit transaction; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_partkey = '2022' and ps_suppkey = '2022'; diff --git a/lab7-transaction/sql/1-6-failure.sql b/lab7-transaction/sql/1-6-failure.sql new file mode 100644 index 0000000..75db07a --- /dev/null +++ b/lab7-transaction/sql/1-6-failure.sql @@ -0,0 +1,7 @@ +begin transaction; + select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_availqty < 10; + insert into partsupp_1 values (999999, 999999, 7, 0, 'comment'); + update partsupp_1 set ps_availqty = ps_availqty - 8 where ps_availqty < 10; +commit transaction; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_partkey = '999999' and ps_suppkey = '999999'; diff --git a/lab7-transaction/sql/2-1-read_committed.sql b/lab7-transaction/sql/2-1-read_committed.sql new file mode 100644 index 0000000..d5f9078 --- /dev/null +++ b/lab7-transaction/sql/2-1-read_committed.sql @@ -0,0 +1,34 @@ +-- 1. dirty read +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_partkey = '2022' and ps_suppkey = '1526'; + +start transaction isolation level read committed; + +update partsupp_1 set ps_availqty = 6 where ps_partkey = '2022' and ps_suppkey = '1526'; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_partkey = '2022' and ps_suppkey = '1526'; + +-- 2. replicated read +start transaction isolation level read committed; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_partkey = '2022' and ps_suppkey = '1526'; + +update partsupp_1 set ps_availqty = 6 where ps_partkey = '2022' and ps_suppkey = '1526'; + +commit; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_1 where ps_partkey = '2022' and ps_suppkey = '1526'; + +commit; + +-- 3. illusion read +start transaction isolation level read committed; + +select * from partsupp_1 where ps_partkey = '2022' and ps_suppkey between '23' and '2022'; + +insert into partsupp_1 values ('2022', '2022', 0, 0, 'comment'); + +commit; + +select * from partsupp_1 where ps_partkey = '2022' and ps_suppkey between '23' and '2022'; + +commit; diff --git a/lab7-transaction/sql/2-2-repeatable_read.sql b/lab7-transaction/sql/2-2-repeatable_read.sql new file mode 100644 index 0000000..d1013ed --- /dev/null +++ b/lab7-transaction/sql/2-2-repeatable_read.sql @@ -0,0 +1,34 @@ +-- 1. dirty read +select ps_partkey, ps_suppkey, ps_availqty from partsupp_2 where ps_partkey = '2022' and ps_suppkey = '1526'; + +start transaction isolation level repeatable read; + +update partsupp_2 set ps_availqty = 6 where ps_partkey = '2022' and ps_suppkey = '1526'; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_2 where ps_partkey = '2022' and ps_suppkey = '1526'; + +-- 2. replicated read +start transaction isolation level repeatable read; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_2 where ps_partkey = '2022' and ps_suppkey = '1526'; + +update partsupp_2 set ps_availqty = 6 where ps_partkey = '2022' and ps_suppkey = '1526'; + +commit; + +select ps_partkey, ps_suppkey, ps_availqty from partsupp_2 where ps_partkey = '2022' and ps_suppkey = '1526'; + +commit; + +-- 3. illusion read +start transaction isolation level repeatable read; + +select * from partsupp_2 where ps_partkey = '2022' and ps_suppkey between '23' and '2022'; + +insert into partsupp_2 values ('2022', '2022', 0, 0, 'comment'); + +commit; + +select * from partsupp_2 where ps_partkey = '2022' and ps_suppkey between '23' and '2022'; + +commit; diff --git a/lab7-transaction/sql/3-deadlock.sql b/lab7-transaction/sql/3-deadlock.sql new file mode 100644 index 0000000..5a66338 --- /dev/null +++ b/lab7-transaction/sql/3-deadlock.sql @@ -0,0 +1,22 @@ +-- 1. repeatable read deadlock +-- session 1 +start transaction isolation level repeatable read; +select ps_partkey from partsupp_1 where ps_suppkey=1526 for update; + +-- session 2 +start transaction isolation level repeatable read; +select ps_suppkey from partsupp_1 where ps_partkey=2022 for update; + +-- 2. particle size +-- session 1 +start transaction isolation level repeatable read; +select ps_partkey from partsupp_1 where ps_suppkey=20 for update; + +-- session 2 +start transaction isolation level repeatable read; + +select ps_suppkey from partsupp_1 where ps_partkey=2022 for update; + +select ps_partkey from partsupp_1 where ps_suppkey=22 for update; + +select ps_partkey from partsupp_1 where ps_suppkey=20 for update; diff --git a/lab7-transaction/sql/init.sql b/lab7-transaction/sql/init.sql new file mode 100644 index 0000000..49a7724 --- /dev/null +++ b/lab7-transaction/sql/init.sql @@ -0,0 +1,24 @@ +drop table if exists partsupp_1; +drop table if exists partsupp_2; + +create table partsupp_1 ( + ps_partkey integer not null, + ps_suppkey integer not null, + ps_availqty integer not null, + ps_supplycost decimal(15, 2) not null, + ps_comment varchar(199) not null +); + +create table partsupp_2 ( + ps_partkey integer not null, + ps_suppkey integer not null, + ps_availqty integer not null, + ps_supplycost decimal(15, 2) not null, + ps_comment varchar(199) not null +); + +insert into partsupp_1 select * from partsupp; +insert into partsupp_2 select * from partsupp; + +alter table partsupp_1 add constraint partsupp_chk_1 check (ps_availqty >= 0); +alter table partsupp_2 add constraint partsupp_chk_2 check (ps_availqty >= 0);