Skip to content

Commit

Permalink
add app-settings-rewriter to altinn-app-cli
Browse files Browse the repository at this point in the history
  • Loading branch information
bjosttveit committed Sep 26, 2023
1 parent 618ab86 commit 806d405
Show file tree
Hide file tree
Showing 2 changed files with 158 additions and 2 deletions.
57 changes: 55 additions & 2 deletions cli-tools/altinn-app-cli/Program.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System.CommandLine;
using System.Reflection;
using altinn_app_cli.v7Tov8.AppSettingsRewriter;
using altinn_app_cli.v7Tov8.CodeRewriters;
using altinn_app_cli.v7Tov8.ProcessRewriter;
using altinn_app_cli.v7Tov8.ProjectChecks;
Expand All @@ -18,26 +19,31 @@ static async Task<int> Main(string[] args)
var projectFolderOption = new Option<string>(name: "--folder", description: "The project folder to read", getDefaultValue: () => "CurrentDirectory");
var projectFileOption = new Option<string>(name: "--project", description: "The project file to read relative to --folder", getDefaultValue: () => "App/App.csproj");
var processFileOption = new Option<string>(name: "--process", description: "The process file to read relative to --folder", getDefaultValue: () => "App/config/process/process.bpmn");
var appSettingsFolderOption = new Option<string>(name: "--appsettings-folder", description: "The folder where the appsettings.*.json files are located", getDefaultValue: () => "App");
var targetVersionOption = new Option<string>(name: "--target-version", description: "The target version to upgrade to", getDefaultValue: () => "8.0.0-preview.9");
var skipCsprojUpgradeOption = new Option<bool>(name: "--skip-csproj-upgrade", description: "Skip csproj file upgrade", getDefaultValue: () => false);
var skipCodeUpgradeOption = new Option<bool>(name: "--skip-code-upgrade", description: "Skip code upgrade", getDefaultValue: () => false);
var skipProcessUpgradeOption = new Option<bool>(name: "--skip-process-upgrade", description: "Skip process file upgrade", getDefaultValue: () => false);
var skipAppSettingsUpgradeOption = new Option<bool>(name: "--skip-appsettings-upgrade", description: "Skip appsettings file upgrade", getDefaultValue: () => false);
var rootCommand = new RootCommand("Command line interface for working with Altinn 3 Applications");
var upgradeCommand = new Command("upgrade", "Upgrade an app from v7 to v8")
{
projectFolderOption,
projectFileOption,
processFileOption,
appSettingsFolderOption,
targetVersionOption,
skipCsprojUpgradeOption,
skipCodeUpgradeOption,
skipProcessUpgradeOption,
skipAppSettingsUpgradeOption,
};
rootCommand.AddCommand(upgradeCommand);
var versionCommand = new Command("version", "Print version of altinn-app-cli");
rootCommand.AddCommand(versionCommand);

upgradeCommand.SetHandler(async (projectFolder, projectFile, processFile, targetVersion, skipCodeUpgrade, skipProcessUpgrade, skipCsprojUpgrade) =>
upgradeCommand.SetHandler(
async (projectFolder, projectFile, processFile, appSettingsFolder, targetVersion, skipCodeUpgrade, skipProcessUpgrade, skipCsprojUpgrade, skipAppSettingsUpgrade) =>
{
if (projectFolder == "CurrentDirectory")
{
Expand All @@ -63,11 +69,13 @@ static async Task<int> Main(string[] args)
{
projectFile = Path.Combine(Directory.GetCurrentDirectory(), projectFolder, projectFile);
processFile = Path.Combine(Directory.GetCurrentDirectory(), projectFolder, processFile);
appSettingsFolder = Path.Combine(Directory.GetCurrentDirectory(), projectFolder, appSettingsFolder);
}
else
{
projectFile = Path.Combine(projectFolder, projectFile);
processFile = Path.Combine(projectFolder, processFile);
appSettingsFolder = Path.Combine(projectFolder, appSettingsFolder);
}
var projectChecks = new ProjectChecks(projectFile);
Expand All @@ -77,6 +85,7 @@ static async Task<int> Main(string[] args)
returnCode = 2;
return;
}
if (!skipCsprojUpgrade)
{
returnCode = await UpgradeNugetVersions(projectFile, targetVersion);
Expand All @@ -92,6 +101,11 @@ static async Task<int> Main(string[] args)
returnCode = await UpgradeProcess(processFile);
}
if (!skipAppSettingsUpgrade && returnCode == 0)
{
returnCode = await UpgradeAppSettings(appSettingsFolder);
}
if (returnCode == 0)
{
Console.WriteLine("Upgrade completed without errors. Please verify that the application is still working as expected.");
Expand All @@ -101,7 +115,17 @@ static async Task<int> Main(string[] args)
Console.WriteLine("Upgrade completed with errors. Please check for errors in the log above.");
}
},
projectFolderOption, projectFileOption, processFileOption, targetVersionOption, skipCodeUpgradeOption, skipProcessUpgradeOption, skipCsprojUpgradeOption);
projectFolderOption,
projectFileOption,
processFileOption,
appSettingsFolderOption,
targetVersionOption,
skipCodeUpgradeOption,
skipProcessUpgradeOption,
skipCsprojUpgradeOption,
skipAppSettingsUpgradeOption
);

versionCommand.SetHandler(() =>
{
var version = Assembly.GetEntryAssembly()?.GetCustomAttribute<AssemblyInformationalVersionAttribute>()?.InformationalVersion ?? "Unknown";
Expand Down Expand Up @@ -188,4 +212,33 @@ static async Task<int> UpgradeProcess(string processFile)

return 0;
}

static async Task<int> UpgradeAppSettings(string appSettingsFolder)
{
if (!Directory.Exists(appSettingsFolder))
{
Console.WriteLine($"App settings folder {appSettingsFolder} does not exist. Please supply location with --appsettings-folder [path/to/appsettings]");
return 1;
}

if (Directory.GetFiles(appSettingsFolder, "appsettings.*.json").Count() == 0)
{
Console.WriteLine($"No appsettings.*.json files found in {appSettingsFolder}");
return 1;
}

Console.WriteLine("Trying to upgrade appsettings.*.json files");
AppSettingsRewriter rewriter = new(appSettingsFolder);
rewriter.Upgrade();
await rewriter.Write();
var warnings = rewriter.GetWarnings();
foreach (var warning in warnings)
{
Console.WriteLine(warning);
}

Console.WriteLine(warnings.Any() ? "AppSettings files upgraded with warnings. Review the warnings above and make sure that the appsettings files are still valid." : "AppSettings files upgraded");

return 0;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,103 @@

using System.Text.Json;
using System.Text.Json.Nodes;

namespace altinn_app_cli.v7Tov8.AppSettingsRewriter;

/// <summary>
/// Rewrites the appsettings.*.json files
/// </summary>
public class AppSettingsRewriter
{
private Dictionary<string, JsonObject> appSettingsJsonCollection;
private readonly IList<string> warnings = new List<string>();

/// <summary>
/// Initializes a new instance of the <see cref="AppSettingsRewriter"/> class.
/// </summary>
public AppSettingsRewriter(string appSettingsFolder)
{
appSettingsJsonCollection = new Dictionary<string, JsonObject>();
foreach (var file in Directory.GetFiles(appSettingsFolder, "appsettings.*.json"))
{
var json = File.ReadAllText(file);
var appSettingsJson = JsonNode.Parse(json);
if (appSettingsJson is not JsonObject appSettingsJsonObject)
{
warnings.Add($"Unable to parse AppSettings file {file} as a json object, skipping");
continue;
}

this.appSettingsJsonCollection.Add(file, appSettingsJsonObject);
}
}

/// <summary>
/// Gets the warnings
/// </summary>
public IList<string> GetWarnings()
{
return warnings;
}

/// <summary>
/// Upgrades the appsettings.*.json files
/// </summary>
public void Upgrade()
{
foreach ((var fileName, var appSettingsJson) in appSettingsJsonCollection)
{
RewriteRemoveHiddenDataSetting(fileName, appSettingsJson);
}
}

/// <summary>
/// Writes the appsettings.*.json files
/// </summary>
public async Task Write()
{
var tasks = appSettingsJsonCollection.Select(async appSettingsFiles =>
{
appSettingsFiles.Deconstruct(out var fileName, out var appSettingsJson);
JsonSerializerOptions options = new JsonSerializerOptions
{
WriteIndented = true,
};
await File.WriteAllTextAsync(fileName, appSettingsJson.ToJsonString(options));
});

await Task.WhenAll(tasks);
}

private void RewriteRemoveHiddenDataSetting(string fileName, JsonObject settings)
{
// Look for "AppSettings" object
settings.TryGetPropertyValue("AppSettings", out var appSettingsNode);
if (appSettingsNode is not JsonObject appSettingsObject)
{
// No "AppSettings" object found, nothing to change
return;
}

// Look for "RemoveHiddenDataPreview" property
appSettingsObject.TryGetPropertyValue("RemoveHiddenDataPreview", out var removeHiddenDataPreviewNode);
if (removeHiddenDataPreviewNode is not JsonValue removeHiddenDataPreviewValue)
{
// No "RemoveHiddenDataPreview" property found, nothing to change
return;
}

// Get value of "RemoveHiddenDataPreview" property
if (!removeHiddenDataPreviewValue.TryGetValue<bool>(out var removeHiddenDataValue))
{
warnings.Add($"RemoveHiddenDataPreview has unexpected value {removeHiddenDataPreviewValue.ToJsonString()} in {fileName}, expected a boolean");
return;
}

appSettingsObject.Remove("RemoveHiddenDataPreview");
appSettingsObject.Add("RemoveHiddenData", removeHiddenDataValue);
appSettingsObject.Add("RequiredValidation", removeHiddenDataValue);

}
}

0 comments on commit 806d405

Please sign in to comment.