User api endpoints done

This commit is contained in:
Jeas0001 2025-03-18 12:45:31 +01:00
parent b194766464
commit ac5bef968f
225 changed files with 10858 additions and 80 deletions

View File

@ -10,8 +10,22 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="9.0.3" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="9.0.3">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.EntityFrameworkCore.Sqlite" Version="9.0.3" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="10.0.0-preview.1.25081.1">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.19.6" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.4.0" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\Models\Models.csproj" />
</ItemGroup>
</Project>

View File

@ -1,6 +1,9 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="Current" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<ActiveDebugProfile>Container (Dockerfile)</ActiveDebugProfile>
<ActiveDebugProfile>http</ActiveDebugProfile>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
<DebuggerFlavor>ProjectDebugger</DebuggerFlavor>
</PropertyGroup>
</Project>

View File

@ -0,0 +1,28 @@
using Microsoft.AspNetCore.Mvc;
using Models;
namespace Api.Controllers
{
[ApiController]
[Route("api/[controller]")]
public class DeviceController : Controller
{
[HttpGet]
public async Task<IActionResult> GetDevices(int userId)
{
return Ok();
}
[HttpGet("logs/{userId}")]
public async Task<IActionResult> GetLogs(int userId)
{
return Ok();
}
[HttpPut("Edit")]
public async Task<IActionResult> EditDevice([FromBody] Device device)
{
return Ok();
}
}
}

View File

@ -0,0 +1,43 @@
using Microsoft.AspNetCore.Mvc;
using Models;
namespace Api.Controllers
{
[ApiController]
[Route("api/[controller]")]
public class UserController : Controller
{
private readonly DBContext _context;
public UserController(DBContext context)
{
_context = context;
}
[HttpPost("Login")]
public async Task<IActionResult> Login([FromBody] User user)
{
DBAccess.DBAccess dBAccess = new DBAccess.DBAccess(_context);
user = await dBAccess.Login(user);
if (user.Id == 0) { return BadRequest(new { error = "User can't be logged in" }); }
return Ok(user);
}
[HttpPost("Create")]
public async Task<IActionResult> CreateUser([FromBody] User user)
{
DBAccess.DBAccess dBAccess = new DBAccess.DBAccess(_context);
bool success = await dBAccess.CreateUser(user);
if (!success) { return BadRequest(new { error = "User can't be created" }); }
return Ok();
}
[HttpPut("Edit")]
public async Task<IActionResult> EditUser([FromBody] User user)
{
DBAccess.DBAccess dBAccess = new DBAccess.DBAccess(_context);
bool success = await dBAccess.EditUser(user);
if (!success) { return BadRequest(new { error = "User can't be edited" }); }
return Ok();
}
}
}

View File

@ -1,33 +0,0 @@
using Microsoft.AspNetCore.Mvc;
namespace Api.Controllers
{
[ApiController]
[Route("[controller]")]
public class WeatherForecastController : ControllerBase
{
private static readonly string[] Summaries = new[]
{
"Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
};
private readonly ILogger<WeatherForecastController> _logger;
public WeatherForecastController(ILogger<WeatherForecastController> logger)
{
_logger = logger;
}
[HttpGet(Name = "GetWeatherForecast")]
public IEnumerable<WeatherForecast> Get()
{
return Enumerable.Range(1, 5).Select(index => new WeatherForecast
{
Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
TemperatureC = Random.Shared.Next(-20, 55),
Summary = Summaries[Random.Shared.Next(Summaries.Length)]
})
.ToArray();
}
}
}

View File

@ -0,0 +1,56 @@
using Microsoft.EntityFrameworkCore;
using Models;
namespace Api.DBAccess
{
public class DBAccess
{
private readonly DBContext _context;
public DBAccess(DBContext context)
{
_context = context;
}
public async Task<bool> CreateUser(User user)
{
var users = await _context.Users.ToListAsync();
foreach (var item in users)
{
if (item.UserName == user.UserName || item.Email == user.Email)
{
return false;
}
}
_context.Users.Add(user);
return await _context.SaveChangesAsync() == 1;
}
public async Task<User> Login(User user)
{
var profile = await _context.Users.FirstAsync(u => u.UserName == user.UserName);
if (profile.Password == user.Password)
{
profile.Password = "";
return profile;
}
return new User();
}
public async Task<bool> EditUser(User user)
{
var profile = await _context.Users.FirstAsync(u => u.Id == user.Id);
profile.UserName = user.UserName;
profile.Email = user.Email;
profile.Password = user.Password;
return await _context.SaveChangesAsync() == 1;
}
}
}

View File

@ -0,0 +1,14 @@
using Microsoft.EntityFrameworkCore;
using Models;
namespace Api
{
public class DBContext : DbContext
{
public DbSet<User> Users { get; set; }
public DbSet<Device> Devices { get; set; }
public DBContext(DbContextOptions<DBContext> options) : base(options) { }
}
}

View File

@ -0,0 +1,122 @@
// <auto-generated />
using System;
using Api;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
#nullable disable
namespace Api.Migrations
{
[DbContext(typeof(DBContext))]
[Migration("20250318102328_init")]
partial class init
{
/// <inheritdoc />
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
#pragma warning disable 612, 618
modelBuilder.HasAnnotation("ProductVersion", "9.0.3");
modelBuilder.Entity("Models.Device", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<double>("TempHigh")
.HasColumnType("REAL");
b.Property<double>("TempLow")
.HasColumnType("REAL");
b.Property<int?>("UserId")
.HasColumnType("INTEGER");
b.HasKey("Id");
b.HasIndex("UserId");
b.ToTable("Devices");
});
modelBuilder.Entity("Models.TemperatureLogs", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<DateTime>("Date")
.HasColumnType("TEXT");
b.Property<int?>("DeviceId")
.HasColumnType("INTEGER");
b.Property<double>("TempHigh")
.HasColumnType("REAL");
b.Property<double>("TempLow")
.HasColumnType("REAL");
b.Property<double>("Temperature")
.HasColumnType("REAL");
b.HasKey("Id");
b.HasIndex("DeviceId");
b.ToTable("TemperatureLogs");
});
modelBuilder.Entity("Models.User", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<string>("FullName")
.IsRequired()
.HasColumnType("TEXT");
b.Property<string>("Password")
.IsRequired()
.HasColumnType("TEXT");
b.Property<string>("UserName")
.IsRequired()
.HasColumnType("TEXT");
b.HasKey("Id");
b.ToTable("Users");
});
modelBuilder.Entity("Models.Device", b =>
{
b.HasOne("Models.User", null)
.WithMany("Devices")
.HasForeignKey("UserId");
});
modelBuilder.Entity("Models.TemperatureLogs", b =>
{
b.HasOne("Models.Device", null)
.WithMany("Logs")
.HasForeignKey("DeviceId");
});
modelBuilder.Entity("Models.Device", b =>
{
b.Navigation("Logs");
});
modelBuilder.Entity("Models.User", b =>
{
b.Navigation("Devices");
});
#pragma warning restore 612, 618
}
}
}

View File

@ -0,0 +1,95 @@
using System;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace Api.Migrations
{
/// <inheritdoc />
public partial class init : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "Users",
columns: table => new
{
Id = table.Column<int>(type: "INTEGER", nullable: false)
.Annotation("Sqlite:Autoincrement", true),
UserName = table.Column<string>(type: "TEXT", nullable: false),
Password = table.Column<string>(type: "TEXT", nullable: false),
FullName = table.Column<string>(type: "TEXT", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("PK_Users", x => x.Id);
});
migrationBuilder.CreateTable(
name: "Devices",
columns: table => new
{
Id = table.Column<int>(type: "INTEGER", nullable: false)
.Annotation("Sqlite:Autoincrement", true),
TempHigh = table.Column<double>(type: "REAL", nullable: false),
TempLow = table.Column<double>(type: "REAL", nullable: false),
UserId = table.Column<int>(type: "INTEGER", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("PK_Devices", x => x.Id);
table.ForeignKey(
name: "FK_Devices_Users_UserId",
column: x => x.UserId,
principalTable: "Users",
principalColumn: "Id");
});
migrationBuilder.CreateTable(
name: "TemperatureLogs",
columns: table => new
{
Id = table.Column<int>(type: "INTEGER", nullable: false)
.Annotation("Sqlite:Autoincrement", true),
Temperature = table.Column<double>(type: "REAL", nullable: false),
Date = table.Column<DateTime>(type: "TEXT", nullable: false),
TempHigh = table.Column<double>(type: "REAL", nullable: false),
TempLow = table.Column<double>(type: "REAL", nullable: false),
DeviceId = table.Column<int>(type: "INTEGER", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("PK_TemperatureLogs", x => x.Id);
table.ForeignKey(
name: "FK_TemperatureLogs_Devices_DeviceId",
column: x => x.DeviceId,
principalTable: "Devices",
principalColumn: "Id");
});
migrationBuilder.CreateIndex(
name: "IX_Devices_UserId",
table: "Devices",
column: "UserId");
migrationBuilder.CreateIndex(
name: "IX_TemperatureLogs_DeviceId",
table: "TemperatureLogs",
column: "DeviceId");
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "TemperatureLogs");
migrationBuilder.DropTable(
name: "Devices");
migrationBuilder.DropTable(
name: "Users");
}
}
}

View File

@ -0,0 +1,125 @@
// <auto-generated />
using System;
using Api;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
#nullable disable
namespace Api.Migrations
{
[DbContext(typeof(DBContext))]
[Migration("20250318112004_init2")]
partial class init2
{
/// <inheritdoc />
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
#pragma warning disable 612, 618
modelBuilder.HasAnnotation("ProductVersion", "9.0.3");
modelBuilder.Entity("Models.Device", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<double>("TempHigh")
.HasColumnType("REAL");
b.Property<double>("TempLow")
.HasColumnType("REAL");
b.Property<string>("UnikId")
.HasColumnType("TEXT");
b.Property<int?>("UserId")
.HasColumnType("INTEGER");
b.HasKey("Id");
b.HasIndex("UserId");
b.ToTable("Devices");
});
modelBuilder.Entity("Models.TemperatureLogs", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<DateTime>("Date")
.HasColumnType("TEXT");
b.Property<int?>("DeviceId")
.HasColumnType("INTEGER");
b.Property<double>("TempHigh")
.HasColumnType("REAL");
b.Property<double>("TempLow")
.HasColumnType("REAL");
b.Property<double>("Temperature")
.HasColumnType("REAL");
b.HasKey("Id");
b.HasIndex("DeviceId");
b.ToTable("TemperatureLogs");
});
modelBuilder.Entity("Models.User", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<string>("Email")
.IsRequired()
.HasColumnType("TEXT");
b.Property<string>("Password")
.IsRequired()
.HasColumnType("TEXT");
b.Property<string>("UserName")
.IsRequired()
.HasColumnType("TEXT");
b.HasKey("Id");
b.ToTable("Users");
});
modelBuilder.Entity("Models.Device", b =>
{
b.HasOne("Models.User", null)
.WithMany("Devices")
.HasForeignKey("UserId");
});
modelBuilder.Entity("Models.TemperatureLogs", b =>
{
b.HasOne("Models.Device", null)
.WithMany("Logs")
.HasForeignKey("DeviceId");
});
modelBuilder.Entity("Models.Device", b =>
{
b.Navigation("Logs");
});
modelBuilder.Entity("Models.User", b =>
{
b.Navigation("Devices");
});
#pragma warning restore 612, 618
}
}
}

View File

@ -0,0 +1,38 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace Api.Migrations
{
/// <inheritdoc />
public partial class init2 : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.RenameColumn(
name: "FullName",
table: "Users",
newName: "Email");
migrationBuilder.AddColumn<string>(
name: "UnikId",
table: "Devices",
type: "TEXT",
nullable: true);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "UnikId",
table: "Devices");
migrationBuilder.RenameColumn(
name: "Email",
table: "Users",
newName: "FullName");
}
}
}

View File

@ -0,0 +1,122 @@
// <auto-generated />
using System;
using Api;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
#nullable disable
namespace Api.Migrations
{
[DbContext(typeof(DBContext))]
partial class DBContextModelSnapshot : ModelSnapshot
{
protected override void BuildModel(ModelBuilder modelBuilder)
{
#pragma warning disable 612, 618
modelBuilder.HasAnnotation("ProductVersion", "9.0.3");
modelBuilder.Entity("Models.Device", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<double>("TempHigh")
.HasColumnType("REAL");
b.Property<double>("TempLow")
.HasColumnType("REAL");
b.Property<string>("UnikId")
.HasColumnType("TEXT");
b.Property<int?>("UserId")
.HasColumnType("INTEGER");
b.HasKey("Id");
b.HasIndex("UserId");
b.ToTable("Devices");
});
modelBuilder.Entity("Models.TemperatureLogs", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<DateTime>("Date")
.HasColumnType("TEXT");
b.Property<int?>("DeviceId")
.HasColumnType("INTEGER");
b.Property<double>("TempHigh")
.HasColumnType("REAL");
b.Property<double>("TempLow")
.HasColumnType("REAL");
b.Property<double>("Temperature")
.HasColumnType("REAL");
b.HasKey("Id");
b.HasIndex("DeviceId");
b.ToTable("TemperatureLogs");
});
modelBuilder.Entity("Models.User", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("INTEGER");
b.Property<string>("Email")
.IsRequired()
.HasColumnType("TEXT");
b.Property<string>("Password")
.IsRequired()
.HasColumnType("TEXT");
b.Property<string>("UserName")
.IsRequired()
.HasColumnType("TEXT");
b.HasKey("Id");
b.ToTable("Users");
});
modelBuilder.Entity("Models.Device", b =>
{
b.HasOne("Models.User", null)
.WithMany("Devices")
.HasForeignKey("UserId");
});
modelBuilder.Entity("Models.TemperatureLogs", b =>
{
b.HasOne("Models.Device", null)
.WithMany("Logs")
.HasForeignKey("DeviceId");
});
modelBuilder.Entity("Models.Device", b =>
{
b.Navigation("Logs");
});
modelBuilder.Entity("Models.User", b =>
{
b.Navigation("Devices");
});
#pragma warning restore 612, 618
}
}
}

View File

@ -1,25 +1,15 @@
var builder = WebApplication.CreateBuilder(args);
using Api;
using Microsoft.AspNetCore;
using Microsoft.EntityFrameworkCore;
// Add services to the container.
builder.Services.AddControllers();
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
var app = builder.Build();
// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
public class Program
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.UseHttpsRedirection();
app.UseAuthorization();
app.MapControllers();
app.Run();
private static void Main(string[] args)
{
CreateWebHostBuilder(args).Build().Run();
}
// Calls the startup class and creates the webinterface
public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
WebHost.CreateDefaultBuilder(args)
.UseStartup<Startup>();
}

66
backend/Api/Startup.cs Normal file
View File

@ -0,0 +1,66 @@
using Microsoft.EntityFrameworkCore;
using Microsoft.OpenApi.Models;
namespace Api
{
public class Startup
{
public IConfiguration _configuration { get; }
public Startup(IConfiguration configuration)
{
_configuration = configuration;
}
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
// Sets the connectionstring to the database so dbcontext can find it
services.AddDbContext<DBContext>(options =>
options.UseSqlite(_configuration.GetConnectionString("Database")));
services.AddControllers();
services.AddCors(options =>
{
options.AddPolicy("AllowAll", builder =>
{
builder.AllowAnyOrigin()
.AllowAnyMethod().AllowAnyHeader();
});
});
services.AddSwaggerGen(c =>
{
c.SwaggerDoc("v1", new OpenApiInfo { Title = "My API", Version = "v1" });
});
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
app.UseSwagger();
app.UseSwaggerUI(c =>
{
c.SwaggerEndpoint("/swagger/v1/swagger.json", "My API V1");
});
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseCors("AllowAll");
app.UseRouting();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
}
}
}

File diff suppressed because it is too large Load Diff

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,20 @@
{
"runtimeOptions": {
"tfm": "net8.0",
"frameworks": [
{
"name": "Microsoft.NETCore.App",
"version": "8.0.0"
},
{
"name": "Microsoft.AspNetCore.App",
"version": "8.0.0"
}
],
"configProperties": {
"System.GC.Server": true,
"System.Reflection.NullabilityInfoContext.IsSupported": true,
"System.Runtime.Serialization.EnableUnsafeBinaryFormatterSerialization": false
}
}
}

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Some files were not shown because too many files have changed in this diff Show More