From e0161613dd53e8a6867f6d4ecc6198ec837c1f55 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=BA=90=E6=96=87=E9=9B=A8?= <41315874+fumiama@users.noreply.github.com> Date: Wed, 22 Mar 2023 22:32:51 +0800 Subject: [PATCH] user.db add table Regex --- backend/global/file.go | 15 ++++---- backend/global/user.go | 84 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 92 insertions(+), 7 deletions(-) diff --git a/backend/global/file.go b/backend/global/file.go index ed437dc..b629760 100644 --- a/backend/global/file.go +++ b/backend/global/file.go @@ -52,9 +52,9 @@ func (pt PaperType) MiddleFinal() string { func (pt PaperType) SetMiddleFinal(x string) PaperType { n := PaperType(0) switch x { - case "期中": + case "中": n = 1 << 4 - case "期末": + case "末": n = 2 << 4 } return pt | n @@ -72,12 +72,12 @@ func (pt PaperType) FirstSecond() string { } } -func (pt PaperType) SetFirstSecond(x string) PaperType { +func (pt PaperType) SetFirstSecond(x byte) PaperType { n := PaperType(0) switch x { - case "第1学期": + case '1': n = 1 << 8 - case "第2学期": + case '2': n = 2 << 8 } return pt | n @@ -151,6 +151,9 @@ type File struct { Year StudyYear Type PaperType Date uint32 // Date is the yyyymmdd of 考试日期 + UID int // UID is the uploader's ID + UpTime int64 // UpTime is time.Now().Unix() when uploading + Size int64 // Size of the original file Time time.Duration // Time is 考试时长 Class string // Class is 考试科目 Rate string // Rate is 成绩构成比例 @@ -158,8 +161,6 @@ type File struct { Questions []byte // Questions is for json struct QuestionJSON } -func (f *FileDatabase) AddFile() {} - // QuestionJSON is the struct representation of File.Questions type QuestionJSON struct { Name string `json:"name"` // Name is name or Question ID diff --git a/backend/global/user.go b/backend/global/user.go index 3eb19a4..3e94ddf 100644 --- a/backend/global/user.go +++ b/backend/global/user.go @@ -3,6 +3,8 @@ package global import ( "errors" "os" + "reflect" + "regexp" "strconv" "time" @@ -64,6 +66,7 @@ const ( UserTableUser = "user" UserTableMessage = "msg" UserTableMonthlyAPIVisit = "visit" + UserTableRegex = "re" ) var ( @@ -77,6 +80,9 @@ var ( ErrUsernameExists = errors.New("username exists") ErrInvalidName = errors.New("invalid name") ErrInvalidContact = errors.New("invalid contact") + ErrInvalidFieldName = errors.New("invalid field name") + ErrNoSuchFieldName = errors.New("no such field name") + ErrEmptyRegex = errors.New("empty regex") ) func init() { @@ -103,6 +109,10 @@ func init() { if err != nil { panic(err) } + err = UserDB.db.Create(UserTableRegex, &Regex{}) + if err != nil { + panic(err) + } if isinit { // 添加初始账户 UserDB.AddUser(&User{ Role: RoleSuper, @@ -786,3 +796,77 @@ func (u *UserDatabase) GetAnnualAPIVisitCount() (cnts [12]uint32) { } return } + +// Regex stores user's config of splitting docx file +type Regex struct { + ID int // ID is User(ID) + Title string // Title default `.*(\d{4})\s*-.*学年.*(\d).*([中末]).*([AB])\s*卷` + Class string // Class default `考试科目:\s*(\S+)\s*` + OpenCl string // OpenCl default `考试形式:\s*(\S+)\s*` + Date string // Date default `考试日期:\s*(\d+)\s*年\s*(\d+)\s*月\s*(\d+)\s*日` + Time string // Time default `考试时长:\s*(\d+)\s*分钟` + Rate string // Rate default `成绩构成比例:\s*(.*%)\s*` + Major string // Major default `([一二三四五六七八九十]+)、\s*(.*)\s*(.*([空题]?)\s*(\d*).*共\s*(\d+)\s*分.*)` + Sub string // Sub default `(\d+)、` +} + +func newRegex() (reg Regex) { + reg.Title = `.*(\d{4})\s*-.*学年.*(\d).*([中末]).*([AB])\s*卷` + reg.Class = `考试科目:\s*(\S+)\s*` + reg.OpenCl = `考试形式:\s*(\S+)\s*` + reg.Date = `考试日期:\s*(\d+)\s*年\s*(\d+)\s*月\s*(\d+)\s*日` + reg.Time = `考试时长:\s*(\d+)\s*分钟` + reg.Rate = `成绩构成比例:\s*(.*%)\s*` + reg.Major = `([一二三四五六七八九十]+)、\s*(.*)\s*(.*([空题]?)\s*(\d*).*共\s*(\d+)\s*分.*)` + reg.Sub = `(\d+)、` + return +} + +// SetUserRegex set Regex.name = re +func (u *UserDatabase) SetUserRegex(id int, name, re string) error { + if name == "" || name == "ID" { + return ErrInvalidFieldName + } + if re == "" { + return ErrEmptyRegex + } + user, err := UserDB.GetUserByID(id) + if err != nil { + return err + } + if !user.IsFileManager() { + return ErrInvalidRole + } + _, err = regexp.Compile(re) + if err != nil { + return err + } + reg := newRegex() + rreg := reflect.ValueOf(®).Elem() + f := rreg.FieldByName(name) + if !f.IsValid() { + return ErrNoSuchFieldName + } + u.mu.Lock() + defer u.mu.Unlock() + _ = u.db.Find(UserTableRegex, ®, "WHERE ID="+strconv.Itoa(id)) + reg.ID = id + f.SetString(re) + return u.db.Insert(UserTableRegex, ®) +} + +// GetUserRegex default newRegex() +func (u *UserDatabase) GetUserRegex(id int) (*Regex, error) { + user, err := UserDB.GetUserByID(id) + if err != nil { + return nil, err + } + if !user.IsFileManager() { + return nil, ErrInvalidRole + } + reg := newRegex() + u.mu.RLock() + _ = u.db.Find(UserTableRegex, ®, "WHERE ID="+strconv.Itoa(id)) + u.mu.RUnlock() + return ®, nil +}