Skip to content

Commit

Permalink
Project limits: Use InstanceList (#14318)
Browse files Browse the repository at this point in the history
Follow-up to #14315

This tidies up the queries used for project limits checking; it likely
results in improved performance for clusters with many entities.
  • Loading branch information
tomponline authored Oct 24, 2024
2 parents 13db980 + 6d46fd6 commit ead3a69
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 24 deletions.
32 changes: 32 additions & 0 deletions lxd/db/instances.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import (
"github.com/canonical/lxd/lxd/instance/instancetype"
"github.com/canonical/lxd/shared"
"github.com/canonical/lxd/shared/api"
"github.com/canonical/lxd/shared/osarch"
)

// InstanceArgs is a value object holding all db-related details about an instance.
Expand Down Expand Up @@ -44,6 +45,37 @@ type InstanceArgs struct {
ExpiryDate time.Time
}

// ToAPI converts InstanceArgs to api.Instance.
// The returned Instance has ExpandedConfig and ExpandedDevices set.
func (i *InstanceArgs) ToAPI() (*api.Instance, error) {
var err error

rslt := &api.Instance{
Name: i.Name,
Description: i.Description,

CreatedAt: i.CreationDate,
LastUsedAt: i.LastUsedDate,
Location: i.Node,
Type: i.Type.String(),
Project: i.Project,
Ephemeral: i.Ephemeral,
Stateful: i.Stateful,

Config: i.Config,
Devices: i.Devices.CloneNative(),
}

rslt.Architecture, err = osarch.ArchitectureName(i.Architecture)

rslt.Profiles = make([]string, 0, len(i.Profiles))
for _, profile := range i.Profiles {
rslt.Profiles = append(rslt.Profiles, profile.Name)
}

return rslt, err
}

// GetInstanceNames returns the names of all containers the given project.
func (c *ClusterTx) GetInstanceNames(ctx context.Context, project string) ([]string, error) {
stmt := `
Expand Down
44 changes: 20 additions & 24 deletions lxd/project/limits/permissions.go
Original file line number Diff line number Diff line change
Expand Up @@ -1288,43 +1288,39 @@ func fetchProject(globalConfig map[string]any, tx *db.ClusterTx, projectName str
profiles = append(profiles, *apiProfile)
}

drivers, err := tx.GetStoragePoolDrivers(ctx)
if err != nil {
return nil, fmt.Errorf("Fetch storage pools from database: %w", err)
}

dbInstances, err := cluster.GetInstances(ctx, tx.Tx(), cluster.InstanceFilter{Project: &projectName})
if err != nil {
return nil, fmt.Errorf("Fetch project instances from database: %w", err)
info := &projectInfo{
Project: *project,
Profiles: profiles,
}

dbInstanceDevices, err := cluster.GetDevices(ctx, tx.Tx(), "instance")
if err != nil {
return nil, fmt.Errorf("Fetch instance devices from database: %w", err)
instanceFilter := cluster.InstanceFilter{
Project: &projectName,
}

instances := make([]api.Instance, 0, len(dbInstances))
for _, instance := range dbInstances {
apiInstance, err := instance.ToAPI(ctx, tx.Tx(), globalConfig, dbInstanceDevices, dbProfileConfigs, dbProfileDevices)
instanceFunc := func(inst db.InstanceArgs, project api.Project) error {
apiInstance, err := inst.ToAPI()
if err != nil {
return nil, fmt.Errorf("Failed to get API data for instance %q in project %q: %w", instance.Name, instance.Project, err)
return err
}

instances = append(instances, *apiInstance)
info.Instances = append(info.Instances, *apiInstance)

return nil
}

volumes, err := tx.GetCustomVolumesInProject(ctx, projectName)
err = tx.InstanceList(ctx, instanceFunc, instanceFilter)
if err != nil {
return nil, fmt.Errorf("Fetch project custom volumes from database: %w", err)
return nil, fmt.Errorf("Fetch instances from database: %w", err)
}

info := &projectInfo{
Project: *project,
Profiles: profiles,
Instances: instances,
Volumes: volumes,
info.StoragePoolDrivers, err = tx.GetStoragePoolDrivers(ctx)
if err != nil {
return nil, fmt.Errorf("Fetch storage pools from database: %w", err)
}

StoragePoolDrivers: drivers,
info.Volumes, err = tx.GetCustomVolumesInProject(ctx, projectName)
if err != nil {
return nil, fmt.Errorf("Fetch project custom volumes from database: %w", err)
}

return info, nil
Expand Down

0 comments on commit ead3a69

Please sign in to comment.