2022-05-20 19:55:45 +00:00
|
|
|
|
// Copyright (c) HashiCorp, Inc.
|
|
|
|
|
|
// SPDX-License-Identifier: BUSL-1.1
|
2023-02-02 17:15:17 -08:00
|
|
|
|
|
2022-05-20 19:55:45 +00:00
|
|
|
|
package session
|
|
|
|
|
|
|
|
|
|
|
|
import (
|
|
|
|
|
|
"context"
|
2024-10-23 16:16:39 -04:00
|
|
|
|
"sync"
|
2022-05-20 19:55:45 +00:00
|
|
|
|
"time"
|
|
|
|
|
|
|
|
|
|
|
|
"github.com/hashicorp/boundary/internal/errors"
|
|
|
|
|
|
"github.com/hashicorp/boundary/internal/scheduler"
|
2024-10-23 16:16:39 -04:00
|
|
|
|
"github.com/hashicorp/boundary/internal/scheduler/batch"
|
2022-05-20 19:55:45 +00:00
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
type deleteTerminatedJob struct {
|
|
|
|
|
|
repo *Repository
|
|
|
|
|
|
|
|
|
|
|
|
// the amount of time that a session must be in the terminated
|
|
|
|
|
|
// state for it to be deleted.
|
|
|
|
|
|
threshold time.Duration
|
|
|
|
|
|
|
2024-10-23 16:16:39 -04:00
|
|
|
|
mu sync.Mutex
|
|
|
|
|
|
batch *batch.Batch
|
2022-05-20 19:55:45 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
func newDeleteTerminatedJob(ctx context.Context, repo *Repository, threshold time.Duration) (*deleteTerminatedJob, error) {
|
|
|
|
|
|
const op = "session.newDeleteTerminatedJob"
|
|
|
|
|
|
switch {
|
|
|
|
|
|
case repo == nil:
|
|
|
|
|
|
return nil, errors.New(ctx, errors.InvalidParameter, op, "missing repository")
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
return &deleteTerminatedJob{
|
|
|
|
|
|
repo: repo,
|
|
|
|
|
|
threshold: threshold,
|
|
|
|
|
|
}, nil
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// Status reports the job’s current status. The status is periodically persisted by
|
|
|
|
|
|
// the scheduler when a job is running, and will be used to verify a job is making progress.
|
|
|
|
|
|
func (d *deleteTerminatedJob) Status() scheduler.JobStatus {
|
2024-10-23 16:16:39 -04:00
|
|
|
|
d.mu.Lock()
|
|
|
|
|
|
defer d.mu.Unlock()
|
|
|
|
|
|
if d.batch != nil {
|
|
|
|
|
|
return d.batch.Status()
|
2022-05-20 19:55:45 +00:00
|
|
|
|
}
|
2024-10-23 16:16:39 -04:00
|
|
|
|
return scheduler.JobStatus{}
|
2022-05-20 19:55:45 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// Run performs the required work depending on the implementation.
|
|
|
|
|
|
// The context is used to notify the job that it should exit early.
|
2024-10-23 16:16:39 -04:00
|
|
|
|
func (d *deleteTerminatedJob) Run(ctx context.Context, statusThreshold time.Duration) error {
|
2022-05-20 19:55:45 +00:00
|
|
|
|
const op = "session.(deleteTerminatedJob).Run"
|
|
|
|
|
|
|
2024-10-23 16:16:39 -04:00
|
|
|
|
params, err := d.repo.getDeleteJobParams(ctx, d.threshold)
|
|
|
|
|
|
switch {
|
|
|
|
|
|
case err != nil:
|
|
|
|
|
|
return errors.Wrap(ctx, err, op)
|
|
|
|
|
|
case params.TotalToDelete == 0:
|
|
|
|
|
|
return nil
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
exec := func() batch.Exec {
|
|
|
|
|
|
return func(ctx context.Context, batchSize int) (int, error) {
|
|
|
|
|
|
return d.repo.deleteTerminatedSessionsBatch(ctx, params.WindowStartTime, batchSize)
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
config := &batch.Config{
|
|
|
|
|
|
Size: params.BatchSize,
|
|
|
|
|
|
TotalToComplete: params.TotalToDelete,
|
|
|
|
|
|
StatusThreshold: statusThreshold,
|
|
|
|
|
|
Exec: exec(),
|
|
|
|
|
|
Store: d.repo.setDeleteJobBatchSize,
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
batch, err := batch.New(ctx, config)
|
2022-05-20 19:55:45 +00:00
|
|
|
|
if err != nil {
|
|
|
|
|
|
return errors.Wrap(ctx, err, op)
|
|
|
|
|
|
}
|
2024-10-23 16:16:39 -04:00
|
|
|
|
d.mu.Lock()
|
|
|
|
|
|
d.batch = batch
|
|
|
|
|
|
d.mu.Unlock()
|
|
|
|
|
|
return batch.Run(ctx)
|
2022-05-20 19:55:45 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// NextRunIn returns the duration until the next job run should be scheduled. This
|
|
|
|
|
|
// method is invoked after a run has successfully completed and the next run time
|
|
|
|
|
|
// is being persisted by the scheduler. If an error is returned, the error will be logged
|
|
|
|
|
|
// but the duration returned will still be used in scheduling. If a zero duration is returned
|
|
|
|
|
|
// the job will be scheduled to run again immediately.
|
|
|
|
|
|
func (d *deleteTerminatedJob) NextRunIn(_ context.Context) (time.Duration, error) {
|
|
|
|
|
|
return time.Minute * 30, nil
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// Name is the unique name of the job.
|
|
|
|
|
|
func (d *deleteTerminatedJob) Name() string {
|
|
|
|
|
|
return "delete_terminated_sessions"
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// Description is the human readable description of the job.
|
|
|
|
|
|
func (d *deleteTerminatedJob) Description() string {
|
|
|
|
|
|
return "Delete terminated sessions that were terminated "
|
|
|
|
|
|
}
|