From 69af0547744ec064bda37b306f1d65fb785909e8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Ty=C5=84ski?= Date: Sun, 4 Oct 2026 05:42:35 +0200 Subject: [PATCH] chore(dev): add HTTPS Vite dev server and HTTP launch profile Serve Vite over HTTPS on :7081 using a certificate exported from dotnet dev-certs (scripts/dev-certs.ps1). Add an http launch profile on :5078 as the default backend and point the /api proxy at it, so dev runs on defaults without env vars. --- backend/Properties/launchSettings.json | 9 ++++ client/.gitignore | 3 ++ client/package.json | 1 + client/vite.config.ts | 21 +++++++- scripts/dev-certs.ps1 | 66 ++++++++++++++++++++++++++ 5 files changed, 99 insertions(+), 1 deletion(-) create mode 100644 scripts/dev-certs.ps1 diff --git a/backend/Properties/launchSettings.json b/backend/Properties/launchSettings.json index 03aa453..284ad9b 100644 --- a/backend/Properties/launchSettings.json +++ b/backend/Properties/launchSettings.json @@ -1,6 +1,15 @@ { "$schema": "https://json.schemastore.org/launchsettings.json", "profiles": { + "http": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": false, + "applicationUrl": "http://localhost:5078", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "Development" + } + }, "https": { "commandName": "Project", "dotnetRunMessages": true, diff --git a/client/.gitignore b/client/.gitignore index a547bf3..7d76868 100644 --- a/client/.gitignore +++ b/client/.gitignore @@ -12,6 +12,9 @@ dist dist-ssr *.local +# Lokalne certyfikaty dev (scripts/dev-certs.ps1) +.certs/ + # Editor directories and files .vscode/* !.vscode/extensions.json diff --git a/client/package.json b/client/package.json index 3ec34a0..3a55123 100644 --- a/client/package.json +++ b/client/package.json @@ -5,6 +5,7 @@ "type": "module", "scripts": { "dev": "vite", + "certs": "pwsh ../scripts/dev-certs.ps1", "build": "vue-tsc -b && vite build", "preview": "vite preview", "copy": "node ../scripts/copy-client.mjs", diff --git a/client/vite.config.ts b/client/vite.config.ts index 0fe36a4..cb4eb9e 100644 --- a/client/vite.config.ts +++ b/client/vite.config.ts @@ -1,11 +1,30 @@ +import fs from 'node:fs' +import { fileURLToPath } from 'node:url' import vue from '@vitejs/plugin-vue' import { defineConfig } from 'vite' +// Certyfikat PEM wygenerowany przez scripts/dev-certs.ps1 (dotnet dev-certs https). +const certDir = fileURLToPath(new URL('./.certs', import.meta.url)) +const certFile = `${certDir}/dev.pem` +const keyFile = `${certDir}/dev-key.pem` +const hasCerts = fs.existsSync(certFile) && fs.existsSync(keyFile) + +if (!hasCerts) { + console.warn( + '[vite] Brak certyfikatów w client/.certs — dev-server wstanie po HTTP. ' + + 'Uruchom: pwsh ../scripts/dev-certs.ps1 (z katalogu client/).', + ) +} + +// Domyślnie backend z profilu `http` (launchSettings.json), port 5078. // https://vite.dev/config/ export default defineConfig({ plugins: [vue()], server: { - port: 5173, + port: 7081, + https: hasCerts + ? { cert: fs.readFileSync(certFile), key: fs.readFileSync(keyFile) } + : undefined, proxy: { '/api': { target: 'http://localhost:5078', diff --git a/scripts/dev-certs.ps1 b/scripts/dev-certs.ps1 new file mode 100644 index 0000000..5671eb2 --- /dev/null +++ b/scripts/dev-certs.ps1 @@ -0,0 +1,66 @@ +<# +.SYNOPSIS + Eksportuje certyfikat deweloperski ASP.NET Core (dotnet dev-certs) do formatu + PEM używanego przez dev-serwer Vite (HTTPS). + +.DESCRIPTION + Zapewnia istnienie zaufanego certyfikatu deweloperskiego `dotnet dev-certs https`, + a następnie eksportuje go do plików PEM (certyfikat + klucz prywatny) w katalogu + client/.certs. Pliki są ignorowane przez Git i służą wyłącznie lokalnemu dev. + + Wymagany PowerShell Core 7+ (`pwsh`) — używamy metod PEM z .NET 7+. +#> +param( + [string]$OutDir = (Join-Path $PSScriptRoot "..\client\.certs"), + [string]$Password = "tarninahub-dev", + [switch]$NoTrust +) + +$ErrorActionPreference = "Stop" + +if (-not (Get-Command dotnet -ErrorAction SilentlyContinue)) { + throw "Nie znaleziono 'dotnet' w PATH. Zainstaluj .NET SDK 10+: https://dotnet.microsoft.com/download" +} + +if ($NoTrust) { + dotnet dev-certs https | Out-Host +} +else { + dotnet dev-certs https --trust | Out-Host +} + +$resolvedOut = [System.IO.Path]::GetFullPath($OutDir) +New-Item -ItemType Directory -Force -Path $resolvedOut | Out-Null + +$pfxPath = Join-Path ([System.IO.Path]::GetTempPath()) ("tarninahub-dev-" + [guid]::NewGuid().ToString("N") + ".pfx") +$certPath = Join-Path $resolvedOut "dev.pem" +$keyPath = Join-Path $resolvedOut "dev-key.pem" + +try { + dotnet dev-certs https --export-path $pfxPath --password $Password | Out-Host + + $flags = [System.Security.Cryptography.X509Certificates.X509KeyStorageFlags]::Exportable + $cert = [System.Security.Cryptography.X509Certificates.X509Certificate2]::new($pfxPath, $Password, $flags) + + $certPem = [System.Security.Cryptography.PemEncoding]::Write( + "CERTIFICATE", $cert.Export([System.Security.Cryptography.X509Certificates.X509ContentType]::Cert)) + + $privateKey = [System.Security.Cryptography.X509Certificates.RSACertificateExtensions]::GetRSAPrivateKey($cert) + if (-not $privateKey) { + $privateKey = [System.Security.Cryptography.X509Certificates.ECDsaCertificateExtensions]::GetECDsaPrivateKey($cert) + } + if (-not $privateKey) { throw "Certyfikat deweloperski nie zawiera klucza prywatnego (RSA/ECDSA)." } + + $keyPem = [System.Security.Cryptography.PemEncoding]::Write("PRIVATE KEY", $privateKey.ExportPkcs8PrivateKey()) + + [System.IO.File]::WriteAllText($certPath, $certPem) + [System.IO.File]::WriteAllText($keyPath, $keyPem) +} +finally { + if (Test-Path -LiteralPath $pfxPath) { + Remove-Item -LiteralPath $pfxPath -Force + } +} + +Write-Host "Certyfikat PEM: $certPath" +Write-Host "Klucz prywatny: $keyPath"