· 7 years ago · Nov 18, 2018, 01:22 PM
1using FitnessApp.Auth;
2using FitnessApp.Data;
3using FitnessApp.Helpers;
4using FitnessApp.Models;
5using FitnessApp.Models.Entities;
6using Microsoft.AspNetCore.Authentication.JwtBearer;
7using Microsoft.AspNetCore.Builder;
8using Microsoft.AspNetCore.Hosting;
9using Microsoft.AspNetCore.HttpsPolicy;
10using Microsoft.AspNetCore.Identity;
11using Microsoft.AspNetCore.Mvc;
12using Microsoft.AspNetCore.SpaServices.AngularCli;
13using Microsoft.EntityFrameworkCore;
14using Microsoft.Extensions.Configuration;
15using Microsoft.Extensions.DependencyInjection;
16using Microsoft.IdentityModel.Tokens;
17using System;
18using System.Text;
19
20namespace FitnessApp
21{
22 public class Startup
23 {
24 private const string SecretKey = "iNivDmHLpUA783sqs12qGoMRdRj1PVkH"; // todo: get this from somewhere secure
25 private readonly SymmetricSecurityKey _signingKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(SecretKey));
26
27 public Startup(IConfiguration configuration)
28 {
29 Configuration = configuration;
30 }
31
32 public IConfiguration Configuration { get; }
33
34 // This method gets called by the runtime. Use this method to add services to the container.
35 public void ConfigureServices(IServiceCollection services)
36 {
37 // Add framework services.
38 var connection = @"Server=(localdb)\mssqllocaldb;Database=FitnessApp;Trusted_Connection=True;ConnectRetryCount=0";
39 services.AddDbContext<ApplicationDbContext>(options =>
40 options.UseSqlServer(connection, b => b.MigrationsAssembly("FitnessApp")));
41
42 services.AddIdentity<AppUser, IdentityRole>()
43 .AddEntityFrameworkStores<ApplicationDbContext>()
44 .AddDefaultTokenProviders();
45
46 services.AddSingleton<IJwtFactory, JwtFactory>();
47
48 services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
49
50 // In production, the Angular files will be served from this directory
51 services.AddSpaStaticFiles(configuration =>
52 {
53 configuration.RootPath = "ClientApp/dist";
54 });
55
56
57
58 // Get options from app settings
59 var jwtAppSettingOptions = Configuration.GetSection(nameof(JwtIssuerOptions));
60
61 // Configure JwtIssuerOptions
62 services.Configure<JwtIssuerOptions>(options =>
63 {
64 options.Issuer = jwtAppSettingOptions[nameof(JwtIssuerOptions.Issuer)];
65 options.Audience = jwtAppSettingOptions[nameof(JwtIssuerOptions.Audience)];
66 options.SigningCredentials = new SigningCredentials(_signingKey, SecurityAlgorithms.HmacSha256);
67 });
68
69 var tokenValidationParameters = new TokenValidationParameters
70 {
71 ValidateIssuer = true,
72 ValidIssuer = jwtAppSettingOptions[nameof(JwtIssuerOptions.Issuer)],
73
74 ValidateAudience = true,
75 ValidAudience = jwtAppSettingOptions[nameof(JwtIssuerOptions.Audience)],
76
77 ValidateIssuerSigningKey = true,
78 IssuerSigningKey = _signingKey,
79
80 RequireExpirationTime = false,
81 ValidateLifetime = true,
82 ClockSkew = TimeSpan.Zero
83 };
84
85 services.AddAuthentication(options =>
86 {
87 options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
88 options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
89
90 }).AddJwtBearer(configureOptions =>
91 {
92 configureOptions.ClaimsIssuer = jwtAppSettingOptions[nameof(JwtIssuerOptions.Issuer)];
93 configureOptions.TokenValidationParameters = tokenValidationParameters;
94 configureOptions.SaveToken = true;
95 });
96
97 // api user claim policy
98 services.AddAuthorization(options =>
99 {
100 options.AddPolicy("ApiUser", policy => policy.RequireClaim(Constants.Strings.JwtClaimIdentifiers.Rol, Constants.Strings.JwtClaims.ApiAccess));
101 });
102 }
103
104 // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
105 public void Configure(IApplicationBuilder app, IHostingEnvironment env)
106 {
107 if (env.IsDevelopment())
108 {
109 app.UseDeveloperExceptionPage();
110 }
111 else
112 {
113 app.UseExceptionHandler("/Error");
114 app.UseHsts();
115 }
116
117 app.UseAuthentication();
118 app.UseHttpsRedirection();
119
120
121 app.UseStaticFiles();
122 app.UseSpaStaticFiles();
123
124 app.UseMvc(routes =>
125 {
126 routes.MapRoute(
127 name: "default",
128 template: "{controller}/{action=Index}/{id?}");
129 });
130
131 app.UseSpa(spa =>
132 {
133 // To learn more about options for serving an Angular SPA from ASP.NET Core,
134 // see https://go.microsoft.com/fwlink/?linkid=864501
135
136 spa.Options.SourcePath = "ClientApp";
137
138 if (env.IsDevelopment())
139 {
140 spa.UseAngularCliServer(npmScript: "start");
141 }
142 });
143 }
144 }
145}