schedule

package
v1.167.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jan 12, 2026 License: MIT Imports: 22 Imported by: 0

Documentation

Index

Constants

View Source
const (
	// LabelSchedule is the label key for schedule resources
	LabelSchedule = "agentapi.proxy/schedule"
	// LabelScheduleID is the label key for schedule ID
	LabelScheduleID = "agentapi.proxy/schedule-id"
	// LabelScheduleScope is the label key for schedule scope (user or team)
	LabelScheduleScope = "agentapi.proxy/schedule-scope"
	// LabelScheduleUserID is the label key for schedule user ID
	LabelScheduleUserID = "agentapi.proxy/schedule-user-id"
	// LabelScheduleTeamID is the label key for schedule team ID
	LabelScheduleTeamID = "agentapi.proxy/schedule-team-id"
	// SecretKeySchedule is the key in the Secret data for single schedule JSON
	SecretKeySchedule = "schedule.json"
	// ScheduleSecretPrefix is the prefix for schedule Secret names
	ScheduleSecretPrefix = "agentapi-schedule-"
	// LegacyScheduleSecretName is the name of the legacy Secret containing all schedules
	LegacyScheduleSecretName = "agentapi-schedules"
	// LegacySecretKeySchedules is the key in the legacy Secret data for schedules JSON
	LegacySecretKeySchedules = "schedules.json"
)

Variables

This section is empty.

Functions

func CalculateNextExecution

func CalculateNextExecution(s *Schedule, from time.Time) (*time.Time, error)

CalculateNextExecution calculates the next execution time for a schedule

Types

type CreateScheduleRequest

type CreateScheduleRequest struct {
	Name          string                 `json:"name"`
	Scope         entities.ResourceScope `json:"scope,omitempty"`
	TeamID        string                 `json:"team_id,omitempty"`
	ScheduledAt   *time.Time             `json:"scheduled_at,omitempty"`
	CronExpr      string                 `json:"cron_expr,omitempty"`
	Timezone      string                 `json:"timezone,omitempty"`
	SessionConfig SessionConfig          `json:"session_config"`
}

CreateScheduleRequest represents the request body for creating a schedule

type CronParser

type CronParser struct {
	// contains filtered or unexported fields
}

CronParser handles cron expression parsing and next execution calculation

func NewCronParser

func NewCronParser() *CronParser

NewCronParser creates a new CronParser

func (*CronParser) Next

func (p *CronParser) Next(cronExpr string, timezone string, from time.Time) (time.Time, error)

Next calculates the next execution time after the given time

func (*CronParser) Validate

func (p *CronParser) Validate(cronExpr string) error

Validate checks if a cron expression is valid

type ErrInvalidSchedule

type ErrInvalidSchedule struct {
	Field   string
	Message string
}

ErrInvalidSchedule represents a validation error

func (ErrInvalidSchedule) Error

func (e ErrInvalidSchedule) Error() string

type ErrScheduleNotFound

type ErrScheduleNotFound struct {
	ID string
}

ErrScheduleNotFound is returned when a schedule is not found

func (ErrScheduleNotFound) Error

func (e ErrScheduleNotFound) Error() string

type ExecutionRecord

type ExecutionRecord struct {
	// ExecutedAt is when the execution was attempted
	ExecutedAt time.Time `json:"executed_at"`
	// SessionID is the ID of the created session (if successful)
	SessionID string `json:"session_id,omitempty"`
	// Status is the result of the execution: "success", "failed", or "skipped"
	Status string `json:"status"`
	// Error contains the error message if execution failed
	Error string `json:"error,omitempty"`
}

ExecutionRecord represents a single execution attempt

type Handlers

type Handlers struct {
	// contains filtered or unexported fields
}

Handlers handles schedule management endpoints

func NewHandlers

func NewHandlers(manager Manager, sessionManager portrepos.SessionManager) *Handlers

NewHandlers creates a new Handlers instance

func NewHandlersWithTimezone

func NewHandlersWithTimezone(manager Manager, sessionManager portrepos.SessionManager, defaultTimezone string) *Handlers

NewHandlersWithTimezone creates a new Handlers instance with a custom default timezone

func (*Handlers) CreateSchedule

func (h *Handlers) CreateSchedule(c echo.Context) error

CreateSchedule handles POST /schedules

func (*Handlers) DeleteSchedule

func (h *Handlers) DeleteSchedule(c echo.Context) error

DeleteSchedule handles DELETE /schedules/:id

func (*Handlers) GetName

func (h *Handlers) GetName() string

GetName returns the name of this handler for logging

func (*Handlers) GetSchedule

func (h *Handlers) GetSchedule(c echo.Context) error

GetSchedule handles GET /schedules/:id

func (*Handlers) ListSchedules

func (h *Handlers) ListSchedules(c echo.Context) error

ListSchedules handles GET /schedules

func (*Handlers) RegisterRoutes

func (h *Handlers) RegisterRoutes(e *echo.Echo, _ *app.Server) error

RegisterRoutes registers schedule management routes Implements the app.CustomHandler interface

func (*Handlers) TriggerSchedule

func (h *Handlers) TriggerSchedule(c echo.Context) error

TriggerSchedule handles POST /schedules/:id/trigger

func (*Handlers) UpdateSchedule

func (h *Handlers) UpdateSchedule(c echo.Context) error

UpdateSchedule handles PUT /schedules/:id

type KubernetesManager

type KubernetesManager struct {
	// contains filtered or unexported fields
}

KubernetesManager implements Manager using Kubernetes Secrets

func NewKubernetesManager

func NewKubernetesManager(client kubernetes.Interface, namespace string) *KubernetesManager

NewKubernetesManager creates a new KubernetesManager

func (*KubernetesManager) Create

func (m *KubernetesManager) Create(ctx context.Context, schedule *Schedule) error

Create creates a new schedule

func (*KubernetesManager) Delete

func (m *KubernetesManager) Delete(ctx context.Context, id string) error

Delete removes a schedule by ID

func (*KubernetesManager) Get

func (m *KubernetesManager) Get(ctx context.Context, id string) (*Schedule, error)

Get retrieves a schedule by ID

func (*KubernetesManager) GetDueSchedules

func (m *KubernetesManager) GetDueSchedules(ctx context.Context, now time.Time) ([]*Schedule, error)

GetDueSchedules returns schedules that are due for execution

func (*KubernetesManager) List

func (m *KubernetesManager) List(ctx context.Context, filter ScheduleFilter) ([]*Schedule, error)

List retrieves schedules matching the filter

func (*KubernetesManager) MigrateFromLegacy added in v1.160.0

func (m *KubernetesManager) MigrateFromLegacy(ctx context.Context) error

MigrateFromLegacy migrates schedules from the legacy single-Secret format to individual Secrets per schedule. This is idempotent - schedules that already exist as individual Secrets are skipped. The legacy Secret is preserved after migration for backup purposes.

func (*KubernetesManager) RecordExecution

func (m *KubernetesManager) RecordExecution(ctx context.Context, id string, record ExecutionRecord) error

RecordExecution records an execution attempt

func (*KubernetesManager) Update

func (m *KubernetesManager) Update(ctx context.Context, schedule *Schedule) error

Update updates an existing schedule

func (*KubernetesManager) UpdateNextExecution

func (m *KubernetesManager) UpdateNextExecution(ctx context.Context, id string, nextAt time.Time) error

UpdateNextExecution updates the next execution time for a schedule

type LeaderElectionConfig

type LeaderElectionConfig struct {
	// LeaseDuration is the duration that non-leader candidates will wait to force acquire leadership
	LeaseDuration time.Duration
	// RenewDeadline is the duration that the acting master will retry refreshing leadership before giving up
	RenewDeadline time.Duration
	// RetryPeriod is the duration the LeaderElector clients should wait between tries of actions
	RetryPeriod time.Duration
	// LeaseName is the name of the lease resource
	LeaseName string
	// Namespace is the namespace for the lease resource
	Namespace string
}

LeaderElectionConfig contains configuration for leader election

func DefaultLeaderElectionConfig

func DefaultLeaderElectionConfig(namespace string) LeaderElectionConfig

DefaultLeaderElectionConfig returns the default leader election configuration

type LeaderElector

type LeaderElector struct {
	// contains filtered or unexported fields
}

LeaderElector manages leader election for the schedule worker

func NewLeaderElector

func NewLeaderElector(client kubernetes.Interface, config LeaderElectionConfig) *LeaderElector

NewLeaderElector creates a new LeaderElector

func (*LeaderElector) Identity

func (l *LeaderElector) Identity() string

Identity returns the identity of this elector

func (*LeaderElector) Run

func (l *LeaderElector) Run(ctx context.Context, onStartedLeading func(ctx context.Context), onStoppedLeading func())

Run starts the leader election loop onStartedLeading is called when this instance becomes the leader onStoppedLeading is called when this instance loses leadership

type LeaderWorker

type LeaderWorker struct {
	// contains filtered or unexported fields
}

LeaderWorker combines leader election with the schedule worker

func NewLeaderWorker

func NewLeaderWorker(
	manager Manager,
	sessionManager portrepos.SessionManager,
	client kubernetes.Interface,
	workerConfig WorkerConfig,
	electionConfig LeaderElectionConfig,
) *LeaderWorker

NewLeaderWorker creates a new LeaderWorker

func (*LeaderWorker) Run

func (lw *LeaderWorker) Run(ctx context.Context)

Run starts the leader worker Only the leader will process schedules

func (*LeaderWorker) Stop

func (lw *LeaderWorker) Stop()

Stop gracefully stops the leader worker

type Manager

type Manager interface {
	// Create creates a new schedule
	Create(ctx context.Context, schedule *Schedule) error

	// Get retrieves a schedule by ID
	Get(ctx context.Context, id string) (*Schedule, error)

	// List retrieves schedules matching the filter
	List(ctx context.Context, filter ScheduleFilter) ([]*Schedule, error)

	// Update updates an existing schedule
	Update(ctx context.Context, schedule *Schedule) error

	// Delete removes a schedule by ID
	Delete(ctx context.Context, id string) error

	// GetDueSchedules returns schedules that are due for execution
	GetDueSchedules(ctx context.Context, now time.Time) ([]*Schedule, error)

	// RecordExecution records an execution attempt
	RecordExecution(ctx context.Context, id string, record ExecutionRecord) error

	// UpdateNextExecution updates the next execution time for a schedule
	UpdateNextExecution(ctx context.Context, id string, nextAt time.Time) error
}

Manager defines the interface for schedule management

type Schedule

type Schedule struct {
	// ID is the unique identifier for the schedule
	ID string `json:"id"`
	// Name is a human-readable name for the schedule
	Name string `json:"name"`
	// UserID is the ID of the user who created the schedule
	UserID string `json:"user_id"`
	// Scope defines the ownership scope ("user" or "team"). Defaults to "user".
	Scope entities.ResourceScope `json:"scope,omitempty"`
	// TeamID is the team identifier (e.g., "org/team-slug") when Scope is "team"
	TeamID string `json:"team_id,omitempty"`
	// Status is the current status of the schedule
	Status ScheduleStatus `json:"status"`

	// ScheduledAt is the time when the schedule should first execute (optional)
	// If set without CronExpr, this is a one-time schedule
	// If set with CronExpr, execution starts from this time
	ScheduledAt *time.Time `json:"scheduled_at,omitempty"`

	// CronExpr is the cron expression for recurring execution (optional)
	// Standard cron format: minute hour day-of-month month day-of-week
	// Example: "0 9 * * 1-5" (weekdays at 9:00 AM)
	CronExpr string `json:"cron_expr,omitempty"`

	// Timezone is the IANA timezone for schedule evaluation (default: UTC)
	Timezone string `json:"timezone,omitempty"`

	// SessionConfig contains the configuration for creating sessions
	SessionConfig SessionConfig `json:"session_config"`

	// LastExecution contains the most recent execution record
	LastExecution *ExecutionRecord `json:"last_execution,omitempty"`

	// NextExecutionAt is the calculated next execution time
	NextExecutionAt *time.Time `json:"next_execution_at,omitempty"`

	// ExecutionCount is the total number of executions
	ExecutionCount int `json:"execution_count"`

	// CreatedAt is when the schedule was created
	CreatedAt time.Time `json:"created_at"`

	// UpdatedAt is when the schedule was last updated
	UpdatedAt time.Time `json:"updated_at"`
}

Schedule represents a scheduled session configuration

func (*Schedule) GetScope added in v1.146.0

func (s *Schedule) GetScope() entities.ResourceScope

GetScope returns the resource scope, defaulting to "user" if not set

func (*Schedule) IsDue

func (s *Schedule) IsDue(now time.Time) bool

IsDue checks if the schedule is due for execution at the given time

func (*Schedule) IsOneTime

func (s *Schedule) IsOneTime() bool

IsOneTime returns true if this is a one-time schedule (no recurring)

func (*Schedule) IsRecurring

func (s *Schedule) IsRecurring() bool

IsRecurring returns true if this is a recurring schedule

func (*Schedule) Validate

func (s *Schedule) Validate() error

Validate checks if the schedule is valid

type ScheduleFilter

type ScheduleFilter struct {
	// UserID filters by user ID
	UserID string
	// Status filters by schedule status
	Status ScheduleStatus
	// Scope filters by resource scope
	Scope entities.ResourceScope
	// TeamID filters by team ID (for team-scoped schedules)
	TeamID string
	// TeamIDs filters by multiple team IDs (returns schedules for any of these teams)
	TeamIDs []string
}

ScheduleFilter defines filter criteria for listing schedules

type ScheduleResponse

type ScheduleResponse struct {
	ID              string                 `json:"id"`
	Name            string                 `json:"name"`
	UserID          string                 `json:"user_id"`
	Scope           entities.ResourceScope `json:"scope,omitempty"`
	TeamID          string                 `json:"team_id,omitempty"`
	Status          ScheduleStatus         `json:"status"`
	ScheduledAt     *time.Time             `json:"scheduled_at,omitempty"`
	CronExpr        string                 `json:"cron_expr,omitempty"`
	Timezone        string                 `json:"timezone,omitempty"`
	SessionConfig   SessionConfig          `json:"session_config"`
	NextExecutionAt *time.Time             `json:"next_execution_at,omitempty"`
	ExecutionCount  int                    `json:"execution_count"`
	LastExecution   *ExecutionRecord       `json:"last_execution,omitempty"`
	CreatedAt       time.Time              `json:"created_at"`
	UpdatedAt       time.Time              `json:"updated_at"`
}

ScheduleResponse represents the response for a schedule

type ScheduleStatus

type ScheduleStatus string

ScheduleStatus defines the current status of a schedule

const (
	// ScheduleStatusActive indicates the schedule is active and will execute
	ScheduleStatusActive ScheduleStatus = "active"
	// ScheduleStatusPaused indicates the schedule is paused
	ScheduleStatusPaused ScheduleStatus = "paused"
	// ScheduleStatusCompleted indicates a one-time schedule has completed
	ScheduleStatusCompleted ScheduleStatus = "completed"
)

type SessionConfig

type SessionConfig struct {
	// Environment variables to set for the session
	Environment map[string]string `json:"environment,omitempty"`
	// Tags for the session (including repository info)
	Tags map[string]string `json:"tags,omitempty"`
	// Params contains session parameters like initial message
	Params *entities.SessionParams `json:"params,omitempty"`
}

SessionConfig contains session creation parameters

type UpdateScheduleRequest

type UpdateScheduleRequest struct {
	Name          *string         `json:"name,omitempty"`
	Status        *ScheduleStatus `json:"status,omitempty"`
	ScheduledAt   *time.Time      `json:"scheduled_at,omitempty"`
	CronExpr      *string         `json:"cron_expr,omitempty"`
	Timezone      *string         `json:"timezone,omitempty"`
	SessionConfig *SessionConfig  `json:"session_config,omitempty"`
}

UpdateScheduleRequest represents the request body for updating a schedule

type Worker

type Worker struct {
	// contains filtered or unexported fields
}

Worker processes scheduled sessions

func NewWorker

func NewWorker(manager Manager, sessionManager portrepos.SessionManager, config WorkerConfig) *Worker

NewWorker creates a new schedule worker

func (*Worker) Start

func (w *Worker) Start(ctx context.Context) error

Start begins the worker loop

func (*Worker) Stop

func (w *Worker) Stop()

Stop gracefully stops the worker

type WorkerConfig

type WorkerConfig struct {
	// CheckInterval is how often to check for due schedules
	CheckInterval time.Duration
	// Enabled indicates whether the worker should run
	Enabled bool
}

WorkerConfig contains configuration for the schedule worker

func DefaultWorkerConfig

func DefaultWorkerConfig() WorkerConfig

DefaultWorkerConfig returns the default worker configuration

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL