package pg
import (
)
type (
BeforeScanHook = orm.BeforeScanHook
AfterScanHook = orm.AfterScanHook
AfterSelectHook = orm.AfterSelectHook
BeforeInsertHook = orm.BeforeInsertHook
AfterInsertHook = orm.AfterInsertHook
BeforeUpdateHook = orm.BeforeUpdateHook
AfterUpdateHook = orm.AfterUpdateHook
BeforeDeleteHook = orm.BeforeDeleteHook
AfterDeleteHook = orm.AfterDeleteHook
)
type dummyFormatter struct{}
func (dummyFormatter) ( []byte, string, ...interface{}) []byte {
return append(, ...)
}
type QueryEvent struct {
StartTime time.Time
DB orm.DB
Model interface{}
Query interface{}
Params []interface{}
fmtedQuery []byte
Result Result
Err error
Stash map[interface{}]interface{}
}
type QueryHook interface {
BeforeQuery(context.Context, *QueryEvent) (context.Context, error)
AfterQuery(context.Context, *QueryEvent) error
}
func ( *QueryEvent) () ([]byte, error) {
return queryString(.Query)
}
func ( interface{}) ([]byte, error) {
switch query := .(type) {
case orm.TemplateAppender:
return .AppendTemplate(nil)
case string:
return dummyFormatter{}.FormatQuery(nil, ), nil
default:
return nil, fmt.Errorf("pg: can't append %T", )
}
}
func ( *QueryEvent) () ([]byte, error) {
return .fmtedQuery, nil
}
func ( *baseDB) ( QueryHook) {
.queryHooks = append(.queryHooks, )
}
func ( *baseDB) (
context.Context,
orm.DB,
, interface{},
[]interface{},
[]byte,
) (context.Context, *QueryEvent, error) {
if len(.queryHooks) == 0 {
return , nil, nil
}
:= &QueryEvent{
StartTime: time.Now(),
DB: ,
Model: ,
Query: ,
Params: ,
fmtedQuery: ,
}
for , := range .queryHooks {
var error
, = .BeforeQuery(, )
if != nil {
if := .afterQueryFromIndex(, , ); != nil {
return , nil,
}
return , nil,
}
}
return , , nil
}
func ( *baseDB) (
context.Context,
*QueryEvent,
Result,
error,
) error {
if == nil {
return nil
}
.Err =
.Result =
return .afterQueryFromIndex(, , len(.queryHooks)-1)
}
func ( *baseDB) ( context.Context, *QueryEvent, int) error {
for ; >= 0; -- {
if := .queryHooks[].AfterQuery(, ); != nil {
return
}
}
return nil
}
func ( []QueryHook) []QueryHook {
return [:len():len()]
}