O autor gosta muito do jogo, e ele próprio é o administrador de um pequeno servidor "apenas para amigos". Como de costume entre amadores, tudo é modulado no servidor, e isso implica em instabilidade do trabalho e como resultado da queda. Como o autor conhece Powershell melhor do que a localização das lojas em sua rua, ele decidiu criar "O melhor script para lançar o Minecraft 2020 ". O mesmo script serviu de base para o modelo no mercado Ruvds . Mas todas as fontes já estão no artigo. Agora, em ordem, como tudo aconteceu.Precisamos de equipes
Log alternativo
Depois de colocar mais alguns mods, descobri que o servidor parece travar sem declarar guerra. O servidor não gravou erros no arquivo latest.log ou depuração, e o console, que deveria gravar e interromper esse erro, foi fechado.Não quer escrever - não há necessidade. Temos o PowerShell com o cmdlet Tee-Object , que pega um objeto e o exibe em um arquivo e no console ao mesmo tempo..\handler.ps1 | Tee-Object .\StandardOutput.txt -Append
Dessa forma, o Powershell pegará o StandardOutput e o gravará em um arquivo. Não tente usar o Start-Process , pois ele retornará System.ComponentModel.Component, não StandardOutput e -RedirectStandardOutput impossibilitará a entrada no console, o que queremos evitar.Argumentos de lançamento
Colocando o mesmo par de mods, o autor notou que o servidor também não possui RAM. E isso precisa alterar os argumentos de inicialização. Em vez de alterá-los sempre no start.bat, que todos usam, basta usar este script.Como Tee-Object lê StandardOutput somente quando o executável é chamado “Right So”, você terá que criar outro script. Este script executará o próprio minecraft. Vamos começar com os argumentos.Para entrar em preguiça final no futuro, o script deve coletar argumentos de início em tempo real. Para fazer isso, comece procurando a versão mais recente do forge .$forge = ((Get-ChildItem | Where-Object Name -Like "forge*").Name | Sort-Object -Descending) | Select-Object -last 1
Com a ajuda do objeto de classificação, sempre levaremos o objeto com o maior dígito, não importa o quanto você os coloque lá. A preguiça final.Agora você precisa atribuir memória ao servidor. Para fazer isso, pegue a quantidade de memória do sistema e escreva sua quantidade em string.$ram = ((Get-CimInstance Win32_PhysicalMemory | Measure-Object -Property capacity -Sum).sum /1gb)
$xmx = "-Xms" + $ram + "G"
Reinício automático correto
O autor viu arquivos .bat de outras pessoas, mas não levou em consideração o motivo pelo qual o servidor foi parado. É inconveniente que, se você só precise alterar o arquivo mod ou excluir algo?Agora vamos reiniciar corretamente. O autor já se deparou com scripts estranhos que reiniciam o servidor, apesar de o servidor ter sido desligado. Usaremos o código de saída. Java usa 0 como uma conclusão bem-sucedida, portanto, vamos dançar.Primeiro, crie uma função que reiniciará o servidor se ele não for concluído.function Get-MinecraftExitCode {
do {
if ($global:Process.ExitCode -ne 0) {
Write-Log
Restart-Minecraft
}
else {
Write-Log
}
} until ($global:Process.ExitCode -eq 0)
}
O script permanecerá no loop até que o servidor do seu próprio console seja desligado normalmente usando o comando / stop.Se todos nós decidirmos automatizar, seria bom coletar a data de lançamento, a conclusão e o motivo da conclusão.Para fazer isso, escrevemos o resultado do processo inicial em uma variável. No script, fica assim:$global:Process = Start-Process -FilePath "C:\Program Files (x86)\common files\Oracle\Java\javapath_target_*\java.exe" -ArgumentList "$xmx -server -jar $forge nogui" -Wait -NoNewWindow -PassThru
E então escrevemos os resultados em um arquivo. Aqui está o que retorna para nós na variável:$global:Process.StartTime
$global:Process.ExitCode
$global:Process.ExitTime
Tudo isso usando Add-Content pode ser adicionado ao arquivo. Depois de pentear um pouco, obtemos um script e o chamamos de handler.ps1.Add-Content -Value "Start time:" -Path $Logfile
$global:Process.StartTime
Add-Content -Value "Exit code:" -Path $Logfile
$global:Process.ExitCode | Add-Content $Logfile
Add-Content -Value "Exit time:" -Path $Logfile
$global:Process.ExitTime | Add-Content $Logfile
Agora vamos executar o script com o lançamento do manipulador.Inicialização adequada
O autor deseja que um módulo inicie minecraft de várias versões a partir de qualquer caminho e também seja capaz de colocar logs em uma pasta específica.O problema é que o processo deve ser iniciado pelo usuário que está no sistema. Isso pode ser feito na área de trabalho ou no WinRm. Se você iniciar o servidor em nome do sistema ou mesmo do administrador, mas não fizer o login, o Server.jar nem poderá ler o eula.txt e iniciar.Podemos ativar o login automático no sistema adicionando três entradas ao registro.New-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name DefaultUserName -Value $Username -ErrorAction SilentlyContinue
New-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name DefaultPassword -Value $Password -ErrorAction SilentlyContinue
New-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name AutoAdminLogon -Value 1 -ErrorAction SilentlyContinue
Não é seguro. O login e a senha são indicados aqui em texto sem formatação, portanto, é necessário iniciar um usuário individual que tenha acesso no nível do usuário ou em um grupo ainda mais restrito para iniciar o servidor. Usar um administrador padrão para isso é altamente desencorajado.Com entrada automática resolvida. Agora você precisa registrar uma nova tarefa no servidor. Como executaremos o comando do Powershell, ele ficará assim:$Trigger = New-ScheduledTaskTrigger -AtLogOn
$User = "ServerAdmin"
$PS = New-ScheduledTaskAction -Execute 'PowerShell.exe" -Argument "Start-Minecraft -Type Forge -LogFile "C:\minecraft\stdout.txt" -MinecraftPath "C:\minecraft\"'
Register-ScheduledTask -TaskName "StartSSMS" -Trigger $Trigger -User $User -Action $PS -RunLevel Highest
Juntando o módulo
Agora vamos transformar tudo em módulos que podem ser usados posteriormente. Todo o código de scripts prontos está aqui, importe e use.Você pode usar tudo o que foi descrito acima separadamente, se não quiser se preocupar com os módulos.Iniciar minecraft
Primeiro, criaremos um módulo que apenas fará isso, executaremos um script que ouvirá e gravará a saída padrão.No bloco de parâmetros, ele pergunta de qual pasta iniciar o minecraft e onde colocar o log.Set-Location (Split-Path $MyInvocation.MyCommand.Path)
function Start-Minecraft {
[CmdletBinding()]
param (
[Parameter()]
[ValidateNotNullOrEmpty()]
[string]
$LogFile,
[Parameter(Mandatory)]
[ValidateSet('Vanilla', 'Forge')]
[ValidateNotNullOrEmpty()]
[string]
$Type,
[Parameter(Mandatory)]
[ValidateNotNullOrEmpty()]
[string[]]
$MinecraftPath
)
powershell.exe -file .\handler.ps1 -type $type -MinecraftPath $MinecraftPath | Tee-Object $LogFile -Append
}
Export-ModuleMember -Function Start-Minecraft
E você precisará executar minecraft assim:Start-Minecraft -Type Forge -LogFile "C:\minecraft\stdout.txt" -MinecraftPath "C:\minecraft\"
Agora vamos passar para o Handler.ps1 pronto para usar.Para que nosso script possa aceitar parâmetros quando chamado, também precisamos especificar um bloco de parâmetros. Observe que ele inicia o Oracle Java; se você usar uma distribuição diferente, será necessário alterar o caminho para o arquivo executável.param (
[Parameter()]
[ValidateNotNullOrEmpty()]
[string]$type,
[Parameter()]
[ValidateNotNullOrEmpty()]
[string]$MinecraftPath,
[Parameter()]
[ValidateNotNullOrEmpty()]
[string]$StandardOutput
)
Set-Location $MinecraftPath
function Restart-Minecraft {
Write-host "=============== Starting godlike game server ============"
$forge = ((Get-ChildItem | Where-Object Name -Like "forge*").Name | Sort-Object -Descending) | Select-Object -first 1
$ram = ((Get-CimInstance Win32_PhysicalMemory | Measure-Object -Property capacity -Sum).sum /1gb)
$xmx = "-Xms" + $ram + "G"
$global:Process = Start-Process -FilePath "C:\Program Files (x86)\common files\Oracle\Java\javapath_target_*\java.exe" -ArgumentList "$xmx -server -jar $forge nogui" -Wait -NoNewWindow -PassThru
}
function Write-Log {
Write-host "Start time:" $global:Process.StartTime
Write-host "Exit code:" $global:Process.ExitCode
Write-host "Exit time:" $global:Process.ExitTime
Write-host "=============== Stopped godlike game server ============="
}
function Get-MinecraftExitCode {
do {
if ($global:Process.ExitCode -ne 0) {
Restart-Minecraft
Write-Log
}
else {
Write-Log
}
} until ($global:Process.ExitCode -eq 0)
}
Get-MinecraftExitCode
Registrar-minecraft
O script praticamente repete o Start-Minecraft, exceto que ele registra apenas uma nova tarefa. Aceita os mesmos argumentos. O nome de usuário, se não especificado, assume o atual.function Register-Minecraft {
[CmdletBinding()]
param (
[Parameter()]
[ValidateNotNullOrEmpty()]
[string]
$LogFile,
[Parameter(Mandatory)]
[ValidateSet('Vanilla', 'Forge')]
[ValidateNotNullOrEmpty()]
[string]$Type,
[Parameter(Mandatory)]
[ValidateNotNullOrEmpty()]
[string]$MinecraftPath,
[Parameter(Mandatory)]
[ValidateNotNullOrEmpty()]
[string]$User,
[Parameter(Mandatory)]
[string]$TaskName = $env:USERNAME
)
$Trigger = New-ScheduledTaskTrigger -AtLogOn
$arguments = "Start-Minecraft -Type $Type -LogFile $LogFile -MinecraftPath $MinecraftPath"
$PS = New-ScheduledTaskAction -Execute "PowerShell" -Argument "-noexit -command $arguments"
Register-ScheduledTask -TaskName $TaskName -Trigger $Trigger -User $User -Action $PS -RunLevel Highest
}
Export-ModuleMember -Function Register-Minecraft
Register-autologon
No bloco de parâmetros, o script aceita o parâmetro Nome de usuário e Senha. Se o nome de usuário não foi especificado, o nome do usuário atual é usado.function Set-Autologon {
param (
[Parameter(
HelpMessage="Username for autologon")]
$Username = $env:USERNAME,
[Parameter(Mandatory=$true,
HelpMessage="User password")]
[ValidateNotNullOrEmpty()]
$Password
)
$i = Get-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon"
if ($null -eq $i) {
New-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name DefaultUserName -Value $Username
New-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name DefaultPassword -Value $Password
New-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name AutoAdminLogon -Value 1
Write-Verbose "Set-Autologon will enable user auto logon."
}
else {
Set-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name DefaultUserName -Value $Username
Set-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name DefaultPassword -Value $Password
Set-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -Name AutoAdminLogon -Value 1
}
Write-Verbose "Autologon was set successfully."
}
A execução desse script se parece com o seguinte:Set-Autologon -Password "PlaintextPassword"
Como usar
Agora vamos considerar como o próprio autor usa tudo isso. Como implantar o servidor público Minecraft no Windows. Vamos começar desde o começo.1. Crie um usuário$pass = Get-Credential
New-LocalUser -Name "MinecraftServer" -Password $pass.Password -AccountNeverExpires -PasswordNeverExpires -UserMayNotChangePassword
2. Registre a tarefa de execução do script.Vocêpode se registrar usando o módulo, da seguinte maneira:Register-Minecraft -Type Forge -LogFile "C:\minecraft\stdout.txt" -MinecraftPath "C:\minecraft\" -User "MInecraftServer" -TaskName "MinecraftStarter"
Ou use as ferramentas padrão:$Trigger = New-ScheduledTaskTrigger -AtLogOn
$User = "ServerAdmin"
$PS = New-ScheduledTaskAction -Execute 'PowerShell.exe" -Argument "Start-Minecraft -Type Forge -LogFile "C:\minecraft\stdout.txt" -MinecraftPath "C:\minecraft\"'
Register-ScheduledTask -TaskName "StartSSMS" -Trigger $Trigger -User $User -Action $PS -RunLevel Highest
3. Ligue o login automático ao sistema e reinicie a máquinaSet-Autologon -Username "MinecraftServer" -Password "Qw3"
Conclusão
O autor fez o script, inclusive para si mesmo, portanto, ficará feliz em ouvir suas sugestões para melhorar o script. O autor espera que todo esse código seja pelo menos minimamente útil para você, e o artigo é interessante.