public static AngularWorkspace Create(StandardGlobalInfo globalInfo, NPMSolution npmSolution, NormalizedPath path) { NormalizedPath packageJsonPath = path.AppendPart("package.json"); NormalizedPath angularJsonPath = path.AppendPart("angular.json"); JObject packageJson = JObject.Parse(File.ReadAllText(packageJsonPath)); JObject angularJson = JObject.Parse(File.ReadAllText(angularJsonPath)); if (!(packageJson["private"]?.ToObject <bool>() ?? false)) { throw new InvalidDataException("A workspace project should be private."); } List <NPMProject> projects = new List <NPMProject>(); var jsonProject = angularJson["projects"].ToObject <JObject>(); foreach (var project in jsonProject.Properties()) { var projectPath = project.Value["root"].ToString(); var options = project.Value["architect"]["build"]["options"]; string outputPathJson = options["outputPath"]?.Value <string>(); bool havePath = outputPathJson != null; string ngPackagePath = options["project"]?.Value <string>(); bool haveNgPackageJson = ngPackagePath != null; if (havePath && haveNgPackageJson) { throw new NotImplementedException(); //I don't know what to do in this case. } NormalizedPath outputPath; NormalizedPath ngPackagePathFullPath = path.Combine(ngPackagePath); if (haveNgPackageJson) { JObject ngPackage = JObject.Parse(File.ReadAllText(ngPackagePathFullPath)); string dest = ngPackage["dest"]?.Value <string>(); if (dest == null) { throw new InvalidDataException("ng package does not contain dest path."); } outputPath = ngPackagePathFullPath.RemoveLastPart().Combine(dest).ResolveDots(); } else if (havePath) { outputPath = path.Combine(outputPathJson); } else { globalInfo.Cake.Warning($"No path found for angular project '{path}'."); outputPath = path.Combine(projectPath); } projects.Add( NPMPublishedProject.Create( globalInfo, npmSolution, path.Combine(projectPath), outputPath ) ); } return(new AngularWorkspace(NPMPublishedProject.Create(globalInfo, npmSolution, path, path), projects)); }
public static AngularWorkspace Create(StandardGlobalInfo globalInfo, NPMSolution npmSolution, NormalizedPath path) { NormalizedPath packageJsonPath = path.AppendPart("package.json"); NormalizedPath angularJsonPath = path.AppendPart("angular.json"); JObject packageJson = JObject.Parse(File.ReadAllText(packageJsonPath)); JObject angularJson = JObject.Parse(File.ReadAllText(angularJsonPath)); if (!(packageJson["private"]?.ToObject <bool>() ?? false)) { throw new InvalidDataException("A workspace project should be private."); } List <NPMProject> projects = new List <NPMProject>(); var jsonProject = angularJson["projects"].ToObject <JObject>(); foreach (var project in jsonProject.Properties()) { var projectPath = project.Value["root"].ToString(); var outputPath = project.Value["architect"]?["build"]?["options"]?["outputPath"]?.Value <string>() ?? projectPath; projects.Add( NPMPublishedProject.Create( globalInfo, npmSolution, path.Combine(projectPath), path.Combine(outputPath) ) ); } return(new AngularWorkspace(NPMPublishedProject.Create(globalInfo, npmSolution, path, path), projects)); }
public static AngularWorkspace Create(StandardGlobalInfo globalInfo, NPMSolution npmSolution, NormalizedPath path, NormalizedPath outputFolder) { NormalizedPath packageJsonPath = path.AppendPart("package.json"); NormalizedPath angularJsonPath = path.AppendPart("angular.json"); JObject packageJson = JObject.Parse(File.ReadAllText(packageJsonPath)); JObject angularJson = JObject.Parse(File.ReadAllText(angularJsonPath)); if (!(packageJson["private"]?.ToObject <bool>() ?? false)) { throw new InvalidDataException("A workspace project should be private."); } string solutionName = packageJson["name"].ToString(); List <string> unscopedNames = angularJson["projects"].ToObject <JObject>().Properties().Select(p => p.Name).ToList(); List <NPMProject> projects = unscopedNames.Select( p => NPMPublishedProject.Create( globalInfo, npmSolution, path.Combine(new NormalizedPath(angularJson["projects"][p]["root"].ToString())), outputFolder.AppendPart(p) ) ).ToList(); return(new AngularWorkspace(projects.Single(p => p.DirectoryPath == path), projects, outputFolder)); }
// This method gets called by the runtime. Use this method to add services to the container. public void ConfigureServices(IServiceCollection services) { services.AddCors(); services.AddSingleton <IWebFrontAuthLoginService, SqlWebFrontAuthLoginService>(); services.AddSingleton <IAuthenticationTypeSystem, StdAuthenticationTypeSystem>(); services.AddSingleton <IWebFrontAuthAutoCreateAccountService, AutoCreateAccountService>(); services.Configure <SpaOptions>(o => { o.Host = Configuration["Spa:Host"]; }); services.AddAuthentication(WebFrontAuthOptions.OnlyAuthenticationScheme) .AddOpenIdConnect("Oidc", options => { options.SignInScheme = WebFrontAuthOptions.OnlyAuthenticationScheme; options.Authority = "https://login.microsoftonline.com/" + Configuration["Authentication:Outlook:TenantId"]; options.ClientId = Configuration["Authentication:Outlook:ClientId"]; options.ResponseType = OpenIdConnectResponseType.IdToken; options.CallbackPath = "/auth/signin-callback"; options.SignedOutRedirectUri = "https://localhost:8080/"; options.TokenValidationParameters.NameClaimType = "name"; options.Events.OnTicketReceived = c => c.WebFrontAuthRemoteAuthenticateAsync <ICustomUserOidcInfos>(payload => { payload.Email = c.Principal.FindFirst(ClaimTypes.Name).Value; payload.FirstName = c.Principal.FindFirst(ClaimTypes.GivenName).Value; payload.LastName = c.Principal.FindFirst(ClaimTypes.Surname).Value; payload.SchemeSuffix = ""; // Instead of "http://schemas.xmlsoap.org/ws/2005/05/identity/claims/nameidentifier" // Use standard System.Security.Claims.ClaimTypes. payload.Sub = c.Principal.FindFirst(ClaimTypes.NameIdentifier).Value; }); }) .AddWebFrontAuth(options => { options.ExpireTimeSpan = TimeSpan.FromHours(1); options.SlidingExpirationTime = TimeSpan.FromHours(1); }) .AddCookie(); if (_env.IsDevelopment()) { NormalizedPath dllPath = Configuration["StObjMap:Path"]; if (!dllPath.IsEmptyPath) { var solutionPath = new NormalizedPath(AppContext.BaseDirectory).RemoveLastPart(4); dllPath = solutionPath.Combine(dllPath).AppendPart("CK.StObj.AutoAssembly.dll"); File.Copy(dllPath, Path.Combine(AppContext.BaseDirectory, "CK.StObj.AutoAssembly.dll"), overwrite: true); } } services.AddCKDatabase("CK.StObj.AutoAssembly"); services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1); services.AddSingleton <Emailer>(); services.Configure <EmailerOptions>(Configuration.GetSection("gmail")); services.AddOptions(); services.AddSignalR(); }
private static IModule[] GetTitleAndDestinationModules(IDocument archiveDoc) => new IModule[] { new AddTitle( Config.FromDocument(doc => { if (doc.ContainsKey(WebKeys.ArchiveTitle)) { return(doc.GetString(WebKeys.ArchiveTitle)); } // Default title string title = doc.GetString(Keys.Title); if (doc.ContainsKey(Keys.GroupKey)) { title += " - " + doc.GetString(Keys.GroupKey); } int index = doc.GetInt(Keys.Index); return(index <= 1 ? title : (title + $" (Page {index})")); })).KeepExisting(false), new SetDestination( Config.FromDocument(doc => { if (doc.ContainsKey(WebKeys.ArchiveDestination)) { return(doc.GetPath(WebKeys.ArchiveDestination)); } // Default destination NormalizedPath destination = archiveDoc.Destination.ChangeExtension(null); if (doc.ContainsKey(Keys.GroupKey)) { destination.Combine(NormalizedPath.ReplaceInvalidFileNameChars(doc.GetString(Keys.GroupKey))); } int index = doc.GetInt(Keys.Index); if (index > 1) { destination = destination.Combine(index.ToString()); } return(destination.AppendExtension(".html")); }), true) };
public void ShouldCombinePaths(string first, string second, string expected) { // Given NormalizedPath path = new NormalizedPath(first); // When NormalizedPath result = path.Combine(new NormalizedPath(second)); // Then Assert.AreEqual(expected, result.FullPath); }
public void ShouldThrowIfPathIsNull() { // Given NormalizedPath path = new NormalizedPath("assets"); // When TestDelegate test = () => path.Combine(null); // Then Assert.Throws <ArgumentNullException>(test); }
/// <summary> /// Gets the <see cref="Value"/> as an absolute path or relative to <see cref="BasePath"/>. /// <para> /// Placeholders {BuildConfiguration} and {TestProjectName} can appear anywhere in the Value /// and are replaced with <see cref="IBasicTestHelper.BuildConfiguration"/> and <see cref="IBasicTestHelper.TestProjectName"/>. /// </para> /// <para> /// The Value can start with {BinFolder}, {SolutionFolder} or {RepositoryFolder}: <see cref="IBasicTestHelper.BinFolder"/>, /// <see cref="IBasicTestHelper.SolutionFolder"/> or <see cref="IBasicTestHelper.RepositoryFolder"/> is expanded. /// If the Value does not start with one of this 3 paths and no { appear, the <see cref="BasePath"/> is prepended. /// </para> /// <para> /// If there is no '{' (ie. there is no unresolved placeholder), all '/../' are automatically resolved. /// If a '{' remains in the path, the dots are not resolved: this is up to the code that will use the path to resolve the placeholders /// and the dots (see <see cref="NormalizedPath.ResolveDots(int, bool)"/>). /// </para> /// Note that if the value is not a valid path, result is what it is, without any warranty. /// </summary> /// <returns>The path.</returns> public string GetValueAsPath() { Debug.Assert(Value != null && !BasePath.IsEmptyPath); string v = Value.Replace("{BuildConfiguration}", BasicTestHelper._buildConfiguration) .Replace("{TestProjectName}", BasicTestHelper._testProjectName); string SubPathNoRoot(string theV, int prefixLen) { if (theV.Length > prefixLen && (theV[prefixLen] == System.IO.Path.DirectorySeparatorChar || theV[prefixLen] == System.IO.Path.AltDirectorySeparatorChar)) { ++prefixLen; } return(v.Substring(prefixLen)); } Debug.Assert("{BinFolder}".Length == 11); Debug.Assert("{SolutionFolder}".Length == 16); Debug.Assert("{RepositoryFolder}".Length == 18); NormalizedPath raw; if (v.StartsWith("{BinFolder}")) { raw = BasicTestHelper._binFolder.Combine(SubPathNoRoot(v, 11)); } else if (v.StartsWith("{SolutionFolder}")) { raw = BasicTestHelper._solutionFolder.Combine(SubPathNoRoot(v, 16)); } else if (v.StartsWith("{RepositoryFolder}")) { raw = BasicTestHelper._repositoryFolder.Combine(SubPathNoRoot(v, 18)); } else { if (Path.IsPathRooted(v)) { return(Path.GetFullPath(v)); } if (v.IndexOf('{') >= 0) { return(v); } raw = BasePath.Combine(v); } return(raw.Path.IndexOf('{') < 0 ? raw.ResolveDots() : raw); }
static internal AngularWorkspace LoadAngularSolution(NPMProjectsDriver driver, IActivityMonitor m, IAngularWorkspaceSpec spec) { NormalizedPath packageJsonPath = spec.Path.AppendPart("package.json"); NormalizedPath angularJsonPath = spec.Path.AppendPart("angular.json"); var fs = driver.GitFolder.FileSystem; NormalizedPath path = driver.BranchPath; JObject packageJson = fs.GetFileInfo(path.Combine(packageJsonPath)).ReadAsJObject(); JObject angularJson = fs.GetFileInfo(path.Combine(angularJsonPath)).ReadAsJObject(); if (!(packageJson["private"]?.ToObject <bool?>() ?? false)) { throw new InvalidDataException("A workspace project should be private."); } string solutionName = packageJson["name"].ToString(); List <string> unscopedNames = angularJson["projects"].ToObject <JObject>().Properties().Select(p => p.Name).ToList(); List <NPMProject> projects = unscopedNames.Select( unscopedName => { var projPathRelativeToWorkspace = new NormalizedPath(angularJson["projects"][unscopedName]["root"].ToString()); var projPathRelativeToGitRepo = spec.Path.Combine(projPathRelativeToWorkspace); var projectPathVirtualPath = driver.BranchPath.Combine(projPathRelativeToGitRepo); JObject json = fs.GetFileInfo(projectPathVirtualPath.AppendPart("package.json")).ReadAsJObject(); return(new NPMProject( driver, m, new NPMProjectSpec( projPathRelativeToGitRepo, json["name"].ToString(), json["private"]?.ToObject <bool>() ?? false ) )); }).ToList(); return(new AngularWorkspace(driver, spec, projects)); }
public void ShouldReturnRelativePathWithDirectoryPath(string source, string target, string expected) { // Given NormalizedPath sourcePath = new NormalizedPath(source); NormalizedPath targetPath = new NormalizedPath(target); // When NormalizedPath relativePath = RelativePathResolver.Resolve(sourcePath, targetPath); // Then expected.ShouldBe((string)relativePath); if (targetPath.IsAbsolute) { sourcePath.Combine(relativePath).ShouldBe(targetPath); } }
static NormalizedPath MakeAbsolute(NormalizedPath basePath, NormalizedPath p) { if (basePath.IsEmptyPath) { throw new InvalidOperationException("Configuration BasePath is empty."); } if (!basePath.IsRooted) { throw new InvalidOperationException($"Configuration BasePath '{basePath}' is not rooted."); } if (!p.IsRooted) { p = basePath.Combine(p); } return(p.ResolveDots()); }
static string ReplacePattern(NormalizedPath basePath, string pattern, string v) { int len = pattern.Length; if (v.Length >= len) { NormalizedPath result; if (v.StartsWith(pattern, StringComparison.OrdinalIgnoreCase)) { if (v.Length > len && (v[len] == '\\' || v[len] == '/')) { ++len; } result = basePath.Combine(v.Substring(len)).ResolveDots(); } } return(v); }
public void ConfigureServices(IServiceCollection services) { services.AddOptions(); if (_env.IsDevelopment()) { NormalizedPath dllPath = _configuration["StObjMap:Path"]; if (!dllPath.IsEmpty) { var solutionPath = new NormalizedPath(AppContext.BaseDirectory).RemoveLastPart(4); dllPath = solutionPath.Combine(dllPath).AppendPart("CK.StObj.AutoAssembly.dll"); File.Copy(dllPath, Path.Combine(AppContext.BaseDirectory, "CK.StObj.AutoAssembly.dll"), overwrite: true); } } services.AddStObjMap("CK.StObj.AutoAssembly"); services.AddCors(); services.AddAmbientValues(_ => { }); services.AddMvc(); }
private string GetRelativePath(NormalizedPath path, IExecutionContext context) { // Calculate a relative path from the input path(s) (or root) to the provided path if (!path.IsNull) { NormalizedPath inputPath = context.FileSystem.GetContainingInputPath(path); if (inputPath.IsNull) { inputPath = NormalizedPath.AbsoluteRoot; } if (path.IsRelative) { // If the path is relative, combine it with the input path to make it absolute path = inputPath.Combine(path); } return($"/{inputPath.GetRelativePath(path).FullPath}"); } // If there's no path, give this document a placeholder name return($"/{Path.GetRandomFileName()}.cshtml"); }
/// <summary> /// Initializes a new <see cref="PluginFolderBase"/> on a folder path inside a branch path. /// </summary> /// <param name="f">The folder.</param> /// <param name="branchPath">The actual branch path (relative to the <see cref="FileSystem"/>).</param> /// <param name="folderPath"> /// The actual sub folder path (ie. 'CodeCakeBuilder') where resources must be updated.</param> /// <param name="resourcePrefix"> /// Optional resource prfix that defaults to <paramref name="resourceHolder"/>.Namespace + ".Res.". /// When not null, this path prefix is combined withe the namespace of the resourceHolder. /// </param> /// <param name="resourceHolder"> /// Optional type used to locate resources. /// By default it is the actual type of this folder object: the defining assembly and namespace are used. /// </param> public PluginFolderBase(GitFolder f, NormalizedPath branchPath, NormalizedPath subFolderPath, NormalizedPath?resourcePrefix = null, Type resourceHolder = null) : base(f, branchPath) { FolderPath = branchPath.Combine(subFolderPath).ResolveDots(branchPath.Parts.Count); if (resourceHolder == null) { resourceHolder = GetType(); } _resourceAssembly = resourceHolder.Assembly; if (!resourcePrefix.HasValue) { _resourcePrefix = resourceHolder.Namespace + ".Res."; } else { NormalizedPath p = resourceHolder.Namespace.Replace('.', '/'); _resourcePrefix = p.Combine(resourcePrefix.Value).ResolveDots().Path.Replace('/', '.') + '.'; } _csResourcePrefix = _csProtocol + _resourcePrefix; _csResourcePrefixSlash = _csProtocolSlash + _resourcePrefix; }
private static void ApplyCommandSettings(Engine engine, IConfigurationSettings configurationSettings, EngineCommandSettings commandSettings) { // Set folders NormalizedPath currentDirectory = Environment.CurrentDirectory; engine.FileSystem.RootPath = string.IsNullOrEmpty(commandSettings.RootPath) ? currentDirectory : currentDirectory.Combine(commandSettings.RootPath); if (commandSettings.InputPaths?.Length > 0) { // Clear existing default paths if new ones are set // and reverse the inputs so the last one is first to match the semantics of multiple occurrence single options engine.FileSystem.InputPaths.Clear(); engine.FileSystem.InputPaths.AddRange(commandSettings.InputPaths.Select(x => new NormalizedPath(x)).Reverse()); } if (!string.IsNullOrEmpty(commandSettings.OutputPath)) { engine.FileSystem.OutputPath = commandSettings.OutputPath; } if (commandSettings.NoClean) { configurationSettings[Keys.CleanOutputPath] = false; } // Set no cache if requested if (commandSettings.NoCache) { configurationSettings[Keys.UseCache] = false; } // Set serial mode if (commandSettings.SerialExecution) { engine.SerialExecution = true; } }
protected override async Task <int> ExecuteEngineAsync( CommandContext commandContext, ServeCommandSettings commandSettings, IEngineManager engineManager) { ExitCode exitCode = ExitCode.Normal; ILogger logger = engineManager.Engine.Services.GetRequiredService <ILogger <Bootstrapper> >(); // Set folders IFileSystem fileSystem = engineManager.Engine.FileSystem; NormalizedPath currentDirectory = Environment.CurrentDirectory; IDirectory serveDirectory; if (string.IsNullOrEmpty(commandSettings.RootPath)) { fileSystem.RootPath = currentDirectory; serveDirectory = fileSystem.GetOutputDirectory(); } else { fileSystem.RootPath = currentDirectory.Combine(commandSettings.RootPath); serveDirectory = fileSystem.GetRootDirectory(); } Dictionary <string, string> contentTypes = commandSettings.ContentTypes?.Length > 0 ? PreviewCommand.GetContentTypes(commandSettings.ContentTypes) : new Dictionary <string, string>(); ILoggerProvider loggerProvider = engineManager.Engine.Services.GetRequiredService <ILoggerProvider>(); Server previewServer = null; FileSystemWatcher serveFolderWatcher = null; if (serveDirectory.Exists) { // Starts Preview server previewServer = await PreviewCommand.StartPreviewServerAsync( serveDirectory.Path, commandSettings.Port, commandSettings.ForceExt, commandSettings.VirtualDirectory, !commandSettings.NoReload, contentTypes, loggerProvider, logger); // Start the watchers if (!commandSettings.NoReload) { logger.LogInformation("Watching path {0}", serveDirectory.Path); serveFolderWatcher = new FileSystemWatcher(serveDirectory.Path.FullPath, "*.*") { IncludeSubdirectories = true, EnableRaisingEvents = true }; serveFolderWatcher.Changed += OnFileChanged; serveFolderWatcher.Created += OnFileChanged; } // Start the message pump CommandUtilities.WaitForControlC( () => { _exit.Set(); _messageEvent.Set(); }, logger); // Wait for activity while (true) { _messageEvent.WaitOne(); // Blocks the current thread until a signal if (_exit) { break; } // Execute if files have changed HashSet <string> changedFiles = new HashSet <string>(); while (_changedFiles.TryDequeue(out string changedFile)) { if (changedFiles.Add(changedFile)) { logger.LogDebug($"{changedFile} has changed"); } } if (changedFiles.Count > 0) { logger.LogInformation($"{changedFiles.Count} files have changed, re-loading"); await previewServer.TriggerReloadAsync(); } // Check one more time for exit if (_exit) { break; } logger.LogInformation("Hit Ctrl-C to exit"); _messageEvent.Reset(); } } else { logger.LogError($"Directory {serveDirectory.Path} does not exist."); } // Shutdown logger.LogInformation("Shutting down"); if (serveFolderWatcher != null) { serveFolderWatcher.EnableRaisingEvents = false; serveFolderWatcher.Changed -= OnFileChanged; serveFolderWatcher.Created -= OnFileChanged; serveFolderWatcher.Dispose(); } previewServer?.Dispose(); return((int)exitCode); }
//TODO: Introduce a "common" project for extension method duplicated across projects internal static NormalizedPath ToAbsolutePath(this NormalizedPath path, NormalizedPath absoluteTo) { return(path.IsAbsolute ? path : absoluteTo.Combine(path)); }
protected override async Task <IEnumerable <IDocument> > ExecuteInputAsync(IDocument input, IExecutionContext context) { context.LogDebug($"Processing Sass for {input.ToSafeDisplayString()}"); NormalizedPath inputPath = await _inputPath.GetValueAsync(input, context); if (inputPath.IsNull || inputPath.IsRelative) { inputPath = context.FileSystem.GetInputFile(new NormalizedPath(Path.GetRandomFileName())).Path; context.LogWarning($"No input path found for document {input.ToSafeDisplayString()}, using {inputPath.FileName.FullPath}"); } string content = await input.GetContentStringAsync(); // Sass conversion FileImporter importer = new FileImporter(context.FileSystem, _importPathFunc); ScssOptions options = new ScssOptions { OutputStyle = _outputStyle, GenerateSourceMap = _generateSourceMap, SourceComments = _includeSourceComments, InputFile = inputPath.FullPath, TryImport = importer.TryImport }; IEnumerable <string> includePaths = _includePaths .Where(x => !x.IsNull) .Select(x => { if (x.IsAbsolute) { return(x.FullPath); } NormalizedPath containingInputPath = context.FileSystem.GetContainingInputPath(x); return(containingInputPath.IsNull ? null : containingInputPath.Combine(x).FullPath); }) .Where(x => x != null); options.IncludePaths.AddRange(includePaths); ScssResult result = Scss.ConvertToCss(content, options); // Process the result NormalizedPath relativeDirectory = context.FileSystem.GetContainingInputPath(inputPath); NormalizedPath relativePath = relativeDirectory.IsNull ? NormalizedPath.Null : relativeDirectory.GetRelativePath(inputPath); if (relativePath.IsNull) { relativePath = inputPath.FileName; } NormalizedPath cssPath = relativePath.ChangeExtension("css"); IDocument cssDocument = input.Clone( cssPath, await context.GetContentProviderAsync(result.Css ?? string.Empty, MediaTypes.Css)); // Generate a source map if requested if (_generateSourceMap && result.SourceMap != null) { NormalizedPath sourceMapPath = relativePath.ChangeExtension("map"); IDocument sourceMapDocument = input.Clone( sourceMapPath, await context.GetContentProviderAsync(result.SourceMap)); return(new[] { cssDocument, sourceMapDocument }); } return(cssDocument.Yield()); }