private List <CloudFormationParameter> PromptModuleParameters( ModuleManifest manifest, CloudFormationStack existing = null, Dictionary <string, string> parameters = null, bool promptAll = false ) { var stackParameters = new Dictionary <string, CloudFormationParameter>(); // tentatively indicate to reuse previous parameter values if (existing != null) { foreach (var parameter in manifest.ParameterSections .SelectMany(section => section.Parameters) .Where(moduleParameter => existing.Parameters.Any(existingParameter => existingParameter.ParameterKey == moduleParameter.Name)) ) { stackParameters[parameter.Name] = new CloudFormationParameter { ParameterKey = parameter.Name, UsePreviousValue = true }; } } // deployment bucket must always be set to match deployment tier in case it changed because LambdaSharp.Core was recreated stackParameters["DeploymentBucketName"] = new CloudFormationParameter { ParameterKey = "DeploymentBucketName", ParameterValue = Settings.DeploymentBucketName }; // add all provided parameters if (parameters != null) { foreach (var parameter in parameters) { stackParameters[parameter.Key] = new CloudFormationParameter { ParameterKey = parameter.Key, ParameterValue = parameter.Value }; } } // check if module requires any prompts if (manifest.GetAllParameters().Any(RequiresPrompt)) { Console.WriteLine(); Console.WriteLine($"Configuration for {manifest.GetFullName()} (v{manifest.GetVersion()})"); // only list parameter sections that contain a parameter that requires a prompt foreach (var parameterGroup in manifest.ParameterSections.Where(group => group.Parameters.Any(RequiresPrompt))) { Console.WriteLine(); Settings.PromptLabel(parameterGroup.Title.ToUpper()); // only prompt for required parameters foreach (var parameter in parameterGroup.Parameters.Where(RequiresPrompt)) { // check if parameter is multiple choice string enteredValue; if (parameter.AllowedValues?.Any() ?? false) { var message = parameter.Name; if (parameter.Label != null) { message += $": {parameter.Label}"; } enteredValue = Settings.PromptChoice(message, parameter.AllowedValues); } else { var constraints = new StringBuilder(); if ((parameter.MinValue != null) || (parameter.MaxValue != null)) { // append value constraints constraints.Append(" ("); if ((parameter.MinValue != null) && (parameter.MaxValue != null)) { constraints.Append($"Range: {parameter.MinValue.Value}..{parameter.MaxValue.Value}"); } else if (parameter.MinValue != null) { constraints.Append($"Mininum: {parameter.MinValue.Value}"); } else if (parameter.MaxValue != null) { constraints.Append($"Maximum: {parameter.MaxValue.Value}"); } constraints.Append(")"); } else if ((parameter.MinLength != null) || (parameter.MaxLength != null)) { // append length constraints constraints.Append(" ("); if ((parameter.MinLength != null) || (parameter.MaxLength != null)) { constraints.Append($"Length: {parameter.MinValue.Value}..{parameter.MaxValue.Value}"); } else if (parameter.MinLength != null) { constraints.Append($"Mininum Length: {parameter.MinLength.Value}"); } else if (parameter.MaxLength != null) { constraints.Append($"Maximum Length: {parameter.MaxLength.Value}"); } constraints.Append(")"); } var message = $"{parameter.Name} [{parameter.Type}]{constraints}"; if (parameter.Label != null) { message += $": {parameter.Label}"; } enteredValue = Settings.PromptString(message, parameter.Default, parameter.AllowedPattern, parameter.ConstraintDescription) ?? ""; } stackParameters[parameter.Name] = new CloudFormationParameter { ParameterKey = parameter.Name, ParameterValue = enteredValue }; } } } // check if LambdaSharp.Core services should be enabled by default if ( (Settings.CoreServices == CoreServices.Enabled) && manifest.GetAllParameters().Any(p => p.Name == "LambdaSharpCoreServices") && !stackParameters.Any(p => p.Value.ParameterKey == "LambdaSharpCoreServices") ) { stackParameters.Add("LambdaSharpCoreServices", new CloudFormationParameter { ParameterKey = "LambdaSharpCoreServices", ParameterValue = Settings.CoreServices.ToString() }); } return(stackParameters.Values.ToList()); // local functions bool RequiresPrompt(ModuleManifestParameter parameter) { if (parameters?.ContainsKey(parameter.Name) == true) { // no prompt since parameter is provided explicitly return(false); } if (existing?.Parameters.Any(p => p.ParameterKey == parameter.Name) == true) { // no prompt since we can reuse the previous parameter value return(false); } if (!promptAll && (parameter.Default != null)) { // no prompt since parameter has a default value return(false); } if (Settings.PromptsAsErrors) { LogError($"{manifest.GetFullName()} requires value for parameter '{parameter.Name}'"); return(false); } return(true); } }
private List <CloudFormationParameter> PromptModuleParameters( ModuleManifest manifest, CloudFormationStack existing = null, Dictionary <string, string> parameters = null, bool promptAll = false, bool promptsAsErrors = false ) { var stackParameters = new Dictionary <string, CloudFormationParameter>(); // tentatively indicate to reuse previous parameter values if (existing != null) { foreach (var parameter in manifest.ParameterSections .SelectMany(section => section.Parameters) .Where(moduleParameter => existing.Parameters.Any(existingParameter => existingParameter.ParameterKey == moduleParameter.Name)) ) { stackParameters[parameter.Name] = new CloudFormationParameter { ParameterKey = parameter.Name, UsePreviousValue = true }; } } // add all provided parameters if (parameters != null) { foreach (var parameter in parameters) { stackParameters[parameter.Key] = new CloudFormationParameter { ParameterKey = parameter.Key, ParameterValue = parameter.Value }; } } // check if module requires any prompts if (manifest.GetAllParameters().Any(RequiresPrompt)) { Console.WriteLine(); Console.WriteLine($"Configuration for {manifest.GetFullName()} (v{manifest.GetVersion()})"); // only list parameter sections that contain a parameter that requires a prompt foreach (var parameterGroup in manifest.ParameterSections.Where(group => group.Parameters.Any(RequiresPrompt))) { Console.WriteLine(); Console.WriteLine($"*** {parameterGroup.Title.ToUpper()} ***"); // only prompt for required parameters foreach (var parameter in parameterGroup.Parameters.Where(RequiresPrompt)) { var enteredValue = PromptString(parameter, parameter.Default) ?? ""; stackParameters[parameter.Name] = new CloudFormationParameter { ParameterKey = parameter.Name, ParameterValue = enteredValue }; } } } return(stackParameters.Values.ToList()); // local functions bool RequiresPrompt(ModuleManifestParameter parameter) { if (parameters?.ContainsKey(parameter.Name) == true) { // no prompt since parameter is provided explicitly return(false); } if (existing?.Parameters.Any(p => p.ParameterKey == parameter.Name) == true) { // no prompt since we can reuse the previous parameter value return(false); } if (!promptAll && (parameter.Default != null)) { // no prompt since parameter has a default value return(false); } if (promptsAsErrors) { LogError($"{manifest.GetFullName()} requires value for parameter '{parameter.Name}'"); return(false); } return(true); } string PromptString(ModuleManifestParameter parameter, string defaultValue = null) { var prompt = $"|=> {parameter.Name} [{parameter.Type}]:"; if (parameter.Label != null) { prompt += $" {parameter.Label}:"; } if (!string.IsNullOrEmpty(defaultValue)) { prompt = $"{prompt} [{defaultValue}]"; } Console.Write(prompt); Console.Write(' '); SetCursorVisible(true); var resp = Console.ReadLine(); SetCursorVisible(false); if (!string.IsNullOrEmpty(resp)) { return(resp); } return(defaultValue); // local functions void SetCursorVisible(bool visible) { try { Console.CursorVisible = visible; } catch { } } } }