gen-model.sh 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244
  1. #!/bin/bash
  2. #
  3. # gen-model.sh — 基于自定义 goctl 模板生成 model 代码
  4. #
  5. # 用法:
  6. # ./gen-model.sh ddl -src <sql文件> [-table <表1,表2,...>]
  7. # ./gen-model.sh datasource -url <DSN> -table <表1,表2,...>
  8. #
  9. # 示例:
  10. # ./gen-model.sh ddl -src perms.sql # 从 DDL 生成所有表
  11. # ./gen-model.sh ddl -src perms.sql -table sys_user,sys_role # 从 DDL 生成指定表
  12. # ./gen-model.sh datasource \
  13. # -url 'root:123456@tcp(127.0.0.1:3306)/mydb' \
  14. # -table sys_user,sys_role # 从数据库生成指定表
  15. #
  16. # 表名到目录的映射规则:
  17. # 去掉 sys_ 前缀,再去掉下划线。如 sys_role_perm -> roleperm
  18. # 生成目录: internal/model/<pkg>/
  19. # 文件风格: 小驼峰 (--style goZero)
  20. set -euo pipefail
  21. SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)"
  22. TEMPLATE_HOME="$SCRIPT_DIR/cli/goctl"
  23. MODEL_BASE_DIR="$SCRIPT_DIR/internal/model"
  24. STYLE="goZero"
  25. # ---- 工具函数 ----
  26. # 表名 -> 包名/目录名
  27. # sys_user -> user, sys_role_perm -> roleperm, sys_product_member -> productmember
  28. table_to_pkg() {
  29. local table="$1"
  30. local name="${table#sys_}"
  31. echo "${name//_/}"
  32. }
  33. # 从 SQL 文件中拆分出每张表的独立 DDL
  34. # 输出: 临时目录路径(包含 <表名>.sql 文件)
  35. split_ddl() {
  36. local sql_file="$1"
  37. local tmp_dir
  38. tmp_dir=$(mktemp -d)
  39. local current_table=""
  40. local outfile=""
  41. local printing=0
  42. while IFS= read -r line; do
  43. if echo "$line" | grep -qE "(DROP TABLE IF EXISTS|CREATE TABLE IF NOT EXISTS|CREATE TABLE)"; then
  44. current_table=$(echo "$line" | sed "s/.*\`\([^\`]*\)\`.*/\1/")
  45. outfile="$tmp_dir/${current_table}.sql"
  46. printing=1
  47. echo "$line" > "$outfile"
  48. elif [[ $printing -eq 1 ]]; then
  49. echo "$line" >> "$outfile"
  50. if echo "$line" | grep -qE "^\).*ENGINE" ; then
  51. printing=0
  52. fi
  53. fi
  54. done < "$sql_file"
  55. echo "$tmp_dir"
  56. }
  57. # 从 DDL 文件生成单张表的 model
  58. gen_from_ddl() {
  59. local ddl_file="$1"
  60. local table_name="$2"
  61. local pkg
  62. pkg=$(table_to_pkg "$table_name")
  63. local out_dir="$MODEL_BASE_DIR/$pkg"
  64. mkdir -p "$out_dir"
  65. echo " [$table_name] -> $out_dir/"
  66. goctl model mysql ddl \
  67. -src "$ddl_file" \
  68. -dir "$out_dir" \
  69. -c \
  70. --home "$TEMPLATE_HOME" \
  71. --style "$STYLE"
  72. }
  73. # 从数据库连接生成单张表的 model
  74. gen_from_datasource() {
  75. local url="$1"
  76. local table_name="$2"
  77. local pkg
  78. pkg=$(table_to_pkg "$table_name")
  79. local out_dir="$MODEL_BASE_DIR/$pkg"
  80. mkdir -p "$out_dir"
  81. echo " [$table_name] -> $out_dir/"
  82. goctl model mysql datasource \
  83. -url "$url" \
  84. -table "$table_name" \
  85. -dir "$out_dir" \
  86. -c \
  87. --home "$TEMPLATE_HOME" \
  88. --style "$STYLE"
  89. }
  90. # ---- 主流程 ----
  91. usage() {
  92. cat <<'EOF'
  93. 用法:
  94. ./gen-model.sh ddl -src <sql文件> [-table <表1,表2,...>]
  95. ./gen-model.sh datasource -url <DSN> -table <表1,表2,...>
  96. 选项:
  97. ddl 模式:
  98. -src SQL DDL 文件路径(必填)
  99. -table 要生成的表名,逗号分隔(可选,默认生成 SQL 中所有表)
  100. datasource 模式:
  101. -url MySQL DSN 连接串(必填),如 'root:pass@tcp(127.0.0.1:3306)/dbname'
  102. -table 要生成的表名,逗号分隔(必填)
  103. 示例:
  104. ./gen-model.sh ddl -src perm.sql
  105. ./gen-model.sh ddl -src perm.sql -table sys_user,sys_role
  106. ./gen-model.sh datasource -url 'root:123456@tcp(127.0.0.1:3306)/mydb' -table sys_user
  107. EOF
  108. exit 1
  109. }
  110. if [[ $# -lt 1 ]]; then
  111. usage
  112. fi
  113. MODE="$1"
  114. shift
  115. case "$MODE" in
  116. ddl)
  117. SRC=""
  118. TABLES=""
  119. while [[ $# -gt 0 ]]; do
  120. case "$1" in
  121. -src) SRC="$2"; shift 2 ;;
  122. -table) TABLES="$2"; shift 2 ;;
  123. *) echo "未知选项: $1"; usage ;;
  124. esac
  125. done
  126. if [[ -z "$SRC" ]]; then
  127. echo "错误: ddl 模式必须指定 -src"
  128. usage
  129. fi
  130. # 支持相对路径
  131. if [[ "$SRC" != /* ]]; then
  132. SRC="$SCRIPT_DIR/$SRC"
  133. fi
  134. if [[ ! -f "$SRC" ]]; then
  135. echo "错误: SQL 文件不存在: $SRC"
  136. exit 1
  137. fi
  138. echo "拆分 DDL 文件: $SRC"
  139. TMP_DIR=$(split_ddl "$SRC")
  140. trap "rm -rf '$TMP_DIR'" EXIT
  141. # 获取拆分出的所有表名
  142. ALL_TABLES=()
  143. for f in "$TMP_DIR"/*.sql; do
  144. [[ -f "$f" ]] || continue
  145. ALL_TABLES+=("$(basename "$f" .sql)")
  146. done
  147. # 如果指定了 -table 则过滤
  148. if [[ -n "$TABLES" ]]; then
  149. IFS=',' read -ra FILTER <<< "$TABLES"
  150. TARGET_TABLES=()
  151. for t in "${FILTER[@]}"; do
  152. t="${t## }"; t="${t%% }"
  153. if [[ -f "$TMP_DIR/${t}.sql" ]]; then
  154. TARGET_TABLES+=("$t")
  155. else
  156. echo "警告: 表 '$t' 未在 SQL 文件中找到,跳过"
  157. fi
  158. done
  159. else
  160. TARGET_TABLES=("${ALL_TABLES[@]}")
  161. fi
  162. if [[ ${#TARGET_TABLES[@]} -eq 0 ]]; then
  163. echo "错误: 没有可生成的表"
  164. exit 1
  165. fi
  166. echo "即将生成 ${#TARGET_TABLES[@]} 张表: ${TARGET_TABLES[*]}"
  167. echo ""
  168. for t in "${TARGET_TABLES[@]}"; do
  169. gen_from_ddl "$TMP_DIR/${t}.sql" "$t"
  170. done
  171. echo ""
  172. echo "完成!共生成 ${#TARGET_TABLES[@]} 个 model。"
  173. ;;
  174. datasource)
  175. URL=""
  176. TABLES=""
  177. while [[ $# -gt 0 ]]; do
  178. case "$1" in
  179. -url) URL="$2"; shift 2 ;;
  180. -table) TABLES="$2"; shift 2 ;;
  181. *) echo "未知选项: $1"; usage ;;
  182. esac
  183. done
  184. if [[ -z "$URL" ]]; then
  185. echo "错误: datasource 模式必须指定 -url"
  186. usage
  187. fi
  188. if [[ -z "$TABLES" ]]; then
  189. echo "错误: datasource 模式必须指定 -table"
  190. usage
  191. fi
  192. IFS=',' read -ra TARGET_TABLES <<< "$TABLES"
  193. echo "连接数据库..."
  194. echo "即将生成 ${#TARGET_TABLES[@]} 张表: ${TARGET_TABLES[*]}"
  195. echo ""
  196. for t in "${TARGET_TABLES[@]}"; do
  197. t="${t## }"; t="${t%% }"
  198. gen_from_datasource "$URL" "$t"
  199. done
  200. echo ""
  201. echo "完成!共生成 ${#TARGET_TABLES[@]} 个 model。"
  202. ;;
  203. *)
  204. echo "未知模式: $MODE"
  205. usage
  206. ;;
  207. esac