PowerShell: install Oracle Java 21

Just another Tech site

PowerShell: install Oracle Java 21

learning to install silently install Oracle Java 21 SDK

  • Search for a .msi file containing jdk-21 in its name.
  • Install it silently to the target directory.
  • Set JAVA_HOME and update PATH.
  • Handle errors gracefully.

 

# PowerShell Script: Auto-detect and install Oracle Java 21 SDK (64-bit) from local MSI
# Requirements:
# - Run as Administrator
# - MSI file must already be downloaded in $searchDir

# Folder where the MSI file is located
$searchDir = "C:\Path\To\Downloaded\Java"

# Target installation directory
$installDir = "C:\JavaApps"

try {
    # Validate search directory
    if (-not (Test-Path -Path $searchDir -PathType Container)) {
        throw "Search directory not found: $searchDir"
    }

    # Find the MSI file for Java 21 (64-bit)
    $msiFile = Get-ChildItem -Path $searchDir -Filter "*.msi" -File |
               Where-Object { $_.Name -match "jdk-21.*x64" } |
               Sort-Object LastWriteTime -Descending |
               Select-Object -First 1

    if (-not $msiFile) {
        throw "No Oracle Java 21 64-bit MSI file found in: $searchDir"
    }

    $msiPath = $msiFile.FullName
    Write-Host "Found MSI: $msiPath" -ForegroundColor Cyan

    # Ensure target directory exists
    if (-not (Test-Path -Path $installDir -PathType Container)) {
        New-Item -Path $installDir -ItemType Directory -Force | Out-Null
    }

    Write-Host "Installing Oracle Java 21 SDK to $installDir ..." -ForegroundColor Cyan

    # Run MSI installation silently with custom directory
    $arguments = "/i `"$msiPath`" INSTALLDIR=`"$installDir`" /qn /norestart"
    $process = Start-Process -FilePath "msiexec.exe" -ArgumentList $arguments -Wait -PassThru

    if ($process.ExitCode -eq 0) {
        Write-Host "Java 21 SDK installed successfully to $installDir" -ForegroundColor Green
    } else {
        throw "MSI installation failed with exit code $($process.ExitCode)"
    }

    # Set JAVA_HOME and update PATH
    $javaHome = $installDir
    [Environment]::SetEnvironmentVariable("JAVA_HOME", $javaHome, [System.EnvironmentVariableTarget]::Machine)

    $currentPath = [Environment]::GetEnvironmentVariable("Path", [System.EnvironmentVariableTarget]::Machine)
    if ($currentPath -notlike "*$javaHome\bin*") {
        [Environment]::SetEnvironmentVariable("Path", "$currentPath;$javaHome\bin", [System.EnvironmentVariableTarget]::Machine)
    }

    Write-Host "JAVA_HOME set to $javaHome and PATH updated." -ForegroundColor Yellow
    Write-Host "You may need to restart your terminal or log off/on for changes to take effect." -ForegroundColor Yellow

} catch {
    Write-Host "Error: $_" -ForegroundColor Red
    exit 1
}

How to Use

  1. Save this script as InstallJava21Auto.ps1.
  2. Change the $searchDir variable to the folder where your downloaded MSI is stored.
  3. Open PowerShell as Administrator.

when running it use the following:

Set-ExecutionPolicy Bypass -Scope Process -Force
.\InstallJava21Auto.ps1

JDK

 

param(
    [string]$MsiPath = "C:\Path\To\jdk-21_windows-x64_bin.msi",  # Path to MSI
    [string]$LogPath = "C:\Path\To\jdk21_install.log",           # Path to log file
    [string]$InstallDir = "C:\Program Files\Java\jdk-21",        # Install location
    [switch]$SetEnv                                               # Use -SetEnv to set JAVA_HOME & PATH
)

# --- Check if MSI exists ---
if (-Not (Test-Path $MsiPath)) {
    Write-Host "ERROR: MSI file not found at $MsiPath" -ForegroundColor Red
    exit 1
}

# --- Install JDK 21 silently ---
Write-Host "Starting Oracle JDK 21 installation..."
Start-Process msiexec.exe -ArgumentList @(
    "/i `"$MsiPath`"",
    "/qn",                      # Quiet mode
    "/norestart",               # No auto-restart
    "INSTALLDIR=`"$InstallDir`"",
    "/L*v `"$LogPath`""
) -Wait

# --- Verify installation ---
$javaExe = Join-Path $InstallDir "bin\java.exe"
if (Test-Path $javaExe) {
    Write-Host "Oracle JDK 21 installed successfully." -ForegroundColor Green
    Write-Host "Log file saved to: $LogPath"
} else {
    Write-Host "Installation may have failed. Check log file: $LogPath" -ForegroundColor Yellow
    exit 1
}

# --- Optionally set JAVA_HOME and update PATH ---
if ($SetEnv) {
    Write-Host "Setting JAVA_HOME and updating PATH..."

    # Set JAVA_HOME system-wide
    setx JAVA_HOME "`"$InstallDir`"" /M | Out-Null

    # Update PATH if not already present
    $currentPath = [Environment]::GetEnvironmentVariable("Path", "Machine")
    if ($currentPath -notlike "*$InstallDir\bin*") {
        $newPath = "$currentPath;$InstallDir\bin"
        setx Path "`"$newPath`"" /M | Out-Null
        Write-Host "PATH updated to include $InstallDir\bin"
    } else {
        Write-Host "PATH already contains $InstallDir\bin"
    }

    Write-Host "JAVA_HOME set to $InstallDir" -ForegroundColor Cyan
} else {
    Write-Host "Skipping environment variable setup (JAVA_HOME & PATH not changed)." -ForegroundColor Yellow
}

<#
only
.\Install-JDK21.ps1
with set path
.\Install-JDK21.ps1 -SetEnv

#>

Uninstall JDK

How It Works

  1. Registry Search – Looks in both 64-bit and 32-bit uninstall registry keys.
  2. Pattern Match – Matches Java SE Development Kit 21 to target only JDK 21.
  3. Silent Execution – Uses /qn /norestart for MSI or /s for EXE uninstallers.
  4. Logging – Writes all actions and errors to C:\Temp\Java21JDK_Uninstall.log.
  5. Error Handling – Catches and logs unexpected errors.
<#
.SYNOPSIS
    Silently uninstalls Oracle Java 21 JDK (64-bit) and logs the process.

.DESCRIPTION
    This script searches the registry for Oracle Java 21 JDK 64-bit installations,
    executes the uninstall command silently, and logs all actions and errors.

.NOTES
    Author: Your Name
    Tested on: Windows 10/11, PowerShell 5.1+
#>

# =========================
# CONFIGURATION
# =========================
$LogFile = "C:\Temp\Java21JDK_Uninstall.log"
$ProductNamePattern = "Java SE Development Kit 21"  # Exact match pattern for Oracle JDK 21
$SilentArgs = "/qn /norestart"  # MSI silent uninstall arguments

# =========================
# LOGGING FUNCTION
# =========================
function Write-Log {
    param (
        [string]$Message,
        [string]$Level = "INFO"
    )
    $timestamp = Get-Date -Format "yyyy-MM-dd HH:mm:ss"
    $logEntry = "$timestamp [$Level] $Message"
    Add-Content -Path $LogFile -Value $logEntry
    Write-Output $logEntry
}

# =========================
# MAIN SCRIPT
# =========================
try {
    Write-Log "=== Starting Oracle Java 21 JDK 64-bit Uninstall ==="

    # Search registry for installed products
    $UninstallKeys = @(
        "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall",
        "HKLM:\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall"
    )

    $Found = $false

    foreach ($KeyPath in $UninstallKeys) {
        Get-ChildItem -Path $KeyPath -ErrorAction SilentlyContinue | ForEach-Object {
            $DisplayName = (Get-ItemProperty -Path $_.PSPath -ErrorAction SilentlyContinue).DisplayName
            $UninstallString = (Get-ItemProperty -Path $_.PSPath -ErrorAction SilentlyContinue).UninstallString

            if ($DisplayName -and $DisplayName -like "*$ProductNamePattern*") {
                Write-Log "Found: $DisplayName"
                Write-Log "Uninstall command: $UninstallString"

                if ($UninstallString) {
                    $Found = $true

                    # Handle MSI-based uninstall
                    if ($UninstallString -match "msiexec\.exe") {
                        $cmd = "$UninstallString $SilentArgs"
                    }
                    else {
                        # For EXE uninstallers, append silent flags if supported
                        $cmd = "$UninstallString /s"
                    }

                    Write-Log "Executing: $cmd"
                    $process = Start-Process -FilePath "cmd.exe" -ArgumentList "/c $cmd" -Wait -PassThru -WindowStyle Hidden

                    if ($process.ExitCode -eq 0) {
                        Write-Log "Uninstall successful for $DisplayName" "SUCCESS"
                    }
                    else {
                        Write-Log "Uninstall failed for $DisplayName with exit code $($process.ExitCode)" "ERROR"
                    }
                }
            }
        }
    }

    if (-not $Found) {
        Write-Log "No Oracle Java 21 JDK 64-bit installation found." "WARN"
    }

    Write-Log "=== Uninstall process completed ==="
}
catch {
    Write-Log "Unexpected error: $_" "ERROR"
}