diff --git a/.dockerignore b/.dockerignore new file mode 100644 index 0000000..af50df1 --- /dev/null +++ b/.dockerignore @@ -0,0 +1,25 @@ +**/.dockerignore +**/.env +**/.git +**/.gitignore +**/.project +**/.settings +**/.toolstarget +**/.vs +**/.vscode +**/.idea +**/*.*proj.user +**/*.dbmdl +**/*.jfm +**/azds.yaml +**/bin +**/charts +**/docker-compose* +**/Dockerfile* +**/node_modules +**/npm-debug.log +**/obj +**/secrets.dev.yaml +**/values.dev.yaml +LICENSE +README.md \ No newline at end of file diff --git a/ImageBoardServerApp/App.razor b/ImageBoardServerApp/App.razor index a72e02f..f3b63cd 100644 --- a/ImageBoardServerApp/App.razor +++ b/ImageBoardServerApp/App.razor @@ -1,16 +1,18 @@ - - - - - - - Not found - -

404

-
- noimageFound -

Sorry, nothing found. Please go back to the main page. Or watch the tree and find the hidden Cat..

-
-
-
-
\ No newline at end of file + + + + + + + + Not found + +

404

+
+ noimageFound +

Sorry, nothing found. Please go back to the main page. Or watch the tree and find the hidden Cat..

+
+
+
+
+
\ No newline at end of file diff --git a/ImageBoardServerApp/Auth/CustomAuthenticationStateProvider.cs b/ImageBoardServerApp/Auth/CustomAuthenticationStateProvider.cs new file mode 100644 index 0000000..d1bb214 --- /dev/null +++ b/ImageBoardServerApp/Auth/CustomAuthenticationStateProvider.cs @@ -0,0 +1,60 @@ +using System.Security.Claims; +using ImageBoardServerApp.Data; +using Microsoft.AspNetCore.Components.Authorization; +using Microsoft.AspNetCore.Components.Server.ProtectedBrowserStorage; + +namespace ImageBoardServerApp.Auth; + +public class CustomAuthenticationStateProvider : AuthenticationStateProvider +{ + private readonly ProtectedSessionStorage _sessionStorage; + private ClaimsPrincipal _anonymous = new ClaimsPrincipal(new ClaimsIdentity()); + + public CustomAuthenticationStateProvider(ProtectedSessionStorage sessionStorage) + { + _sessionStorage = sessionStorage; + } + + public override async Task GetAuthenticationStateAsync() + { + try + { + var userSessionStorageResult = await _sessionStorage.GetAsync("UserSession"); + var userSession = userSessionStorageResult.Success ? userSessionStorageResult.Value : null; + if (userSession == null) + return await Task.FromResult(new AuthenticationState(_anonymous)); + var claimsPrincipal = new ClaimsPrincipal(new ClaimsIdentity(new List + { + new Claim(ClaimTypes.Email, userSession.Email), + new Claim(ClaimTypes.Role, userSession.Role) + }, "CustomAuth")); + return await Task.FromResult(new AuthenticationState(claimsPrincipal)); + } + catch + { + return await Task.FromResult(new AuthenticationState(_anonymous)); + } + } + + public async Task UpdateAuthenticationStateAsync(UserData session) + { + ClaimsPrincipal claimsPrincipal; + + if (session != null) + { + await _sessionStorage.SetAsync("UserSession", session); + claimsPrincipal = new ClaimsPrincipal(new ClaimsIdentity(new List + { + new Claim(ClaimTypes.Email, session.Email), + new Claim(ClaimTypes.Email, session.Role) + })); + } + else + { + await _sessionStorage.DeleteAsync("UserSession"); + claimsPrincipal = _anonymous; + } + + NotifyAuthenticationStateChanged(Task.FromResult(new AuthenticationState(claimsPrincipal))); + } +} \ No newline at end of file diff --git a/ImageBoardServerApp/Auth/UserSession.cs b/ImageBoardServerApp/Auth/UserSession.cs new file mode 100644 index 0000000..1bfa832 --- /dev/null +++ b/ImageBoardServerApp/Auth/UserSession.cs @@ -0,0 +1,7 @@ +namespace ImageBoardServerApp.Auth; + +public class UserSession +{ + public string Email { get; set; } + public string Role { get; set; } +} \ No newline at end of file diff --git a/ImageBoardServerApp/Data/AccountData.cs b/ImageBoardServerApp/Data/AccountData.cs deleted file mode 100644 index c12ce39..0000000 --- a/ImageBoardServerApp/Data/AccountData.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System.ComponentModel.DataAnnotations; -using System.ComponentModel.DataAnnotations.Schema; - -namespace ImageBoardServerApp.Data; - -public class AccountData -{ - [Required] - [DatabaseGenerated((DatabaseGeneratedOption.Identity))] - [Key] - public int AccountID { get; set; } - - [Required] - public string Email { get; set; } - - [Required] - public string Password { get; set; } - - [Required] - public int PermissionInteger { get; set; } -} \ No newline at end of file diff --git a/ImageBoardServerApp/Data/AppDBContext.cs b/ImageBoardServerApp/Data/AppDBContext.cs index 7d08c13..3841952 100644 --- a/ImageBoardServerApp/Data/AppDBContext.cs +++ b/ImageBoardServerApp/Data/AppDBContext.cs @@ -8,7 +8,6 @@ internal sealed class AppDBContext : DbContext public DbSet Posts { get; set; } public DbSet Images { get; set; } public DbSet Comments { get; set; } - public DbSet Accounts { get; set; } protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) => optionsBuilder.UseSqlite("Data Source=./Data/Nils.db"); diff --git a/ImageBoardServerApp/Data/Repository/AccountsRepository.cs b/ImageBoardServerApp/Data/Repository/AccountsRepository.cs deleted file mode 100644 index a198f26..0000000 --- a/ImageBoardServerApp/Data/Repository/AccountsRepository.cs +++ /dev/null @@ -1,53 +0,0 @@ -using Microsoft.EntityFrameworkCore; - -namespace ImageBoardServerApp.Data.Repository; - -public static class AccountsRepository -{ - public static async Task> getAccountsAsync() - { - await using var db = new AppDBContext(); - return await db.Accounts.ToListAsync(); - } - - public static async Task> getAccountsByMailAsync(string email) - { - await using var db = new AppDBContext(); - return await db.Accounts - .Where(acc => acc.Email.Equals(email)) - .ToListAsync(); - } - - public static async Task getAccountByIdAsync(int accountId) - { - await using var db = new AppDBContext(); - return await db.Accounts.FirstOrDefaultAsync(post => post.AccountID == accountId); - } - - public static async Task createAccountAsync(AccountData accountToCreate) - { - await using var db = new AppDBContext(); - await db.Accounts.AddAsync(accountToCreate); - if (await db.SaveChangesAsync() >= 1) - { - Console.WriteLine($"Created post with ID: {accountToCreate.AccountID}"); - return accountToCreate.AccountID; - } - return -1; - } - - public static async Task updateAccountAsync(AccountData accountToUpdate) - { - await using var db = new AppDBContext(); - db.Accounts.Update(accountToUpdate); - return await db.SaveChangesAsync() >= 1; - } - - public static async Task deleteAccountAsync(int postId) - { - await using var db = new AppDBContext(); - AccountData accountToDelete = await getAccountByIdAsync(postId); - db.Remove(accountToDelete); - return await db.SaveChangesAsync() >= 1; - } -} \ No newline at end of file diff --git a/ImageBoardServerApp/Data/Repository/UsersRepository.cs b/ImageBoardServerApp/Data/Repository/UsersRepository.cs index bcd695d..4f4b53b 100644 --- a/ImageBoardServerApp/Data/Repository/UsersRepository.cs +++ b/ImageBoardServerApp/Data/Repository/UsersRepository.cs @@ -16,10 +16,10 @@ public static class UsersRepository return await db.Users.FirstOrDefaultAsync(user => user.UserID == userId); } - public static async Task getUserByIPAsync(string userIp) + public static async Task getUserByEmailAsync(string email) { await using var db = new AppDBContext(); - return await db.Users.FirstOrDefaultAsync(user => user.Ipv4Address == userIp); + return await db.Users.FirstOrDefaultAsync(user => user.Email == email); } public static async Task createUserAsync(UserData userToCreate) diff --git a/ImageBoardServerApp/Data/UserData.cs b/ImageBoardServerApp/Data/UserData.cs index 57c97c3..7ed22df 100644 --- a/ImageBoardServerApp/Data/UserData.cs +++ b/ImageBoardServerApp/Data/UserData.cs @@ -11,12 +11,9 @@ public class UserData [DatabaseGenerated((DatabaseGeneratedOption.Identity))] [Key] public int UserID { get; set; } - + [Required] - public string Ipv4Address { get; set; } - - [Required] - public bool Banned { get; set; } + public long TimeBanned { get; set; } [Required] public long lastActionTimeStamp { get; set; } @@ -24,4 +21,16 @@ public class UserData public List Posts { get; set; } public List Comments { get; set; } + + [Required] + public string Email { get; set; } + + [Required] + public string Password { get; set; } + + [Required] + public int PermissionInteger { get; set; } + + [Required] + public string Role { get; set; } } \ No newline at end of file diff --git a/ImageBoardServerApp/Dockerfile b/ImageBoardServerApp/Dockerfile new file mode 100644 index 0000000..5b127e8 --- /dev/null +++ b/ImageBoardServerApp/Dockerfile @@ -0,0 +1,20 @@ +FROM mcr.microsoft.com/dotnet/aspnet:6.0 AS base +WORKDIR /app +EXPOSE 80 +EXPOSE 443 + +FROM mcr.microsoft.com/dotnet/sdk:6.0 AS build +WORKDIR /src +COPY ["ImageBoardServerApp/ImageBoardServerApp.csproj", "ImageBoardServerApp/"] +RUN dotnet restore "ImageBoardServerApp/ImageBoardServerApp.csproj" +COPY . . +WORKDIR "/src/BlazorServerTest" +RUN dotnet build "BlazorServerTest.csproj" -c Release -o /app/build + +FROM build AS publish +RUN dotnet publish "ImageBoardServerApp.csproj" -c Release -o /app/publish + +FROM base AS final +WORKDIR /app +COPY --from=publish /app/publish . +ENTRYPOINT ["dotnet", "ImageBoardServerApp.dll"] diff --git a/ImageBoardServerApp/Pages/Login.razor b/ImageBoardServerApp/Pages/Login.razor index 3856758..4058ea7 100644 --- a/ImageBoardServerApp/Pages/Login.razor +++ b/ImageBoardServerApp/Pages/Login.razor @@ -1,6 +1,12 @@ -@page "/Login" +@page "/login" @using ImageBoardServerApp.Data.Repository -

Login

+@using ImageBoardServerApp.Auth +@using System.Runtime.InteropServices +@inject IJSRuntime js +@inject AuthenticationStateProvider authStateProvider +@inject NavigationManager navManager + +

Login to bulletbroards

@@ -11,48 +17,41 @@
- +
- - @if (tried) - { - @if (verified) - { - Verifed! - } - else - { - False login - } - } - else - { - Plz login - } - +
@code { private string Email { get; set; } private string Password { get; set; } - private bool verified = false; - private bool tried = false; + private bool verified; - private async Task SubmitForm() + private async Task login() { - tried = true; - AccountData target = (await AccountsRepository.getAccountsByMailAsync(Email))[0]; - if (target == null) + Console.WriteLine("loggin you in..."); + var user = await UsersRepository.getUserByEmailAsync(Email); + if (user == null) { + await js.InvokeVoidAsync("alert", "User does not exist"); verified = false; return; } - verified = BCrypt.Net.BCrypt.Verify(Password, target.Password); + verified = BCrypt.Net.BCrypt.Verify(Password, user.Password); if (verified) { verified = true; + var customAuthStateProvider = (CustomAuthenticationStateProvider)authStateProvider; + await customAuthStateProvider.UpdateAuthenticationStateAsync(user); + navManager.NavigateTo("/", true); return; } - verified = false; + await js.InvokeVoidAsync("alert", $"Wrong creds:\n{BCrypt.Net.BCrypt.HashPassword(Password)}"); } + + /* + * + UserData target = (await UsersRepository.getUserByEmailAsync(Email)); + + */ } \ No newline at end of file diff --git a/ImageBoardServerApp/Program.cs b/ImageBoardServerApp/Program.cs index 9e80ae6..4f3c1fb 100644 --- a/ImageBoardServerApp/Program.cs +++ b/ImageBoardServerApp/Program.cs @@ -1,14 +1,15 @@ -using ImageBoardServerApp.Data; -using Microsoft.AspNetCore.Components; -using Microsoft.AspNetCore.Components.Web; -using Microsoft.EntityFrameworkCore; -using Microsoft.EntityFrameworkCore.Design; +using ImageBoardServerApp.Auth; +using Microsoft.AspNetCore.Components.Authorization; +using Microsoft.AspNetCore.Components.Server.ProtectedBrowserStorage; var builder = WebApplication.CreateBuilder(args); // Add services to the container. +builder.Services.AddAuthenticationCore(); builder.Services.AddRazorPages(); builder.Services.AddServerSideBlazor(); +builder.Services.AddScoped(); +builder.Services.AddScoped(); var app = builder.Build(); diff --git a/ImageBoardServerApp/Shared/Components/Forms/CommentForm.razor b/ImageBoardServerApp/Shared/Components/Forms/CommentForm.razor index 1733a25..cdecaf0 100644 --- a/ImageBoardServerApp/Shared/Components/Forms/CommentForm.razor +++ b/ImageBoardServerApp/Shared/Components/Forms/CommentForm.razor @@ -87,13 +87,15 @@ { var userToCreate = new UserData { - Ipv4Address = "192.168.178.101", - Banned = false, + Email = "dev@limited-dev.de", + Password = "$2a$10$C/ZPY5aVGkImLGyIP0SySuQaEYIwnY0J99i/m6tqqf6tMkax89Eku", + PermissionInteger = 100, + TimeBanned = -1, lastActionTimeStamp = DateTime.Now.Millisecond }; int userID; - UserData foundusr = await UsersRepository.getUserByIPAsync(userToCreate.Ipv4Address); + UserData foundusr = await UsersRepository.getUserByEmailAsync(userToCreate.Email); if (foundusr == null) { userID = await UsersRepository.createUserAsync(userToCreate); @@ -101,9 +103,9 @@ else { userID = foundusr.UserID; - if(foundusr.Banned) + if(foundusr.TimeBanned != -1) return; - foundusr.lastActionTimeStamp = DateTime.Now.Millisecond; + foundusr.lastActionTimeStamp = DateTimeOffset.UnixEpoch.ToUnixTimeMilliseconds(); await UsersRepository.updateUserAsync(foundusr); } diff --git a/ImageBoardServerApp/Shared/Components/Forms/PostForm.razor b/ImageBoardServerApp/Shared/Components/Forms/PostForm.razor index 3e42dd2..f38ac31 100644 --- a/ImageBoardServerApp/Shared/Components/Forms/PostForm.razor +++ b/ImageBoardServerApp/Shared/Components/Forms/PostForm.razor @@ -100,13 +100,15 @@ { var userToCreate = new UserData { - Ipv4Address = "192.168.178.101", - Banned = false, + Email = "test@mail.org", + Password = "$2a$10$C/ZPY5aVGkImLGyIP0SySuQaEYIwnY0J99i/m6tqqf6tMkax89Eku", + PermissionInteger = 100, + TimeBanned = -1, lastActionTimeStamp = DateTime.Now.Millisecond }; - + int userID; - UserData foundusr = await UsersRepository.getUserByIPAsync(userToCreate.Ipv4Address); + UserData foundusr = await UsersRepository.getUserByEmailAsync(userToCreate.Email); if (foundusr == null) { userID = await UsersRepository.createUserAsync(userToCreate); @@ -114,9 +116,9 @@ else { userID = foundusr.UserID; - if(foundusr.Banned) + if(foundusr.TimeBanned != -1) return; - foundusr.lastActionTimeStamp = DateTime.Now.Millisecond; + foundusr.lastActionTimeStamp = DateTimeOffset.UnixEpoch.ToUnixTimeMilliseconds(); await UsersRepository.updateUserAsync(foundusr); } diff --git a/ImageBoardServerApp/Shared/MainLayout.razor b/ImageBoardServerApp/Shared/MainLayout.razor index 63130fc..2c83802 100644 --- a/ImageBoardServerApp/Shared/MainLayout.razor +++ b/ImageBoardServerApp/Shared/MainLayout.razor @@ -1,4 +1,7 @@ @inherits LayoutComponentBase +@using ImageBoardServerApp.Auth +@inject AuthenticationStateProvider authStateProvder +@inject NavigationManager navManager BulletBoard @@ -11,10 +14,28 @@
[FAQ] [Rules] + + + [Logout] + + + [Login] + +
@Body
- \ No newline at end of file + + +@code +{ + private async Task logout() + { + var customAuthStateProvider = (CustomAuthenticationStateProvider)authStateProvder; + await customAuthStateProvider.UpdateAuthenticationStateAsync(null); + navManager.NavigateTo("/", true); + } +}