private static Task <bool> RunCommandAsync( string command, Action <string> outputAction = null, GCloudContext context = null, Dictionary <string, string> extraEnvironment = null) { var actualCommand = FormatCommand(command, context, jsonFormat: false); Dictionary <string, string> environment = null; if (context?.AppName != null) { environment = new Dictionary <string, string> { { GCloudMetricsVariable, context?.AppName } }; if (context?.AppVersion != null) { environment[GCloudMetricsVersionVariable] = context?.AppVersion; } if (extraEnvironment != null) { foreach (var entry in extraEnvironment) { environment.Add(entry.Key, entry.Value); } } } // This code depends on the fact that gcloud.cmd is a batch file. Debug.Write($"Executing gcloud command: {actualCommand}"); return(ProcessUtils.RunCommandAsync("cmd.exe", $"/c {actualCommand}", (o, e) => outputAction?.Invoke(e.Line), environment)); }
private static Dictionary <string, string> GetContextEnvironment( GCloudContext context, Dictionary <string, string> extraEnvironment = null) { Dictionary <string, string> environment = new Dictionary <string, string>(); if (context?.AppName != null) { environment[GCloudMetricsVariable] = context.AppName; if (context.AppVersion != null) { environment[GCloudMetricsVersionVariable] = context.AppVersion; } } if (extraEnvironment != null) { foreach (var entry in extraEnvironment) { environment.Add(entry.Key, entry.Value); } } return(environment); }
private static async Task <T> GetJsonOutputAsync <T>(string command, GCloudContext context = null) { var actualCommand = FormatCommand(command, context, jsonFormat: true); try { Dictionary <string, string> environment = null; if (context?.AppName != null) { environment = new Dictionary <string, string> { { GCloudMetricsVariable, context?.AppName } }; if (context?.AppVersion != null) { environment[GCloudMetricsVersionVariable] = context?.AppVersion; } } // This code depends on the fact that gcloud.cmd is a batch file. Debug.Write($"Executing gcloud command: {actualCommand}"); return(await ProcessUtils.GetJsonOutputAsync <T>("cmd.exe", $"/c {actualCommand}", environment)); } catch (JsonOutputException ex) { throw new GCloudException($"Failed to execute command {actualCommand}\nInner message:\n{ex.Message}", ex); } }
/// <summary> /// Resets, or creates, the password for the given <paramref name="userName"/> in the given instance. /// </summary> public static Task <WindowsInstanceCredentials> ResetWindowsCredentialsAsync( string instanceName, string zoneName, string userName, GCloudContext context) => GetJsonOutputAsync <WindowsInstanceCredentials>( $"compute reset-windows-password {instanceName} --zone={zoneName} --user=\"{userName}\" --quiet ", context);
private static string FormatCommand(string command, GCloudContext context, bool jsonFormat) { var projectId = context?.ProjectId != null ? $"--project={context.ProjectId}" : ""; var credentialsPath = context?.CredentialsPath != null ? $"--credential-file-override=\"{context.CredentialsPath}\"" : ""; var format = jsonFormat ? "--format=json" : ""; return($"gcloud {command} {projectId} {credentialsPath} {format}"); }
/// <summary> /// Deploys an app to App Engine. /// </summary> /// <param name="appYaml">The path to the app.yaml file to deploy.</param> /// <param name="version">The version to use, if no version is used gcloud will decide the version name.</param> /// <param name="promote">Whether to promote the app or not.</param> /// <param name="outputAction">The action to call with output from the command.</param> /// <param name="context">The context under which the command is executed.</param> public static Task <bool> DeployAppAsync( string appYaml, string version, bool promote, Action <string> outputAction, GCloudContext context) { var versionParameter = version != null ? $"--version={version}" : ""; var promoteParameter = promote ? "--promote" : "--no-promote"; return(RunCommandAsync($"app deploy \"{appYaml}\" {versionParameter} {promoteParameter} --quiet", outputAction, context)); }
private static Task <bool> RunCommandAsync( string command, Action <string> outputAction = null, GCloudContext context = null, Dictionary <string, string> extraEnvironment = null) { var actualCommand = FormatCommand(command, context, jsonFormat: false); var environment = GetContextEnvironment(context, extraEnvironment); // This code depends on the fact that gcloud.cmd is a batch file. Debug.Write($"Executing gcloud command: {actualCommand}"); return(ProcessUtils.RunCommandAsync( file: "cmd.exe", args: $"/c {actualCommand}", handler: (o, e) => outputAction?.Invoke(e.Line), environment: environment)); }
private static async Task <T> GetJsonOutputAsync <T>(string command, GCloudContext context = null) { var actualCommand = FormatCommand(command, context, jsonFormat: true); try { var environment = GetContextEnvironment(context); // This code depends on the fact that gcloud.cmd is a batch file. Debug.Write($"Executing gcloud command: {actualCommand}"); return(await ProcessUtils.GetJsonOutputAsync <T>(file : "cmd.exe", args : $"/c {actualCommand}", environment : environment)); } catch (JsonOutputException ex) { throw new GCloudException($"Failed to execute command {actualCommand}\nInner message:\n{ex.Message}", ex); } }
/// <summary> /// Returns the <seealso cref="KubectlContext"/> instance to use for the given <paramref name="cluster"/> when /// performing Kubernetes operations. /// </summary> /// <param name="cluster">The name of the cluster for which to create credentials.</param> /// <param name="zone">The zone of the cluster.</param> /// <param name="context">The context under which the command is executed.</param> /// <returns>The <seealso cref="KubectlContext"/> for the given <paramref name="cluster"/>.</returns> public static async Task <KubectlContext> GetKubectlContextForClusterAsync( string cluster, string zone, GCloudContext context) { var tempPath = Path.GetTempFileName(); if (!await CreateCredentialsForClusterAsync( cluster: cluster, zone: zone, path: tempPath, context: context)) { throw new GCloudException($"Failed to get credentials for cluster {cluster}"); } return(new KubectlContext(tempPath)); }
/// <summary> /// Deploys an app to App Engine. /// </summary> /// <param name="appYaml">The path to the app.yaml file to deploy.</param> /// <param name="version">The version to use, if no version is used gcloud will decide the version name.</param> /// <param name="promote">Whether to promote the app or not.</param> /// <param name="outputAction">The action to call with output from the command.</param> /// <param name="context">The context under which the command is executed.</param> public static Task <bool> DeployAppAsync( string appYaml, string version, bool promote, Action <string> outputAction, GCloudContext context) { var versionParameter = version != null ? $"--version={version}" : ""; var promoteParameter = promote ? "--promote" : "--no-promote"; var environment = new Dictionary <string, string> { [GCloudAppUseRuntimeBuilders] = CommonEnvironmentVariables.TrueValue, [GCloudAppRuntimeBuildersRoot] = RuntimeBuildersRootValue }; return(RunCommandAsync( $"beta app deploy \"{appYaml}\" {versionParameter} {promoteParameter} --skip-staging --quiet", outputAction, context, environment)); }
/// <summary> /// Creates a file with the cluster credentials at the given <paramref name="path"/> /// </summary> /// <param name="cluster">The name of the cluster for which to create credentials.</param> /// <param name="zone">The zone of the cluster.</param> /// <param name="path">The path where to store the credentials.</param> /// <param name="context">The context under which the command is executed.</param> public static Task <bool> CreateCredentialsForClusterAsync(string cluster, string zone, string path, GCloudContext context) { return(RunCommandAsync( $"container clusters get-credentials {cluster} --zone={zone}", context: context, extraEnvironment: new Dictionary <string, string> { [CommonEnvironmentVariables.GCloudKubeConfigVariable] = path, [CommonEnvironmentVariables.GCloudContainerUseApplicationDefaultCredentialsVariable] = CommonEnvironmentVariables.TrueValue, [CommonEnvironmentVariables.GoogleApplicationCredentialsVariable] = context.CredentialsPath, })); }
/// <summary> /// Builds a container using the Container Builder service. /// </summary> /// <param name="imageTag">The name of the image to build.</param> /// <param name="contentsPath">The contents of the container, including the Dockerfile.</param> /// <param name="outputAction">The action to perform on each line of output.</param> /// <param name="context">The context under which the command is executed.</param> public static Task <bool> BuildContainerAsync(string imageTag, string contentsPath, Action <string> outputAction, GCloudContext context) { return(RunCommandAsync( $"container builds submit --tag=\"{imageTag}\" \"{contentsPath}\"", outputAction, context)); }
/// <summary> /// Creates a file with the cluster credentials at the given <paramref name="path"/> /// </summary> /// <param name="cluster">The name of the cluster for which to create credentials.</param> /// <param name="zone">The zone of the cluster.</param> /// <param name="path">The path where to store the credentials.</param> /// <param name="context">The context under which the command is executed.</param> public static Task <bool> CreateCredentialsForClusterAsync(string cluster, string zone, string path, GCloudContext context) { return(RunCommandAsync( $"container clusters get-credentials {cluster} --zone={zone}", context: context, extraEnvironment: new Dictionary <string, string> { [GCloudKubeConfigVariable] = path })); }