Exemple #1
0
        public void Configure(ILifetimeScope lifetimeScope)
        {
            var app = lifetimeScope.Resolve <IApplicationBuilder>();

            var fileRepository = lifetimeScope.Resolve <IFileRepository>();

            //Set the static file options
            var staticFileOptions = new StaticFileOptions
            {
                OnPrepareResponse = ctx =>
                {
                    //Caching static files is required to reduce connections since the default behavior of checking if a static file has changed and returning a 304 still requires a connection.
                    if (_responseCachingOptions.StaticCacheSeconds > 0)
                    {
                        ctx.Context.SetResponseCache(_responseCachingOptions.StaticCacheSeconds);
                    }
                }
            };

            // Include un-bundled js + css folders to serve the source files in dev environment
            if (_sharedOptions.IsLocal())
            {
                var wwwroot = Path.Combine(Directory.GetParent(Environment.CurrentDirectory).FullName, this.GetType().Namespace, "wwwroot");
                staticFileOptions.FileProvider = new PhysicalFileProvider(wwwroot);
            }

            app.UseStaticFiles(staticFileOptions);

            //Ensure ShortCodes, SicCodes and SicSections exist on remote
            Task.WaitAll(
                fileRepository.PushRemoteFileAsync(Filenames.ShortCodes, _sharedOptions.DataPath),
                fileRepository.PushRemoteFileAsync(Filenames.SicCodes, _sharedOptions.DataPath),
                fileRepository.PushRemoteFileAsync(Filenames.SicSections, _sharedOptions.DataPath)
                );
        }
        private string GetStaticFile(string directory, string fileRegex)
        {
            if (_sharedOptions.IsLocal())
            {
                // When developing locally, skip the cache
                return(FindMatchingFile(directory, fileRegex));
            }

            // In all other environments (Dev, Test, Pre-Prod, Prod)
            // cache the filename so we don't need to search a directory for each request
            var cacheKey = directory + "/" + fileRegex;

            if (!cachedFilenames.ContainsKey(cacheKey))
            {
                cachedFilenames[cacheKey] = FindMatchingFile(directory, fileRegex);
            }

            return(cachedFilenames[cacheKey]);
        }
Exemple #3
0
        public void Register(IDependencyBuilder builder)
        {
            //Allow handler for caching of http responses
            builder.Services.AddResponseCaching();

            //Allow creation of a static http context anywhere
            builder.Services.AddHttpContextAccessor();

            var mvcBuilder = builder.Services.AddControllersWithViews(
                options =>
            {
                options.AddStringTrimmingProvider();                                         //Add modelstate binder to trim input
                options.ModelMetadataDetailsProviders.Add(
                    new TrimModelBinder());                                                  //Set DisplayMetadata to input empty strings as null
                options.ModelMetadataDetailsProviders.Add(
                    new DefaultResourceValidationMetadataProvider());                        // sets default resource type to use for display text and error messages
                _responseCachingOptions.CacheProfiles.ForEach(p =>
                                                              options.CacheProfiles.Add(p)); //Load the response cache profiles from options
                options.Filters.Add <ErrorHandlingFilter>();
            });

            mvcBuilder.AddRazorClassLibrary <WebUI.Account.DependencyModule>();
            mvcBuilder.AddRazorClassLibrary <WebUI.Admin.DependencyModule>();
            mvcBuilder.AddRazorClassLibrary <WebUI.Registration.DependencyModule>();
            mvcBuilder.AddRazorClassLibrary <WebUI.Submission.DependencyModule>();
            mvcBuilder.AddRazorClassLibrary <WebUI.Viewing.DependencyModule>();

            mvcBuilder.AddRazorClassLibrary <WebUI.Shared.DependencyModule>();
            mvcBuilder.AddRazorClassLibrary <WebUI.GDSDesignSystem.DependencyModule>();

            builder.RegisterModule <WebUI.StaticFiles.DependencyModule>();
            builder.RegisterModule <WebUI.Account.DependencyModule>();
            builder.RegisterModule <WebUI.Admin.DependencyModule>();
            builder.RegisterModule <WebUI.Registration.DependencyModule>();
            builder.RegisterModule <WebUI.Submission.DependencyModule>();
            builder.RegisterModule <WebUI.Viewing.DependencyModule>();

            // Add controllers, taghelpers, views as services so attribute dependencies can be resolved in their contructors
            mvcBuilder.AddControllersAsServices();
            mvcBuilder.AddTagHelpersAsServices();
            mvcBuilder.AddViewComponentsAsServices();

            // Set the default resolver to use Pascalcase instead of the default camelCase which may break Ajaz responses
            mvcBuilder.AddJsonOptions(options =>
            {
                options.JsonSerializerOptions.PropertyNameCaseInsensitive = true;
                options.JsonSerializerOptions.PropertyNamingPolicy        = null;
            });

            mvcBuilder.AddDataAnnotationsLocalization(
                options =>
            {
                options.DataAnnotationLocalizerProvider =
                    DataAnnotationLocalizerProvider.DefaultResourceHandler;
            });

            //Add antiforgery token by default to forms
            builder.Services.AddAntiforgery();

            builder.Services.AddRazorPages();

            // we need to explicitly set AllowRecompilingViewsOnFileChange because we use a custom environment "Local" for local dev
            // https://docs.microsoft.com/en-us/aspnet/core/mvc/views/view-compilation?view=aspnetcore-3.1#runtime-compilation
            // However this doesnt work on razor class/com,ponent libraries so we instead use a workaround
            //if (_sharedOptions.IsDevelopment() || _sharedOptions.IsLocal()) mvcBuilder.AddRazorRuntimeCompilation();

            //Add services needed for sessions
            builder.Services.AddSession(
                o =>
            {
                o.Cookie.IsEssential  = true;  //This is required otherwise session will not load
                o.Cookie.SecurePolicy =
                    CookieSecurePolicy.Always; //Equivalent to <httpCookies requireSSL="true" /> from Web.Config
                o.Cookie.HttpOnly = false;     //Always use https cookies
                o.Cookie.SameSite = SameSiteMode.Strict;
                o.Cookie.Domain   =
                    _sharedOptions.ExternalHost
                    .BeforeFirst(":");         //Domain cannot be an authority and contain a port number
                o.IdleTimeout =
                    TimeSpan.FromMinutes(_sharedOptions
                                         .SessionTimeOutMinutes); //Equivalent to <sessionState timeout="20"> from old Web.config
            });

            //Add the distributed cache and data protection
            builder.Services.AddDistributedCache(_distributedCacheOptions)
            .AddDataProtection(_dataProtectionOptions);

            //Add app insights tracking
            builder.Services.AddApplicationInsightsTelemetry(_sharedOptions.AppInsights_InstrumentationKey);

            //This may now be required
            builder.Services.AddHttpsRedirection(options => { options.HttpsPort = 443; });

            //Override any test services
            ConfigureTestServices?.Invoke(builder.Services);

            //Register the file storage dependencies
            builder.RegisterModule <FileStorageDependencyModule>();

            //Register the queue storage dependencies
            builder.RegisterModule <QueueStorageDependencyModule>();

            //Register the queue storage dependencies
            builder.Autofac.RegisterType <DnBOrgsRepository>().As <IDnBOrgsRepository>().WithParameter("dataPath", _sharedOptions.DataPath).WithAttributeFiltering();

            //Register the log storage dependencies
            builder.RegisterModule <Infrastructure.Logging.DependencyModule>();

            //Register the search dependencies
            builder.RegisterModule <Infrastructure.Search.DependencyModule>();

            builder.Autofac.RegisterType <GovNotifyAPI>().As <IGovNotifyAPI>().SingleInstance();

            //Register the user audit log repository
            builder.Autofac.RegisterType <UserRepository>().As <IUserRepository>().InstancePerLifetimeScope();

            // Register Action helpers
            builder.Autofac.RegisterType <ActionContextAccessor>().As <IActionContextAccessor>()
            .SingleInstance();

            #region Configure authentication client
            //Configure the services required for authentication by IdentityServer
            builder.Services.AddIdentityServerClient(
                _sharedOptions.IdentityIssuer,
                _sharedOptions.SiteAuthority,
                "ModernSlaveryServiceWebsite",
                _sharedOptions.AuthSecret,
                BackChannelHandler);
            #endregion

            builder.Autofac.Register(
                x =>
            {
                var actionContext = x.Resolve <IActionContextAccessor>().ActionContext;
                var factory       = x.Resolve <IUrlHelperFactory>();
                return(factory.GetUrlHelper(actionContext));
            });

            //Register google analytics tracker
            builder.RegisterModule <GoogleAnalyticsDependencyModule>();

            //Register the AutoMapper configurations in all domain assemblies
            builder.Services.AddAutoMapper(_sharedOptions.IsLocal() || _sharedOptions.IsDevelopment());

            //Override any test services
            ConfigureTestContainer?.Invoke(builder.Autofac);
        }
        public void Register(IDependencyBuilder builder)
        {
            #region Configure authentication server

            builder.Services.AddSingleton <IEventSink, AuditEventSink>();

            var clients   = new Clients(_sharedOptions);
            var resources = new Resources(_sharedOptions);

            var identityServer = builder.Services.AddIdentityServer(
                options =>
            {
                options.Events.RaiseSuccessEvents = true;
                options.Events.RaiseFailureEvents = true;
                options.Events.RaiseErrorEvents   = true;
                options.UserInteraction.LoginUrl  = "/sign-in";
                options.UserInteraction.LogoutUrl = "/sign-out";
                options.UserInteraction.ErrorUrl  = "/error";
            })
                                 .AddInMemoryClients(clients.Get())
                                 .AddInMemoryIdentityResources(resources.GetIdentityResources())
                                 //.AddInMemoryApiResources(Resources.GetApiResources())
                                 .AddCustomUserStore();

            if (Debugger.IsAttached || _sharedOptions.IsDevelopment() || _sharedOptions.IsLocal())
            {
                identityServer.AddDeveloperSigningCredential();
            }
            else
            {
                identityServer.AddSigningCredential(LoadCertificate(_sharedOptions));
            }

            #endregion

            //Allow caching of http responses
            builder.Services.AddResponseCaching();

            //This is to allow access to the current http context anywhere
            builder.Services.AddHttpContextAccessor();

            var mvcBuilder = builder.Services.AddControllersWithViews();

            mvcBuilder.AddRazorClassLibrary <DependencyModule>();
            mvcBuilder.AddRazorClassLibrary <WebUI.Shared.DependencyModule>();
            mvcBuilder.AddRazorClassLibrary <WebUI.GDSDesignSystem.DependencyModule>();

            builder.RegisterModule <WebUI.StaticFiles.DependencyModule>();
            builder.RegisterModule <ModernSlavery.BusinessDomain.Account.DependencyModule>();
            //builder.RegisterModule<ModernSlavery.Infrastructure.CompaniesHouse.DependencyModule>();

            // Add controllers, taghelpers, views as services so attribute dependencies can be resolved in their contructors
            mvcBuilder.AddControllersAsServices();
            mvcBuilder.AddTagHelpersAsServices();
            mvcBuilder.AddViewComponentsAsServices();

            builder.Services.AddRazorPages();

            // we need to explicitly set AllowRecompilingViewsOnFileChange because we use a custom environment "Local" for local dev
            // https://docs.microsoft.com/en-us/aspnet/core/mvc/views/view-compilation?view=aspnetcore-3.1#runtime-compilation
            // However this doesnt work on razor class/com,ponent libraries so we instead use a workaround
            //if (_sharedOptions.IsDevelopment() || _sharedOptions.IsLocal()) mvcBuilder.AddRazorRuntimeCompilation();

            //Add services needed for sessions
            builder.Services.AddSession(
                o =>
            {
                o.Cookie.IsEssential  = true;  //This is required otherwise session will not load
                o.Cookie.SecurePolicy =
                    CookieSecurePolicy.Always; //Equivalent to <httpCookies requireSSL="true" /> from Web.Config
                o.Cookie.HttpOnly = false;     //Always use https cookies
                o.Cookie.SameSite = SameSiteMode.Strict;
                o.Cookie.Domain   =
                    _sharedOptions.ExternalHost
                    .BeforeFirst(":");         //Domain cannot be an authority and contain a port number
                o.IdleTimeout =
                    TimeSpan.FromMinutes(_sharedOptions
                                         .SessionTimeOutMinutes); //Equivalent to <sessionState timeout="20"> from old Web.config
            });

            //Add the distributed cache and data protection
            builder.Services.AddDistributedCache(_distributedCacheOptions)
            .AddDataProtection(_dataProtectionOptions);

            //Add app insights tracking
            builder.Services.AddApplicationInsightsTelemetry(_sharedOptions.AppInsights_InstrumentationKey);

            //This may now be required
            builder.Services.AddHttpsRedirection(options => { options.HttpsPort = 443; });

            //Override any test services
            ConfigureTestServices?.Invoke(builder.Services);

            //Register the file storage dependencies
            builder.RegisterModule <FileStorageDependencyModule>();

            // Register queues (without key filtering)
            builder.Autofac
            .Register(c => new LogEventQueue(_storageOptions.AzureConnectionString, c.Resolve <IFileRepository>()))
            .SingleInstance();
            builder.Autofac
            .Register(c => new LogRecordQueue(_storageOptions.AzureConnectionString, c.Resolve <IFileRepository>()))
            .SingleInstance();

            // Register log records (without key filtering)
            builder.Autofac.RegisterType <UserAuditLogger>().As <IUserLogger>().SingleInstance();

            // Register Action helpers
            builder.Autofac.RegisterType <ActionContextAccessor>().As <IActionContextAccessor>()
            .SingleInstance();

            //Register google analytics tracker
            builder.RegisterModule <GoogleAnalyticsDependencyModule>();

            //Register the AutoMapper configurations in all domain assemblies
            builder.Services.AddAutoMapper(_sharedOptions.IsLocal() || _sharedOptions.IsDevelopment());

            //Override any test services
            ConfigureTestContainer?.Invoke(builder.Autofac);
        }