Golang后端学习笔记 — 1. 设计数据库结构
这个Golang后端大师班中,我们将学习如何使用Golang
、PostgreSQL
和Docker
从头开始设计、开发和部署一个完整的后端。
课程包括:
- 设计数据库模式并从中自动生成 SQL 代码
- 深入了解数据库隔离级别、事务以及如何避免死锁
- 自动生成 Golang 代码与数据库交互
- 使用
Gin
框架开发RESTful
后端 Web 服务 - 使用用户身份验证、
JWT
和 PASETO 保护 API - 使用接口和模拟编写具有高覆盖率的更强大的测试集
- 构建用于部署的最小
Docker
映像并使用Docker-compose
进行开发 - 设置
Github Action
以自动构建应用程序并将其部署到AWS Kubernetes
集群 - 注册域并配置
Kubernetes
入口以将流量路由到 Web 服务 - 使用 Let's Encrypt 为域启用自动颁发和更新 TLS 证书
- 其他
学习笔记的改进:
替换为符合国内使用习惯的服务或软件,比如:
- 自建的
Gitlab
替代Github - 腾讯云或阿里云的Kubernetes替代亚马逊云的Kubernetes
课程项目:一个简单的银行系统
主要功能时,它为前端提供API接口来做以下事情:
- 创建和管理银行账户 账户由所有者的姓名、余额和币种组成
- 记录每个账户的所有余额变化 每次账户中增加或减少钱,都会生成一个账户变化记录的账目
- 在两个账户直接转账
它应该是个事务处理,要么两个账户都更新成功,要么都不成功。
通过这个小项目,来学习整个
Golang
后端的开发过程。
本节的内容:数据库设计
- 数据库设计 使用dbdiagram设计数据库结构
- 生成
SQL
代码
1、使用dbdiagram设计表结构
打开dbdiagram.io/,点击 Go To App 按钮
删除左侧所有的示例代码,成为一个新的工作空间,项目命名为
银行
,如下图:
2、创建一个账户表(accounts)
- 字段:
id
、主键、自增,数据类型使用bigserial
,范围更大的整形。 - 字段:
owner
,用于保存账户所有者的名字,数据类型可以是text
或者varchar
- 字段:
balance
账户的可用余额,简单的示例,这里用了bigint
数据类型,实际情况金额可能不会是整数。 - 字段:
currency
币种,varchar
- 字段:
created_at
账户的创建时间, 数据类型使用timestamptz
,而不是timestamp
,因为timestamptz
包含时区信息,默认值设置为now()
,让数据库自动为我们生成当前时间。 在左侧编辑区,输入下面的内容,右侧会自动生成一个图
Table accounts as a {
id bigserial [pk, increment]
owner varchar [not null, note: '账户所有者的名字']
balance bigint [not null, note: '余额']
currency varchar [not null, note: '币种']
created_at timestamptz [not null, default: 'now()']
}
3、账目表(entries),记录账户余额的所有变化
- 字段:
id
、主键、自增,数据类型bigserial
- 字段:
account_id
账户id,和account
表属于1对多的关系,1个账号可以有多条账目数据。 - 字段:
amount
金额, 数据类型bigint
- 字段:
created_at
,数据类型timestamptz
,默认now()
Table entries as e {
id bigserial [pk, increment]
account_id bigint [not null, note: '账户ID', ref: > a.id]
amount bigint [not null, note: '金额']
created_at timestamptz [not null, default: 'now()']
}
ref: > a.id
代表和accounts
表的关联关系
4、转账表(transfers),记录两个账户之间的转账
- 字段:
id
、主键、自增,数据类型bigserial
- 字段:
from_account_id
, 从哪个账户转账,数据类型bigserial
, 和account
表属于1对多的关系 - 字段:
to_account_id
, 转到哪个账户上,数据类型bigserial
,和account
表属于1对多的关系 - 字段:
amount
转账金额,数据类型bigint
- 字段:
created_at
,数据类型timestamptz
,默认now()
Table transfers as t {
id bigserial [pk, increment]
from_account_id bigint [not null, ref: > a.id]
to_account_id bigint [not null, ref: > a.id]
amount bigint [not null, note: '金额,只能为正数']
created_at timestamptz [not null, default: 'now()']
}
5、添加索引
Table accounts as a {
id int [pk, increment]
owner varchar [not null, note: '账户所有者的名字']
balance bigint [not null, note: '余额']
currency varchar [not null, note: '币种']
created_at timestamptz [not null, default: 'now()']
indexes {
owner
}
}
Table entries as e {
id bigserial [pk, increment]
account_id bigint [not null, note: '账户ID', ref: > a.id]
amount bigint [not null, note: '金额,可以为正数,也可以为负数']
created_at timestamptz [not null, default: 'now()']
indexes {
account_id
}
}
Table transfers as t {
id bigserial [pk, increment]
from_account_id bigint [not null, ref: > a.id]
to_account_id bigint [not null, ref: > a.id]
amount bigint [not null, note: '金额,只能为正数']
created_at timestamptz [not null, default: 'now()']
indexes {
from_account_id
to_account_id
(from_account_id, to_account_id)
}
}
调整一下右侧的布局
6、导出SQL
点击菜单上的Export to PostgreSQL
,导出建表的SQL脚本
如下:
CREATE TABLE "accounts" (
"id" SERIAL PRIMARY KEY,
"owner" varchar NOT NULL,
"balance" bigint NOT NULL,
"currency" varchar NOT NULL,
"created_at" timestamptz NOT NULL DEFAULT 'now()'
);
CREATE TABLE "entries" (
"id" SERIAL PRIMARY KEY,
"account_id" bigint NOT NULL,
"amount" bigint NOT NULL,
"created_at" timestamptz NOT NULL DEFAULT 'now()'
);
CREATE TABLE "transfers" (
"id" SERIAL PRIMARY KEY,
"from_account_id" bigint NOT NULL,
"to_account_id" bigint NOT NULL,
"amount" bigint NOT NULL,
"created_at" timestamptz NOT NULL DEFAULT 'now()'
);
ALTER TABLE "entries" ADD FOREIGN KEY ("account_id") REFERENCES "accounts" ("id");
ALTER TABLE "transfers" ADD FOREIGN KEY ("from_account_id") REFERENCES "accounts" ("id");
ALTER TABLE "transfers" ADD FOREIGN KEY ("to_account_id") REFERENCES "accounts" ("id");
CREATE INDEX ON "accounts" ("owner");
CREATE INDEX ON "entries" ("account_id");
CREATE INDEX ON "transfers" ("from_account_id");
CREATE INDEX ON "transfers" ("to_account_id");
CREATE INDEX ON "transfers" ("from_account_id", "to_account_id");
COMMENT ON COLUMN "accounts"."owner" IS '账户所有者的名字';
COMMENT ON COLUMN "accounts"."balance" IS '余额';
COMMENT ON COLUMN "accounts"."currency" IS '币种';
COMMENT ON COLUMN "entries"."account_id" IS '账户ID';
COMMENT ON COLUMN "entries"."amount" IS '金额,可以为正数,也可以为负数';
COMMENT ON COLUMN "transfers"."amount" IS '金额,只能为正数';
好了,本节内容就是这样,下节,我们将使用这个导出的SQL脚本
,在Docker中的Postgres
数据容器中使用。
转载自:https://juejin.cn/post/7084154424989319198