github.com/projectriff/riff-cli@v0.0.5-0.20180301104501-5db7a3bd9fc1/cmd/logs.go (about) 1 /* 2 * Copyright 2018 the original author or authors. 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package cmd 18 19 import ( 20 "fmt" 21 "os/exec" 22 "os" 23 "bufio" 24 25 "github.com/spf13/cobra" 26 "github.com/projectriff/riff-cli/pkg/ioutils" 27 "github.com/projectriff/riff-cli/pkg/kubectl" 28 "github.com/projectriff/riff-cli/cmd/utils" 29 ) 30 31 type LogsOptions struct { 32 function string 33 container string 34 namespace string 35 tail bool 36 } 37 38 var logsOptions LogsOptions 39 40 // logsCmd represents the logs command 41 var logsCmd = &cobra.Command{ 42 Use: "logs", 43 Short: "Display the logs for a running function", 44 Long: `Display the logs for a running function For example: 45 46 riff logs -n myfunc -t 47 48 will tail the logs from the 'sidecar' container for the function 'myfunc' 49 50 `, 51 Run: func(cmd *cobra.Command, args []string) { 52 53 // get the viper value from env var, config file or flag option 54 logsOptions.namespace = utils.GetStringValueWithOverride("namespace", *cmd.Flags()) 55 56 fmt.Printf("Displaying logs for container %v of function %v in namespace %v\n\n", logsOptions.container, logsOptions.function, logsOptions.namespace) 57 58 cmdArgs := []string{"--namespace", logsOptions.namespace, "get", "pod", "-l", "function=" + logsOptions.function, "-o", "jsonpath={.items[0].metadata.name}"} 59 60 output, err := kubectl.ExecForString(cmdArgs) 61 62 if err != nil { 63 ioutils.Errorf("Error %v - Function %v may not be currently active\n\n", err, logsOptions.function) 64 return 65 } 66 67 pod := output 68 69 if logsOptions.tail { 70 71 cmdArgs = []string{"--namespace", logsOptions.namespace, "logs", "-c", logsOptions.container, "-f", pod} 72 73 kubectlCmd := exec.Command("kubectl", cmdArgs...) 74 cmdReader, err := kubectlCmd.StdoutPipe() 75 if err != nil { 76 fmt.Fprintln(os.Stderr, "Error creating StdoutPipe for kubectlCmd", err) 77 return 78 } 79 80 scanner := bufio.NewScanner(cmdReader) 81 go func() { 82 for scanner.Scan() { 83 fmt.Printf("%s\n\n", scanner.Text()) 84 } 85 }() 86 87 err = kubectlCmd.Start() 88 if err != nil { 89 fmt.Fprintln(os.Stderr, "Error starting kubectlCmd", err) 90 return 91 } 92 93 err = kubectlCmd.Wait() 94 if err != nil { 95 fmt.Fprintln(os.Stderr, "Error waiting for kubectlCmd", err) 96 return 97 } 98 99 } else { 100 101 cmdArgs = []string{"--namespace", logsOptions.namespace, "logs", "-c", logsOptions.container, pod} 102 103 output, err := kubectl.ExecForString(cmdArgs) 104 105 if err != nil { 106 ioutils.Errorf("Error: %v\n", err) 107 return 108 } 109 110 fmt.Printf("%v\n", output) 111 } 112 113 }, 114 } 115 116 func init() { 117 rootCmd.AddCommand(logsCmd) 118 119 logsCmd.Flags().StringVarP(&logsOptions.function, "name", "n", "", "the name of the function") 120 logsCmd.Flags().StringVarP(&logsOptions.container, "container", "c", "sidecar", "the name of the function container (sidecar or main)") 121 logsCmd.Flags().BoolVarP(&logsOptions.tail, "tail", "t", false, "tail the logs") 122 123 logsCmd.Flags().StringP("namespace", "", "default", "the namespace used for the deployed resources") 124 125 logsCmd.MarkFlagRequired("name") 126 }