From 261e13d7966bdc4b118303f8b6a13a525e9a9486 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Fri, 27 Jun 2025 18:50:05 +0800 Subject: [PATCH 01/16] =?UTF-8?q?=E4=BF=AE=E5=A4=8Dissue=E6=89=80=E6=8F=90?= =?UTF-8?q?=E5=88=B0=E7=9A=84bug=EF=BC=8C=E9=87=8D=E7=BD=AEniuniu=E6=95=B0?= =?UTF-8?q?=E6=8D=AE=E5=BA=93?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- go.mod | 9 +- go.sum | 43 +++++++- niu/db.go | 64 ++++++++++++ niu/main.go | 275 +++++++++++++++++++++++++++++++++++++------------- niu/models.go | 182 ++++++++++----------------------- niu/utils.go | 26 +++-- 6 files changed, 385 insertions(+), 214 deletions(-) create mode 100644 niu/db.go diff --git a/go.mod b/go.mod index 3a468ae..71667f3 100644 --- a/go.mod +++ b/go.mod @@ -10,12 +10,15 @@ require ( github.com/corona10/goimagehash v1.1.0 github.com/fumiama/go-base16384 v1.7.0 github.com/fumiama/terasu v0.0.0-20241027183601-987ab91031ce + github.com/glebarez/sqlite v1.11.0 + github.com/google/uuid v1.6.0 github.com/pkg/errors v0.9.1 github.com/pkumza/numcn v1.0.0 github.com/sirupsen/logrus v1.9.3 github.com/stretchr/testify v1.9.0 github.com/tidwall/gjson v1.18.0 golang.org/x/image v0.21.0 + gorm.io/gorm v1.30.0 ) require ( @@ -27,8 +30,10 @@ require ( github.com/fumiama/go-registry v0.2.7 // indirect github.com/fumiama/go-simple-protobuf v0.2.0 // indirect github.com/fumiama/gofastTEA v0.0.10 // indirect + github.com/glebarez/go-sqlite v1.21.2 // indirect github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect - github.com/google/uuid v1.6.0 // indirect + github.com/jinzhu/inflection v1.0.0 // indirect + github.com/jinzhu/now v1.1.5 // indirect github.com/mattn/go-isatty v0.0.20 // indirect github.com/ncruces/go-strftime v0.1.9 // indirect github.com/nfnt/resize v0.0.0-20180221191011-83c6a9932646 // indirect @@ -40,7 +45,7 @@ require ( github.com/wdvxdr1123/ZeroBot v1.8.0 // indirect golang.org/x/net v0.24.0 // indirect golang.org/x/sys v0.26.0 // indirect - golang.org/x/text v0.19.0 // indirect + golang.org/x/text v0.20.0 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect modernc.org/libc v1.61.0 // indirect modernc.org/mathutil v1.6.0 // indirect diff --git a/go.sum b/go.sum index 50b4bec..63fa392 100644 --- a/go.sum +++ b/go.sum @@ -4,8 +4,10 @@ github.com/FloatTech/sqlite v1.7.1 h1:XKUY0+MNaRmvEIgRv7QLbl7PFVpUfQ72+XQg+no2Vq github.com/FloatTech/sqlite v1.7.1/go.mod h1:/4tzfCGhrZnnjC1U8vcfwGQeF6eR649fhOsS3+Le0+s= github.com/FloatTech/ttl v0.0.0-20240716161252-965925764562 h1:snfw7FNFym1eNnLrQ/VCf80LiQo9C7jHgrunZDwiRcY= github.com/FloatTech/ttl v0.0.0-20240716161252-965925764562/go.mod h1:fHZFWGquNXuHttu9dUYoKuNbm3dzLETnIOnm1muSfDs= +github.com/PuerkitoBio/goquery v1.5.1/go.mod h1:GsLWisAFVj4WgDibEWF4pvYnkVQBpKBKeU+7zCJoLcc= github.com/RomiChan/syncx v0.0.0-20240418144900-b7402ffdebc7 h1:S/ferNiehVjNaBMNNBxUjLtVmP/YWD6Yh79RfPv4ehU= github.com/RomiChan/syncx v0.0.0-20240418144900-b7402ffdebc7/go.mod h1:vD7Ra3Q9onRtojoY5sMCLQ7JBgjUsrXDnDKyFxqpf9w= +github.com/andybalholm/cascadia v1.1.0/go.mod h1:GsXiBklL0woXo1j/WYWtSYYC4ouU9PqHO0sqidkEA4Y= github.com/antchfx/htmlquery v1.3.3 h1:x6tVzrRhVNfECDaVxnZi1mEGrQg3mjE/rxbH2Pe6dNE= github.com/antchfx/htmlquery v1.3.3/go.mod h1:WeU3N7/rL6mb6dCwtE30dURBnBieKDC/fR8t6X+cKjU= github.com/antchfx/xpath v1.3.2 h1:LNjzlsSjinu3bQpw9hWMY9ocB80oLOWuQqFvO6xt51U= @@ -15,8 +17,12 @@ github.com/corona10/goimagehash v1.1.0/go.mod h1:VkvE0mLn84L4aF8vCb6mafVajEb6QYM github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/denisenkom/go-mssqldb v0.0.0-20191124224453-732737034ffd h1:83Wprp6ROGeiHFAP8WJdI2RoxALQYgdllERc3N5N2DM= +github.com/denisenkom/go-mssqldb v0.0.0-20191124224453-732737034ffd/go.mod h1:xbL0rPBG9cCiLr28tMa8zpbdarY27NDyej4t/EjAShU= github.com/dustin/go-humanize v1.0.1 h1:GzkhY7T5VNhEkwH0PVJgjz+fX1rhBrR7pRT3mDkpeCY= github.com/dustin/go-humanize v1.0.1/go.mod h1:Mu1zIs6XwVuF/gI1OepvI0qD18qycQx+mFykh5fBlto= +github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5 h1:Yzb9+7DPaBjB8zlTR87/ElzFsnQfuHnVUVqpZZIcV5Y= +github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0= github.com/fumiama/cron v1.3.0 h1:ZWlwuexF+HQHl3cYytEE5HNwD99q+3vNZF1GrEiXCFo= github.com/fumiama/cron v1.3.0/go.mod h1:bz5Izvgi/xEUI8tlBN8BI2jr9Moo8N4or0KV8xXuPDY= github.com/fumiama/go-base16384 v1.7.0 h1:6fep7XPQWxRlh4Hu+KsdH+6+YdUp+w6CwRXtMWSsXCA= @@ -33,12 +39,32 @@ github.com/fumiama/sqlite3 v1.29.10-simp h1:c5y3uKyU0q9t0/SyfynzYyuslQ5zP+5CD8e0 github.com/fumiama/sqlite3 v1.29.10-simp/go.mod h1:ItX2a1OVGgNsFh6Dv60JQvGfJfTPHPVpV6DF59akYOA= github.com/fumiama/terasu v0.0.0-20241027183601-987ab91031ce h1:T6iDDU16rFyxV/FwfJJR6qcgkIlXJEIFlUTSmTD1h6s= github.com/fumiama/terasu v0.0.0-20241027183601-987ab91031ce/go.mod h1:UVx8YP1jKKL1Cj+uy+OnQRM2Ih6U36Mqy9GSf7jabsI= +github.com/glebarez/go-sqlite v1.21.2 h1:3a6LFC4sKahUunAmynQKLZceZCOzUthkRkEAl9gAXWo= +github.com/glebarez/go-sqlite v1.21.2/go.mod h1:sfxdZyhQjTM2Wry3gVYWaW072Ri1WMdWJi0k6+3382k= +github.com/glebarez/sqlite v1.11.0 h1:wSG0irqzP6VurnMEpFGer5Li19RpIRi2qvQz++w0GMw= +github.com/glebarez/sqlite v1.11.0/go.mod h1:h8/o8j5wiAsqSPoWELDUdJXhjAhsVliSn7bWZjOhrgQ= +github.com/go-sql-driver/mysql v1.5.0 h1:ozyZYNQW3x3HtqT1jira07DN2PArx2v7/mN66gGcHOs= +github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg= +github.com/golang-sql/civil v0.0.0-20190719163853-cb61b32ac6fe h1:lXe2qZdvpiX5WZkZR4hgp4KJVfY3nMkvmwbVkpv1rVY= +github.com/golang-sql/civil v0.0.0-20190719163853-cb61b32ac6fe/go.mod h1:8vg3r2VgvsThLBIFL93Qb5yWzgyZWhEmBwUJWevAkK0= github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da h1:oI5xCqsCo564l8iNU+DwB5epxmsaqB+rhGL0m5jtYqE= github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/google/pprof v0.0.0-20240409012703-83162a5b38cd h1:gbpYu9NMq8jhDVbvlGkMFWCjLFlqqEZjEmObmhUy6Vo= github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/jinzhu/gorm v1.9.16 h1:+IyIjPEABKRpsu/F8OvDPy9fyQlgsg2luMV2ZIH5i5o= +github.com/jinzhu/gorm v1.9.16/go.mod h1:G3LB3wezTOWM2ITLzPxEXgSkOXAntiLHS7UdBefADcs= +github.com/jinzhu/inflection v1.0.0 h1:K317FqzuhWc8YvSVlFMCCUb36O/S9MCKRDI7QkRKD/E= +github.com/jinzhu/inflection v1.0.0/go.mod h1:h+uFLlag+Qp1Va5pdKtLDYj+kHp5pxUVkryuEj+Srlc= +github.com/jinzhu/now v1.0.1/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8= +github.com/jinzhu/now v1.1.5 h1:/o9tlHleP7gOFmsnYNz3RGnqzefHA47wQpKrrdTIwXQ= +github.com/jinzhu/now v1.1.5/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8= +github.com/lib/pq v1.1.1 h1:sJZmqHoEaY7f+NPP8pgLB/WxulyR3fewgCM2qaSlBb4= +github.com/lib/pq v1.1.1/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= +github.com/mattn/go-sqlite3 v1.14.0 h1:mLyGNKR8+Vv9CAU7PphKa2hkEqxxhn8i32J6FPj1/QA= +github.com/mattn/go-sqlite3 v1.14.0/go.mod h1:JIl7NbARA7phWnGvh0LKTyg7S9BA+6gx71ShQilpsus= github.com/ncruces/go-strftime v0.1.9 h1:bY0MQC28UADQmHmaF5dgpLmImcShSi2kHU9XLdhx/f4= github.com/ncruces/go-strftime v0.1.9/go.mod h1:Fwc5htZGVVkseilnfgOVb9mKy6w1naJmn9CehxcKcls= github.com/nfnt/resize v0.0.0-20180221191011-83c6a9932646 h1:zYyBkD/k9seD2A7fsi6Oo2LfFZAehjjQMERAvZLEDnQ= @@ -70,12 +96,19 @@ github.com/wdvxdr1123/ZeroBot v1.8.0 h1:v7m+0kGtL6XQlUH9O/LzmOntDJs2clzVj93YsAWW github.com/wdvxdr1123/ZeroBot v1.8.0/go.mod h1:C86nQ0gIdAri4K2vg8IIQIslt08zzrKMcqYt8zhkx1M= github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20191205180655-e7c4368fe9dd/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/crypto v0.22.0 h1:g1v0xeRhjcugydODzvb3mEM9SQ0HGp9s/nh3COQ/C30= golang.org/x/image v0.21.0 h1:c5qV36ajHpdj4Qi0GnE0jUc/yuo33OLFaa0d+crTD5s= golang.org/x/image v0.21.0/go.mod h1:vUbsLavqK/W303ZroQQVKQ+Af3Yl6Uz1Ppu5J/cLz78= golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= golang.org/x/mod v0.17.0 h1:zY54UmvipHiNd+pm+m0x9KhZ9hl1/7QNMyxXbc6ICqA= +golang.org/x/net v0.0.0-20180218175443-cbe0f9307d01/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= @@ -83,8 +116,10 @@ golang.org/x/net v0.24.0 h1:1PcaxkF854Fu3+lvBIx5SYn9wRlBzzcnHZSiaFFAb0w= golang.org/x/net v0.24.0/go.mod h1:2Q7sJY5mzlzWjKtYUEXSlBWCdyaioyXzRB2RtU8KVE8= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.8.0 h1:3NFvSEYkUoMifnESzZl15y791HH1qU2xm6eCJU5ZPXQ= +golang.org/x/sync v0.9.0 h1:fEo0HyrW1GIgZdpbhCRO0PkJajUS5H9IFUztCgEo2jQ= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= @@ -101,8 +136,8 @@ golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= -golang.org/x/text v0.19.0 h1:kTxAhCbGbxhK0IwgSKiMO5awPoDQ0RpfiVYBfK860YM= -golang.org/x/text v0.19.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY= +golang.org/x/text v0.20.0 h1:gK/Kv2otX8gz+wn7Rmb3vT96ZwuoxnQlY+HlJVj7Qug= +golang.org/x/text v0.20.0/go.mod h1:D4IsuqiFMhST5bX19pQ9ikHC2GsaKyk/oF+pn3ducp4= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= @@ -113,6 +148,8 @@ gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8 gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gorm.io/gorm v1.30.0 h1:qbT5aPv1UH8gI99OsRlvDToLxW5zR7FzS9acZDOZcgs= +gorm.io/gorm v1.30.0/go.mod h1:8Z33v652h4//uMA76KjeDH8mJXPm1QNCYrMeatR0DOE= modernc.org/cc/v4 v4.21.2 h1:dycHFB/jDc3IyacKipCNSDrjIC0Lm1hyoWOZTRR20Lk= modernc.org/ccgo/v4 v4.17.8 h1:yyWBf2ipA0Y9GGz/MmCmi3EFpKgeS7ICrAFes+suEbs= modernc.org/fileutil v1.3.0 h1:gQ5SIzK3H9kdfai/5x41oQiKValumqNTDXMvKo62HvE= diff --git a/niu/db.go b/niu/db.go new file mode 100644 index 0000000..1bcbf62 --- /dev/null +++ b/niu/db.go @@ -0,0 +1,64 @@ +package niu + +import ( + "fmt" + "github.com/RomiChan/syncx" + "gorm.io/gorm" +) + +var ( + migratedGroups = syncx.Map[string, bool]{} // key: string, value: bool +) + +type t interface { + userInfo | AuctionInfo +} + +func ensureUserInfoTable[T t](gid int64, prefix string) error { + table := fmt.Sprintf("group_%d_%s_info", gid, prefix) + if _, ok := migratedGroups.Load(table); ok { + return nil + } + err := db.Table(table).AutoMigrate(new(T)) + if err != nil { + return err + } + + // 设置为已迁移 + migratedGroups.Store(table, true) + return nil +} + +func TableFor(gid int64, prefix string) *gorm.DB { + return db.Table(fmt.Sprintf("group_%d_%s_info", gid, prefix)) +} + +func listUsers(gid int64) (users, error) { + var us users + err := TableFor(gid, ur).Find(&us).Error + return us, err +} + +func listAuction(gid int64) ([]AuctionInfo, error) { + var as []AuctionInfo + err := TableFor(gid, ac).Order("money DESC").Find(&as).Error + return as, err +} + +func createUser(gid int64, user *userInfo, fix string) error { + return TableFor(gid, fix).Create(user).Error +} + +func getUserByID(gid int64, uid int64, fix string) (*userInfo, error) { + var user userInfo + err := TableFor(gid, fix).Where("user_id = ?", uid).First(&user).Error + return &user, err +} + +func updatesUserByID(gid int64, id int64, fields map[string]interface{}, fix string) error { + return TableFor(gid, fix).Where("user_id = ?", id).Updates(fields).Error +} + +func deleteUserByID(gid int64, id int64, fix string) error { + return TableFor(gid, fix).Where("user_id = ?", id).Delete(&userInfo{}).Error +} diff --git a/niu/main.go b/niu/main.go index 6388b0e..beeca15 100644 --- a/niu/main.go +++ b/niu/main.go @@ -4,20 +4,26 @@ package niu import ( "errors" "fmt" + "github.com/glebarez/sqlite" + "github.com/google/uuid" + "gorm.io/gorm" "os" "strconv" "strings" "sync" - "time" "github.com/FloatTech/floatbox/file" - sql "github.com/FloatTech/sqlite" "github.com/FloatTech/AnimeAPI/wallet" ) +const ( + ur = "user" + ac = "auction" +) + var ( - db = &model{} + db *gorm.DB globalLock sync.Mutex // ErrNoBoys 表示当前没有男孩子可用的错误。 ErrNoBoys = errors.New("暂时没有男孩子哦") @@ -63,30 +69,41 @@ func init() { panic(err) } } - db.sql = sql.New("data/niuniu/niuniu.db") - err := db.sql.Open(time.Hour * 24) + + sdb, err := gorm.Open(sqlite.Open("data/niuniu/niuniu.db"), &gorm.Config{}) if err != nil { panic(err) } + + if err = sdb.AutoMigrate(&niuNiuManager{}); err != nil { + panic(err) + } + + db = sdb + } // DeleteWordNiuNiu ... func DeleteWordNiuNiu(gid, uid int64) error { globalLock.Lock() defer globalLock.Unlock() - return db.deleteWordNiuNiu(gid, uid) + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return err + } + return deleteUserByID(gid, uid, ur) } // SetWordNiuNiu length > 0 就增加 , length < 0 就减小 func SetWordNiuNiu(gid, uid int64, length float64) error { globalLock.Lock() defer globalLock.Unlock() - niu, err := db.getWordNiuNiu(gid, uid) - if err != nil { + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { return err } - niu.Length += length - return db.setWordNiuNiu(gid, niu) + m := map[string]interface{}{ + "length": length, + } + return updatesUserByID(gid, uid, m, ur) } // GetWordNiuNiu ... @@ -94,8 +111,18 @@ func GetWordNiuNiu(gid, uid int64) (float64, error) { globalLock.Lock() defer globalLock.Unlock() - niu, err := db.getWordNiuNiu(gid, uid) - return niu.Length, err + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return 0, err + } + + info, err := getUserByID(gid, uid, ur) + if errors.Is(err, gorm.ErrRecordNotFound) { + return 0, ErrNoNiuNiu + } else if err != nil { + return 0, err + } + + return info.Length, err } // GetRankingInfo 获取排行信息 @@ -104,15 +131,18 @@ func GetRankingInfo(gid int64, t bool) (BaseInfos, error) { defer globalLock.Unlock() var ( list users - err error ) - niuOfGroup, err := db.getAllNiuNiuOfGroup(gid) + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return nil, err + } + + us, err := listUsers(gid) if err != nil { return nil, err } - list = niuOfGroup.filter(t) + list = us.filter(t) list.sort(t) if len(list) == 0 { if t { @@ -123,7 +153,7 @@ func GetRankingInfo(gid int64, t bool) (BaseInfos, error) { f := make(BaseInfos, len(list)) for i, info := range list { f[i] = BaseInfo{ - UID: info.UID, + UID: info.UserID, Length: info.Length, } } @@ -134,20 +164,29 @@ func GetRankingInfo(gid int64, t bool) (BaseInfos, error) { func GetGroupUserRank(gid, uid int64) (int, error) { globalLock.Lock() defer globalLock.Unlock() - niu, err := db.getWordNiuNiu(gid, uid) + + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return 0, err + } + niu, err := getUserByID(gid, uid, ur) if err != nil { return -1, err } - group, err := db.getAllNiuNiuOfGroup(gid) + + group, err := listUsers(gid) if err != nil { return -1, err } + return group.ranking(niu.Length, uid), nil } // View 查看牛牛 func View(gid, uid int64, name string) (string, error) { - i, err := db.getWordNiuNiu(gid, uid) + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return "", err + } + i, err := getUserByID(gid, uid, ur) if err != nil { return "", ErrNoNiuNiu } @@ -159,7 +198,7 @@ func View(gid, uid int64, name string) (string, error) { sexLong = "深" sex = "♀️" } - niuniuList, err := db.getAllNiuNiuOfGroup(gid) + niuniuList, err := listUsers(gid) if err != nil { return "", err } @@ -171,7 +210,10 @@ func View(gid, uid int64, name string) (string, error) { // HitGlue 打胶 func HitGlue(gid, uid int64, prop string) (string, error) { - niuniu, err := db.getWordNiuNiu(gid, uid) + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return "", err + } + niuniu, err := getUserByID(gid, uid, ur) if err != nil { return "", ErrNoNiuNiuTwo } @@ -180,37 +222,62 @@ func HitGlue(gid, uid int64, prop string) (string, error) { if err != nil { return "", err } - if err = db.setWordNiuNiu(gid, niuniu); err != nil { + + if err = TableFor(gid, ur).Where("user_id = ?", uid).Save(niuniu).Error; err != nil { return "", err } + return messages, nil } // Register 注册牛牛 func Register(gid, uid int64) (string, error) { - if _, err := db.getWordNiuNiu(gid, uid); err == nil { + globalLock.Lock() + defer globalLock.Unlock() + + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return "", err + } + + if _, err := getUserByID(gid, uid, ur); err == nil { return "", ErrAlreadyRegistered } // 获取初始长度 - length := db.newLength() + length := newLength() u := userInfo{ - UID: uid, + UserID: uid, + NiuID: uuid.New(), Length: length, } - if err := db.setWordNiuNiu(gid, &u); err != nil { + + if err := createUser(gid, &u, ur); err != nil { + return "", err + } + + if err := db.Model(&niuNiuManager{}).Create(&niuNiuManager{ + NiuID: u.NiuID, + }).Error; err != nil { return "", err } + return fmt.Sprintf("注册成功,你的牛牛现在有%.2fcm", u.Length), nil } // JJ ... func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength float64, err error) { - myniuniu, err := db.getWordNiuNiu(gid, uid) + globalLock.Lock() + defer globalLock.Unlock() + + if err = ensureUserInfoTable[userInfo](gid, ur); err != nil { + return "", 0, ErrNoNiuNiu + } + + myniuniu, err := getUserByID(gid, uid, ur) if err != nil { return "", 0, ErrNoNiuNiu } - adduserniuniu, err := db.getWordNiuNiu(gid, adduser) + adduserniuniu, err := getUserByID(gid, adduser, ur) if err != nil { return "", 0, ErrAdduserNoNiuNiu } @@ -219,44 +286,73 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo return "", 0, ErrCannotFight } + m := map[string]interface{}{} message, err = myniuniu.processJJ(adduserniuniu, prop) if err != nil { - return "", 0, err + return "", 0, ErrNoNiuNiu } - if err = db.setWordNiuNiu(gid, myniuniu); err != nil { - return "", 0, err + m["length"] = myniuniu.Length + if err = updatesUserByID(gid, uid, m, ur); err != nil { + return "", 0, ErrNoNiuNiu } - if err = db.setWordNiuNiu(gid, adduserniuniu); err != nil { - return "", 0, err + m["length"] = adduserniuniu.Length + if err = updatesUserByID(gid, adduser, m, ur); err != nil { + return "", 0, ErrNoNiuNiu } adduserLength = adduserniuniu.Length - if err = db.setWordNiuNiu(gid, adduserniuniu); err != nil { - return "", 0, err - } - return } // Cancel 注销牛牛 func Cancel(gid, uid int64) (string, error) { - _, err := db.getWordNiuNiu(gid, uid) + globalLock.Lock() + defer globalLock.Unlock() + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return "", err + } + _, err := getUserByID(gid, uid, ur) if err != nil { return "", ErrNoNiuNiuTwo } - err = db.deleteWordNiuNiu(gid, uid) + err = deleteUserByID(gid, uid, ur) if err != nil { err = errors.New("遇到不可抗力因素,注销失败!") } + err = db.Model(&niuNiuManager{}).Where("niu_id = ?", uid).Update("status", 2).Error return "注销成功,你已经没有牛牛了", err } // Redeem 赎牛牛 func Redeem(gid, uid int64, lastLength float64) error { + globalLock.Lock() + defer globalLock.Unlock() + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return err + } + + _, err := getUserByID(gid, uid, ur) + if err != nil { + return ErrNoNiuNiu + } + + /* var n niuNiuManager + if err = db.Where("niu_id = ?", niuID).First(&n).Error; err != nil { + return err + } + + switch n.Status { + case 1: + return errors.New("你的牛牛已经被拍卖无法赎回") + case 2: + return errors.New("你的牛牛已经被注销无法赎回") + }*/ + money := wallet.GetWalletOf(uid) + if money < 150 { var builder strings.Builder walletName := wallet.GetWalletName() @@ -269,23 +365,22 @@ func Redeem(gid, uid int64, lastLength float64) error { return errors.New(builder.String()) } - if err := wallet.InsertWalletOf(uid, -150); err != nil { + if err = wallet.InsertWalletOf(uid, -150); err != nil { return err } - niu, err := db.getWordNiuNiu(gid, uid) - if err != nil { - return ErrNoNiuNiu - } - - niu.Length = lastLength - - return db.setWordNiuNiu(gid, niu) + return TableFor(gid, ur).Where("user_id = ?", uid).Update("length", lastLength).Error } // Store 牛牛商店 func Store(gid, uid int64, n int) error { - info, err := db.getWordNiuNiu(gid, uid) + globalLock.Lock() + defer globalLock.Unlock() + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return err + } + + info, err := getUserByID(gid, uid, ur) if err != nil { return err } @@ -303,12 +398,20 @@ func Store(gid, uid int64, n int) error { return err } - return db.setWordNiuNiu(uid, info) + return TableFor(gid, ur).Save(info).Error } // Sell 出售牛牛 func Sell(gid, uid int64) (string, error) { - niu, err := db.getWordNiuNiu(gid, uid) + globalLock.Lock() + defer globalLock.Unlock() + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return "", err + } + if err := ensureUserInfoTable[AuctionInfo](gid, ac); err != nil { + return "", err + } + niu, err := getUserByID(gid, uid, ur) if err != nil { return "", ErrNoNiuNiu } @@ -317,7 +420,7 @@ func Sell(gid, uid int64) (string, error) { return "", errors.New(message) } - if err := db.deleteWordNiuNiu(gid, uid); err != nil { + if err = deleteUserByID(gid, uid, ur); err != nil { return "", err } @@ -326,16 +429,23 @@ func Sell(gid, uid int64) (string, error) { return message, err } - infos, _ := db.getAllNiuNiuAuction(gid) + if err = db.Model(&niu).Where("niu_id = ?", niu.NiuID).Update("status", 1).Error; err != nil { + return message, err + } u := AuctionInfo{ - ID: len(infos), - UserID: niu.UID, + UserID: uid, + NiuID: niu.NiuID, Length: niu.Length, Money: money * 2, } - err = db.setNiuNiuAuction(gid, &u) + if err = TableFor(gid, ac).Create(&u).Error; err != nil { + return "", err + } + + db.Model(&niuNiuManager{}).Where("niu_id = ?", niu.NiuID).Update("status", 1) + return message, err } @@ -343,41 +453,61 @@ func Sell(gid, uid int64) (string, error) { func ShowAuction(gid int64) ([]AuctionInfo, error) { globalLock.Lock() defer globalLock.Unlock() - return db.getAllNiuNiuAuction(gid) + if err := ensureUserInfoTable[AuctionInfo](gid, ac); err != nil { + return nil, err + } + return listAuction(gid) } // Auction 购买牛牛 func Auction(gid, uid int64, index int) (string, error) { - infos, err := db.getAllNiuNiuAuction(gid) - if err != nil { + globalLock.Lock() + defer globalLock.Unlock() + if err := ensureUserInfoTable[AuctionInfo](gid, ac); err != nil { + return "", err + } + + infos, err := listAuction(gid) + if len(infos) == 0 || err != nil { return "", ErrNoNiuNiuINAuction } - if err := wallet.InsertWalletOf(uid, -infos[index].Money); err != nil { + + var info AuctionInfo + if err = TableFor(gid, ac).Where("id = ?", index).First(&info).Error; err != nil { + return "", err + } + + if err = wallet.InsertWalletOf(uid, -info.Money); err != nil { return "", ErrNoMoney } - niu, err := db.getWordNiuNiu(gid, uid) + niu, err := getUserByID(gid, uid, ur) if err != nil { - niu.UID = uid + niu.UserID = uid } - niu.Length = infos[index].Length + niu.Length = info.Length + niu.NiuID = info.NiuID - if infos[index].Money >= 500 { + if info.Money >= 500 { niu.WeiGe += 2 - niu.Philter += 2 + niu.MeiYao += 2 } - if err = db.deleteNiuNiuAuction(gid, uint(index)); err != nil { + if err = TableFor(gid, ac).Delete(&info).Error; err != nil { return "", err } - if err = db.setWordNiuNiu(gid, niu); err != nil { + if err = TableFor(gid, ur).Save(&niu).Error; err != nil { return "", err } - if infos[index].Money >= 500 { + if err = db.Model(&niuNiuManager{}).Where("niu_id = ?", niu.NiuID).Update("status", 0).Error; err != nil { + return "", err + } + + if info.Money >= 500 { return fmt.Sprintf("恭喜你购买成功,当前长度为%.2fcm,此次购买将赠送你2个伟哥,2个媚药", niu.Length), nil } @@ -386,7 +516,12 @@ func Auction(gid, uid int64, index int) (string, error) { // Bag 牛牛背包 func Bag(gid, uid int64) (string, error) { - niu, err := db.getWordNiuNiu(gid, uid) + globalLock.Lock() + defer globalLock.Unlock() + if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { + return "", err + } + niu, err := getUserByID(gid, uid, ur) if err != nil { return "", ErrNoNiuNiu } @@ -396,7 +531,7 @@ func Bag(gid, uid int64) (string, error) { result.WriteString("当前牛牛背包如下\n") result.WriteString(fmt.Sprintf("伟哥: %v\n", niu.WeiGe)) - result.WriteString(fmt.Sprintf("媚药: %v\n", niu.Philter)) + result.WriteString(fmt.Sprintf("媚药: %v\n", niu.MeiYao)) result.WriteString(fmt.Sprintf("击剑神器: %v\n", niu.Artifact)) result.WriteString(fmt.Sprintf("击剑神稽: %v\n", niu.ShenJi)) diff --git a/niu/models.go b/niu/models.go index 1acdc27..753076f 100644 --- a/niu/models.go +++ b/niu/models.go @@ -4,49 +4,55 @@ package niu import ( "errors" "fmt" + "github.com/google/uuid" + "gorm.io/gorm" "math" "math/rand" "sort" - "strconv" - "sync" - - sql "github.com/FloatTech/sqlite" + "time" ) var ( daJiaoProps = []string{"伟哥", "媚药"} jjPorps = []string{"击剑神器", "击剑神稽"} - query = "WHERE UID = ?" ) type users []*userInfo -type model struct { - sql sql.Sqlite - sync.RWMutex +type niuNiuManager struct { + ID uint `gorm:"primaryKey;autoIncrement"` + CreatedAt time.Time + UpdatedAt time.Time + NiuID uuid.UUID `gorm:"type:varchar(36);uniqueIndex"` + Status int `gorm:"default:0"` // 0正常 1拍卖 2注销 } +// UserInfo 结构体 type userInfo struct { - UID int64 - Length float64 - UserCount int - WeiGe int // 伟哥 - Philter int // 媚药 - Artifact int // 击剑神器 - ShenJi int // 击剑神稽 - Buff1 int // 暂定 - Buff2 int // 暂定 - Buff3 int // 暂定 - Buff4 int // 暂定 - Buff5 int // 暂定 + gorm.Model + UserID int64 `gorm:"column:user_id;index"` + NiuID uuid.UUID `gorm:"type:char(36);index"` + Length float64 `gorm:"default:1"` + WeiGe int `gorm:"default:0"` + MeiYao int `gorm:"default:0"` + Artifact int `gorm:"default:0"` + ShenJi int `gorm:"default:0"` + Buff2 int `gorm:"default:0"` + Buff3 int `gorm:"default:0"` + Buff4 int `gorm:"default:0"` + Buff5 int `gorm:"default:0"` } -// AuctionInfo 拍卖信息 +// AuctionInfo 结构体 type AuctionInfo struct { - ID int `db:"id"` - UserID int64 `db:"user_id"` - Length float64 `db:"length"` - Money int `db:"money"` + ID uint `gorm:"primaryKey"` + CreatedAt time.Time + UpdatedAt time.Time + + UserID int64 `gorm:"column:user_id;index"` + NiuID uuid.UUID `gorm:"type:varchar(36);uniqueIndex"` + Length float64 `gorm:"default:0.01"` + Money int } // BaseInfo ... @@ -100,7 +106,7 @@ func (m users) sort(isDesc bool) { func (m users) ranking(niuniu float64, uid int64) int { m.sort(niuniu > 0) for i, user := range m { - if user.UID == uid { + if user.UserID == uid { return i + 1 } } @@ -118,12 +124,12 @@ func (u *userInfo) useWeiGe() (string, float64) { }), niuniu } -func (u *userInfo) usePhilter() (string, float64) { +func (u *userInfo) useMeiYao() (string, float64) { niuniu := u.Length reduce := math.Abs(hitGlue(niuniu)) niuniu -= reduce return randomChoice([]string{ - fmt.Sprintf("你使用媚药,咿呀咿呀一下使当前长度发生了一些变化,当前长度%.2f", niuniu), + fmt.Sprintf("你使用媚药,咿呀咿呀一下使当前长度发生了一些变化,当前长度%.2fcm", niuniu), fmt.Sprintf("看来你追求的是‘微观之美’,故意使用道具让牛牛凹进去了%.2fcm!", reduce), fmt.Sprintf("缩小奇迹’在你身上发生了,牛牛凹进去了%.2fcm,你的选择真是独特!", reduce), }), niuniu @@ -187,15 +193,17 @@ func (u *userInfo) applyProp(props string) error { errMsg string }{ "伟哥": {&u.WeiGe, "你还没有伟哥呢,不能使用"}, - "媚药": {&u.Philter, "你还没有媚药呢,不能使用"}, + "媚药": {&u.MeiYao, "你还没有媚药呢,不能使用"}, "击剑神器": {&u.Artifact, "你还没有击剑神器呢,不能使用"}, "击剑神稽": {&u.ShenJi, "你还没有击剑神稽呢,不能使用"}, } - if propInfo, ok := propsMap[props]; ok { - return u.useItem(propInfo.itemCount, propInfo.errMsg) + propInfo, ok := propsMap[props] + if !ok { + return ErrPropNotFound } - return ErrPropNotFound + + return u.useItem(propInfo.itemCount, propInfo.errMsg) } func (u *userInfo) useItem(itemCount *int, errMsg string) error { @@ -203,6 +211,7 @@ func (u *userInfo) useItem(itemCount *int, errMsg string) error { *itemCount-- return nil } + fmt.Println(*u) return errors.New(errMsg) } @@ -255,7 +264,7 @@ func (u *userInfo) purchaseItem(n int) (int, error) { u.WeiGe += 5 case 2: money = 300 - u.Philter += 5 + u.MeiYao += 5 case 3: money = 500 u.Artifact += 2 @@ -268,20 +277,16 @@ func (u *userInfo) purchaseItem(n int) (int, error) { return money, err } -func (u *userInfo) processDaJiao(props string) (string, error) { - var ( - messages string - info userInfo - err error - f float64 - ) - info = *u +func (u *userInfo) processDaJiao(props string) (messages string, err error) { + var f float64 + + info := *u if props != "" { - err := u.checkProps(props, "dajiao") + err = u.checkProps(props, "dajiao") if err != nil { return "", err } - if err := u.applyProp(props); err != nil { + if err = u.applyProp(props); err != nil { return "", err } } @@ -289,16 +294,14 @@ func (u *userInfo) processDaJiao(props string) (string, error) { case u.WeiGe-info.WeiGe != 0: messages, f = u.useWeiGe() u.Length = f - - case u.Philter-info.Philter != 0: - messages, f = u.usePhilter() + case u.MeiYao-info.MeiYao != 0: + messages, f = u.useMeiYao() u.Length = f - default: messages, f = hitGlueNiuNiu(u.Length) u.Length = f } - return messages, err + return } func (u *userInfo) processJJ(adduserniuniu *userInfo, props string) (string, error) { @@ -311,11 +314,11 @@ func (u *userInfo) processJJ(adduserniuniu *userInfo, props string) (string, err ) info = *u if props != "" { - err := u.checkProps(props, "jj") + err = u.checkProps(props, "jj") if err != nil { return "", err } - if err := u.applyProp(props); err != nil { + if err = u.applyProp(props); err != nil { return "", err } } @@ -338,83 +341,6 @@ func (u *userInfo) processJJ(adduserniuniu *userInfo, props string) (string, err return fencingResult, err } -func (db *model) newLength() float64 { +func newLength() float64 { return float64(rand.Intn(9)+1) + (float64(rand.Intn(100)) / 100) } - -func (db *model) getWordNiuNiu(gid, uid int64) (*userInfo, error) { - db.RLock() - defer db.RUnlock() - - var u userInfo - err := db.sql.Find(strconv.FormatInt(gid, 10), &u, query, uid) - return &u, err -} - -func (db *model) setWordNiuNiu(gid int64, u *userInfo) error { - db.Lock() - defer db.Unlock() - err := db.sql.Insert(strconv.FormatInt(gid, 10), u) - if err != nil { - err = db.sql.Create(strconv.FormatInt(gid, 10), &userInfo{}) - if err != nil { - return err - } - err = db.sql.Insert(strconv.FormatInt(gid, 10), u) - } - return err -} - -func (db *model) deleteWordNiuNiu(gid, uid int64) error { - db.Lock() - defer db.Unlock() - return db.sql.Del(strconv.FormatInt(gid, 10), query, uid) -} - -func (db *model) getAllNiuNiuOfGroup(gid int64) (users, error) { - db.Lock() - defer db.Unlock() - var user userInfo - var useras users - err := db.sql.FindFor(fmt.Sprintf("%d", gid), &user, "", - func() error { - newUser := user - useras = append(useras, &newUser) - return nil - }) - return useras, err -} - -func (db *model) setNiuNiuAuction(gid int64, u *AuctionInfo) error { - db.Lock() - defer db.Unlock() - err := db.sql.Insert(fmt.Sprintf("auction_%d", gid), u) - if err != nil { - err = db.sql.Create(fmt.Sprintf("auction_%d", gid), &AuctionInfo{}) - if err != nil { - return err - } - err = db.sql.Insert(fmt.Sprintf("auction_%d", gid), u) - } - return err -} - -func (db *model) deleteNiuNiuAuction(gid int64, id uint) error { - db.Lock() - defer db.Unlock() - return db.sql.Del(fmt.Sprintf("auction_%d", gid), "WHERE id = ?", id) -} - -func (db *model) getAllNiuNiuAuction(gid int64) ([]AuctionInfo, error) { - db.RLock() - defer db.RUnlock() - var user AuctionInfo - var useras []AuctionInfo - err := db.sql.FindFor(fmt.Sprintf("auction_%d", gid), &user, "", - func() error { - useras = append(useras, user) - return nil - }) - - return useras, err -} diff --git a/niu/utils.go b/niu/utils.go index 2322990..9bb8894 100644 --- a/niu/utils.go +++ b/niu/utils.go @@ -222,20 +222,24 @@ func fence(rd float64) float64 { } func hitGlue(l float64) float64 { - if l == 0 { + l = math.Abs(l) + if l < 0.1 { l = 0.1 } - l = math.Abs(l) + + var logValue float64 switch { - case l > 1 && l <= 10: - return rand.Float64() * math.Log2(l*2) - case 10 < l && l <= 100: - return rand.Float64() * math.Log2(l*1.5) - case 100 < l && l <= 1000: - return rand.Float64() * (math.Log10(l*1.5) * 2) case l > 1000: - return rand.Float64() * (math.Log10(l) * 2) - default: - return rand.Float64() + logValue = math.Log10(l) * 2 + case l > 100: + logValue = math.Log10(l*1.5) * 2 + case l > 10: + logValue = math.Log2(l * 1.5) + case l > 1: + logValue = math.Log2(l * 2) + default: // 0.1 <= l <= 1 + logValue = 1 } + + return rand.Float64() * logValue } From 1b503b7020f6ba72b3aca5ef604517f5684b962c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Sat, 28 Jun 2025 21:55:54 +0800 Subject: [PATCH 02/16] =?UTF-8?q?=E4=BF=AElint=EF=BC=8C=E4=BC=98=E5=8C=96?= =?UTF-8?q?=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 19 ++++++++----------- niu/main.go | 42 ++++++++++++++++++++++-------------------- niu/test_test.go | 4 ++-- 3 files changed, 32 insertions(+), 33 deletions(-) diff --git a/niu/db.go b/niu/db.go index 1bcbf62..e5789b8 100644 --- a/niu/db.go +++ b/niu/db.go @@ -10,11 +10,7 @@ var ( migratedGroups = syncx.Map[string, bool]{} // key: string, value: bool ) -type t interface { - userInfo | AuctionInfo -} - -func ensureUserInfoTable[T t](gid int64, prefix string) error { +func ensureUserInfoTable[T userInfo | AuctionInfo](gid int64, prefix string) error { table := fmt.Sprintf("group_%d_%s_info", gid, prefix) if _, ok := migratedGroups.Load(table); ok { return nil @@ -29,6 +25,7 @@ func ensureUserInfoTable[T t](gid int64, prefix string) error { return nil } +// TableFor 大写是为了防止数据操作哪里有问题留个保底可以在zbp的项目里直接改 func TableFor(gid int64, prefix string) *gorm.DB { return db.Table(fmt.Sprintf("group_%d_%s_info", gid, prefix)) } @@ -49,16 +46,16 @@ func createUser(gid int64, user *userInfo, fix string) error { return TableFor(gid, fix).Create(user).Error } -func getUserByID(gid int64, uid int64, fix string) (*userInfo, error) { +func getUserByID(gid int64, uid int64) (*userInfo, error) { var user userInfo - err := TableFor(gid, fix).Where("user_id = ?", uid).First(&user).Error + err := TableFor(gid, ur).Where("user_id = ?", uid).First(&user).Error return &user, err } -func updatesUserByID(gid int64, id int64, fields map[string]interface{}, fix string) error { - return TableFor(gid, fix).Where("user_id = ?", id).Updates(fields).Error +func updatesUserByID(gid int64, id int64, fields map[string]interface{}) error { + return TableFor(gid, ur).Where("user_id = ?", id).Updates(fields).Error } -func deleteUserByID(gid int64, id int64, fix string) error { - return TableFor(gid, fix).Where("user_id = ?", id).Delete(&userInfo{}).Error +func deleteUserByID(gid int64, id int64) error { + return TableFor(gid, ur).Where("user_id = ?", id).Delete(&userInfo{}).Error } diff --git a/niu/main.go b/niu/main.go index beeca15..f448da9 100644 --- a/niu/main.go +++ b/niu/main.go @@ -25,6 +25,8 @@ const ( var ( db *gorm.DB globalLock sync.Mutex + + errCancelFail = errors.New("遇到不可抗力因素,注销失败!") // ErrNoBoys 表示当前没有男孩子可用的错误。 ErrNoBoys = errors.New("暂时没有男孩子哦") @@ -90,7 +92,7 @@ func DeleteWordNiuNiu(gid, uid int64) error { if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { return err } - return deleteUserByID(gid, uid, ur) + return deleteUserByID(gid, uid) } // SetWordNiuNiu length > 0 就增加 , length < 0 就减小 @@ -103,7 +105,7 @@ func SetWordNiuNiu(gid, uid int64, length float64) error { m := map[string]interface{}{ "length": length, } - return updatesUserByID(gid, uid, m, ur) + return updatesUserByID(gid, uid, m) } // GetWordNiuNiu ... @@ -115,7 +117,7 @@ func GetWordNiuNiu(gid, uid int64) (float64, error) { return 0, err } - info, err := getUserByID(gid, uid, ur) + info, err := getUserByID(gid, uid) if errors.Is(err, gorm.ErrRecordNotFound) { return 0, ErrNoNiuNiu } else if err != nil { @@ -168,7 +170,7 @@ func GetGroupUserRank(gid, uid int64) (int, error) { if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { return 0, err } - niu, err := getUserByID(gid, uid, ur) + niu, err := getUserByID(gid, uid) if err != nil { return -1, err } @@ -186,7 +188,7 @@ func View(gid, uid int64, name string) (string, error) { if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { return "", err } - i, err := getUserByID(gid, uid, ur) + i, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiu } @@ -213,7 +215,7 @@ func HitGlue(gid, uid int64, prop string) (string, error) { if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { return "", err } - niuniu, err := getUserByID(gid, uid, ur) + niuniu, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiuTwo } @@ -239,7 +241,7 @@ func Register(gid, uid int64) (string, error) { return "", err } - if _, err := getUserByID(gid, uid, ur); err == nil { + if _, err := getUserByID(gid, uid); err == nil { return "", ErrAlreadyRegistered } // 获取初始长度 @@ -272,12 +274,12 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo return "", 0, ErrNoNiuNiu } - myniuniu, err := getUserByID(gid, uid, ur) + myniuniu, err := getUserByID(gid, uid) if err != nil { return "", 0, ErrNoNiuNiu } - adduserniuniu, err := getUserByID(gid, adduser, ur) + adduserniuniu, err := getUserByID(gid, adduser) if err != nil { return "", 0, ErrAdduserNoNiuNiu } @@ -293,12 +295,12 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo } m["length"] = myniuniu.Length - if err = updatesUserByID(gid, uid, m, ur); err != nil { + if err = updatesUserByID(gid, uid, m); err != nil { return "", 0, ErrNoNiuNiu } m["length"] = adduserniuniu.Length - if err = updatesUserByID(gid, adduser, m, ur); err != nil { + if err = updatesUserByID(gid, adduser, m); err != nil { return "", 0, ErrNoNiuNiu } @@ -314,13 +316,13 @@ func Cancel(gid, uid int64) (string, error) { if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { return "", err } - _, err := getUserByID(gid, uid, ur) + _, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiuTwo } - err = deleteUserByID(gid, uid, ur) + err = deleteUserByID(gid, uid) if err != nil { - err = errors.New("遇到不可抗力因素,注销失败!") + return "", errCancelFail } err = db.Model(&niuNiuManager{}).Where("niu_id = ?", uid).Update("status", 2).Error return "注销成功,你已经没有牛牛了", err @@ -334,7 +336,7 @@ func Redeem(gid, uid int64, lastLength float64) error { return err } - _, err := getUserByID(gid, uid, ur) + _, err := getUserByID(gid, uid) if err != nil { return ErrNoNiuNiu } @@ -380,7 +382,7 @@ func Store(gid, uid int64, n int) error { return err } - info, err := getUserByID(gid, uid, ur) + info, err := getUserByID(gid, uid) if err != nil { return err } @@ -411,7 +413,7 @@ func Sell(gid, uid int64) (string, error) { if err := ensureUserInfoTable[AuctionInfo](gid, ac); err != nil { return "", err } - niu, err := getUserByID(gid, uid, ur) + niu, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiu } @@ -420,7 +422,7 @@ func Sell(gid, uid int64) (string, error) { return "", errors.New(message) } - if err = deleteUserByID(gid, uid, ur); err != nil { + if err = deleteUserByID(gid, uid); err != nil { return "", err } @@ -481,7 +483,7 @@ func Auction(gid, uid int64, index int) (string, error) { return "", ErrNoMoney } - niu, err := getUserByID(gid, uid, ur) + niu, err := getUserByID(gid, uid) if err != nil { niu.UserID = uid @@ -521,7 +523,7 @@ func Bag(gid, uid int64) (string, error) { if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { return "", err } - niu, err := getUserByID(gid, uid, ur) + niu, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiu } diff --git a/niu/test_test.go b/niu/test_test.go index 4cfae11..913a332 100644 --- a/niu/test_test.go +++ b/niu/test_test.go @@ -4,7 +4,7 @@ import "testing" func TestCreateUserInfoByProps(t *testing.T) { user := &userInfo{ - UID: 123, + UserID: 123, Length: 12, WeiGe: 2, } @@ -17,7 +17,7 @@ func TestCreateUserInfoByProps(t *testing.T) { func TestCheckProp(t *testing.T) { user := &userInfo{ - UID: 123, + UserID: 123, Length: 12, WeiGe: 2, } From 6a7c3e3a2a68618ea796a4406d9687b7769161ee Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Thu, 10 Jul 2025 19:51:43 +0800 Subject: [PATCH 03/16] =?UTF-8?q?gorm=E4=BF=AE=E6=94=B9=E6=88=90v1?= =?UTF-8?q?=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- go.mod | 3 +-- niu/db.go | 4 ++-- niu/main.go | 9 ++++----- niu/models.go | 19 ++++++++----------- 4 files changed, 15 insertions(+), 20 deletions(-) diff --git a/go.mod b/go.mod index 71667f3..253d6c7 100644 --- a/go.mod +++ b/go.mod @@ -10,15 +10,14 @@ require ( github.com/corona10/goimagehash v1.1.0 github.com/fumiama/go-base16384 v1.7.0 github.com/fumiama/terasu v0.0.0-20241027183601-987ab91031ce - github.com/glebarez/sqlite v1.11.0 github.com/google/uuid v1.6.0 + github.com/jinzhu/gorm v1.9.16 github.com/pkg/errors v0.9.1 github.com/pkumza/numcn v1.0.0 github.com/sirupsen/logrus v1.9.3 github.com/stretchr/testify v1.9.0 github.com/tidwall/gjson v1.18.0 golang.org/x/image v0.21.0 - gorm.io/gorm v1.30.0 ) require ( diff --git a/niu/db.go b/niu/db.go index e5789b8..0bd1138 100644 --- a/niu/db.go +++ b/niu/db.go @@ -3,7 +3,7 @@ package niu import ( "fmt" "github.com/RomiChan/syncx" - "gorm.io/gorm" + "github.com/jinzhu/gorm" ) var ( @@ -15,7 +15,7 @@ func ensureUserInfoTable[T userInfo | AuctionInfo](gid int64, prefix string) err if _, ok := migratedGroups.Load(table); ok { return nil } - err := db.Table(table).AutoMigrate(new(T)) + err := db.Table(table).AutoMigrate(new(T)).Error if err != nil { return err } diff --git a/niu/main.go b/niu/main.go index f448da9..42c6ef8 100644 --- a/niu/main.go +++ b/niu/main.go @@ -4,9 +4,8 @@ package niu import ( "errors" "fmt" - "github.com/glebarez/sqlite" "github.com/google/uuid" - "gorm.io/gorm" + "github.com/jinzhu/gorm" "os" "strconv" "strings" @@ -72,16 +71,16 @@ func init() { } } - sdb, err := gorm.Open(sqlite.Open("data/niuniu/niuniu.db"), &gorm.Config{}) + sdb, err := gorm.Open("sqlite3", "data/niuniu/niuniu.db") if err != nil { panic(err) } - if err = sdb.AutoMigrate(&niuNiuManager{}); err != nil { + if err = sdb.AutoMigrate(&niuNiuManager{}).Error; err != nil { panic(err) } - db = sdb + db = sdb.LogMode(false) } diff --git a/niu/models.go b/niu/models.go index 753076f..6324416 100644 --- a/niu/models.go +++ b/niu/models.go @@ -5,7 +5,7 @@ import ( "errors" "fmt" "github.com/google/uuid" - "gorm.io/gorm" + "github.com/jinzhu/gorm" "math" "math/rand" "sort" @@ -20,10 +20,9 @@ var ( type users []*userInfo type niuNiuManager struct { - ID uint `gorm:"primaryKey;autoIncrement"` + ID uint `gorm:"primary_key"` CreatedAt time.Time - UpdatedAt time.Time - NiuID uuid.UUID `gorm:"type:varchar(36);uniqueIndex"` + NiuID uuid.UUID `gorm:"type:varchar(36);unique_index"` Status int `gorm:"default:0"` // 0正常 1拍卖 2注销 } @@ -45,14 +44,12 @@ type userInfo struct { // AuctionInfo 结构体 type AuctionInfo struct { - ID uint `gorm:"primaryKey"` + ID uint `gorm:"primary_key"` CreatedAt time.Time - UpdatedAt time.Time - - UserID int64 `gorm:"column:user_id;index"` - NiuID uuid.UUID `gorm:"type:varchar(36);uniqueIndex"` - Length float64 `gorm:"default:0.01"` - Money int + UserID int64 `gorm:"column:user_id;index"` + NiuID uuid.UUID `gorm:"type:varchar(36);unique_index"` + Length float64 `gorm:"default:0.01"` + Money int } // BaseInfo ... From fdf474ae6a2a69ecb453308fc38696c42eb1fd7c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Thu, 10 Jul 2025 19:53:54 +0800 Subject: [PATCH 04/16] =?UTF-8?q?=E5=88=A0=E9=99=A4go.mod=E4=B8=8D?= =?UTF-8?q?=E4=BD=BF=E7=94=A8=E7=9A=84go-sqlite=E4=BE=9D=E8=B5=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- go.mod | 1 - 1 file changed, 1 deletion(-) diff --git a/go.mod b/go.mod index 253d6c7..64979a3 100644 --- a/go.mod +++ b/go.mod @@ -29,7 +29,6 @@ require ( github.com/fumiama/go-registry v0.2.7 // indirect github.com/fumiama/go-simple-protobuf v0.2.0 // indirect github.com/fumiama/gofastTEA v0.0.10 // indirect - github.com/glebarez/go-sqlite v1.21.2 // indirect github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect github.com/jinzhu/inflection v1.0.0 // indirect github.com/jinzhu/now v1.1.5 // indirect From 61f930dc854ae604aabc218778fa928e7a431ac0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Thu, 10 Jul 2025 21:48:06 +0800 Subject: [PATCH 05/16] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E8=B0=83=E7=94=A8proce?= =?UTF-8?q?ssJJ=E6=96=B9=E6=B3=95=E6=97=B6=E8=BF=94=E5=9B=9E=E7=9A=84?= =?UTF-8?q?=E9=94=99=E8=AF=AFerr=EF=BC=8C=E4=BC=98=E5=8C=96jj=E5=87=BD?= =?UTF-8?q?=E6=95=B0=E7=9A=84=E6=95=B0=E6=8D=AE=E5=BA=93=E6=93=8D=E4=BD=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/main.go | 13 +++++-------- 1 file changed, 5 insertions(+), 8 deletions(-) diff --git a/niu/main.go b/niu/main.go index 42c6ef8..83d65ec 100644 --- a/niu/main.go +++ b/niu/main.go @@ -287,20 +287,17 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo return "", 0, ErrCannotFight } - m := map[string]interface{}{} message, err = myniuniu.processJJ(adduserniuniu, prop) if err != nil { - return "", 0, ErrNoNiuNiu + return "", 0, err } - m["length"] = myniuniu.Length - if err = updatesUserByID(gid, uid, m); err != nil { - return "", 0, ErrNoNiuNiu + if err = TableFor(gid, ur).Where("user_id =?", uid).Update("length", myniuniu.Length).Error; err != nil { + return "", 0, err } - m["length"] = adduserniuniu.Length - if err = updatesUserByID(gid, adduser, m); err != nil { - return "", 0, ErrNoNiuNiu + if err = TableFor(gid, ur).Where("user_id =?", adduser).Update("length", adduserniuniu.Length).Error; err != nil { + return "", 0, err } adduserLength = adduserniuniu.Length From 87bd28ffc40c8792d96117157140d58070de180b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Mon, 28 Jul 2025 19:25:43 +0800 Subject: [PATCH 06/16] =?UTF-8?q?=E4=BC=98=E5=8C=96purchaseItem=E6=96=B9?= =?UTF-8?q?=E6=B3=95,=E5=88=A0=E9=99=A4Redeem=E5=87=BD=E6=95=B0=E7=9A=84?= =?UTF-8?q?=E6=97=A0=E7=94=A8=E6=B3=A8=E9=87=8A=E4=BB=A3=E7=A0=81,?= =?UTF-8?q?=E4=BF=AE=E6=94=B9=E7=89=9B=E7=89=9B=E5=95=86=E5=BA=97=E7=9A=84?= =?UTF-8?q?=E5=95=86=E5=93=81=E4=B8=BA=E5=8F=AF=E8=87=AA=E5=AE=9A=E4=B9=89?= =?UTF-8?q?=E8=B4=AD=E4=B9=B0=E6=95=B0=E9=87=8F,=E4=BC=98=E5=8C=96?= =?UTF-8?q?=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/main.go | 37 ++++++++++++++++--------------------- niu/models.go | 37 ++++++++++++++++--------------------- 2 files changed, 32 insertions(+), 42 deletions(-) diff --git a/niu/main.go b/niu/main.go index 83d65ec..fb3562b 100644 --- a/niu/main.go +++ b/niu/main.go @@ -26,6 +26,10 @@ var ( globalLock sync.Mutex errCancelFail = errors.New("遇到不可抗力因素,注销失败!") + + // ErrInvalidProductID 商品ID无效 + ErrInvalidProductID = errors.New("商品id不存在") + // ErrNoBoys 表示当前没有男孩子可用的错误。 ErrNoBoys = errors.New("暂时没有男孩子哦") @@ -337,24 +341,15 @@ func Redeem(gid, uid int64, lastLength float64) error { return ErrNoNiuNiu } - /* var n niuNiuManager - if err = db.Where("niu_id = ?", niuID).First(&n).Error; err != nil { - return err - } - - switch n.Status { - case 1: - return errors.New("你的牛牛已经被拍卖无法赎回") - case 2: - return errors.New("你的牛牛已经被注销无法赎回") - }*/ - money := wallet.GetWalletOf(uid) - if money < 150 { + price := 150 + + if money < price { var builder strings.Builder walletName := wallet.GetWalletName() - builder.WriteString("赎牛牛需要150") + builder.WriteString("赎牛牛需要") + builder.WriteString(strconv.Itoa(price)) builder.WriteString(walletName) builder.WriteString(",快去赚钱吧,目前仅有:") builder.WriteString(strconv.Itoa(money)) @@ -363,7 +358,7 @@ func Redeem(gid, uid int64, lastLength float64) error { return errors.New(builder.String()) } - if err = wallet.InsertWalletOf(uid, -150); err != nil { + if err = wallet.InsertWalletOf(uid, -price); err != nil { return err } @@ -371,7 +366,7 @@ func Redeem(gid, uid int64, lastLength float64) error { } // Store 牛牛商店 -func Store(gid, uid int64, n int) error { +func Store(gid, uid int64, productID int, quantity int) error { globalLock.Lock() defer globalLock.Unlock() if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { @@ -383,7 +378,7 @@ func Store(gid, uid int64, n int) error { return err } - money, err := info.purchaseItem(n) + money, err := info.purchaseItem(productID, quantity) if err != nil { return err } @@ -442,9 +437,7 @@ func Sell(gid, uid int64) (string, error) { return "", err } - db.Model(&niuNiuManager{}).Where("niu_id = ?", niu.NiuID).Update("status", 1) - - return message, err + return message, db.Model(&niuNiuManager{}).Where("niu_id = ?", niu.NiuID).Update("status", 1).Error } // ShowAuction 展示牛牛拍卖行 @@ -481,8 +474,10 @@ func Auction(gid, uid int64, index int) (string, error) { niu, err := getUserByID(gid, uid) - if err != nil { + if errors.Is(err, gorm.ErrRecordNotFound) { niu.UserID = uid + } else if err != nil { + return "", err } niu.Length = info.Length diff --git a/niu/models.go b/niu/models.go index 6324416..7028ce7 100644 --- a/niu/models.go +++ b/niu/models.go @@ -250,28 +250,23 @@ func (u *userInfo) checkProps(props, propSort string) error { return ErrPropNotFound } -func (u *userInfo) purchaseItem(n int) (int, error) { - var ( - money int - err error - ) - switch n { - case 1: - money = 300 - u.WeiGe += 5 - case 2: - money = 300 - u.MeiYao += 5 - case 3: - money = 500 - u.Artifact += 2 - case 4: - money = 500 - u.ShenJi += 2 - default: - err = errors.New("无效的选择") +func (u *userInfo) purchaseItem(productID, quantity int) (money int, err error) { + + m := map[int]int{ + 1: 300, // 伟哥 + 2: 300, // 媚药 + 3: 500, // 击剑神器 + 4: 500, // 击剑神稽 } - return money, err + + var ok bool + if money, ok = m[productID]; !ok { + return 0, ErrInvalidProductID + } + + money *= quantity + + return } func (u *userInfo) processDaJiao(props string) (messages string, err error) { From fd11da7ed642fcfa5bf052bde6ef0e331832a730 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Thu, 14 Aug 2025 23:42:47 +0800 Subject: [PATCH 07/16] =?UTF-8?q?=E5=B0=86=20ensureTable=20=E5=B0=81?= =?UTF-8?q?=E8=A3=85=E5=88=B0=E9=92=A9=E5=AD=90=E4=B8=AD=EF=BC=8C=E5=87=8F?= =?UTF-8?q?=E5=B0=91=E5=86=97=E4=BD=99=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 40 ++++++++++++++++++++++++++++++++--- niu/main.go | 60 +++-------------------------------------------------- 2 files changed, 40 insertions(+), 60 deletions(-) diff --git a/niu/db.go b/niu/db.go index 0bd1138..3b7f0d1 100644 --- a/niu/db.go +++ b/niu/db.go @@ -4,13 +4,22 @@ import ( "fmt" "github.com/RomiChan/syncx" "github.com/jinzhu/gorm" + "sync" ) var ( migratedGroups = syncx.Map[string, bool]{} // key: string, value: bool + tableHooks []tableHook + hooksMtx sync.RWMutex ) -func ensureUserInfoTable[T userInfo | AuctionInfo](gid int64, prefix string) error { +type tableHook func(gid int64) error + +type model struct { + *gorm.DB +} + +func ensureTable[T userInfo | AuctionInfo](gid int64, prefix string) error { table := fmt.Sprintf("group_%d_%s_info", gid, prefix) if _, ok := migratedGroups.Load(table); ok { return nil @@ -25,9 +34,34 @@ func ensureUserInfoTable[T userInfo | AuctionInfo](gid int64, prefix string) err return nil } +func ensureUserInfo(gid int64) error { + return ensureTable[userInfo](gid, ur) +} + +func ensureAuctionInfo(gid int64) error { + return ensureTable[AuctionInfo](gid, ac) +} + +// registerTableHook 注册钩子 +func registerTableHook(h ...tableHook) { + hooksMtx.Lock() + defer hooksMtx.Unlock() + tableHooks = append(tableHooks, h...) +} + // TableFor 大写是为了防止数据操作哪里有问题留个保底可以在zbp的项目里直接改 -func TableFor(gid int64, prefix string) *gorm.DB { - return db.Table(fmt.Sprintf("group_%d_%s_info", gid, prefix)) +func TableFor(gid int64, prefix string) *model { + // 先执行钩子 + hooksMtx.RLock() + for _, h := range tableHooks { + if err := h(gid); err != nil { + panic(fmt.Sprintf("执行表钩子失败: %v", err)) + } + } + hooksMtx.RUnlock() + + tableName := fmt.Sprintf("group_%d_%s_info", gid, prefix) + return &model{db.Table(tableName)} } func listUsers(gid int64) (users, error) { diff --git a/niu/main.go b/niu/main.go index fb3562b..c536032 100644 --- a/niu/main.go +++ b/niu/main.go @@ -22,7 +22,7 @@ const ( ) var ( - db *gorm.DB + db *model globalLock sync.Mutex errCancelFail = errors.New("遇到不可抗力因素,注销失败!") @@ -84,17 +84,15 @@ func init() { panic(err) } - db = sdb.LogMode(false) + db = &model{sdb.LogMode(false)} + registerTableHook(ensureUserInfo, ensureAuctionInfo) } // DeleteWordNiuNiu ... func DeleteWordNiuNiu(gid, uid int64) error { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return err - } return deleteUserByID(gid, uid) } @@ -102,9 +100,6 @@ func DeleteWordNiuNiu(gid, uid int64) error { func SetWordNiuNiu(gid, uid int64, length float64) error { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return err - } m := map[string]interface{}{ "length": length, } @@ -116,10 +111,6 @@ func GetWordNiuNiu(gid, uid int64) (float64, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return 0, err - } - info, err := getUserByID(gid, uid) if errors.Is(err, gorm.ErrRecordNotFound) { return 0, ErrNoNiuNiu @@ -138,10 +129,6 @@ func GetRankingInfo(gid int64, t bool) (BaseInfos, error) { list users ) - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return nil, err - } - us, err := listUsers(gid) if err != nil { return nil, err @@ -170,9 +157,6 @@ func GetGroupUserRank(gid, uid int64) (int, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return 0, err - } niu, err := getUserByID(gid, uid) if err != nil { return -1, err @@ -188,9 +172,6 @@ func GetGroupUserRank(gid, uid int64) (int, error) { // View 查看牛牛 func View(gid, uid int64, name string) (string, error) { - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return "", err - } i, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiu @@ -215,9 +196,6 @@ func View(gid, uid int64, name string) (string, error) { // HitGlue 打胶 func HitGlue(gid, uid int64, prop string) (string, error) { - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return "", err - } niuniu, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiuTwo @@ -240,10 +218,6 @@ func Register(gid, uid int64) (string, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return "", err - } - if _, err := getUserByID(gid, uid); err == nil { return "", ErrAlreadyRegistered } @@ -273,10 +247,6 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo globalLock.Lock() defer globalLock.Unlock() - if err = ensureUserInfoTable[userInfo](gid, ur); err != nil { - return "", 0, ErrNoNiuNiu - } - myniuniu, err := getUserByID(gid, uid) if err != nil { return "", 0, ErrNoNiuNiu @@ -313,9 +283,6 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo func Cancel(gid, uid int64) (string, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return "", err - } _, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiuTwo @@ -332,9 +299,6 @@ func Cancel(gid, uid int64) (string, error) { func Redeem(gid, uid int64, lastLength float64) error { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return err - } _, err := getUserByID(gid, uid) if err != nil { @@ -369,9 +333,6 @@ func Redeem(gid, uid int64, lastLength float64) error { func Store(gid, uid int64, productID int, quantity int) error { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return err - } info, err := getUserByID(gid, uid) if err != nil { @@ -398,12 +359,6 @@ func Store(gid, uid int64, productID int, quantity int) error { func Sell(gid, uid int64) (string, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return "", err - } - if err := ensureUserInfoTable[AuctionInfo](gid, ac); err != nil { - return "", err - } niu, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiu @@ -444,9 +399,6 @@ func Sell(gid, uid int64) (string, error) { func ShowAuction(gid int64) ([]AuctionInfo, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[AuctionInfo](gid, ac); err != nil { - return nil, err - } return listAuction(gid) } @@ -454,9 +406,6 @@ func ShowAuction(gid int64) ([]AuctionInfo, error) { func Auction(gid, uid int64, index int) (string, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[AuctionInfo](gid, ac); err != nil { - return "", err - } infos, err := listAuction(gid) if len(infos) == 0 || err != nil { @@ -511,9 +460,6 @@ func Auction(gid, uid int64, index int) (string, error) { func Bag(gid, uid int64) (string, error) { globalLock.Lock() defer globalLock.Unlock() - if err := ensureUserInfoTable[userInfo](gid, ur); err != nil { - return "", err - } niu, err := getUserByID(gid, uid) if err != nil { return "", ErrNoNiuNiu From 0a3a03e2483289c846d94bfd04e39916c4b39292 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Thu, 14 Aug 2025 23:49:16 +0800 Subject: [PATCH 08/16] =?UTF-8?q?=E4=BF=AE=E6=94=B9model=20->=20Model?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 6 +++--- niu/main.go | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/niu/db.go b/niu/db.go index 3b7f0d1..561f636 100644 --- a/niu/db.go +++ b/niu/db.go @@ -15,7 +15,7 @@ var ( type tableHook func(gid int64) error -type model struct { +type Model struct { *gorm.DB } @@ -50,7 +50,7 @@ func registerTableHook(h ...tableHook) { } // TableFor 大写是为了防止数据操作哪里有问题留个保底可以在zbp的项目里直接改 -func TableFor(gid int64, prefix string) *model { +func TableFor(gid int64, prefix string) *Model { // 先执行钩子 hooksMtx.RLock() for _, h := range tableHooks { @@ -61,7 +61,7 @@ func TableFor(gid int64, prefix string) *model { hooksMtx.RUnlock() tableName := fmt.Sprintf("group_%d_%s_info", gid, prefix) - return &model{db.Table(tableName)} + return &Model{db.Table(tableName)} } func listUsers(gid int64) (users, error) { diff --git a/niu/main.go b/niu/main.go index c536032..6727628 100644 --- a/niu/main.go +++ b/niu/main.go @@ -22,7 +22,7 @@ const ( ) var ( - db *model + db *Model globalLock sync.Mutex errCancelFail = errors.New("遇到不可抗力因素,注销失败!") @@ -84,7 +84,7 @@ func init() { panic(err) } - db = &model{sdb.LogMode(false)} + db = &Model{sdb.LogMode(false)} registerTableHook(ensureUserInfo, ensureAuctionInfo) } From ed4ff6e0660874844de5702f0f7c50ad2a525eb7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Thu, 14 Aug 2025 23:52:37 +0800 Subject: [PATCH 09/16] =?UTF-8?q?=E5=88=A0=E9=99=A4hooksMtx=E9=94=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/niu/db.go b/niu/db.go index 561f636..a841e16 100644 --- a/niu/db.go +++ b/niu/db.go @@ -4,13 +4,11 @@ import ( "fmt" "github.com/RomiChan/syncx" "github.com/jinzhu/gorm" - "sync" ) var ( migratedGroups = syncx.Map[string, bool]{} // key: string, value: bool tableHooks []tableHook - hooksMtx sync.RWMutex ) type tableHook func(gid int64) error @@ -44,21 +42,17 @@ func ensureAuctionInfo(gid int64) error { // registerTableHook 注册钩子 func registerTableHook(h ...tableHook) { - hooksMtx.Lock() - defer hooksMtx.Unlock() tableHooks = append(tableHooks, h...) } // TableFor 大写是为了防止数据操作哪里有问题留个保底可以在zbp的项目里直接改 func TableFor(gid int64, prefix string) *Model { - // 先执行钩子 - hooksMtx.RLock() + // 先跑钩子 for _, h := range tableHooks { if err := h(gid); err != nil { - panic(fmt.Sprintf("执行表钩子失败: %v", err)) + panic(fmt.Sprintf("执行钩子失败: %v", err)) } } - hooksMtx.RUnlock() tableName := fmt.Sprintf("group_%d_%s_info", gid, prefix) return &Model{db.Table(tableName)} From d1890345523ec71ebae80694601bdf323d6df93b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Thu, 14 Aug 2025 23:54:41 +0800 Subject: [PATCH 10/16] =?UTF-8?q?=E4=BF=AElint?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 1 + 1 file changed, 1 insertion(+) diff --git a/niu/db.go b/niu/db.go index a841e16..5c8c4d8 100644 --- a/niu/db.go +++ b/niu/db.go @@ -13,6 +13,7 @@ var ( type tableHook func(gid int64) error +// Model ... type Model struct { *gorm.DB } From fc9084097332b1494dd94aaab196833238b7dedf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Fri, 15 Aug 2025 00:00:14 +0800 Subject: [PATCH 11/16] Table -> table --- niu/db.go | 20 +++++++++----------- niu/main.go | 22 +++++++++++----------- 2 files changed, 20 insertions(+), 22 deletions(-) diff --git a/niu/db.go b/niu/db.go index 5c8c4d8..7c231ec 100644 --- a/niu/db.go +++ b/niu/db.go @@ -13,8 +13,7 @@ var ( type tableHook func(gid int64) error -// Model ... -type Model struct { +type model struct { *gorm.DB } @@ -46,8 +45,7 @@ func registerTableHook(h ...tableHook) { tableHooks = append(tableHooks, h...) } -// TableFor 大写是为了防止数据操作哪里有问题留个保底可以在zbp的项目里直接改 -func TableFor(gid int64, prefix string) *Model { +func tableFor(gid int64, prefix string) *model { // 先跑钩子 for _, h := range tableHooks { if err := h(gid); err != nil { @@ -56,35 +54,35 @@ func TableFor(gid int64, prefix string) *Model { } tableName := fmt.Sprintf("group_%d_%s_info", gid, prefix) - return &Model{db.Table(tableName)} + return &model{db.Table(tableName)} } func listUsers(gid int64) (users, error) { var us users - err := TableFor(gid, ur).Find(&us).Error + err := tableFor(gid, ur).Find(&us).Error return us, err } func listAuction(gid int64) ([]AuctionInfo, error) { var as []AuctionInfo - err := TableFor(gid, ac).Order("money DESC").Find(&as).Error + err := tableFor(gid, ac).Order("money DESC").Find(&as).Error return as, err } func createUser(gid int64, user *userInfo, fix string) error { - return TableFor(gid, fix).Create(user).Error + return tableFor(gid, fix).Create(user).Error } func getUserByID(gid int64, uid int64) (*userInfo, error) { var user userInfo - err := TableFor(gid, ur).Where("user_id = ?", uid).First(&user).Error + err := tableFor(gid, ur).Where("user_id = ?", uid).First(&user).Error return &user, err } func updatesUserByID(gid int64, id int64, fields map[string]interface{}) error { - return TableFor(gid, ur).Where("user_id = ?", id).Updates(fields).Error + return tableFor(gid, ur).Where("user_id = ?", id).Updates(fields).Error } func deleteUserByID(gid int64, id int64) error { - return TableFor(gid, ur).Where("user_id = ?", id).Delete(&userInfo{}).Error + return tableFor(gid, ur).Where("user_id = ?", id).Delete(&userInfo{}).Error } diff --git a/niu/main.go b/niu/main.go index 6727628..05de63d 100644 --- a/niu/main.go +++ b/niu/main.go @@ -22,7 +22,7 @@ const ( ) var ( - db *Model + db *model globalLock sync.Mutex errCancelFail = errors.New("遇到不可抗力因素,注销失败!") @@ -84,7 +84,7 @@ func init() { panic(err) } - db = &Model{sdb.LogMode(false)} + db = &model{sdb.LogMode(false)} registerTableHook(ensureUserInfo, ensureAuctionInfo) } @@ -206,7 +206,7 @@ func HitGlue(gid, uid int64, prop string) (string, error) { return "", err } - if err = TableFor(gid, ur).Where("user_id = ?", uid).Save(niuniu).Error; err != nil { + if err = tableFor(gid, ur).Where("user_id = ?", uid).Save(niuniu).Error; err != nil { return "", err } @@ -266,11 +266,11 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo return "", 0, err } - if err = TableFor(gid, ur).Where("user_id =?", uid).Update("length", myniuniu.Length).Error; err != nil { + if err = tableFor(gid, ur).Where("user_id =?", uid).Update("length", myniuniu.Length).Error; err != nil { return "", 0, err } - if err = TableFor(gid, ur).Where("user_id =?", adduser).Update("length", adduserniuniu.Length).Error; err != nil { + if err = tableFor(gid, ur).Where("user_id =?", adduser).Update("length", adduserniuniu.Length).Error; err != nil { return "", 0, err } @@ -326,7 +326,7 @@ func Redeem(gid, uid int64, lastLength float64) error { return err } - return TableFor(gid, ur).Where("user_id = ?", uid).Update("length", lastLength).Error + return tableFor(gid, ur).Where("user_id = ?", uid).Update("length", lastLength).Error } // Store 牛牛商店 @@ -352,7 +352,7 @@ func Store(gid, uid int64, productID int, quantity int) error { return err } - return TableFor(gid, ur).Save(info).Error + return tableFor(gid, ur).Save(info).Error } // Sell 出售牛牛 @@ -388,7 +388,7 @@ func Sell(gid, uid int64) (string, error) { Money: money * 2, } - if err = TableFor(gid, ac).Create(&u).Error; err != nil { + if err = tableFor(gid, ac).Create(&u).Error; err != nil { return "", err } @@ -413,7 +413,7 @@ func Auction(gid, uid int64, index int) (string, error) { } var info AuctionInfo - if err = TableFor(gid, ac).Where("id = ?", index).First(&info).Error; err != nil { + if err = tableFor(gid, ac).Where("id = ?", index).First(&info).Error; err != nil { return "", err } @@ -437,11 +437,11 @@ func Auction(gid, uid int64, index int) (string, error) { niu.MeiYao += 2 } - if err = TableFor(gid, ac).Delete(&info).Error; err != nil { + if err = tableFor(gid, ac).Delete(&info).Error; err != nil { return "", err } - if err = TableFor(gid, ur).Save(&niu).Error; err != nil { + if err = tableFor(gid, ur).Save(&niu).Error; err != nil { return "", err } From d81975e047a51cbc02af2eca3d71b653ab16545f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Sat, 16 Aug 2025 09:55:09 +0800 Subject: [PATCH 12/16] =?UTF-8?q?=E7=9B=B4=E6=8E=A5=E5=9C=A8tableFor?= =?UTF-8?q?=E9=87=8C=E5=88=9B=E5=BB=BA=E8=A1=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 40 +++++++++++++++------------------------- niu/main.go | 12 ++++++------ 2 files changed, 21 insertions(+), 31 deletions(-) diff --git a/niu/db.go b/niu/db.go index 7c231ec..236781a 100644 --- a/niu/db.go +++ b/niu/db.go @@ -4,19 +4,13 @@ import ( "fmt" "github.com/RomiChan/syncx" "github.com/jinzhu/gorm" + "github.com/sirupsen/logrus" ) var ( migratedGroups = syncx.Map[string, bool]{} // key: string, value: bool - tableHooks []tableHook ) -type tableHook func(gid int64) error - -type model struct { - *gorm.DB -} - func ensureTable[T userInfo | AuctionInfo](gid int64, prefix string) error { table := fmt.Sprintf("group_%d_%s_info", gid, prefix) if _, ok := migratedGroups.Load(table); ok { @@ -32,29 +26,25 @@ func ensureTable[T userInfo | AuctionInfo](gid int64, prefix string) error { return nil } -func ensureUserInfo(gid int64) error { - return ensureTable[userInfo](gid, ur) -} +func tableFor(gid int64, prefix string) *gorm.DB { -func ensureAuctionInfo(gid int64) error { - return ensureTable[AuctionInfo](gid, ac) -} - -// registerTableHook 注册钩子 -func registerTableHook(h ...tableHook) { - tableHooks = append(tableHooks, h...) -} - -func tableFor(gid int64, prefix string) *model { - // 先跑钩子 - for _, h := range tableHooks { - if err := h(gid); err != nil { - panic(fmt.Sprintf("执行钩子失败: %v", err)) + switch prefix { + case ur: + err := ensureTable[userInfo](gid, ur) + if err != nil { + logrus.Error("ensureTable error: %v", err) + return nil + } + case ac: + err := ensureTable[AuctionInfo](gid, ac) + if err != nil { + logrus.Error("ensureTable error: %v", err) + return nil } } tableName := fmt.Sprintf("group_%d_%s_info", gid, prefix) - return &model{db.Table(tableName)} + return db.Table(tableName) } func listUsers(gid int64) (users, error) { diff --git a/niu/main.go b/niu/main.go index 05de63d..2322b02 100644 --- a/niu/main.go +++ b/niu/main.go @@ -22,7 +22,7 @@ const ( ) var ( - db *model + db *gorm.DB globalLock sync.Mutex errCancelFail = errors.New("遇到不可抗力因素,注销失败!") @@ -84,9 +84,7 @@ func init() { panic(err) } - db = &model{sdb.LogMode(false)} - - registerTableHook(ensureUserInfo, ensureAuctionInfo) + db = sdb.LogMode(false) } // DeleteWordNiuNiu ... @@ -449,11 +447,13 @@ func Auction(gid, uid int64, index int) (string, error) { return "", err } + bs := fmt.Sprintf("恭喜你购买成功,当前长度为%.2fcm", niu.Length) + if info.Money >= 500 { - return fmt.Sprintf("恭喜你购买成功,当前长度为%.2fcm,此次购买将赠送你2个伟哥,2个媚药", niu.Length), nil + return fmt.Sprintf("%s,此次购买将赠送你2个伟哥,2个媚药", bs), nil } - return fmt.Sprintf("恭喜你购买成功,当前长度为%.2fcm", niu.Length), nil + return bs, nil } // Bag 牛牛背包 From d91ce11d6deb599690b61d23019a76fb9d4f328c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Sat, 16 Aug 2025 10:01:11 +0800 Subject: [PATCH 13/16] =?UTF-8?q?=E4=BF=AElint,logrus.Error=20->=20logurs.?= =?UTF-8?q?Errorf?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/niu/db.go b/niu/db.go index 236781a..4f96804 100644 --- a/niu/db.go +++ b/niu/db.go @@ -32,13 +32,13 @@ func tableFor(gid int64, prefix string) *gorm.DB { case ur: err := ensureTable[userInfo](gid, ur) if err != nil { - logrus.Error("ensureTable error: %v", err) + logrus.Errorf("ensureTable error: %v", err) return nil } case ac: err := ensureTable[AuctionInfo](gid, ac) if err != nil { - logrus.Error("ensureTable error: %v", err) + logrus.Errorf("ensureTable error: %v", err) return nil } } From 084e1945969b733722dd934d9cca99a864b0b954 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Sun, 24 Aug 2025 11:18:41 +0800 Subject: [PATCH 14/16] =?UTF-8?q?=E4=BC=98=E5=8C=96=E4=BB=A3=E7=A0=81,?= =?UTF-8?q?=E4=BF=AE=E6=94=B9jj()=E8=BF=94=E5=9B=9EniuID=E5=90=8E=E7=BB=AD?= =?UTF-8?q?=E8=B5=8E=E7=89=9B=E7=89=9B=E5=8F=AF=E8=87=AA=E5=AE=9A=E4=B9=89?= =?UTF-8?q?=E5=9B=9E=E5=A4=8D?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/main.go | 39 +++++++++++++++++++++++++++++---------- niu/models.go | 24 +++++++++++++++++++++--- 2 files changed, 50 insertions(+), 13 deletions(-) diff --git a/niu/main.go b/niu/main.go index 2322b02..96ec3fc 100644 --- a/niu/main.go +++ b/niu/main.go @@ -27,6 +27,12 @@ var ( errCancelFail = errors.New("遇到不可抗力因素,注销失败!") + // ErrAuctioned 已被拍卖无法赎回 + ErrAuctioned = errors.New("你的牛牛已经被拍卖无法赎回") + + // ErrCanceled 已被注销无法赎回 + ErrCanceled = errors.New("你的牛牛已经被注销无法赎回") + // ErrInvalidProductID 商品ID无效 ErrInvalidProductID = errors.New("商品id不存在") @@ -241,37 +247,38 @@ func Register(gid, uid int64) (string, error) { } // JJ ... -func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength float64, err error) { +func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength float64, niuID uuid.UUID, err error) { globalLock.Lock() defer globalLock.Unlock() myniuniu, err := getUserByID(gid, uid) if err != nil { - return "", 0, ErrNoNiuNiu + return "", 0, uuid.Nil, ErrNoNiuNiu } adduserniuniu, err := getUserByID(gid, adduser) if err != nil { - return "", 0, ErrAdduserNoNiuNiu + return "", 0, uuid.Nil, ErrAdduserNoNiuNiu } if uid == adduser { - return "", 0, ErrCannotFight + return "", 0, uuid.Nil, ErrCannotFight } message, err = myniuniu.processJJ(adduserniuniu, prop) if err != nil { - return "", 0, err + return "", 0, uuid.Nil, err } if err = tableFor(gid, ur).Where("user_id =?", uid).Update("length", myniuniu.Length).Error; err != nil { - return "", 0, err + return "", 0, uuid.Nil, err } if err = tableFor(gid, ur).Where("user_id =?", adduser).Update("length", adduserniuniu.Length).Error; err != nil { - return "", 0, err + return "", 0, uuid.Nil, err } + niuID = adduserniuniu.NiuID adduserLength = adduserniuniu.Length return @@ -294,7 +301,7 @@ func Cancel(gid, uid int64) (string, error) { } // Redeem 赎牛牛 -func Redeem(gid, uid int64, lastLength float64) error { +func Redeem(gid, uid int64, r Rm) error { globalLock.Lock() defer globalLock.Unlock() @@ -305,7 +312,19 @@ func Redeem(gid, uid int64, lastLength float64) error { money := wallet.GetWalletOf(uid) - price := 150 + var niuManager niuNiuManager + if err = db.Model(&niuNiuManager{}).Where("niu_id = ?", r.NiuID).First(&niuManager).Error; err != nil { + return err + } + + switch niuManager.Status { + case 1: + return ErrAuctioned + case 2: + return ErrCanceled + } + + price := int(hitGlue(r.Length))*100 + 150 if money < price { var builder strings.Builder @@ -324,7 +343,7 @@ func Redeem(gid, uid int64, lastLength float64) error { return err } - return tableFor(gid, ur).Where("user_id = ?", uid).Update("length", lastLength).Error + return tableFor(gid, ur).Where("user_id = ?", uid).Update("length", r.Length).Error } // Store 牛牛商店 diff --git a/niu/models.go b/niu/models.go index 7028ce7..e99cff8 100644 --- a/niu/models.go +++ b/niu/models.go @@ -17,6 +17,13 @@ var ( jjPorps = []string{"击剑神器", "击剑神稽"} ) +type Rm struct { + NiuID uuid.UUID + TimeLimit time.Time + Count int + Length float64 +} + type users []*userInfo type niuNiuManager struct { @@ -115,9 +122,9 @@ func (u *userInfo) useWeiGe() (string, float64) { reduce := math.Abs(hitGlue(niuniu)) niuniu += reduce return randomChoice([]string{ - fmt.Sprintf("哈哈,你这一用道具,牛牛就像是被激发了潜能,增加了%.2fcm!看来今天是个大日子呢!", reduce), + fmt.Sprintf("哈哈,你这一用伟哥,牛牛就像是被激发了潜能,增加了%.2fcm!看来今天是个大日子呢!", reduce), fmt.Sprintf("你这是用了什么神奇的道具?牛牛竟然增加了%.2fcm,简直是牛气冲天!", reduce), - fmt.Sprintf("使用道具后,你的牛牛就像是开启了加速模式,一下增加了%.2fcm,这成长速度让人惊叹!", reduce), + fmt.Sprintf("使用伟哥后,你的牛牛就像是开启了加速模式,一下增加了%.2fcm,这成长速度让人惊叹!", reduce), }), niuniu } @@ -127,7 +134,7 @@ func (u *userInfo) useMeiYao() (string, float64) { niuniu -= reduce return randomChoice([]string{ fmt.Sprintf("你使用媚药,咿呀咿呀一下使当前长度发生了一些变化,当前长度%.2fcm", niuniu), - fmt.Sprintf("看来你追求的是‘微观之美’,故意使用道具让牛牛凹进去了%.2fcm!", reduce), + fmt.Sprintf("看来你追求的是‘微观之美’,故意使用媚药让牛牛凹进去了%.2fcm!", reduce), fmt.Sprintf("缩小奇迹’在你身上发生了,牛牛凹进去了%.2fcm,你的选择真是独特!", reduce), }), niuniu } @@ -266,6 +273,17 @@ func (u *userInfo) purchaseItem(productID, quantity int) (money int, err error) money *= quantity + switch productID { + case 1: + u.WeiGe += quantity + case 2: + u.MeiYao += quantity + case 3: + u.Artifact += quantity + case 4: + u.ShenJi += quantity + } + return } From 02e966714b3fc303236e4af2eb3c4e771d5e619b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Sun, 24 Aug 2025 11:24:44 +0800 Subject: [PATCH 15/16] =?UTF-8?q?=E4=BF=AElint?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/models.go | 1 + 1 file changed, 1 insertion(+) diff --git a/niu/models.go b/niu/models.go index e99cff8..217e61a 100644 --- a/niu/models.go +++ b/niu/models.go @@ -17,6 +17,7 @@ var ( jjPorps = []string{"击剑神器", "击剑神稽"} ) +// Rm ... type Rm struct { NiuID uuid.UUID TimeLimit time.Time From 635942b31affa582b78af89702d9cf7d693ac8f1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B0=8F=E5=AE=87=E5=AE=87?= <3061196825@qq.com> Date: Sun, 31 Aug 2025 14:54:48 +0800 Subject: [PATCH 16/16] =?UTF-8?q?=E5=AE=8C=E6=88=90=E8=A6=81=E6=B1=82?= =?UTF-8?q?=E7=9A=84=E6=9B=B4=E6=94=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- niu/db.go | 29 ++++++++++++++--------------- niu/main.go | 31 ++++++++++++++++--------------- niu/models.go | 4 ++-- 3 files changed, 32 insertions(+), 32 deletions(-) diff --git a/niu/db.go b/niu/db.go index 4f96804..04c303d 100644 --- a/niu/db.go +++ b/niu/db.go @@ -8,7 +8,7 @@ import ( ) var ( - migratedGroups = syncx.Map[string, bool]{} // key: string, value: bool + migratedGroups = syncx.Map[string, struct{}]{} // key: string, value: struct{} ) func ensureTable[T userInfo | AuctionInfo](gid int64, prefix string) error { @@ -22,40 +22,39 @@ func ensureTable[T userInfo | AuctionInfo](gid int64, prefix string) error { } // 设置为已迁移 - migratedGroups.Store(table, true) + migratedGroups.Store(table, struct{}{}) return nil } func tableFor(gid int64, prefix string) *gorm.DB { switch prefix { - case ur: - err := ensureTable[userInfo](gid, ur) + case usr: + err := ensureTable[userInfo](gid, usr) if err != nil { logrus.Errorf("ensureTable error: %v", err) return nil } - case ac: - err := ensureTable[AuctionInfo](gid, ac) + case auct: + err := ensureTable[AuctionInfo](gid, auct) if err != nil { logrus.Errorf("ensureTable error: %v", err) return nil } } - tableName := fmt.Sprintf("group_%d_%s_info", gid, prefix) - return db.Table(tableName) + return db.Table(fmt.Sprintf("group_%d_%s_info", gid, prefix)) } func listUsers(gid int64) (users, error) { - var us users - err := tableFor(gid, ur).Find(&us).Error - return us, err + var users users + err := tableFor(gid, usr).Find(&users).Error + return users, err } func listAuction(gid int64) ([]AuctionInfo, error) { var as []AuctionInfo - err := tableFor(gid, ac).Order("money DESC").Find(&as).Error + err := tableFor(gid, auct).Order("money DESC").Find(&as).Error return as, err } @@ -65,14 +64,14 @@ func createUser(gid int64, user *userInfo, fix string) error { func getUserByID(gid int64, uid int64) (*userInfo, error) { var user userInfo - err := tableFor(gid, ur).Where("user_id = ?", uid).First(&user).Error + err := tableFor(gid, usr).Where("user_id = ?", uid).First(&user).Error return &user, err } func updatesUserByID(gid int64, id int64, fields map[string]interface{}) error { - return tableFor(gid, ur).Where("user_id = ?", id).Updates(fields).Error + return tableFor(gid, usr).Where("user_id = ?", id).Updates(fields).Error } func deleteUserByID(gid int64, id int64) error { - return tableFor(gid, ur).Where("user_id = ?", id).Delete(&userInfo{}).Error + return tableFor(gid, usr).Where("user_id = ?", id).Delete(&userInfo{}).Error } diff --git a/niu/main.go b/niu/main.go index 96ec3fc..612fe09 100644 --- a/niu/main.go +++ b/niu/main.go @@ -17,15 +17,16 @@ import ( ) const ( - ur = "user" - ac = "auction" + usr = "user" + auct = "auction" ) var ( db *gorm.DB globalLock sync.Mutex - errCancelFail = errors.New("遇到不可抗力因素,注销失败!") + // ErrCancelFail 牛牛注销失败 + ErrCancelFail = errors.New("遇到不可抗力因素,注销失败!") // ErrAuctioned 已被拍卖无法赎回 ErrAuctioned = errors.New("你的牛牛已经被拍卖无法赎回") @@ -210,7 +211,7 @@ func HitGlue(gid, uid int64, prop string) (string, error) { return "", err } - if err = tableFor(gid, ur).Where("user_id = ?", uid).Save(niuniu).Error; err != nil { + if err = tableFor(gid, usr).Where("user_id = ?", uid).Save(niuniu).Error; err != nil { return "", err } @@ -233,7 +234,7 @@ func Register(gid, uid int64) (string, error) { Length: length, } - if err := createUser(gid, &u, ur); err != nil { + if err := createUser(gid, &u, usr); err != nil { return "", err } @@ -270,11 +271,11 @@ func JJ(gid, uid, adduser int64, prop string) (message string, adduserLength flo return "", 0, uuid.Nil, err } - if err = tableFor(gid, ur).Where("user_id =?", uid).Update("length", myniuniu.Length).Error; err != nil { + if err = tableFor(gid, usr).Where("user_id =?", uid).Update("length", myniuniu.Length).Error; err != nil { return "", 0, uuid.Nil, err } - if err = tableFor(gid, ur).Where("user_id =?", adduser).Update("length", adduserniuniu.Length).Error; err != nil { + if err = tableFor(gid, usr).Where("user_id =?", adduser).Update("length", adduserniuniu.Length).Error; err != nil { return "", 0, uuid.Nil, err } @@ -294,14 +295,14 @@ func Cancel(gid, uid int64) (string, error) { } err = deleteUserByID(gid, uid) if err != nil { - return "", errCancelFail + return "", ErrCancelFail } err = db.Model(&niuNiuManager{}).Where("niu_id = ?", uid).Update("status", 2).Error return "注销成功,你已经没有牛牛了", err } // Redeem 赎牛牛 -func Redeem(gid, uid int64, r Rm) error { +func Redeem(gid, uid int64, r PKRecord) error { globalLock.Lock() defer globalLock.Unlock() @@ -343,7 +344,7 @@ func Redeem(gid, uid int64, r Rm) error { return err } - return tableFor(gid, ur).Where("user_id = ?", uid).Update("length", r.Length).Error + return tableFor(gid, usr).Where("user_id = ?", uid).Update("length", r.Length).Error } // Store 牛牛商店 @@ -369,7 +370,7 @@ func Store(gid, uid int64, productID int, quantity int) error { return err } - return tableFor(gid, ur).Save(info).Error + return tableFor(gid, usr).Save(info).Error } // Sell 出售牛牛 @@ -405,7 +406,7 @@ func Sell(gid, uid int64) (string, error) { Money: money * 2, } - if err = tableFor(gid, ac).Create(&u).Error; err != nil { + if err = tableFor(gid, auct).Create(&u).Error; err != nil { return "", err } @@ -430,7 +431,7 @@ func Auction(gid, uid int64, index int) (string, error) { } var info AuctionInfo - if err = tableFor(gid, ac).Where("id = ?", index).First(&info).Error; err != nil { + if err = tableFor(gid, auct).Where("id = ?", index).First(&info).Error; err != nil { return "", err } @@ -454,11 +455,11 @@ func Auction(gid, uid int64, index int) (string, error) { niu.MeiYao += 2 } - if err = tableFor(gid, ac).Delete(&info).Error; err != nil { + if err = tableFor(gid, auct).Delete(&info).Error; err != nil { return "", err } - if err = tableFor(gid, ur).Save(&niu).Error; err != nil { + if err = tableFor(gid, usr).Save(&niu).Error; err != nil { return "", err } diff --git a/niu/models.go b/niu/models.go index 217e61a..a57222d 100644 --- a/niu/models.go +++ b/niu/models.go @@ -17,8 +17,8 @@ var ( jjPorps = []string{"击剑神器", "击剑神稽"} ) -// Rm ... -type Rm struct { +// PKRecord ... +type PKRecord struct { NiuID uuid.UUID TimeLimit time.Time Count int