mirror of https://github.com/grafana/grafana
Chore: replace xorm by sqlx in dashboardversion service (#53869)
parent
8deababa50
commit
fd01161bcc
@ -0,0 +1,87 @@ |
|||||||
|
package dashverimpl |
||||||
|
|
||||||
|
import ( |
||||||
|
"context" |
||||||
|
"database/sql" |
||||||
|
"errors" |
||||||
|
"strings" |
||||||
|
|
||||||
|
dashver "github.com/grafana/grafana/pkg/services/dashboardversion" |
||||||
|
"github.com/grafana/grafana/pkg/services/sqlstore/session" |
||||||
|
) |
||||||
|
|
||||||
|
type sqlxStore struct { |
||||||
|
sess *session.SessionDB |
||||||
|
} |
||||||
|
|
||||||
|
func (ss *sqlxStore) Get(ctx context.Context, query *dashver.GetDashboardVersionQuery) (*dashver.DashboardVersion, error) { |
||||||
|
var version dashver.DashboardVersion |
||||||
|
qr := `SELECT dashboard_version.*
|
||||||
|
FROM dashboard_version |
||||||
|
LEFT JOIN dashboard ON dashboard.id=dashboard_version.dashboard_id |
||||||
|
WHERE dashboard_version.dashboard_id=? AND dashboard_version.version=? AND dashboard.org_id=?
|
||||||
|
` |
||||||
|
err := ss.sess.Get(ctx, &version, qr, query.DashboardID, query.Version, query.OrgID) |
||||||
|
if err != nil && errors.Is(err, sql.ErrNoRows) { |
||||||
|
return nil, dashver.ErrDashboardVersionNotFound |
||||||
|
} |
||||||
|
return &version, err |
||||||
|
} |
||||||
|
|
||||||
|
func (ss *sqlxStore) GetBatch(ctx context.Context, cmd *dashver.DeleteExpiredVersionsCommand, perBatch int, versionsToKeep int) ([]interface{}, error) { |
||||||
|
var versionIds []interface{} |
||||||
|
versionIdsToDeleteQuery := `SELECT id |
||||||
|
FROM dashboard_version, ( |
||||||
|
SELECT dashboard_id, count(version) as count, min(version) as min |
||||||
|
FROM dashboard_version |
||||||
|
GROUP BY dashboard_id |
||||||
|
) AS vtd |
||||||
|
WHERE dashboard_version.dashboard_id=vtd.dashboard_id |
||||||
|
AND version < vtd.min + vtd.count - ? |
||||||
|
LIMIT ?` |
||||||
|
err := ss.sess.Get(ctx, &versionIds, versionIdsToDeleteQuery, versionsToKeep, perBatch) |
||||||
|
return versionIds, err |
||||||
|
} |
||||||
|
|
||||||
|
// This service is used by cleanup which need to belong to the same transaction
|
||||||
|
// Here we need to make sure that the transaction is shared between services
|
||||||
|
func (ss *sqlxStore) DeleteBatch(ctx context.Context, cmd *dashver.DeleteExpiredVersionsCommand, versionIdsToDelete []interface{}) (int64, error) { |
||||||
|
var deleted int64 |
||||||
|
err := ss.sess.WithTransaction(ctx, func(tx *session.SessionTx) error { |
||||||
|
deleteExpiredSQL := `DELETE FROM dashboard_version WHERE id IN (?` + strings.Repeat(",?", len(versionIdsToDelete)-1) + `)` |
||||||
|
expiredResponse, err := tx.Exec(ctx, deleteExpiredSQL, versionIdsToDelete...) |
||||||
|
if err != nil { |
||||||
|
return err |
||||||
|
} |
||||||
|
deleted, err = expiredResponse.RowsAffected() |
||||||
|
return err |
||||||
|
}) |
||||||
|
return deleted, err |
||||||
|
} |
||||||
|
|
||||||
|
func (ss *sqlxStore) List(ctx context.Context, query *dashver.ListDashboardVersionsQuery) ([]*dashver.DashboardVersionDTO, error) { |
||||||
|
var dashboardVersion []*dashver.DashboardVersionDTO |
||||||
|
qr := `SELECT dashboard_version.id, |
||||||
|
dashboard_version.dashboard_id, |
||||||
|
dashboard_version.parent_version, |
||||||
|
dashboard_version.restored_from, |
||||||
|
dashboard_version.version, |
||||||
|
dashboard_version.created, |
||||||
|
dashboard_version.message, |
||||||
|
"user".login as created_by_login |
||||||
|
FROM dashboard_version |
||||||
|
LEFT JOIN "user" ON "user".id = dashboard_version.created_by |
||||||
|
LEFT JOIN dashboard ON dashboard.id = dashboard_version.dashboard_id |
||||||
|
WHERE dashboard_version.dashboard_id=? AND dashboard.org_id=? |
||||||
|
ORDER BY dashboard_version.version DESC |
||||||
|
LIMIT ? OFFSET ?` |
||||||
|
|
||||||
|
err := ss.sess.Select(ctx, &dashboardVersion, qr, query.DashboardID, query.OrgID, query.Limit, query.Start) |
||||||
|
if err != nil { |
||||||
|
return nil, err |
||||||
|
} |
||||||
|
if len(dashboardVersion) < 1 { |
||||||
|
return nil, dashver.ErrNoVersionsForDashboardID |
||||||
|
} |
||||||
|
return dashboardVersion, nil |
||||||
|
} |
@ -0,0 +1,15 @@ |
|||||||
|
package dashverimpl |
||||||
|
|
||||||
|
import ( |
||||||
|
"testing" |
||||||
|
|
||||||
|
"github.com/grafana/grafana/pkg/services/sqlstore" |
||||||
|
) |
||||||
|
|
||||||
|
func TestIntegrationSQLxGetDashboardVersion(t *testing.T) { |
||||||
|
testIntegrationGetDashboardVersion(t, func(ss *sqlstore.SQLStore) store { |
||||||
|
return &sqlxStore{ |
||||||
|
sess: ss.GetSqlxSession(), |
||||||
|
} |
||||||
|
}) |
||||||
|
} |
@ -0,0 +1,108 @@ |
|||||||
|
package dashverimpl |
||||||
|
|
||||||
|
import ( |
||||||
|
"context" |
||||||
|
"strings" |
||||||
|
|
||||||
|
dashver "github.com/grafana/grafana/pkg/services/dashboardversion" |
||||||
|
"github.com/grafana/grafana/pkg/services/sqlstore" |
||||||
|
"github.com/grafana/grafana/pkg/services/sqlstore/db" |
||||||
|
"github.com/grafana/grafana/pkg/services/sqlstore/migrator" |
||||||
|
) |
||||||
|
|
||||||
|
type sqlStore struct { |
||||||
|
db db.DB |
||||||
|
dialect migrator.Dialect |
||||||
|
} |
||||||
|
|
||||||
|
func (ss *sqlStore) Get(ctx context.Context, query *dashver.GetDashboardVersionQuery) (*dashver.DashboardVersion, error) { |
||||||
|
var version dashver.DashboardVersion |
||||||
|
err := ss.db.WithDbSession(ctx, func(sess *sqlstore.DBSession) error { |
||||||
|
has, err := sess.Where("dashboard_version.dashboard_id=? AND dashboard_version.version=? AND dashboard.org_id=?", query.DashboardID, query.Version, query.OrgID). |
||||||
|
Join("LEFT", "dashboard", `dashboard.id = dashboard_version.dashboard_id`). |
||||||
|
Get(&version) |
||||||
|
|
||||||
|
if err != nil { |
||||||
|
return err |
||||||
|
} |
||||||
|
|
||||||
|
if !has { |
||||||
|
return dashver.ErrDashboardVersionNotFound |
||||||
|
} |
||||||
|
return nil |
||||||
|
}) |
||||||
|
if err != nil { |
||||||
|
return nil, err |
||||||
|
} |
||||||
|
return &version, nil |
||||||
|
} |
||||||
|
|
||||||
|
func (ss *sqlStore) GetBatch(ctx context.Context, cmd *dashver.DeleteExpiredVersionsCommand, perBatch int, versionsToKeep int) ([]interface{}, error) { |
||||||
|
var versionIds []interface{} |
||||||
|
err := ss.db.WithTransactionalDbSession(ctx, func(sess *sqlstore.DBSession) error { |
||||||
|
versionIdsToDeleteQuery := `SELECT id |
||||||
|
FROM dashboard_version, ( |
||||||
|
SELECT dashboard_id, count(version) as count, min(version) as min |
||||||
|
FROM dashboard_version |
||||||
|
GROUP BY dashboard_id |
||||||
|
) AS vtd |
||||||
|
WHERE dashboard_version.dashboard_id=vtd.dashboard_id |
||||||
|
AND version < vtd.min + vtd.count - ? |
||||||
|
LIMIT ?` |
||||||
|
|
||||||
|
err := sess.SQL(versionIdsToDeleteQuery, versionsToKeep, perBatch).Find(&versionIds) |
||||||
|
return err |
||||||
|
}) |
||||||
|
return versionIds, err |
||||||
|
} |
||||||
|
|
||||||
|
func (ss *sqlStore) DeleteBatch(ctx context.Context, cmd *dashver.DeleteExpiredVersionsCommand, versionIdsToDelete []interface{}) (int64, error) { |
||||||
|
var deleted int64 |
||||||
|
err := ss.db.WithTransactionalDbSession(ctx, func(sess *sqlstore.DBSession) error { |
||||||
|
deleteExpiredSQL := `DELETE FROM dashboard_version WHERE id IN (?` + strings.Repeat(",?", len(versionIdsToDelete)-1) + `)` |
||||||
|
sqlOrArgs := append([]interface{}{deleteExpiredSQL}, versionIdsToDelete...) |
||||||
|
expiredResponse, err := sess.Exec(sqlOrArgs...) |
||||||
|
if err != nil { |
||||||
|
return err |
||||||
|
} |
||||||
|
|
||||||
|
deleted, err = expiredResponse.RowsAffected() |
||||||
|
return err |
||||||
|
}) |
||||||
|
return deleted, err |
||||||
|
} |
||||||
|
|
||||||
|
func (ss *sqlStore) List(ctx context.Context, query *dashver.ListDashboardVersionsQuery) ([]*dashver.DashboardVersionDTO, error) { |
||||||
|
var dashboardVersion []*dashver.DashboardVersionDTO |
||||||
|
err := ss.db.WithDbSession(ctx, func(sess *sqlstore.DBSession) error { |
||||||
|
err := sess.Table("dashboard_version"). |
||||||
|
Select(`dashboard_version.id, |
||||||
|
dashboard_version.dashboard_id, |
||||||
|
dashboard_version.parent_version, |
||||||
|
dashboard_version.restored_from, |
||||||
|
dashboard_version.version, |
||||||
|
dashboard_version.created, |
||||||
|
dashboard_version.created_by as created_by_id, |
||||||
|
dashboard_version.message, |
||||||
|
dashboard_version.data,`+ |
||||||
|
ss.dialect.Quote("user")+`.login as created_by`). |
||||||
|
Join("LEFT", ss.dialect.Quote("user"), `dashboard_version.created_by = `+ss.dialect.Quote("user")+`.id`). |
||||||
|
Join("LEFT", "dashboard", `dashboard.id = dashboard_version.dashboard_id`). |
||||||
|
Where("dashboard_version.dashboard_id=? AND dashboard.org_id=?", query.DashboardID, query.OrgID). |
||||||
|
OrderBy("dashboard_version.version DESC"). |
||||||
|
Limit(query.Limit, query.Start). |
||||||
|
Find(&dashboardVersion) |
||||||
|
if err != nil { |
||||||
|
return err |
||||||
|
} |
||||||
|
|
||||||
|
if len(dashboardVersion) < 1 { |
||||||
|
return dashver.ErrNoVersionsForDashboardID |
||||||
|
} |
||||||
|
return nil |
||||||
|
}) |
||||||
|
if err != nil { |
||||||
|
return nil, err |
||||||
|
} |
||||||
|
return dashboardVersion, nil |
||||||
|
} |
@ -0,0 +1,16 @@ |
|||||||
|
package dashverimpl |
||||||
|
|
||||||
|
import ( |
||||||
|
"testing" |
||||||
|
|
||||||
|
"github.com/grafana/grafana/pkg/services/sqlstore" |
||||||
|
) |
||||||
|
|
||||||
|
func TestIntegrationXORMGetDashboardVersion(t *testing.T) { |
||||||
|
testIntegrationGetDashboardVersion(t, func(ss *sqlstore.SQLStore) store { |
||||||
|
return &sqlStore{ |
||||||
|
db: ss, |
||||||
|
dialect: ss.GetDialect(), |
||||||
|
} |
||||||
|
}) |
||||||
|
} |
Loading…
Reference in new issue