Beispiel #1
0
func (o *NewServiceAccountTokenOptions) Complete(args []string, requestedLabels string, f *clientcmd.Factory, cmd *cobra.Command) error {
	if len(args) != 1 {
		return cmdutil.UsageError(cmd, fmt.Sprintf("expected one service account name as an argument, got %q", args))
	}

	o.SAName = args[0]

	if len(requestedLabels) > 0 {
		labels, err := kubectl.ParseLabels(requestedLabels)
		if err != nil {
			return cmdutil.UsageError(cmd, err.Error())
		}
		o.Labels = labels
	}

	client, err := f.Client()
	if err != nil {
		return err
	}

	namespace, _, err := f.DefaultNamespace()
	if err != nil {
		return fmt.Errorf("could not retrieve default namespace: %v", err)
	}

	o.SAClient = client.ServiceAccounts(namespace)
	o.SecretsClient = client.Secrets(namespace)
	return nil
}
Beispiel #2
0
func (o *CreateKubeconfigOptions) Complete(args []string, f *clientcmd.Factory, cmd *cobra.Command) error {
	if len(args) != 1 {
		return cmdutil.UsageError(cmd, fmt.Sprintf("expected one service account name as an argument, got %q", args))
	}

	o.SAName = args[0]

	client, err := f.Client()
	if err != nil {
		return err
	}

	namespace, _, err := f.DefaultNamespace()
	if err != nil {
		return err
	}

	o.RawConfig, err = f.OpenShiftClientConfig.RawConfig()
	if err != nil {
		return err
	}

	if len(o.ContextNamespace) == 0 {
		o.ContextNamespace = namespace
	}

	o.SAClient = client.ServiceAccounts(namespace)
	o.SecretsClient = client.Secrets(namespace)
	return nil
}
Beispiel #3
0
// Execute() will run a command in a pod and streams the out/err
func Execute(factory *osclientcmd.Factory, command []string, pod *kapi.Pod, in io.Reader, out, errOut io.Writer) error {
	config, err := factory.ClientConfig()
	if err != nil {
		return err
	}
	client, err := factory.Client()
	if err != nil {
		return err
	}

	execOptions := &kubecmd.ExecOptions{
		StreamOptions: kubecmd.StreamOptions{
			Namespace:     pod.Namespace,
			PodName:       pod.Name,
			ContainerName: pod.Name,
			In:            in,
			Out:           out,
			Err:           errOut,
			Stdin:         in != nil,
		},
		Executor: &kubecmd.DefaultRemoteExecutor{},
		Client:   client,
		Config:   config,
		Command:  command,
	}
	err = execOptions.Validate()
	if err != nil {
		return err
	}
	return execOptions.Run()
}
Beispiel #4
0
// newPortForwarder creates a new forwarder for use with rsync
func newPortForwarder(f *clientcmd.Factory, o *RsyncOptions) (forwarder, error) {
	client, err := f.Client()
	if err != nil {
		return nil, err
	}
	config, err := f.ClientConfig()
	if err != nil {
		return nil, err
	}
	return &portForwarder{
		Namespace: o.Namespace,
		PodName:   o.PodName(),
		Client:    client,
		Config:    config,
	}, nil
}
Beispiel #5
0
// Complete applies the command environment to RshOptions
func (o *RshOptions) Complete(f *clientcmd.Factory, cmd *cobra.Command, args []string) error {
	switch {
	case o.ForceTTY && o.DisableTTY:
		return kcmdutil.UsageError(cmd, "you may not specify -t and -T together")
	case o.ForceTTY:
		o.TTY = true
	case o.DisableTTY:
		o.TTY = false
	default:
		o.TTY = term.IsTerminal(o.In)
	}

	if len(args) < 1 {
		return kcmdutil.UsageError(cmd, "rsh requires a single Pod to connect to")
	}
	resource := args[0]
	args = args[1:]
	if len(args) > 0 {
		o.Command = args
	} else {
		o.Command = []string{o.Executable}
	}

	namespace, _, err := f.DefaultNamespace()
	if err != nil {
		return err
	}
	o.Namespace = namespace

	config, err := f.ClientConfig()
	if err != nil {
		return err
	}
	o.Config = config

	client, err := f.Client()
	if err != nil {
		return err
	}
	o.Client = client

	// TODO: Consider making the timeout configurable
	o.PodName, err = f.PodForResource(resource, 10*time.Second)
	return err
}
Beispiel #6
0
func newRemoteExecutor(f *clientcmd.Factory, o *RsyncOptions) (executor, error) {
	config, err := f.ClientConfig()
	if err != nil {
		return nil, err
	}

	client, err := f.Client()
	if err != nil {
		return nil, err
	}

	return &remoteExecutor{
		Namespace:     o.Namespace,
		PodName:       o.PodName(),
		ContainerName: o.ContainerName,
		Config:        config,
		Client:        client,
	}, nil
}
Beispiel #7
0
func (o *GetServiceAccountTokenOptions) Complete(args []string, f *clientcmd.Factory, cmd *cobra.Command) error {
	if len(args) != 1 {
		return cmdutil.UsageError(cmd, fmt.Sprintf("expected one service account name as an argument, got %q", args))
	}

	o.SAName = args[0]

	client, err := f.Client()
	if err != nil {
		return err
	}

	namespace, _, err := f.DefaultNamespace()
	if err != nil {
		return err
	}

	o.SAClient = client.ServiceAccounts(namespace)
	o.SecretsClient = client.Secrets(namespace)
	return nil
}
Beispiel #8
0
func newRsyncStrategy(f *clientcmd.Factory, c *cobra.Command, o *RsyncOptions) (copyStrategy, error) {
	// Determine the rsh command to pass to the local rsync command
	rsh := siblingCommand(c, "rsh")
	rshCmd := []string{rsh}
	// Append all original flags to rsh command
	c.Flags().Visit(func(flag *pflag.Flag) {
		if rshExcludeFlags.Has(flag.Name) {
			return
		}
		rshCmd = append(rshCmd, fmt.Sprintf("--%s=%s", flag.Name, flag.Value.String()))
	})
	rshCmdStr := strings.Join(rshCmd, " ")
	glog.V(4).Infof("Rsh command: %s", rshCmdStr)

	remoteExec, err := newRemoteExecutor(f, o)
	if err != nil {
		return nil, err
	}
	// The blocking-io flag is used to resolve a sync issue when
	// copying from the pod to the local machine
	flags := []string{"-a", "--blocking-io", "--omit-dir-times", "--numeric-ids"}
	flags = append(flags, rsyncFlagsFromOptions(o)...)

	podName := o.Source.PodName
	if o.Source.Local() {
		podName = o.Destination.PodName
	}
	client, err := f.Client()
	if err != nil {
		return nil, err
	}

	return &rsyncStrategy{
		Flags:          flags,
		RshCommand:     rshCmdStr,
		RemoteExecutor: remoteExec,
		LocalExecutor:  newLocalExecutor(),
		podChecker:     podAPIChecker{client, o.Namespace, podName},
	}, nil
}
Beispiel #9
0
func getConfigMapRefValue(f *clientcmd.Factory, store *resourceStore, configMapSelector *kapi.ConfigMapKeySelector) (string, error) {
	configMap, ok := store.configMapStore[configMapSelector.Name]
	if !ok {
		kubeClient, err := f.Client()
		if err != nil {
			return "", err
		}
		namespace, _, err := f.DefaultNamespace()
		if err != nil {
			return "", err
		}
		configMap, err = kubeClient.ConfigMaps(namespace).Get(configMapSelector.Name)
		if err != nil {
			return "", err
		}
		store.configMapStore[configMapSelector.Name] = configMap
	}
	if data, ok := configMap.Data[configMapSelector.Key]; ok {
		return string(data), nil
	}
	return "", fmt.Errorf("key %s not found in config map %s", configMapSelector.Key, configMapSelector.Name)
}
Beispiel #10
0
func getSecretRefValue(f *clientcmd.Factory, store *resourceStore, secretSelector *kapi.SecretKeySelector) (string, error) {
	secret, ok := store.secretStore[secretSelector.Name]
	if !ok {
		kubeClient, err := f.Client()
		if err != nil {
			return "", err
		}
		namespace, _, err := f.DefaultNamespace()
		if err != nil {
			return "", err
		}
		secret, err = kubeClient.Secrets(namespace).Get(secretSelector.Name)
		if err != nil {
			return "", err
		}
		store.secretStore[secretSelector.Name] = secret
	}
	if data, ok := secret.Data[secretSelector.Key]; ok {
		return string(data), nil
	}
	return "", fmt.Errorf("key %s not found in secret %s", secretSelector.Key, secretSelector.Name)
}
Beispiel #11
0
// calculateIdlableAnnotationsByService calculates the list of objects involved in the idling process from a list of services in a file.
// Using the list of services, it figures out the associated scalable objects, and returns a map from the endpoints object for the services to
// the list of scalable resources associated with that endpoints object, as well as a map from CrossGroupObjectReferences to scale to 0 to the
// name of the associated service.
func (o *IdleOptions) calculateIdlableAnnotationsByService(f *clientcmd.Factory) (map[types.NamespacedName]idleUpdateInfo, map[unidlingapi.CrossGroupObjectReference]types.NamespacedName, error) {
	// load our set of services
	client, err := f.Client()
	if err != nil {
		return nil, nil, err
	}

	mapper, _ := f.Object(false)

	podsLoaded := make(map[kapi.ObjectReference]*kapi.Pod)
	getPod := func(ref kapi.ObjectReference) (*kapi.Pod, error) {
		if pod, ok := podsLoaded[ref]; ok {
			return pod, nil
		}
		pod, err := client.Pods(ref.Namespace).Get(ref.Name)
		if err != nil {
			return nil, err
		}

		podsLoaded[ref] = pod

		return pod, nil
	}

	controllersLoaded := make(map[kapi.ObjectReference]runtime.Object)
	helpers := make(map[unversioned.GroupKind]*resource.Helper)
	getController := func(ref kapi.ObjectReference) (runtime.Object, error) {
		if controller, ok := controllersLoaded[ref]; ok {
			return controller, nil
		}
		gv, err := unversioned.ParseGroupVersion(ref.APIVersion)
		if err != nil {
			return nil, err
		}
		// just get the unversioned version of this
		gk := unversioned.GroupKind{Group: gv.Group, Kind: ref.Kind}
		helper, ok := helpers[gk]
		if !ok {
			var mapping *meta.RESTMapping
			mapping, err = mapper.RESTMapping(unversioned.GroupKind{Group: gv.Group, Kind: ref.Kind}, "")
			if err != nil {
				return nil, err
			}
			var client resource.RESTClient
			client, err = f.ClientForMapping(mapping)
			if err != nil {
				return nil, err
			}
			helper = resource.NewHelper(client, mapping)
			helpers[gk] = helper
		}

		var controller runtime.Object
		controller, err = helper.Get(ref.Namespace, ref.Name, false)
		if err != nil {
			return nil, err
		}

		controllersLoaded[ref] = controller

		return controller, nil
	}

	targetScaleRefs := make(map[unidlingapi.CrossGroupObjectReference]types.NamespacedName)
	endpointsInfo := make(map[types.NamespacedName]idleUpdateInfo)

	decoder := f.Decoder(true)
	err = o.svcBuilder.Do().Visit(func(info *resource.Info, err error) error {
		if err != nil {
			return err
		}

		endpoints, isEndpoints := info.Object.(*kapi.Endpoints)
		if !isEndpoints {
			return fmt.Errorf("you must specify endpoints, not %v (view available endpoints with \"%s get endpoints\").", info.Mapping.Resource, o.cmdFullName)
		}

		endpointsName := types.NamespacedName{
			Namespace: endpoints.Namespace,
			Name:      endpoints.Name,
		}
		scaleRefs, err := findScalableResourcesForEndpoints(endpoints, decoder, getPod, getController)
		if err != nil {
			return fmt.Errorf("unable to calculate scalable resources for service %s/%s: %v", endpoints.Namespace, endpoints.Name, err)
		}

		for ref := range scaleRefs {
			targetScaleRefs[ref] = endpointsName
		}

		idleInfo := idleUpdateInfo{
			obj:       endpoints,
			scaleRefs: scaleRefs,
		}

		endpointsInfo[endpointsName] = idleInfo

		return nil
	})

	return endpointsInfo, targetScaleRefs, err
}
Beispiel #12
0
// Complete verifies command line arguments and loads data from the command environment
func (o *RsyncOptions) Complete(f *clientcmd.Factory, cmd *cobra.Command, args []string) error {
	switch n := len(args); {
	case n == 0:
		cmd.Help()
		fallthrough
	case n < 2:
		return kcmdutil.UsageError(cmd, "SOURCE_DIR and POD:DESTINATION_DIR are required arguments")
	case n > 2:
		return kcmdutil.UsageError(cmd, "only SOURCE_DIR and POD:DESTINATION_DIR should be specified as arguments")
	}

	// Set main command arguments
	o.Source = args[0]
	o.Destination = args[1]

	// Determine pod name
	var err error
	o.PodName, o.DestinationDir, err = parseDestination(o.Destination)
	if err != nil {
		return kcmdutil.UsageError(cmd, err.Error())
	}

	// Use tar if running on windows
	// TODO: Figure out how to use rsync in windows so that I/O can be
	// redirected from the openshift native command to the cygwin rsync command
	if runtime.GOOS == "windows" {
		o.UseTar = true
	}

	namespace, _, err := f.DefaultNamespace()
	if err != nil {
		return err
	}
	o.Namespace = namespace

	// Determine the Rsh command to use for rsync
	if !o.UseTar {
		rsh := siblingCommand(cmd, "rsh")
		rshCmd := []string{rsh, "-n", o.Namespace}
		if len(o.ContainerName) > 0 {
			rshCmd = append(rshCmd, "-c", o.ContainerName)
		}
		o.RshCommand = strings.Join(rshCmd, " ")
		glog.V(4).Infof("Rsh command: %s", o.RshCommand)
	}

	config, err := f.ClientConfig()
	if err != nil {
		return err
	}

	client, err := f.Client()
	if err != nil {
		return err
	}

	o.RemoteExecutor = &defaultRemoteExecutor{
		Namespace:     o.Namespace,
		PodName:       o.PodName,
		ContainerName: o.ContainerName,
		Config:        config,
		Client:        client,
	}

	o.PodClient = client.Pods(namespace)

	return nil
}