feat: add global system notices and Beijing order time display
Deploy olons-server production / deploy (push) Successful in 3m12s

This commit is contained in:
richjohnrambo
2026-10-22 21:56:07 +08:00
parent 9bb479b506
commit 8ce67648b1
22 changed files with 581 additions and 121 deletions
+33 -16
View File
@@ -5,10 +5,21 @@ import (
"database/sql"
"encoding/json"
"errors"
"time"
)
const publishStatusPublished = 3
var noticeBusinessLocation = time.FixedZone("Asia/Shanghai", 8*60*60)
func noticeBusinessNow() string {
return formatNoticeBusinessTime(time.Now())
}
func formatNoticeBusinessTime(value time.Time) string {
return value.In(noticeBusinessLocation).Format("2006-01-02 15:04:05.999999999")
}
type Banner struct {
ID int64 `db:"id"`
ImageURL string `db:"image_url"`
@@ -154,29 +165,33 @@ func (s *Store) ActiveMemberNotices(ctx context.Context, tenantID, memberID int6
return nil, errors.New("store is unavailable")
}
rows := make([]MemberNotice, 0)
now := noticeBusinessNow()
err := s.db.SelectContext(ctx, &rows, `SELECT id,title,content,source_type,
DATE_FORMAT(start_at,'%Y-%m-%dT%H:%i:%sZ') AS start_at,
DATE_FORMAT(end_at,'%Y-%m-%dT%H:%i:%sZ') AS end_at,
DATE_FORMAT(created_at,'%Y-%m-%dT%H:%i:%sZ') AS created_at
FROM hg_app_member_notice WHERE tenant_id=? AND member_id IN (0,?) AND notice_status=1
AND start_at<=UTC_TIMESTAMP(3) AND end_at>UTC_TIMESTAMP(3)
ORDER BY start_at DESC,id DESC LIMIT ?`, tenantID, memberID, limit)
AND start_at<=? AND end_at>?
ORDER BY start_at DESC,id DESC LIMIT ?`, tenantID, memberID, now, now, limit)
return rows, err
}
func (s *Store) LatestPopupNotice(ctx context.Context, tenantID, memberID int64) (*MemberNotice, error) {
func (s *Store) NextUnreadMemberNotice(ctx context.Context, tenantID, memberID int64) (*MemberNotice, error) {
if s == nil || s.db == nil {
return nil, errors.New("store is unavailable")
}
var row MemberNotice
err := s.db.GetContext(ctx, &row, `SELECT id,title,content,source_type,
DATE_FORMAT(start_at,'%Y-%m-%dT%H:%i:%sZ') AS start_at,
DATE_FORMAT(end_at,'%Y-%m-%dT%H:%i:%sZ') AS end_at,
DATE_FORMAT(created_at,'%Y-%m-%dT%H:%i:%sZ') AS created_at
FROM hg_app_member_notice
WHERE tenant_id=? AND member_id IN (0,?) AND notice_status=1
AND start_at<=UTC_TIMESTAMP(3) AND end_at>UTC_TIMESTAMP(3)
ORDER BY start_at DESC,id DESC LIMIT 1`, tenantID, memberID)
now := noticeBusinessNow()
err := s.db.GetContext(ctx, &row, `SELECT n.id,n.title,n.content,n.source_type,
DATE_FORMAT(n.start_at,'%Y-%m-%dT%H:%i:%sZ') AS start_at,
DATE_FORMAT(n.end_at,'%Y-%m-%dT%H:%i:%sZ') AS end_at,
DATE_FORMAT(n.created_at,'%Y-%m-%dT%H:%i:%sZ') AS created_at
FROM hg_app_member_notice n
WHERE n.tenant_id=? AND n.member_id=? AND n.notice_status=1
AND n.start_at<=? AND n.end_at>?
AND NOT EXISTS (SELECT 1 FROM hg_app_member_notice_read r
WHERE r.tenant_id=n.tenant_id AND r.notice_id=n.id AND r.member_id=?)
ORDER BY n.start_at ASC,n.id ASC LIMIT 1`, tenantID, memberID, now, now, memberID)
if errors.Is(err, sql.ErrNoRows) {
return nil, nil
}
@@ -187,13 +202,14 @@ func (s *Store) MarkMemberNoticeRead(ctx context.Context, tenantID, memberID, no
if s == nil || s.db == nil {
return errors.New("store is unavailable")
}
now := noticeBusinessNow()
result, err := s.db.ExecContext(ctx, `INSERT INTO hg_app_member_notice_read
(tenant_id,notice_id,member_id,read_at,created_at)
SELECT n.tenant_id,n.id,?,UTC_TIMESTAMP(3),UTC_TIMESTAMP(3)
SELECT n.tenant_id,n.id,?,?,?
FROM hg_app_member_notice n
WHERE n.tenant_id=? AND n.id=? AND n.member_id IN (0,?) AND n.notice_status=1
AND n.start_at<=UTC_TIMESTAMP(3) AND n.end_at>UTC_TIMESTAMP(3)
ON DUPLICATE KEY UPDATE read_at=VALUES(read_at)`, memberID, tenantID, noticeID, memberID)
AND n.start_at<=? AND n.end_at>?
ON DUPLICATE KEY UPDATE read_at=VALUES(read_at)`, memberID, now, now, tenantID, noticeID, memberID, now, now)
if err != nil {
return err
}
@@ -212,8 +228,9 @@ func (s *Store) MemberNotices(ctx context.Context, tenantID, memberID int64, off
return nil, errors.New("store is unavailable")
}
const where = ` WHERE tenant_id=? AND member_id IN (0,?) AND notice_status=1
AND start_at<=UTC_TIMESTAMP(3) AND end_at>UTC_TIMESTAMP(3)`
args := []any{tenantID, memberID}
AND start_at<=? AND end_at>?`
now := noticeBusinessNow()
args := []any{tenantID, memberID, now, now}
var total int64
if err := s.db.GetContext(ctx, &total, `SELECT COUNT(*) FROM hg_app_member_notice`+where, args...); err != nil {
return nil, err