1 Star 0 Fork 2

zongyangleo / sorm

forked from yunyouzi / sorm 
加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
克隆/下载
dialect_mapping_sql.go 20.44 KB
一键复制 编辑 原始数据 按行查看 历史
kunyu 提交于 2023-06-14 17:57 . first commit
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809
package dialect
import (
"encoding/json"
"errors"
"strconv"
"strings"
)
func (this_ *mappingDialect) OwnersSelectSql(param *ParamModel) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.OwnersSelect, param)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) OwnerSelectSql(param *ParamModel, ownerName string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.OwnerSelect, param,
map[string]string{
"ownerName": ownerName,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) OwnerModel(data map[string]interface{}) (owner *OwnerModel, err error) {
if data == nil {
return
}
owner = &OwnerModel{}
bs, err := json.Marshal(data)
if err != nil {
return
}
err = json.Unmarshal(bs, owner)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) OwnerCreateSql(param *ParamModel, owner *OwnerModel) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.OwnerCreate, param, owner)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) OwnerDeleteSql(param *ParamModel, ownerName string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.OwnerDelete, param,
map[string]string{
"ownerName": ownerName,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) TablesSelectSql(param *ParamModel, ownerName string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.TablesSelect, param,
map[string]string{
"ownerName": ownerName,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) TableSelectSql(param *ParamModel, ownerName string, tableName string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.TableSelect, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) TableModel(data map[string]interface{}) (table *TableModel, err error) {
if data == nil {
return
}
table = &TableModel{}
bs, err := json.Marshal(data)
if err != nil {
return
}
err = json.Unmarshal(bs, table)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) TableCreateSql(param *ParamModel, ownerName string, table *TableModel) (sqlList []string, err error) {
var tableCreateColumnContent string
var tableCreateColumnSql string
for _, column := range table.ColumnList {
if column.PrimaryKey {
if StringsIndex(table.PrimaryKeys, column.ColumnName) < 0 {
table.PrimaryKeys = append(table.PrimaryKeys, column.ColumnName)
}
}
}
for i, column := range table.ColumnList {
tableCreateColumnSql, err = this_.TableCreateColumnSql(param, column)
if err != nil {
return
}
tableCreateColumnContent += " " + tableCreateColumnSql
if i < len(table.ColumnList)-1 {
tableCreateColumnContent += ",\n"
}
}
var tableCreatePrimaryKeyContent string
if len(table.PrimaryKeys) > 0 {
tableCreatePrimaryKeyContent, err = this_.TableCreatePrimaryKeySql(param, table.PrimaryKeys)
if len(strings.TrimSpace(tableCreatePrimaryKeyContent)) > 0 {
tableCreatePrimaryKeyContent = " " + tableCreatePrimaryKeyContent
if len(strings.TrimSpace(tableCreateColumnContent)) > 0 {
tableCreateColumnContent += ","
}
}
}
if err != nil {
return
}
sqlList, err = this_.FormatSql(this_.TableCreate, param,
table,
map[string]string{
"ownerName": ownerName,
"tableCreateColumnContent": tableCreateColumnContent,
"tableCreatePrimaryKeyContent": tableCreatePrimaryKeyContent,
},
)
if err != nil {
return
}
var sqlList_ []string
if table.TableComment != "" {
sqlList_, err = this_.TableCommentSql(param, ownerName, table.TableName, table.TableComment)
if err != nil {
return
}
sqlList = append(sqlList, sqlList_...)
}
if !this_.TableCreateColumnHasComment {
for _, column := range table.ColumnList {
if column.ColumnComment != "" {
sqlList_, err = this_.ColumnCommentSql(param, ownerName, table.TableName, column.ColumnName, column.ColumnComment)
if err != nil {
return
}
sqlList = append(sqlList, sqlList_...)
}
}
}
for _, index := range table.IndexList {
sqlList_, err = this_.IndexAddSql(param, ownerName, table.TableName, index)
if err != nil {
return
}
sqlList = append(sqlList, sqlList_...)
}
return
}
func (this_ *mappingDialect) TableCreateColumnSql(param *ParamModel, column *ColumnModel) (sqlInfo string, err error) {
columnTypePack, err := this_.ColumnTypePack(column)
if err != nil {
return
}
columnDefaultPack, err := this_.ColumnDefaultPack(param, column)
if err != nil {
return
}
sqlList, err := this_.FormatSql(this_.TableCreateColumn, param,
column,
map[string]string{
"columnTypePack": columnTypePack,
"columnDefaultPack": columnDefaultPack,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) TableCreatePrimaryKeySql(param *ParamModel, primaryKeys []string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.TableCreatePrimaryKey, param,
map[string]interface{}{
"primaryKeys": primaryKeys,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) TableRenameSql(param *ParamModel, ownerName string, tableName string, newTableName string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.TableRename, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"newTableName": newTableName,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) TableDeleteSql(param *ParamModel, ownerName string, tableName string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.TableDelete, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) TableCommentSql(param *ParamModel, ownerName string, tableName string, tableComment string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.TableComment, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"tableComment": tableComment,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) ColumnsSelectSql(param *ParamModel, ownerName string, tableName string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.ColumnsSelect, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) ColumnSelectSql(param *ParamModel, ownerName string, tableName string, columnName string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.ColumnSelect, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"columnName": columnName,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) ColumnModel(data map[string]interface{}) (column *ColumnModel, err error) {
if data == nil {
return
}
column = &ColumnModel{}
bs, err := json.Marshal(data)
if err != nil {
return
}
err = json.Unmarshal(bs, column)
if err != nil {
return
}
var isNullable string
if data["isNullable"] != nil {
isNullable = GetStringValue(data["isNullable"])
}
if data["ISNULLABLE"] != nil {
isNullable = GetStringValue(data["ISNULLABLE"])
}
if isNullable != "" {
if strings.EqualFold(isNullable, "no") || strings.EqualFold(isNullable, "n") {
column.ColumnNotNull = true
}
}
if GetStringValue(data["isNotNull"]) == "1" || GetStringValue(data["ISNOTNULL"]) == "1" {
column.ColumnNotNull = true
}
var columnType string
if data["columnType"] != nil {
columnType = data["columnType"].(string)
}
if data["COLUMNTYPE"] != nil {
columnType = data["COLUMNTYPE"].(string)
}
if column.ColumnDataType == "" {
if strings.Contains(columnType, "(") {
column.ColumnDataType = columnType[:strings.Index(columnType, "(")]
} else {
column.ColumnDataType = columnType
}
}
if strings.Contains(column.ColumnDataType, "(") {
column.ColumnDataType = column.ColumnDataType[:strings.Index(column.ColumnDataType, "(")]
}
dataLength := GetStringValue(data["DATA_LENGTH"])
if dataLength != "" && dataLength != "0" {
column.ColumnLength, err = StringToInt(dataLength)
if err != nil {
return
}
}
dataPrecision := GetStringValue(data["DATA_PRECISION"])
if dataPrecision != "" && dataPrecision != "0" {
column.ColumnPrecision, err = StringToInt(dataPrecision)
if err != nil {
return
}
}
dataScale := GetStringValue(data["DATA_SCALE"])
if dataScale != "" && dataScale != "0" {
column.ColumnScale, err = StringToInt(dataScale)
if err != nil {
return
}
}
characterMaximumLength := GetStringValue(data["CHARACTER_MAXIMUM_LENGTH"])
if characterMaximumLength != "" && characterMaximumLength != "0" {
column.ColumnLength, err = StringToInt(characterMaximumLength)
if err != nil {
return
}
}
numericPrecision := GetStringValue(data["NUMERIC_PRECISION"])
if numericPrecision != "" && numericPrecision != "0" {
column.ColumnPrecision, err = StringToInt(numericPrecision)
if err != nil {
return
}
}
numericScale := GetStringValue(data["NUMERIC_SCALE"])
if numericScale != "" && numericScale != "0" {
column.ColumnScale, err = StringToInt(numericScale)
if err != nil {
return
}
}
datetimePrecision := GetStringValue(data["DATETIME_PRECISION"])
if datetimePrecision != "" && datetimePrecision != "0" {
column.ColumnPrecision, err = StringToInt(datetimePrecision)
if err != nil {
return
}
}
columnTypeInfo, err := this_.GetColumnTypeInfo(column)
if err != nil {
bs, _ = json.Marshal(data)
err = errors.New("ColumnModel error column data:" + string(bs) + ",error:" + err.Error())
return
}
column.ColumnDataType = columnTypeInfo.Name
if column.ColumnDefault != "" {
if strings.HasSuffix(column.ColumnDefault, "::"+column.ColumnDataType) {
column.ColumnDefault = strings.TrimSuffix(column.ColumnDefault, "::"+column.ColumnDataType)
}
column.ColumnDefault = strings.TrimLeft(column.ColumnDefault, "'")
column.ColumnDefault = strings.TrimRight(column.ColumnDefault, "'")
column.ColumnDefault = strings.TrimLeft(column.ColumnDefault, "\"")
column.ColumnDefault = strings.TrimRight(column.ColumnDefault, "\"")
}
if columnTypeInfo.FullColumnByColumnType != nil {
err = columnTypeInfo.FullColumnByColumnType(columnType, column)
if err != nil {
return
}
} else {
if strings.Contains(columnType, "(") {
if (column.ColumnLength == 0 && column.ColumnPrecision == 0 && column.ColumnScale == 0) ||
(this_.dialectType == TypeMysql && columnTypeInfo.IsInteger) {
lengthStr := columnType[strings.Index(columnType, "(")+1 : strings.Index(columnType, ")")]
var v1 int
var v2 int
if strings.Contains(lengthStr, ",") {
v1, _ = strconv.Atoi(strings.TrimSpace(lengthStr[0:strings.Index(lengthStr, ",")]))
v2, _ = strconv.Atoi(strings.TrimSpace(lengthStr[strings.Index(lengthStr, ",")+1:]))
if strings.Contains(columnTypeInfo.Format, "$l") {
column.ColumnLength = v1
}
if strings.Contains(columnTypeInfo.Format, "$p") {
column.ColumnLength = v1
}
if strings.Contains(columnTypeInfo.Format, "$s") {
column.ColumnScale = v2
}
} else {
v1, _ = strconv.Atoi(lengthStr)
if strings.Contains(columnTypeInfo.Format, "$l") {
column.ColumnLength = v1
}
if strings.Contains(columnTypeInfo.Format, "$p") {
column.ColumnLength = v1
}
if strings.Contains(columnTypeInfo.Format, "$s") {
column.ColumnScale = v1
}
}
if columnTypeInfo.IsInteger {
if column.ColumnPrecision == 0 {
column.ColumnPrecision = column.ColumnLength
} else if column.ColumnLength == 0 {
column.ColumnLength = column.ColumnPrecision
}
}
}
}
}
return
}
func (this_ *mappingDialect) ColumnAddSql(param *ParamModel, ownerName string, tableName string, column *ColumnModel) (sqlList []string, err error) {
columnTypePack, err := this_.ColumnTypePack(column)
if err != nil {
return
}
columnDefaultPack, err := this_.ColumnDefaultPack(param, column)
if err != nil {
return
}
sqlList, err = this_.FormatSql(this_.ColumnAdd, param,
column,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"columnTypePack": columnTypePack,
"columnDefaultPack": columnDefaultPack,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) ColumnUpdateSql(param *ParamModel, ownerName string, tableName string, oldColumn *ColumnModel, column *ColumnModel) (sqlList []string, err error) {
if oldColumn.ColumnName == "" {
oldColumn.ColumnName = column.ColumnName
}
columnTypePack, err := this_.ColumnTypePack(column)
if err != nil {
return
}
columnDefaultPack, err := this_.ColumnDefaultPack(param, column)
if err != nil {
return
}
data := map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"oldColumnName": oldColumn.ColumnName,
"columnTypePack": columnTypePack,
"columnDefaultPack": columnDefaultPack,
}
var sqlList_ []string
var hasChangeName bool
if oldColumn.ColumnName != column.ColumnName {
hasChangeName = true
}
var hasChangeComment bool
if oldColumn.ColumnComment != column.ColumnComment {
hasChangeComment = true
}
var hasChangeAfter bool
if oldColumn.ColumnAfterColumn != column.ColumnAfterColumn {
hasChangeAfter = true
}
if !this_.ColumnUpdateHasRename {
if hasChangeName {
sqlList_, err = this_.ColumnRenameSql(param, ownerName, tableName, oldColumn.ColumnName, column.ColumnName)
if err != nil {
return
}
sqlList = append(sqlList, sqlList_...)
hasChangeName = false
}
}
if !this_.ColumnUpdateHasComment {
if hasChangeComment {
sqlList_, err = this_.ColumnCommentSql(param, ownerName, tableName, column.ColumnName, column.ColumnComment)
if err != nil {
return
}
sqlList = append(sqlList, sqlList_...)
hasChangeComment = false
}
}
if !this_.ColumnUpdateHasAfter {
if hasChangeAfter {
sqlList_, err = this_.ColumnAfterSql(param, ownerName, tableName, column.ColumnName, column.ColumnAfterColumn)
if err != nil {
return
}
sqlList = append(sqlList, sqlList_...)
hasChangeAfter = false
}
}
if hasChangeName || hasChangeComment || hasChangeAfter ||
oldColumn.ColumnDataType != column.ColumnDataType ||
oldColumn.ColumnLength != column.ColumnLength ||
oldColumn.ColumnPrecision != column.ColumnPrecision ||
oldColumn.ColumnScale != column.ColumnScale ||
oldColumn.ColumnDefault != column.ColumnDefault ||
oldColumn.ColumnNotNull != column.ColumnNotNull {
sqlList_, err = this_.FormatSql(this_.ColumnUpdate, param,
oldColumn,
column,
data,
)
if err != nil {
return
}
sqlList = append(sqlList, sqlList_...)
}
return
}
func (this_ *mappingDialect) ColumnDeleteSql(param *ParamModel, ownerName string, tableName string, columnName string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.ColumnDelete, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"columnName": columnName,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) ColumnRenameSql(param *ParamModel, ownerName string, tableName string, oldColumnName string, columnName string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.ColumnRename, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"oldColumnName": oldColumnName,
"columnName": columnName,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) ColumnCommentSql(param *ParamModel, ownerName string, tableName string, columnName string, columnComment string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.ColumnComment, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"columnName": columnName,
"columnComment": columnComment,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) ColumnAfterSql(param *ParamModel, ownerName string, tableName string, columnName string, columnAfterColumn string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.ColumnAfter, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"columnName": columnName,
"columnAfterColumn": columnAfterColumn,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) PrimaryKeysSelectSql(param *ParamModel, ownerName string, tableName string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.PrimaryKeysSelect, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) PrimaryKeyModel(data map[string]interface{}) (primaryKey *PrimaryKeyModel, err error) {
if data == nil {
return
}
primaryKey = &PrimaryKeyModel{}
bs, err := json.Marshal(data)
if err != nil {
return
}
err = json.Unmarshal(bs, primaryKey)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) PrimaryKeyAddSql(param *ParamModel, ownerName string, tableName string, columnNames []string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.PrimaryKeyAdd, param,
map[string]interface{}{
"ownerName": ownerName,
"tableName": tableName,
"columnNames": columnNames,
"primaryKeys": columnNames,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) PrimaryKeyDeleteSql(param *ParamModel, ownerName string, tableName string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.PrimaryKeyDelete, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
},
)
if err != nil {
return
}
return
}
func (this_ *mappingDialect) IndexesSelectSql(param *ParamModel, ownerName string, tableName string) (sqlInfo string, err error) {
sqlList, err := this_.FormatSql(this_.IndexesSelect, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
},
)
if err != nil {
return
}
if len(sqlList) > 0 {
sqlInfo = sqlList[0]
}
return
}
func (this_ *mappingDialect) IndexModel(data map[string]interface{}) (index *IndexModel, err error) {
if data == nil {
return
}
index = &IndexModel{}
bs, err := json.Marshal(data)
if err != nil {
return
}
err = json.Unmarshal(bs, index)
if err != nil {
return
}
if GetStringValue(data["UNIQUENESS"]) == "UNIQUE" {
index.IndexType = "unique"
}
if GetStringValue(data["NON_UNIQUE"]) == "0" {
index.IndexType = "unique"
}
if GetStringValue(data["isUnique"]) == "1" {
index.IndexType = "unique"
}
if GetStringValue(data["UNIQUENESS"]) == "UNIQUE" {
index.IndexType = "unique"
}
indexTypeInfo, err := this_.GetIndexTypeInfo(index.IndexType)
if err != nil {
//fmt.Println(data)
return
}
index.IndexType = indexTypeInfo.Name
return
}
func (this_ *mappingDialect) IndexAddSql(param *ParamModel, ownerName string, tableName string, index *IndexModel) (sqlList []string, err error) {
indexType, err := this_.IndexTypeFormat(index)
if err != nil {
return
}
indexType = strings.TrimSpace(indexType)
if indexType == "" {
return
}
indexName, err := this_.IndexNameFormat(param, ownerName, tableName, index)
if err != nil {
return
}
indexName = strings.TrimSpace(indexName)
if indexName == "" {
indexName = index.IndexName
}
sqlList, err = this_.FormatSql(this_.IndexAdd, param,
index,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"indexName": indexName,
"indexType": indexType,
},
)
if err != nil {
return
}
//fmt.Println("index add sql:", sqlList)
return
}
func (this_ *mappingDialect) IndexDeleteSql(param *ParamModel, ownerName string, tableName string, indexName string) (sqlList []string, err error) {
sqlList, err = this_.FormatSql(this_.IndexDelete, param,
map[string]string{
"ownerName": ownerName,
"tableName": tableName,
"indexName": indexName,
},
)
if err != nil {
return
}
return
}
func (m *mappingDialect) WrapParamSQL(paramIndex int) string {
if m.SqlMapping.WrapParamSQL != nil {
return m.SqlMapping.WrapParamSQL(paramIndex)
}
return "?"
}
Go
1
https://gitee.com/liuzongyang/sorm.git
git@gitee.com:liuzongyang/sorm.git
liuzongyang
sorm
sorm
v1.0.1

搜索帮助