Compare commits

...

10 Commits

Author SHA1 Message Date
Marek Lesko
0a585dd5a2 Update .gitlab-ci.yml file 2025-09-05 14:22:46 +00:00
Marek Lesko
54e888e240 Update .gitlab-ci.yml file 2025-09-05 14:19:30 +00:00
Marek Lesko
3b353c6660 Update .gitlab-ci.yml file 2025-09-05 14:17:09 +00:00
Marek Lesko
ca6c565b2b Update .gitlab-ci.yml file 2025-09-05 12:19:16 +00:00
Marek Lesko
4ac1f94249 Update Dockerfile for multi-stage .NET build process
Implemented a multi-stage build in the Dockerfile, adding a build stage with the .NET SDK for restoring and publishing the application. Introduced a runtime stage using the ASP.NET image, created a non-root user for enhanced security, and set necessary environment variables. The published output is now copied from the build stage, and the entry point is configured to launch the application.
2025-09-04 14:09:52 +02:00
Marek Lesko
8cc3f8e308 FIXED ApiResource 2025-09-03 15:26:54 +00:00
Marek Lesko
1250160b91 FIXED devcontainer 2025-09-03 15:26:40 +00:00
Marek Lesko
b6c52c502d ADDED devcontainer 2025-09-03 14:59:27 +00:00
Marek Lesko
a3eaf0f5b7 WIP 2025-09-02 17:43:26 +02:00
Marek Lesko
b18a89b087 UPDATED gitignore 2025-08-19 17:01:14 +02:00
6 changed files with 166 additions and 14 deletions

4
.devcontainer/Dockerfile Normal file
View File

@@ -0,0 +1,4 @@
FROM mcr.microsoft.com/dotnet/sdk:8.0-alpine
# Optional: install Docker CLI (not Docker daemon)
RUN apk add --no-cache docker-cli bash git

View File

@@ -0,0 +1,27 @@
// The Dev Container format allows you to configure your environment. At the heart of it
// is a Docker image or Dockerfile which controls the tools available in your environment.
//
// See https://aka.ms/devcontainer.json for more information.
{
"name": "Simple Id Server",
// Use "image": "mcr.microsoft.com/devcontainers/base:ubuntu-24.04",
// instead of the build to use a pre-built image.
"build": {
"context": ".",
"dockerfile": "Dockerfile"
},
"runArgs": [
"--privileged"
],
"mounts": [
"source=/var/run/docker.sock,target=/var/run/docker.sock,type=bind"
],
"remoteUser": "root"
// Features add additional features to your environment. See https://containers.dev/features
// Beware: features are not supported on all platforms and may have unintended side-effects.
// "features": {
// "ghcr.io/devcontainers/features/docker-in-docker": {
// "moby": false
// }
// }
}

1
.gitignore vendored
View File

@@ -2,6 +2,7 @@
.vsCode .vsCode
bin bin
obj obj
lib
*.vssscc *.vssscc
*.vspscc *.vspscc
*.user *.user

29
.gitlab-ci.yml Normal file
View File

@@ -0,0 +1,29 @@
stages: # Define the stages of the pipeline.
- build
docker-build:
stage: build
image: docker:latest
tags:
- shared
services:
- name: docker:dind
alias: docker
variables:
DOCKER_DRIVER: overlay2
DOCKER_HOST: tcp://docker:2375
DOCKER_TLS_CERTDIR: ""
before_script:
- docker info
script:
- docker build -t $CI_REGISTRY_IMAGE:latest -t $CI_REGISTRY_IMAGE:${CI_PIPELINE_IID} -t mareklesko/simpleidp:latest -t mareklesko/simpleidp:${CI_PIPELINE_IID} -f Dockerfile .
- echo "$CI_REGISTRY_PASSWORD" | docker login -u "$CI_REGISTRY_USER" --password-stdin $CI_REGISTRY
- docker push $CI_REGISTRY_IMAGE:latest
- docker push $CI_REGISTRY_IMAGE:${CI_PIPELINE_IID}
- docker login -u mareklesko --password $DOCKER_HUB_PASSWORD
- docker push mareklesko/simpleidp:latest
- docker push mareklesko/simpleidp:${CI_PIPELINE_IID}
only:
- dev
- main

35
Dockerfile Normal file
View File

@@ -0,0 +1,35 @@
# =========================
# Build stage
# =========================
FROM mcr.microsoft.com/dotnet/sdk:8.0 AS build
ARG BUILD_CONFIGURATION=Release
WORKDIR /src
# Copy everything (simple + reliable for single-project Razor Pages apps)
COPY . .
# Restore & publish (self-contained trimming can be added later if desired)
RUN dotnet restore
RUN dotnet publish -c $BUILD_CONFIGURATION -o /app/publish --no-restore
# =========================
# Runtime stage
# =========================
FROM mcr.microsoft.com/dotnet/aspnet:8.0 AS final
WORKDIR /app
# (Optional) Create non-root user for better security
RUN useradd -m appuser
ENV ASPNETCORE_URLS=http://+:8080 \
ASPNETCORE_ENVIRONMENT=Production \
DOTNET_RUNNING_IN_CONTAINER=true
EXPOSE 8080
# Copy published output
COPY --from=build /app/publish ./
# Switch to non-root
USER appuser
# Start the Razor Pages app
ENTRYPOINT ["dotnet", "SimpleIdp.dll"]

View File

@@ -9,9 +9,15 @@ using Microsoft.Extensions.DependencyInjection;
using SimpleIdServer.IdServer.Builders; using SimpleIdServer.IdServer.Builders;
using SimpleIdServer.IdServer.Config; using SimpleIdServer.IdServer.Config;
using SimpleIdServer.IdServer.Domains; using SimpleIdServer.IdServer.Domains;
using SimpleIdServer.IdServer.Helpers;
using SimpleIdServer.IdServer.Stores;
var corsPolicyName = "AllowAll"; var corsPolicyName = "AllowAll";
var realm = RealmBuilder.CreateMaster().Build();
//api.Audience = "urn:bighand:api:bi:portal";
var users = new List<User> var users = new List<User>
{ {
UserBuilder UserBuilder
@@ -21,26 +27,37 @@ var users = new List<User>
.AddRole("BI.PORTAL_ADMIN") .AddRole("BI.PORTAL_ADMIN")
.AddRole("BI.TENANT_ADMIN") .AddRole("BI.TENANT_ADMIN")
.AddClaim("tid", "cbaa13c2-e95b-470a-bbcb-18911d5a6025") .AddClaim("tid", "cbaa13c2-e95b-470a-bbcb-18911d5a6025")
.AddClaim("aud","urn:bighand:api:bi:portal")
.AddConsent("master","212C9DB96C2A4B6DA0AFDB2222F6EEAA.bighand.com","bi.portal")
.SetEmailVerified(true)
.Build(), .Build(),
}; };
var api = ApiResourceBuilder.Create("urn:bighand:api:bi:portal", "BI Portal API").Build(); var rUser = new RealmUser
var clients = new List<Client>
{ {
ClientBuilder Realm = realm,
.BuildUserAgentClient("foo", null, null, new[] { "http://localhost:4200/loggedin" }) User = users[0],
.AddScope(new Scope("openid"), new Scope("profile"), new Scope("offline_access"))
.AddRefreshToken()
.Build(),
}; };
var scopes = new List<Scope> { ScopeBuilder.CreateRoleScope(clients[0], "bi.portal", "").Build() }; users[0].Realms.Add(rUser);
var api = new ApiResource
{
Realms = { realm },
Name = "BI Portal API",
Audience = "urn:bighand:api:bi:portal"
};
//var scopes = new List<Scope> { ScopeBuilder.CreateRoleScope(clients[0], "bi.portal", "").Build() };
var biScope = new Scope() var biScope = new Scope()
{ {
Realms = { realm },
ApiResources = { api }, ApiResources = { api },
Protocol = ScopeProtocols.OAUTH,
Type = ScopeTypes.APIRESOURCE,
Name = "bi.portal", Name = "bi.portal",
Clients = { clients[0] },
Description = "BI Portal Scope", Description = "BI Portal Scope",
ClaimMappers = ClaimMappers =
{ {
@@ -48,8 +65,9 @@ var biScope = new Scope()
{ {
IncludeInAccessToken = true, IncludeInAccessToken = true,
TokenClaimJsonType = TokenClaimJsonTypes.STRING, TokenClaimJsonType = TokenClaimJsonTypes.STRING,
TargetClaimPath = "role", TargetClaimPath = "roles",
MapperType = MappingRuleTypes.USERATTRIBUTE, MapperType = MappingRuleTypes.USERATTRIBUTE,
IsMultiValued=true,
SourceUserAttribute = "role", SourceUserAttribute = "role",
SourceUserProperty = "role", SourceUserProperty = "role",
}, },
@@ -66,15 +84,44 @@ var biScope = new Scope()
{ {
IncludeInAccessToken = true, IncludeInAccessToken = true,
TokenClaimJsonType = TokenClaimJsonTypes.STRING, TokenClaimJsonType = TokenClaimJsonTypes.STRING,
TargetClaimPath = "email", TargetClaimPath = "upn",
MapperType = MappingRuleTypes.USERATTRIBUTE, MapperType = MappingRuleTypes.USERATTRIBUTE,
SourceUserAttribute = "email", SourceUserAttribute = "email",
SourceUserProperty = "email", SourceUserProperty = "email",
}, },
}, },
}; };
clients[0].Scopes.Add(biScope); api.Scopes.Add(biScope);
api.Realms.Add(realm);
var scopes = new List<Scope>
{
new Scope("openid") { Realms = { realm } },
new Scope("profile"){ Realms = { realm } },
new Scope("offline_access"){ Realms = { realm } },
biScope
};
var clients = new List<Client>
{
ClientBuilder
.BuildUserAgentClient("212C9DB96C2A4B6DA0AFDB2222F6EEAA.bighand.com", null, realm, new[] { "http://localhost:4200/loggedin" })
.SetClientName("BI Portal")
.AddScope(scopes.ToArray())
.AddRefreshToken()
.Build(),
};
clients[0].IsPublic = true;
clients[0].Realms.Add(realm);
realm.Clients.Add(clients[0]);
realm.ApiResources.Add(api);
realm.Users.Add(rUser);
scopes.ForEach(s => realm.Scopes.Add(s));
var builder = WebApplication.CreateBuilder(args); var builder = WebApplication.CreateBuilder(args);
@@ -92,13 +139,22 @@ builder.Services.AddCors(options =>
builder builder
.AddSidIdentityServer() .AddSidIdentityServer()
.AddDeveloperSigningCredential() .AddDeveloperSigningCredential()
.AddInMemoryRealms(new[] { realm }.ToList())
.AddInMemoryUsers(users) .AddInMemoryUsers(users)
.AddInMemoryClients(clients) .AddInMemoryClients(clients)
.AddInMemoryScopes([biScope]) .AddInMemoryScopes(scopes)
.AddInMemoryLanguages(DefaultLanguages.All) .AddInMemoryLanguages(DefaultLanguages.All)
.AddPwdAuthentication(true); .AddPwdAuthentication(true);
var app = builder.Build(); var app = builder.Build();
using (var sc = app.Services.CreateScope())
{
var s = sc.ServiceProvider.GetRequiredService<IApiResourceRepository>();
s.Add(api);
}
app.Services.SeedData(); app.Services.SeedData();
app.UseSid(); app.UseSid();
app.UseCors(corsPolicyName); app.UseCors(corsPolicyName);