diff --git a/samples/AspNetFeatureFolders/Areas/Products/Search/Index.cshtml b/samples/AspNetFeatureFolders/Areas/Products/Search/Index.cshtml index ed01b1d..387ac17 100644 --- a/samples/AspNetFeatureFolders/Areas/Products/Search/Index.cshtml +++ b/samples/AspNetFeatureFolders/Areas/Products/Search/Index.cshtml @@ -1,2 +1,4 @@ @model AspNetFeatureFolders.Areas.Products.Search.IndexViewModel

Index

+ + \ No newline at end of file diff --git a/samples/AspNetFeatureFolders/Areas/Products/Search/Index.js b/samples/AspNetFeatureFolders/Areas/Products/Search/Index.js new file mode 100644 index 0000000..5f28270 --- /dev/null +++ b/samples/AspNetFeatureFolders/Areas/Products/Search/Index.js @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/samples/AspNetFeatureFolders/R4Mvc.generated.cs b/samples/AspNetFeatureFolders/R4Mvc.generated.cs index 45ce508..e429961 100644 --- a/samples/AspNetFeatureFolders/R4Mvc.generated.cs +++ b/samples/AspNetFeatureFolders/R4Mvc.generated.cs @@ -85,6 +85,26 @@ public static partial class Links public const string UrlPath = "~"; public static string Url() => R4MvcHelpers.ProcessVirtualPath(UrlPath); public static string Url(string fileName) => R4MvcHelpers.ProcessVirtualPath(UrlPath + "/" + fileName); + public static partial class Areas + { + public const string UrlPath = "~/Areas"; + public static string Url() => R4MvcHelpers.ProcessVirtualPath(UrlPath); + public static string Url(string fileName) => R4MvcHelpers.ProcessVirtualPath(UrlPath + "/" + fileName); + public static partial class Products + { + public const string UrlPath = "~/Areas/Products"; + public static string Url() => R4MvcHelpers.ProcessVirtualPath(UrlPath); + public static string Url(string fileName) => R4MvcHelpers.ProcessVirtualPath(UrlPath + "/" + fileName); + public static partial class Search + { + public const string UrlPath = "~/Areas/Products/Search"; + public static string Url() => R4MvcHelpers.ProcessVirtualPath(UrlPath); + public static string Url(string fileName) => R4MvcHelpers.ProcessVirtualPath(UrlPath + "/" + fileName); + public static readonly string Index_js = Url("Index.js"); + } + } + } + public static partial class css { public const string UrlPath = "~/css"; diff --git a/samples/AspNetFeatureFolders/r4mvc.json b/samples/AspNetFeatureFolders/r4mvc.json index 8345a4d..3369d0b 100644 --- a/samples/AspNetFeatureFolders/r4mvc.json +++ b/samples/AspNetFeatureFolders/r4mvc.json @@ -14,7 +14,10 @@ "FeatureFolders": { "Enabled": true, "FeaturesPath": "Features", - "StaticFileAccess": false, + "StaticFileAccess": true, + "IncludedStaticFileExtensions": [ + ".js" + ], "FeatureOnlyAreas": [ "Products" ] diff --git a/src/R4Mvc.Tools/Locators/DefaultStaticFileLocator.cs b/src/R4Mvc.Tools/Locators/DefaultStaticFileLocator.cs index 949e9a3..f2e270a 100644 --- a/src/R4Mvc.Tools/Locators/DefaultStaticFileLocator.cs +++ b/src/R4Mvc.Tools/Locators/DefaultStaticFileLocator.cs @@ -14,7 +14,7 @@ public DefaultStaticFileLocator(IFileLocator fileLocator, Settings settings) _settings = settings; } - public IEnumerable Find(string staticPathRoot) + public IEnumerable Find(string projectRoot, string staticPathRoot) { var files = _fileLocator.GetFiles(staticPathRoot, "*", recurse: true).AsEnumerable(); if (_settings.ExcludedStaticFileExtensions?.Length > 0) diff --git a/src/R4Mvc.Tools/Locators/FeatureFolderStaticFileLocator.cs b/src/R4Mvc.Tools/Locators/FeatureFolderStaticFileLocator.cs new file mode 100644 index 0000000..bc3e031 --- /dev/null +++ b/src/R4Mvc.Tools/Locators/FeatureFolderStaticFileLocator.cs @@ -0,0 +1,39 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; + +namespace R4Mvc.Tools.Locators +{ + public class FeatureFolderStaticFileLocator : IStaticFileLocator + { + private readonly IFileLocator _fileLocator; + private readonly Settings _settings; + + public FeatureFolderStaticFileLocator(IFileLocator fileLocator, Settings settings) + { + _fileLocator = fileLocator; + _settings = settings; + } + + public IEnumerable Find(string projectRoot, string staticPathRoot) + { + if (_settings.FeatureFolders.StaticFileAccess == false) + return Array.Empty(); + + var files = _fileLocator.GetFiles(projectRoot, "*", recurse: true).AsEnumerable(); + files = files.Where(r => r.StartsWith(staticPathRoot, StringComparison.InvariantCultureIgnoreCase) == false); + + if (_settings.ExcludedStaticFileExtensions?.Length > 0) + files = files.Where(f => !_settings.ExcludedStaticFileExtensions.Any(e => f.EndsWith(e))); + if (!projectRoot.EndsWith("/")) + projectRoot += "/"; + var rootUri = new Uri(projectRoot); + if(_settings.FeatureFolders.IncludedStaticFileExtensions?.Length >0) + files = files.Where(r => _settings.FeatureFolders.IncludedStaticFileExtensions.Contains(Path.GetExtension(r))); + return files.Select(f => new StaticFile(rootUri.MakeRelativeUri(new Uri(f)))); + + } + + } +} diff --git a/src/R4Mvc.Tools/Locators/IStaticFileLocator.cs b/src/R4Mvc.Tools/Locators/IStaticFileLocator.cs index d8c8486..edaa638 100644 --- a/src/R4Mvc.Tools/Locators/IStaticFileLocator.cs +++ b/src/R4Mvc.Tools/Locators/IStaticFileLocator.cs @@ -4,6 +4,6 @@ namespace R4Mvc.Tools.Locators { public interface IStaticFileLocator { - IEnumerable Find(string staticPathRoot); + IEnumerable Find(string projectRoot, string staticPathRoot); } } diff --git a/src/R4Mvc.Tools/Program.cs b/src/R4Mvc.Tools/Program.cs index d51c40f..ad38176 100644 --- a/src/R4Mvc.Tools/Program.cs +++ b/src/R4Mvc.Tools/Program.cs @@ -164,6 +164,7 @@ static void ConfigureServices(IServiceCollection services, IConfigurationRoot co services.AddTransient(); services.AddTransient(); services.AddTransient(); + services.AddTransient(); services.AddTransient(); services.AddTransient(); services.AddTransient(); diff --git a/src/R4Mvc.Tools/Properties/launchSettings.json b/src/R4Mvc.Tools/Properties/launchSettings.json index a131804..a26cd64 100644 --- a/src/R4Mvc.Tools/Properties/launchSettings.json +++ b/src/R4Mvc.Tools/Properties/launchSettings.json @@ -2,8 +2,8 @@ "profiles": { "R4Mvc.Tools": { "commandName": "Project", + "commandLineArgs": "generate -p \"..\\..\\..\\..\\..\\samples\\AspNetFeatureFolders\\AspNetFeatureFolders.csproj\"", "commandLineArgs_blank": "", - "commandLineArgs": "generate -p \"..\\..\\..\\..\\..\\samples\\AspNetSimple.NetCore3\\AspNetSimple.NetCore3.csproj\"", "commandLineArgs2": "generate -p \"..\\..\\..\\..\\..\\samples\\AspNetSimple\\AspNetSimple.csproj\"", "commandLineArgs_aspNetFeatureFolders": "generate -p \"..\\..\\..\\..\\..\\samples\\AspNetFeatureFolders\\AspNetFeatureFolders.csproj\"" } diff --git a/src/R4Mvc.Tools/Services/StaticFileGeneratorService.cs b/src/R4Mvc.Tools/Services/StaticFileGeneratorService.cs index 36f38fe..f8a3c52 100644 --- a/src/R4Mvc.Tools/Services/StaticFileGeneratorService.cs +++ b/src/R4Mvc.Tools/Services/StaticFileGeneratorService.cs @@ -23,7 +23,7 @@ public StaticFileGeneratorService(IEnumerable staticFileLoca public MemberDeclarationSyntax GenerateStaticFiles(string projectRoot) { var staticFilesRoot = GetStaticFilesPath(projectRoot); - var staticfiles = _staticFileLocators.SelectMany(x => x.Find(staticFilesRoot)); + var staticfiles = _staticFileLocators.SelectMany(x => x.Find(projectRoot, staticFilesRoot)); var linksClass = new ClassBuilder(_settings.LinksNamespace) .WithModifiers(SyntaxKind.PublicKeyword, SyntaxKind.StaticKeyword, SyntaxKind.PartialKeyword) diff --git a/src/R4Mvc.Tools/Settings.cs b/src/R4Mvc.Tools/Settings.cs index 27b1f48..985ba3a 100644 --- a/src/R4Mvc.Tools/Settings.cs +++ b/src/R4Mvc.Tools/Settings.cs @@ -27,6 +27,7 @@ public class FeatureFoldersClass public bool Enabled { get; set; } public string FeaturesPath { get; set; } = "Features"; public bool StaticFileAccess { get; set; } + public string[] IncludedStaticFileExtensions { get; set; } public string[] FeatureOnlyAreas { get; set; } } } diff --git a/test/R4Mvc.Test/Locators/DefaultStaticFileLocatorTests.cs b/test/R4Mvc.Test/Locators/DefaultStaticFileLocatorTests.cs index a19167b..242bc5f 100644 --- a/test/R4Mvc.Test/Locators/DefaultStaticFileLocatorTests.cs +++ b/test/R4Mvc.Test/Locators/DefaultStaticFileLocatorTests.cs @@ -11,7 +11,7 @@ public void StaticFileLocator() { var settings = new Settings(); var locator = new DefaultStaticFileLocator(VirtualFileLocator.Default, settings); - Assert.Collection(locator.Find(@"D:\Project\wwwroot"), + Assert.Collection(locator.Find(@"D:\Project", @"D:\Project\wwwroot"), f => { Assert.Equal("core.js", f.FileName); @@ -44,7 +44,7 @@ public void StaticFileLocator_Exclusions() { var settings = new Settings { ExcludedStaticFileExtensions = new[] { ".ico", ".css" } }; var locator = new DefaultStaticFileLocator(VirtualFileLocator.Default, settings); - Assert.Collection(locator.Find(@"D:\Project\wwwroot"), + Assert.Collection(locator.Find(@"D:\Project", @"D:\Project\wwwroot"), f => Assert.Equal("lib/jslib/core.js", f.RelativePath.ToString()), f => Assert.Equal("js/site.js", f.RelativePath.ToString()) ); diff --git a/test/R4Mvc.Test/Locators/FeatureFolderStaticFileLocatorTests.cs b/test/R4Mvc.Test/Locators/FeatureFolderStaticFileLocatorTests.cs new file mode 100644 index 0000000..5d3bbd1 --- /dev/null +++ b/test/R4Mvc.Test/Locators/FeatureFolderStaticFileLocatorTests.cs @@ -0,0 +1,51 @@ +using R4Mvc.Tools; +using R4Mvc.Tools.Locators; +using Xunit; + +namespace R4Mvc.Test.Locators +{ + public class FeatureFolderStaticFileLocatorTests + { + Settings _settings; + public FeatureFolderStaticFileLocatorTests() + { + _settings = new Settings(); + _settings.FeatureFolders = new Settings.FeatureFoldersClass + { + Enabled = true, + FeatureOnlyAreas = new[] { "Admin" }, + IncludedStaticFileExtensions = new[] { ".js", ".css" }, + StaticFileAccess = true, + }; + } + [Fact] + public void StaticFileLocator() + { + var locator = new FeatureFolderStaticFileLocator(VirtualFileLocator.Default, _settings); + Assert.Collection(locator.Find(@"D:\Project", @"D:\Project\wwwroot"), + f => + { + Assert.Equal("Index.js", f.FileName); + Assert.Equal("Areas/Admin/Features/Home/Index.js", f.RelativePath.ToString()); + Assert.Equal("Areas/Admin/Features/Home", f.Container); + }, + f => + { + Assert.Equal("Index.css", f.FileName); + Assert.Equal("Areas/Admin/Features/Home/Index.css", f.RelativePath.ToString()); + Assert.Equal("Areas/Admin/Features/Home", f.Container); + } + ); + } + + [Fact] + public void StaticFileLocator_Exclusions() + { + _settings.ExcludedStaticFileExtensions = new[] {".css" }; + var locator = new FeatureFolderStaticFileLocator(VirtualFileLocator.Default, _settings); + Assert.Collection(locator.Find(@"D:\Project", @"D:\Project\wwwroot"), + f => Assert.Equal("Areas/Admin/Features/Home/Index.js", f.RelativePath.ToString()) + ); + } + } +} diff --git a/test/R4Mvc.Test/Locators/VirtualFileLocator.cs b/test/R4Mvc.Test/Locators/VirtualFileLocator.cs index ecd76da..bfba2bf 100644 --- a/test/R4Mvc.Test/Locators/VirtualFileLocator.cs +++ b/test/R4Mvc.Test/Locators/VirtualFileLocator.cs @@ -23,6 +23,8 @@ public static VirtualFileLocator Default @"D:\Project\Areas\Admin\Controllers\HomeController.cs", @"D:\Project\Areas\Admin\Features\Home\HomeController.cs", @"D:\Project\Areas\Admin\Features\Home\Index.cshtml", + @"D:\Project\Areas\Admin\Features\Home\Index.js", + @"D:\Project\Areas\Admin\Features\Home\Index.css", @"D:\Project\Areas\Admin\Views\Home\Index.cshtml", @"D:\Project\Areas\Admin\Views\Shared\EditorTemplates\User.cshtml", @"D:\Project\Areas\Admin\Views\Shared\_Layout.cshtml", diff --git a/test/R4Mvc.Test/Services/StaticFileGeneratorServiceTests.cs b/test/R4Mvc.Test/Services/StaticFileGeneratorServiceTests.cs index 523ea06..8ff677c 100644 --- a/test/R4Mvc.Test/Services/StaticFileGeneratorServiceTests.cs +++ b/test/R4Mvc.Test/Services/StaticFileGeneratorServiceTests.cs @@ -24,7 +24,7 @@ public void AddStaticFiles() { var settings = new Tools.Settings(); var staticFileLocator = new DefaultStaticFileLocator(VirtualFileLocator.Default, settings); - var staticFiles = staticFileLocator.Find(VirtualFileLocator.ProjectRoot_wwwroot); + var staticFiles = staticFileLocator.Find(VirtualFileLocator.ProjectRoot, VirtualFileLocator.ProjectRoot_wwwroot); var staticFileGeneratorService = new StaticFileGeneratorService(new[] { staticFileLocator }, new Tools.Settings()); var c = new ClassBuilder("Test")