חיבור SSH עם Java

ג'אווה טופ

רק הכרזתי על החדש למד אביב קורס, המתמקד ביסודות האביב 5 ומגף האביב 2:

>> בדוק את הקורס

1. הקדמה

SSH, המכונה גם Secure Shell או Secure Socket Shell, הוא פרוטוקול רשת המאפשר למחשב אחד להתחבר בצורה מאובטחת למחשב אחר ברשת לא מאובטחת. במדריך זה נראה כיצד ליצור חיבור לשרת SSH מרוחק עם Java באמצעות ספריות JSch ו- Apache MINA SSHD.

בדוגמאות שלנו, נפתח תחילה את חיבור ה- SSH, לאחר מכן נבצע פקודה אחת, נקרא את הפלט ונכתוב אותו למסוף ולבסוף נסגור את חיבור ה- SSH. נשמור על קוד הדוגמה פשוט ככל האפשר.

2. JSch

JSch הוא יישום ה- Java של SSH2 המאפשר לנו להתחבר לשרת SSH ולהשתמש בהעברת יציאות, העברת X11 והעברת קבצים. כמו כן, הוא מורשה תחת רישיון סגנון BSD ומספק לנו דרך קלה ליצור חיבור SSH עם Java.

ראשית, בואו נוסיף את התלות JSch Maven שלנו pom.xml קוֹבֶץ:

 com.jcraft jsch 0.1.55 

2.1. יישום

כדי ליצור חיבור SSH באמצעות JSch, אנו זקוקים לשם משתמש, סיסמה, כתובת אתר מארחת ויציאת SSH. יציאת SSH המוגדרת כברירת מחדל היא 22, אך יכול לקרות שנגדיר את השרת לשימוש ביציאה אחרת לחיבורי SSH:

רשימת חללים סטטית ציבורית FolderStructure (שם משתמש מחרוזת, סיסמת מחרוזת, מארח מחרוזת, יציאת int, פקודת מחרוזת) זורק חריג {מושב מושב = null; ChannelExec channel = null; נסה {session = new JSch (). getSession (שם משתמש, מארח, יציאה); session.setPassword (סיסמה); session.setConfig ("StrictHostKeyChecking", "no"); session.connect (); channel = (ChannelExec) session.openChannel ("exec"); channel.setCommand (פקודה); ByteArrayOutputStream responsStream = ByteArrayOutputStream חדש (); channel.setOutputStream (responseStream); channel.connect (); בעוד (channel.isConnected ()) {Thread.sleep (100); } מחרוזת responseString = מחרוזת חדשה (responseStream.toByteArray ()); System.out.println (responseString); } סוף סוף {if (session! = null) {session.disconnect (); } אם (channel! = null) {channel.disconnect (); }}}

כפי שאנו רואים בקוד, ראשית אנו יוצרים הפעלת לקוח ומגדירים אותה לחיבור לשרת SSH שלנו. לאחר מכן אנו יוצרים ערוץ לקוח המשמש לתקשורת עם שרת SSH בו אנו מספקים סוג ערוץ - במקרה זה, ביצוע, כלומר נעביר פקודות מעטפת לשרת.

כמו כן, עלינו להגדיר את זרם הפלט של הערוץ שלנו בו תיכתב תגובת השרת. לאחר שנקים את החיבור באמצעות ה- channel.connect () השיטה, הפקודה מועברת והתגובה שהתקבלה נכתבת על המסוף.

בוא נראה כיצד להשתמש בפרמטרים שונים של תצורה ש- JSch מציעה:

  • StrictHostKeyChecking - זה מציין אם היישום יבדוק אם ניתן למצוא את המפתח הציבורי המארח בקרב מארחים ידועים. כמו כן, ערכי הפרמטרים הזמינים הם לִשְׁאוֹל, כן, ו לא, איפה לִשְׁאוֹל הוא ברירת המחדל. אם הגדרנו נכס זה ל- כן, JSch לעולם לא יוסיף אוטומטית את מפתח המארח ל- ידועים_מארחים קובץ, והוא יסרב להתחבר למארחים שמפתח המארח שלהם השתנה. זה מאלץ את המשתמש להוסיף ידנית את כל המארחים החדשים. אם הגדרנו את זה ל לא, JSch יוסיף אוטומטית מפתח מארח חדש לרשימת המארחים הידועים
  • compression.s2c - מציין אם להשתמש בדחיסה עבור זרם הנתונים מהשרת ליישום הלקוח שלנו. הערכים הזמינים הם זליב ו אף אחד כאשר השני הוא ברירת המחדל
  • compression.c2s - מציין אם להשתמש בדחיסה עבור זרם הנתונים בכיוון שרת הלקוח. הערכים הזמינים הם זליב ו אף אחד כאשר השני הוא ברירת המחדל

זה חשוב ל סגור את ההפעלה ואת ערוץ SFTP לאחר סיום התקשורת עם השרת כדי למנוע דליפות זיכרון.

3. אפאצ'י MINA SSHD

Apache MINA SSHD מספק תמיכה ב- SSH ליישומים מבוססי Java. ספרייה זו מבוססת על Apache MINA, ספריית IO אסינכרונית ניתנת להרחבה וביצועים גבוהים.

בואו נוסיף את התלות של Apache Mina SSHD Maven:

 org.apache.sshd sshd-core 2.5.1 

3.1. יישום

בואו נראה את דוגמת הקוד של חיבור לשרת SSH באמצעות Apache MINA SSHD:

רשימת חללים סטטית ציבוריתFolderStructure (שם משתמש מחרוזת, סיסמת מחרוזת, מארח מחרוזת, יציאת int, זמן ברירת מחדל זמן TimeoutSeconds, מחרוזת מחרוזת) זורק IOException {SshClient client = SshClient.setUpDefaultClient (); client.start (); נסה (ClientSession session = client.connect (שם משתמש, מארח, יציאה). verify (defaultTimeoutSeconds, TimeUnit.SECONDS) .getSession ()) {session.addPasswordIdentity (סיסמה); session.auth (). אמת (defaultTimeoutSeconds, TimeUnit.SECONDS); נסה (ByteArrayOutputStream responseStream = ByteArrayOutputStream חדש (); ערוץ ClientChannel = session.createChannel (Channel.CHANNEL_SHELL)) {channel.setOut (responseStream); נסה את {channel.open (). אמת (defaultTimeoutSeconds, TimeUnit.SECONDS); נסה (OutputStream pipedIn = channel.getInvertedIn ()) {pipedIn.write (command.getBytes ()); pipedIn.flush (); } channel.waitFor (EnumSet.of (ClientChannelEvent.CLOSED), TimeUnit.SECONDS.toMillis (defaultTimeoutSeconds)); String responseString = מחרוזת חדשה (responseStream.toByteArray ()); System.out.println (responseString); } סוף סוף {channel.close (false); }}} סוף סוף {client.stop (); }}

כשעובדים עם Apache MINA SSHD, יש לנו רצף אירועים די דומה לזה של JSch. ראשית, אנו מקשרים חיבור לשרת SSH באמצעות ה- SshClient מופע כיתתי. אם נאתחל את זה עם SshClient.setupDefaultClient (), נוכל לעבוד עם המופע בעל תצורת ברירת המחדל המתאימה לרוב מקרי השימוש. זה כולל צפנים, דחיסה, מקש MAC, חילופי מפתח וחתימות.

לאחר מכן ניצור ClientChannel ולצרף את ByteArrayOutputStream אליו, כדי שנשתמש בו כזרם תגובה. כפי שאנו רואים, SSHD דורש פסק זמן מוגדר לכל פעולה. זה גם מאפשר לנו להגדיר כמה זמן זה יחכה לתגובת השרת לאחר העברת הפקודה באמצעות Channel.waitFor () שיטה.

חשוב לשים לב לכך SSHD יכתוב פלט קונסולה שלם לזרם התגובה. JSch תעשה זאת רק עם תוצאת ביצוע הפקודה.

תיעוד מלא אודות Apache Mina SSHD זמין במאגר GitHub הרשמי של הפרויקט.

4. מסקנה

מאמר זה המחיש כיצד ליצור חיבור SSH עם Java באמצעות שתיים מספריות Java הזמינות - JSch ו- Apache Mina SSHD. הראינו גם כיצד להעביר את הפקודה לשרת המרוחק ולקבל את תוצאת הביצוע. כמו כן, דוגמאות קוד מלאות זמינות ב- GitHub.

תחתית Java

רק הכרזתי על החדש למד אביב קורס, המתמקד ביסודות האביב 5 ומגף האביב 2:

>> בדוק את הקורס