Beni güldüren bir sorunum var.PHP Telnet/SSH dinamik giriş
Bir yönlendiriciye CLI girişini otomatikleştirmeye çalışıyorum ve bir web sayfası aracılığıyla elde edilen bazı komutları çalıştırıyorum. Ancak yönlendiricinin telnet veya SSH'nin etkin olup olmadığını bilmiyorum (biri, diğeri veya her ikisi de olabilir) ve erişim elde etmeye çalışmam gereken olası kullanıcı adı/şifre kombinasyonlarım var.
Oh, ve aygıttaki protokol türünü veya kimlik bilgilerini değiştiremiyorum, bu gerçekten bir seçenek değil.
Bilinen bir protokol ve giriş kimlik bilgisine sahip bir yönlendiriciye nasıl giriş yapılabileceğini ve gerekli komutları (aşağıda yer alan) nasıl çalıştıracağımı anlayabiliyorum, ancak eğer çalışmak için bir if/else bloğu kullanmalıyım bilmiyorum telnet/ssh kararları aracılığıyla veya bir anahtar ifadesi daha iyi olabilir mi? PHP içinde Expect kullanmak daha kolay bir yol olabilir mi?
function tunnelRun($commands,$user,$pass, $yubi){
$cpeIP = "1.2.3.4";
$commands_explode = explode("\n", $commands);
$screenOut = "";
$ssh = new Net_SSH2('router_jumphost');
if (!$ssh->login($user, $pass . $yubi)) {
exit('Login Failed');
}
$ssh->setTimeout(2);
$ssh->write("ssh -l username $cpeIP\n");
$ssh->read("assword:");
$ssh->write("password\n");
$ssh->read("#");
$ssh->write("\n");
$cpePrompt = $ssh->read('/.*[#|>]/', NET_SSH2_READ_REGEX);
$cpePrompt = str_replace("\n", '', trim($cpePrompt));
$ssh->write("config t\n");
foreach ($commands_explode as $i) {
$ssh->write("$i\n"); // note the "\n"
$ssh->setTimeout(2);
$screenOut .= $ssh->read();
}
$ssh->write("end\n");
$ssh->read($cpePrompt);
$ssh->write("exit\n");
echo "Router Update completed! Results below:<br><br>";
echo "<div id=\"text_out\"><textarea style=\" border:none; width: 700px;\" rows=\"20\">".$screenOut."</textarea></div>";
Güncelleme:
Bir süre/switch döngüsü oldu gitti çözüm. Ben Expect rotası gitmişti, ama sunucumda PHP'ye entegre Expect modülünü alma konusunda sorun yaşamaya devam ettim (Windows kutusu.) Eğer bir Unix/Linux sunucusu kullanıyor olsaydım, bunu başarmanın en kolay yolu olurdu. . Şimdilik bir çalışma demosuna girdim, bu yüzden hala durum ifadelerinden eksik olan birçok hata var ve hataların hala çözülmesi gerekiyor, ama temel fikir var. Hala while döngüsünün üstündeki eşleşmeyi yapmak için preg_match ifadelerini biraz daha fazla hareket ettirmek istiyorum (bu yüzden farklı preg_match satırları ile tüm vaka bölümünü spam yapmıyorum), ancak bu benden daha fazla iş olabilir şimdi istiyorum. Umarım bu aynı şeyi yapmaya çalışan başkalarına yardımcı olabilir!
<?php
include('Net/SSH2.php');
define('NET_SSH2_LOGGING', NET_SSH2_LOG_COMPLEX);
ini_set('display_errors', 1);
$conn = new Net_SSH2('somewhere.outthere.com');
if (!$conn->login($user, $pass . $yubi)) {
exit('Login Failed');
}
$prompt = "Testing#";
$conn->setTimeout(2);
$conn->write("PS1=\"$prompt\"");
$conn->read();
$conn->write("\n");
$screenOut = $conn->read();
//echo "$screenOut is set on the shell<br><br>";
echo $login_db[3][0]. " ". $login_db[3][1];
$logged_in = false;
$status = "SSH";
$status_prev = "";
$login_counter = 0;
while (!$logged_in && $login_counter <=3) {
switch ($status) {
case "Telnet":
break;
case "SSH":
$conn->write("\n");
$conn->write("ssh -l " . $login_db[$login_counter][0] . " $cpeIP\n");
$status_prev = $status;
$status = $conn->read('/\n([.*])$/', NET_SSH2_READ_REGEX);
break;
case (preg_match('/Permission denied.*/', $status) ? true : false):
$conn->write(chr(3)); //Sends Ctrl+C
$status = $conn->read();
if (strstr($status, "Testing#")) {
$status = "SSH";
$login_counter++;
break;
} else {
break 2;
}
case (preg_match('/[pP]assword:/', $status) ? true : false):
$conn->write($login_db[$login_counter][1] . "\n");
$status_prev = $status;
$status = $conn->read('/\n([.*])$/', NET_SSH2_READ_REGEX);
break;
case (preg_match('/yes\/no/', $status) ? true : false):
$conn->write("yes\n");
$status_prev = $status;
$status = $conn->read('/\n([.*])$/', NET_SSH2_READ_REGEX);
break;
case (preg_match('/(^[a-zA-Z0-9_]+[#]$)|(>)/', $status,$matches) ? true : false):
$conn->write("show version\n");
$status = $conn->read(">");
if(preg_match('/ADTRAN|Adtran|Cisco/', $status)? true:false){
$logged_in = true;
break;
}
default:
echo "<br>Something done messed up! Exiting";
break 2;
}
//echo "<pre>" . $conn->getLog() . "</pre>";
}
if ($logged_in === true) {
echo "<br> Made it out of the While loop cleanly";
} else {
echo "<br> Made it out of the While loop, but not cleanly";
}
echo "<pre>" . $conn->getLog() . "</pre>";
$conn->disconnect();
echo "disconnected cleanly";
}
?>
'if' '' '' '' '' '' '' '' '' '' '' '' '' '' 'blokları' '' '' '' 'blokları hemen hemen aynıdır. –