Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 0 additions & 7 deletions cmd/thv-operator/pkg/controllerutil/resources.go
Original file line number Diff line number Diff line change
Expand Up @@ -174,13 +174,6 @@ func CreateProxyServiceName(resourceName string) string {
return fmt.Sprintf("mcp-%s-proxy", resourceName)
}

// CreateProxyServiceURL generates the full cluster-local service URL
// Shared between MCPServer and MCPRemoteProxy
func CreateProxyServiceURL(resourceName, namespace string, port int32) string {
serviceName := CreateProxyServiceName(resourceName)
return fmt.Sprintf("http://%s.%s.svc.cluster.local:%d", serviceName, namespace, port)
}

// ProxyRunnerServiceAccountName generates the service account name for the proxy runner
// Shared between MCPServer and MCPRemoteProxy
func ProxyRunnerServiceAccountName(resourceName string) string {
Expand Down
5 changes: 0 additions & 5 deletions cmd/thv-operator/pkg/registryapi/podtemplatespec.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,6 @@ type PodTemplateSpecBuilder struct {
defaultSpec *corev1.PodTemplateSpec
}

// NewPodTemplateSpecBuilder creates a new PodTemplateSpecBuilder with an empty template.
func NewPodTemplateSpecBuilder() *PodTemplateSpecBuilder {
return NewPodTemplateSpecBuilderFrom(nil)
}

// NewPodTemplateSpecBuilderFrom creates a new PodTemplateSpecBuilder with a user-provided template.
// The user template is deep-copied to avoid mutating the original.
// Options applied via Apply() act as defaults - Build() will merge them with user values,
Expand Down
2 changes: 1 addition & 1 deletion cmd/thv-operator/pkg/registryapi/podtemplatespec_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -717,7 +717,7 @@ func TestNewPodTemplateSpecBuilderFrom_MergeOnBuild(t *testing.T) {
assert.Equal(t, "default-value", result.Labels["default-label"])
})

t.Run("nil user template behaves like NewPodTemplateSpecBuilder", func(t *testing.T) {
t.Run("nil user template behaves like an empty builder", func(t *testing.T) {
t.Parallel()

builder := NewPodTemplateSpecBuilderFrom(nil)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ import (
"github.com/onsi/gomega"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/types"
"sigs.k8s.io/controller-runtime/pkg/client"
)

Expand Down Expand Up @@ -73,21 +72,6 @@ func (h *ConfigMapTestHelper) NewConfigMapBuilder(name string) *ConfigMapBuilder
}
}

// WithLabel adds a label to the ConfigMap
func (cb *ConfigMapBuilder) WithLabel(key, value string) *ConfigMapBuilder {
if cb.configMap.Labels == nil {
cb.configMap.Labels = make(map[string]string)
}
cb.configMap.Labels[key] = value
return cb
}

// WithData adds arbitrary data to the ConfigMap
func (cb *ConfigMapBuilder) WithData(key, value string) *ConfigMapBuilder {
cb.configMap.Data[key] = value
return cb
}

// WithToolHiveRegistry adds ToolHive format registry data
func (cb *ConfigMapBuilder) WithToolHiveRegistry(key string, servers []RegistryServer) *ConfigMapBuilder {
// Convert slice to map using server names as keys
Expand Down Expand Up @@ -151,21 +135,6 @@ func (h *ConfigMapTestHelper) CreateSampleToolHiveRegistry(name string) *corev1.
Create(h)
}

// GetConfigMap retrieves a ConfigMap by name
func (h *ConfigMapTestHelper) GetConfigMap(name string) (*corev1.ConfigMap, error) {
cm := &corev1.ConfigMap{}
err := h.Client.Get(h.Context, types.NamespacedName{
Namespace: h.Namespace,
Name: name,
}, cm)
return cm, err
}

// UpdateConfigMap updates an existing ConfigMap
func (h *ConfigMapTestHelper) UpdateConfigMap(configMap *corev1.ConfigMap) error {
return h.Client.Update(h.Context, configMap)
}

// DeleteConfigMap deletes a ConfigMap by name
func (h *ConfigMapTestHelper) DeleteConfigMap(name string) error {
cm := &corev1.ConfigMap{
Expand Down
25 changes: 0 additions & 25 deletions cmd/thv-operator/test-integration/mcp-registry/k8s_helpers.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,16 +48,6 @@ func (h *K8sResourceTestHelper) GetService(name string) (*corev1.Service, error)
return service, err
}

// GetConfigMap retrieves a configmap by name
func (h *K8sResourceTestHelper) GetConfigMap(name string) (*corev1.ConfigMap, error) {
configMap := &corev1.ConfigMap{}
err := h.k8sClient.Get(h.ctx, types.NamespacedName{
Namespace: h.namespace,
Name: name,
}, configMap)
return configMap, err
}

// DeploymentExists checks if a deployment exists
func (h *K8sResourceTestHelper) DeploymentExists(name string) bool {
_, err := h.GetDeployment(name)
Expand All @@ -69,18 +59,3 @@ func (h *K8sResourceTestHelper) ServiceExists(name string) bool {
_, err := h.GetService(name)
return err == nil
}

// IsDeploymentReady checks if a deployment is ready (all replicas available)
func (h *K8sResourceTestHelper) IsDeploymentReady(name string) bool {
deployment, err := h.GetDeployment(name)
if err != nil {
return false
}

// Check if deployment has at least one replica and all are available
if deployment.Spec.Replicas == nil || *deployment.Spec.Replicas == 0 {
return false
}

return deployment.Status.ReadyReplicas == *deployment.Spec.Replicas
}
106 changes: 0 additions & 106 deletions cmd/thv-operator/test-integration/mcp-registry/registry_helpers.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@ import (
"encoding/json"
"fmt"
"strings"
"time"

"github.com/onsi/ginkgo/v2"
"github.com/onsi/gomega"
Expand Down Expand Up @@ -112,16 +111,6 @@ func (rb *RegistryBuilder) WithAPISource(endpoint string) *RegistryBuilder {
return rb
}

// WithRegistryName sets the name for the source config
func (rb *RegistryBuilder) WithRegistryName(name string) *RegistryBuilder {
rb.config.SourceName = name
// Recalculate file path if this is a file source
if rb.config.SourceType == sourceTypeFile {
rb.config.FilePath = fmt.Sprintf("/config/registry/%s/registry.json", name)
}
return rb
}

// WithSyncPolicy configures the sync policy interval for the source
func (rb *RegistryBuilder) WithSyncPolicy(interval string) *RegistryBuilder {
rb.config.SyncInterval = interval
Expand All @@ -146,30 +135,6 @@ func (rb *RegistryBuilder) WithLabel(key, value string) *RegistryBuilder {
return rb
}

// WithNameIncludeFilter sets name include patterns for filtering on the source
func (rb *RegistryBuilder) WithNameIncludeFilter(patterns []string) *RegistryBuilder {
rb.config.NameInclude = patterns
return rb
}

// WithNameExcludeFilter sets name exclude patterns for filtering on the source
func (rb *RegistryBuilder) WithNameExcludeFilter(patterns []string) *RegistryBuilder {
rb.config.NameExclude = patterns
return rb
}

// WithTagIncludeFilter sets tag include patterns for filtering on the source
func (rb *RegistryBuilder) WithTagIncludeFilter(tags []string) *RegistryBuilder {
rb.config.TagInclude = tags
return rb
}

// WithTagExcludeFilter sets tag exclude patterns for filtering on the source
func (rb *RegistryBuilder) WithTagExcludeFilter(tags []string) *RegistryBuilder {
rb.config.TagExclude = tags
return rb
}

// Build returns the constructed MCPRegistry with configYAML generated from the builder config.
func (rb *RegistryBuilder) Build() *mcpv1beta1.MCPRegistry {
configYAML := rb.buildConfigYAML()
Expand Down Expand Up @@ -315,21 +280,6 @@ func writeStringList(b *strings.Builder, label string, items []string) {
}
}

// CreateBasicConfigMapRegistry creates a simple MCPRegistry with ConfigMap source
func (h *MCPRegistryTestHelper) CreateBasicConfigMapRegistry(name, configMapName string) *mcpv1beta1.MCPRegistry {
return h.NewRegistryBuilder(name).
WithConfigMapSource(configMapName, "registry.json").
WithSyncPolicy("1h").
Create(h)
}

// CreateManualSyncRegistry creates an MCPRegistry with manual sync only
func (h *MCPRegistryTestHelper) CreateManualSyncRegistry(name, configMapName string) *mcpv1beta1.MCPRegistry {
return h.NewRegistryBuilder(name).
WithConfigMapSource(configMapName, "registry.json").
Create(h)
}

// GetRegistry retrieves an MCPRegistry by name
func (h *MCPRegistryTestHelper) GetRegistry(name string) (*mcpv1beta1.MCPRegistry, error) {
registry := &mcpv1beta1.MCPRegistry{}
Expand All @@ -345,14 +295,6 @@ func (h *MCPRegistryTestHelper) UpdateRegistry(registry *mcpv1beta1.MCPRegistry)
return h.Client.Update(h.Context, registry)
}

// PatchRegistry patches an MCPRegistry with the given patch
func (h *MCPRegistryTestHelper) PatchRegistry(name string, patch client.Patch) error {
registry := &mcpv1beta1.MCPRegistry{}
registry.Name = name
registry.Namespace = h.Namespace
return h.Client.Patch(h.Context, registry, patch)
}

// DeleteRegistry deletes an MCPRegistry by name
func (h *MCPRegistryTestHelper) DeleteRegistry(name string) error {
registry := &mcpv1beta1.MCPRegistry{
Expand All @@ -364,54 +306,6 @@ func (h *MCPRegistryTestHelper) DeleteRegistry(name string) error {
return h.Client.Delete(h.Context, registry)
}

// TriggerManualSync adds the manual sync annotation to trigger a sync
func (h *MCPRegistryTestHelper) TriggerManualSync(name string) error {
registry, err := h.GetRegistry(name)
if err != nil {
return err
}

if registry.Annotations == nil {
registry.Annotations = make(map[string]string)
}
registry.Annotations["toolhive.stacklok.dev/manual-sync"] = fmt.Sprintf("%d", time.Now().Unix())

return h.UpdateRegistry(registry)
}

// GetRegistryStatus returns the current status of an MCPRegistry
func (h *MCPRegistryTestHelper) GetRegistryStatus(name string) (*mcpv1beta1.MCPRegistryStatus, error) {
registry, err := h.GetRegistry(name)
if err != nil {
return nil, err
}
return &registry.Status, nil
}

// GetRegistryPhase returns the current phase of an MCPRegistry
func (h *MCPRegistryTestHelper) GetRegistryPhase(name string) (mcpv1beta1.MCPRegistryPhase, error) {
status, err := h.GetRegistryStatus(name)
if err != nil {
return "", err
}
return status.Phase, nil
}

// GetRegistryCondition returns a specific condition from the registry status
func (h *MCPRegistryTestHelper) GetRegistryCondition(name, conditionType string) (*metav1.Condition, error) {
status, err := h.GetRegistryStatus(name)
if err != nil {
return nil, err
}

for _, condition := range status.Conditions {
if condition.Type == conditionType {
return &condition, nil
}
}
return nil, fmt.Errorf("condition %s not found", conditionType)
}

// ListRegistries returns all MCPRegistries in the namespace
func (h *MCPRegistryTestHelper) ListRegistries() (*mcpv1beta1.MCPRegistryList, error) {
registryList := &mcpv1beta1.MCPRegistryList{}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import (
"github.com/onsi/ginkgo/v2"
"github.com/onsi/gomega"
"k8s.io/apimachinery/pkg/api/errors"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"sigs.k8s.io/controller-runtime/pkg/client"

mcpv1beta1 "github.com/stacklok/toolhive/cmd/thv-operator/api/v1beta1"
Expand Down Expand Up @@ -51,44 +50,3 @@ func (h *StatusTestHelper) WaitForPhaseAny(registryName string,
}, timeout, time.Second).Should(gomega.BeElementOf(expectedPhases),
"MCPRegistry %s should reach one of phases %v", registryName, expectedPhases)
}

// WaitForCondition waits for a specific condition to have the expected status
func (h *StatusTestHelper) WaitForCondition(registryName, conditionType string,
expectedStatus metav1.ConditionStatus, timeout time.Duration) {
gomega.Eventually(func() metav1.ConditionStatus {
condition, err := h.registryHelper.GetRegistryCondition(registryName, conditionType)
if err != nil {
return metav1.ConditionUnknown
}
return condition.Status
}, timeout, time.Second).Should(gomega.Equal(expectedStatus),
"MCPRegistry %s should have condition %s with status %s", registryName, conditionType, expectedStatus)
}

// WaitForConditionReason waits for a condition to have a specific reason
func (h *StatusTestHelper) WaitForConditionReason(registryName, conditionType, expectedReason string, timeout time.Duration) {
gomega.Eventually(func() string {
condition, err := h.registryHelper.GetRegistryCondition(registryName, conditionType)
if err != nil {
return ""
}
return condition.Reason
}, timeout, time.Second).Should(gomega.Equal(expectedReason),
"MCPRegistry %s condition %s should have reason %s", registryName, conditionType, expectedReason)
}

// WaitForSyncCompletion waits for a sync operation to complete (either success or failure)
func (h *StatusTestHelper) WaitForSyncCompletion(registryName string, timeout time.Duration) {
gomega.Eventually(func() bool {
registry, err := h.registryHelper.GetRegistry(registryName)
if err != nil {
return false
}

// Check if sync is no longer in progress
phase := registry.Status.Phase
return phase == mcpv1beta1.MCPRegistryPhaseReady ||
phase == mcpv1beta1.MCPRegistryPhaseFailed
}, timeout, time.Second).Should(gomega.BeTrue(),
"MCPRegistry %s sync operation should complete", registryName)
}
Loading
Loading