====== Applicazione Android per connessione SSH ======
Autore: **//Fabio Di Matteo//** \\ Ultima revisione: **//20/12/2017 - 09:38//** \\ \\
In questo articolo vedremo come fare uso di una libreria esterna ([[http://www.jcraft.com/jsch/|Ssch]]) per la connessione ad un server ssh, come usare i thread e come manipolare i widget da un thread che non รจ quella della view .
===== Includere libreria esterna Jsch nel nostro progetto con Android Studio=====
* Per prima cosa dobbiamo includere nel nostro progetto il file jar della libreria spostandolo nella cartella **libs** della nostra applicazione.
* Click sul file jar in android studio e scegliere **Aggiungi come libreria**
* Controllare che sia stata inclusa in **build.gradle**
Maggiori info: [[https://stackoverflow.com/questions/25610727/adding-external-library-in-android-studio|Adding external library in Android studio]]
===== Codice (versione bloccante della gui)=====
package com.test.fabio.sshtest;
import android.os.AsyncTask;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
//Per jsch
import com.jcraft.jsch.*;
import java.io.*;
import java.util.Properties;
//widget
import android.widget.TextView;
import static android.os.SystemClock.sleep;
class sshCon extends Thread{
/**
* JSch Example Tutorial
* Java SSH Connection Program
*/
public String status="";
public String Err="";
public void run() {
/*Edit this*/
String host="192.168.1.61";
String user="user";
String password="pass";
String command1="echo 'Ciao Mondo' > /home/user/Desktop/hello_world.txt";
int port=22;
try{
status="";
Err="";
java.util.Properties config = new java.util.Properties();
config.put("StrictHostKeyChecking", "no");
JSch jsch = new JSch();
Session session=jsch.getSession(user, host, port);
session.setPassword(password);
session.setConfig(config);
session.connect();
System.out.println("Connected");
Channel channel=session.openChannel("exec");
((ChannelExec)channel).setCommand(command1);
channel.setInputStream(null);
((ChannelExec)channel).setErrStream(System.err);
InputStream in=channel.getInputStream();
channel.connect();
byte[] tmp=new byte[1024];
while(true){
while(in.available()>0){
int i=in.read(tmp, 0, 1024);
if(i<0)break;
System.out.print(new String(tmp, 0, i));
}
if(channel.isClosed()){
System.out.println("exit-status: "+channel.getExitStatus());
break;
}
try{Thread.sleep(1000);}catch(Exception ee){}
}
channel.disconnect();
session.disconnect();
System.out.println("DONE");
//Connessione avvenuta con successo
status="OK";
}catch(Exception e){
e.printStackTrace();
status="ERR";
Err=e.toString();
}
}
}
public class MainActivity extends AppCompatActivity {
TextView txtOut ;
public void ssh0(View view)
{
//Avvio il thread per la connessione ssh
sshCon con = new sshCon();
Thread t = new Thread(con);
t.start();
//Aspetto che il thread termini
while(t.isAlive()) sleep(500);
//Stampo l'esito della connessione
if (!con.Err.isEmpty())
{
txtOut.setText("Impossibile connettersi...! \n\n");
txtOut.append(con.Err);
}else{
txtOut.setText("Connessione: "+con.status.toString()+"\n\n");
txtOut.append("Connessione avvenuta con successo!");
}
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
txtOut = findViewById(R.id.txtOut);
}
}//MainActivity
===== Interfaccia =====
===== Codice versione non bloccante della Gui =====
In questa versione dell'app la gui non viene bloccata dal thread che esegue la connesione ssh. Notate l'utilizzo di **runOnUiThread()** per manippolare i widget della view da un altro thread. Adesso , inoltre, **la classe SshCon risiede dentro la classe MainActivity** .
package com.test.fabio.sshtest;
import android.os.AsyncTask;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
//Per jsch
import com.jcraft.jsch.*;
import java.io.*;
import java.util.Properties;
//widget
import android.widget.TextView;
public class MainActivity extends AppCompatActivity {
TextView txtOut ;
public void ssh0(View view)
{
txtOut.setText("Connessione in corso ... \n\n");
//Avvio il thread per la connessione ssh
sshCon con = new sshCon();
Thread t = new Thread(con);
t.start();
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
txtOut = findViewById(R.id.txtOut);
}
class sshCon extends Thread{
/**
* JSch Example Tutorial
* Java SSH Connection Program
*/
private String Err="";
public void run() {
/*Edit this*/
String host="192.168.1.186";
String user="user";
String password="pass";
String command1="echo 'Ciao Mondo' > /home/user/Desktop/hello_world.txt";
int port=22;
try{
Err="";
java.util.Properties config = new java.util.Properties();
config.put("StrictHostKeyChecking", "no");
JSch jsch = new JSch();
Session session=jsch.getSession(user, host, port);
session.setPassword(password);
session.setConfig(config);
session.connect();
System.out.println("Connected");
Channel channel=session.openChannel("exec");
((ChannelExec)channel).setCommand(command1);
channel.setInputStream(null);
((ChannelExec)channel).setErrStream(System.err);
InputStream in=channel.getInputStream();
channel.connect();
byte[] tmp=new byte[1024];
while(true){
while(in.available()>0){
int i=in.read(tmp, 0, 1024);
if(i<0)break;
System.out.print(new String(tmp, 0, i));
}
if(channel.isClosed()){
System.out.println("exit-status: "+channel.getExitStatus());
break;
}
try{Thread.sleep(1000);}catch(Exception ee){}
}
channel.disconnect();
session.disconnect();
System.out.println("DONE");
//Connessione avvenuta con successo
runOnUiThread(new Runnable() {
@Override
public void run() {
txtOut.setText("Connessione avvenuta con successo!");
}
});
}catch(Exception e){
//Errore nella connessione
e.printStackTrace();
Err=e.toString();
runOnUiThread(new Runnable() {
@Override
public void run() {
txtOut.setText("Connessione Fallita!\n\n");
txtOut.append(Err);
}
});
}
}
}
}//MainActivity