Filter support passing context (#2200) (#2270)

```diff
// Filter is an interface to filter SQL
type Filter interface {
---	Do(sql string) string
+++	Do(ctx context.Context, sql string) string
}
```

### Adds a `Context` parameter to the `Do` method of the Filter interface.

Developers can rewrite SQL through the `Filter` `Do` method and **need to get the necessary data from the Context** to assist.

For example, get user information through `Context`, so that different users can use different tables. Another example is to get the flags through `Context` to add annotations to the SQL, and use the annotations to let the subsequent `DB-Proxy` to achieve read/write separation.

Reviewed-on: https://gitea.com/xorm/xorm/pulls/2270
Reviewed-by: Lunny Xiao <xiaolunwen@gmail.com>
Co-authored-by: LinkinStars <linkinstar@foxmail.com>
Co-committed-by: LinkinStars <linkinstar@foxmail.com>
This commit is contained in:
LinkinStars 2023-05-31 01:43:24 +00:00 committed by Lunny Xiao
parent 57f7d69f1b
commit cb851a2f95
6 changed files with 8 additions and 7 deletions

View File

@ -5,13 +5,14 @@
package dialects package dialects
import ( import (
"context"
"fmt" "fmt"
"strings" "strings"
) )
// Filter is an interface to filter SQL // Filter is an interface to filter SQL
type Filter interface { type Filter interface {
Do(sql string) string Do(ctx context.Context, sql string) string
} }
// SeqFilter filter SQL replace ?, ? ... to $1, $2 ... // SeqFilter filter SQL replace ?, ? ... to $1, $2 ...
@ -71,6 +72,6 @@ func convertQuestionMark(sql, prefix string, start int) string {
} }
// Do implements Filter // Do implements Filter
func (s *SeqFilter) Do(sql string) string { func (s *SeqFilter) Do(ctx context.Context, sql string) string {
return convertQuestionMark(sql, s.Prefix, s.Start) return convertQuestionMark(sql, s.Prefix, s.Start)
} }

View File

@ -30,7 +30,7 @@ func (session *Session) cacheDelete(table *schemas.Table, tableName, sqlStr stri
} }
for _, filter := range session.engine.dialect.Filters() { for _, filter := range session.engine.dialect.Filters() {
sqlStr = filter.Do(sqlStr) sqlStr = filter.Do(session.ctx, sqlStr)
} }
newsql := session.statement.ConvertIDSQL(sqlStr) newsql := session.statement.ConvertIDSQL(sqlStr)

View File

@ -283,7 +283,7 @@ func (session *Session) cacheFind(t reflect.Type, sqlStr string, rowsSlicePtr in
} }
for _, filter := range session.engine.dialect.Filters() { for _, filter := range session.engine.dialect.Filters() {
sqlStr = filter.Do(sqlStr) sqlStr = filter.Do(session.ctx, sqlStr)
} }
newsql := session.statement.ConvertIDSQL(sqlStr) newsql := session.statement.ConvertIDSQL(sqlStr)

View File

@ -278,7 +278,7 @@ func (session *Session) cacheGet(bean interface{}, sqlStr string, args ...interf
} }
for _, filter := range session.engine.dialect.Filters() { for _, filter := range session.engine.dialect.Filters() {
sqlStr = filter.Do(sqlStr) sqlStr = filter.Do(session.ctx, sqlStr)
} }
newsql := session.statement.ConvertIDSQL(sqlStr) newsql := session.statement.ConvertIDSQL(sqlStr)
if newsql == "" { if newsql == "" {

View File

@ -13,7 +13,7 @@ import (
func (session *Session) queryPreprocess(sqlStr *string, paramStr ...interface{}) { func (session *Session) queryPreprocess(sqlStr *string, paramStr ...interface{}) {
for _, filter := range session.engine.dialect.Filters() { for _, filter := range session.engine.dialect.Filters() {
*sqlStr = filter.Do(*sqlStr) *sqlStr = filter.Do(session.ctx, *sqlStr)
} }
session.lastSQL = *sqlStr session.lastSQL = *sqlStr

View File

@ -34,7 +34,7 @@ func (session *Session) cacheUpdate(table *schemas.Table, tableName, sqlStr stri
return ErrCacheFailed return ErrCacheFailed
} }
for _, filter := range session.engine.dialect.Filters() { for _, filter := range session.engine.dialect.Filters() {
newsql = filter.Do(newsql) newsql = filter.Do(session.ctx, newsql)
} }
session.engine.logger.Debugf("[cache] new sql: %v, %v", oldhead, newsql) session.engine.logger.Debugf("[cache] new sql: %v, %v", oldhead, newsql)