03-oct: superguardado automático

This commit is contained in:
minguezsanzjuanjose
2026-10-03 17:18:41 +02:00
parent fdd4ea877a
commit 1b385cca7c
5 changed files with 259 additions and 0 deletions

View File

@@ -0,0 +1,104 @@
<#
.SYNOPSIS
Configura el acceso remoto por SSH (-> PowerShell) en un PC Windows.
.DESCRIPTION
Idempotente. Deja listo el equipo para conectarse desde otro (p. ej. el portatil)
con `ssh usuario@equipo` y caer directamente en PowerShell.
Hace:
1. Instala la capacidad OpenSSH.Server (si falta).
2. Pone y arranca los servicios sshd y ssh-agent (Automatico).
3. Deja PowerShell como shell por defecto de SSH.
4. Crea una regla de firewall para el puerto 22, restringida a Tailscale y LAN.
5. Instala la clave publica recibida en authorized_keys (o administrators_authorized_keys).
Requiere PowerShell ELEVADO (se auto-eleva si hace falta).
.EXAMPLE
powershell -ExecutionPolicy Bypass -File setup_ssh_server.ps1 -PublicKey "ssh-ed25519 AAAA... juanm@portatil"
#>
[CmdletBinding()]
param(
[string]$PublicKey = '',
[string[]]$AllowedNetworks = @('100.64.0.0/10', '192.168.1.0/24', '192.168.50.0/24')
)
$ErrorActionPreference = 'Stop'
# --- Auto-elevacion -------------------------------------------------------
$esAdmin = ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator)
if (-not $esAdmin) {
Write-Host 'Requiere administrador. Reabriendo elevado...' -ForegroundColor Yellow
$argsList = @('-NoProfile', '-ExecutionPolicy', 'Bypass', '-File', "`"$PSCommandPath`"")
if ($PublicKey) { $argsList += @('-PublicKey', "`"$PublicKey`"") }
Start-Process powershell -Verb RunAs -ArgumentList $argsList
exit
}
Write-Host '== Configurando OpenSSH Server (acceso remoto -> PowerShell) ==' -ForegroundColor Cyan
# 1) Capacidad OpenSSH.Server ----------------------------------------------
$cap = Get-WindowsCapability -Online -Name 'OpenSSH.Server*' | Select-Object -First 1
if ($cap.State -ne 'Installed') {
Write-Host ' - Instalando OpenSSH.Server...' -ForegroundColor Yellow
Add-WindowsCapability -Online -Name $cap.Name | Out-Null
}
Write-Host ' - OpenSSH.Server instalado.' -ForegroundColor Green
# 2) Servicios --------------------------------------------------------------
foreach ($svc in @('sshd', 'ssh-agent')) {
if (Get-Service $svc -ErrorAction SilentlyContinue) {
Set-Service -Name $svc -StartupType Automatic
if ((Get-Service $svc).Status -ne 'Running') { Start-Service $svc }
Write-Host " - Servicio '$svc' -> Automatico y en marcha." -ForegroundColor Green
}
}
# 3) Shell por defecto = PowerShell ----------------------------------------
if (-not (Test-Path 'HKLM:\SOFTWARE\OpenSSH')) { New-Item -Path 'HKLM:\SOFTWARE\OpenSSH' -Force | Out-Null }
$pwsh = Join-Path $env:SystemRoot 'System32\WindowsPowerShell\v1.0\powershell.exe'
New-ItemProperty -Path 'HKLM:\SOFTWARE\OpenSSH' -Name 'DefaultShell' -Value $pwsh -PropertyType String -Force | Out-Null
Write-Host " - Shell por defecto: $pwsh" -ForegroundColor Green
# 4) Firewall (solo Tailscale + LAN) ---------------------------------------
$ruleName = 'OpenSSH Server (sshd) - acceso remoto'
Get-NetFirewallRule -DisplayName $ruleName -ErrorAction SilentlyContinue | Remove-NetFirewallRule
New-NetFirewallRule -DisplayName $ruleName -Direction Inbound -Protocol TCP -Action Allow `
-LocalPort 22 -RemoteAddress $AllowedNetworks -Profile Any | Out-Null
Write-Host " - Firewall: puerto 22 permitido desde $($AllowedNetworks -join ', ')." -ForegroundColor Green
# 5) Clave publica ----------------------------------------------------------
if ($PublicKey) {
$usuarioEsAdmin = $null -ne (Get-LocalGroupMember -Group (Get-LocalGroup -SID 'S-1-5-32-544').Name |
Where-Object { $_.Name -like "*\$env:USERNAME" })
if ($usuarioEsAdmin) {
$keyFile = Join-Path $env:ProgramData 'ssh\administrators_authorized_keys'
$dir = Split-Path $keyFile
if (-not (Test-Path $dir)) { New-Item -ItemType Directory -Path $dir -Force | Out-Null }
} else {
$keyFile = Join-Path $env:USERPROFILE '.ssh\authorized_keys'
$dir = Split-Path $keyFile
if (-not (Test-Path $dir)) { New-Item -ItemType Directory -Path $dir -Force | Out-Null }
}
$contenido = if (Test-Path $keyFile) { Get-Content -LiteralPath $keyFile -ErrorAction SilentlyContinue } else { @() }
if ($contenido -notcontains $PublicKey.Trim()) {
Add-Content -LiteralPath $keyFile -Value $PublicKey.Trim() -Encoding ascii
Write-Host " - Clave publica anadida a $keyFile" -ForegroundColor Green
} else {
Write-Host " - La clave publica ya estaba en $keyFile" -ForegroundColor Green
}
if ($usuarioEsAdmin) {
icacls $keyFile /inheritance:r 2>$null | Out-Null
icacls $keyFile /grant 'SYSTEM:F' 'BUILTIN\Administradores:F' 'BUILTIN\Administrators:F' 2>$null | Out-Null
}
Restart-Service sshd
Write-Host ' - sshd reiniciado para aplicar la clave.' -ForegroundColor Green
}
$ips = (Get-NetIPAddress -AddressFamily IPv4 | Where-Object { $_.IPAddress -notlike '127.*' }).IPAddress -join ', '
Write-Host ''
Write-Host 'Listo. Datos de conexion:' -ForegroundColor Cyan
Write-Host " Usuario : $env:USERNAME"
Write-Host " IPs : $ips"
Write-Host " Prueba : ssh $env:USERNAME@<IP-o-nombre-tailscale>"