// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
// SPDX-License-Identifier: Apache-2.0
using System;
using System.IO;
using System.Threading.Tasks;
using AWS.Deploy.Common;
using AWS.Deploy.Common.IO;
using AWS.Deploy.Orchestration.Utilities;
namespace AWS.Deploy.Orchestration.CDK
{
///
/// Orchestrates local node app.
/// It makes sure that a local node application is initialized in order to be able to
/// install CDK CLI in local node_modules.
///
///
/// When npm package is initialized, a specified version of CDK CLI is installed along with initialization.
///
public interface INPMPackageInitializer
{
///
/// Checks whether package.json file exists at given working directory or not.
/// If there exists a package.json file, it is assumed to have node initialized.
///
/// Directory for local node app.
/// True, if package.json exists at
bool IsInitialized(string workingDirectory);
///
/// Initializes npm package at
///
///
/// When npm package is initialized, a specified version of CDK CLI is installed along with installation.
/// w
/// Directory for local node app.
/// Version of CDK CLI.
/// Thrown when package.json IO fails.
/// Thrown when a npm command fails to execute.
Task Initialize(string workingDirectory, Version cdkVersion);
}
public class NPMPackageInitializer : INPMPackageInitializer
{
private readonly ICommandLineWrapper _commandLineWrapper;
private readonly IPackageJsonGenerator _packageJsonGenerator;
private readonly IFileManager _fileManager;
private readonly IDirectoryManager _directoryManager;
private readonly IOrchestratorInteractiveService _interactiveService;
private const string _packageJsonFileName = "package.json";
public NPMPackageInitializer(ICommandLineWrapper commandLineWrapper,
IPackageJsonGenerator packageJsonGenerator,
IFileManager fileManager,
IDirectoryManager directoryManager,
IOrchestratorInteractiveService interactiveService)
{
_commandLineWrapper = commandLineWrapper;
_packageJsonGenerator = packageJsonGenerator;
_fileManager = fileManager;
_directoryManager = directoryManager;
_interactiveService = interactiveService;
}
public bool IsInitialized(string workingDirectory)
{
var packageFilePath = Path.Combine(workingDirectory, _packageJsonFileName);
return _fileManager.Exists(packageFilePath);
}
public async Task Initialize(string workingDirectory, Version cdkVersion)
{
_interactiveService.LogDebugMessage($"Creating package.json at {workingDirectory}.");
var packageJsonFileContent = _packageJsonGenerator.Generate(cdkVersion);
var packageJsonFilePath = Path.Combine(workingDirectory, _packageJsonFileName);
try
{
if (!_directoryManager.Exists(workingDirectory))
{
_directoryManager.CreateDirectory(workingDirectory);
}
await _fileManager.WriteAllTextAsync(packageJsonFilePath, packageJsonFileContent);
}
catch (Exception exception)
{
throw new PackageJsonFileException(DeployToolErrorCode.FailedToWritePackageJsonFile, $"Failed to write {_packageJsonFileName} at {packageJsonFilePath}", exception);
}
try
{
// Install node packages specified in package.json file
await _commandLineWrapper.Run("npm install", workingDirectory, false);
}
catch (Exception exception)
{
throw new NPMCommandFailedException(DeployToolErrorCode.FailedToInstallNpmPackages, $"Failed to install npm packages at {workingDirectory}", exception);
}
}
}
}