質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

90.34%

  • C#

    7680questions

    C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

  • Visual Studio

    1987questions

    Microsoft Visual StudioはMicrosoftによる統合開発環境(IDE)です。多種多様なプログラミング言語に対応しています。

  • SSH

    588questions

    SSH(Secure Shell)は、セキュアチャネルを通してデータを交換するためのネットワークプロトコルです。リモートサーバーへのコマンド実行やファイル転送を行う時に一般的に使用されます。

VSでボタン2つを使ってssh接続の開始,終了を指示したいです.

解決済

回答 1

投稿

  • 評価
  • クリップ 0
  • VIEW 396

inupisu

score 3

 前提・実現したいこと

VS2017(C#)のフォームアプリの中でボタンを2つ配置し,1つ目でssh接続の開始,値の取得を行い,2爪のボタンで取得の終了,ssh接続の終了を行えるプログラムをかきたいです.

ここに質問の内容を詳しく書いてください
VS(C#)でフォームアプリを作成しました.内容としては,ボタンを押すとraspberry piにssh接続をし,GPIOの値を取,labelに表示するというものです.その中で,もう1つボタンを配置し,ssh接続終了の処理を加えたいです.今は,ボタン1で接続の開始,値の取得,接続の終了を行っています.2つめのボタンの中に接続を終了させる処理を書き込んだのですが,エラーが発生してしまい,できません..そこで詳しい方にアドバイスをいただきたく質問させていただきました.

 発生している問題・エラーメッセージ

構文的なエラーはないのですが,ボタン1を押すと,ssh接続が開始され値を取得します.しかし,ボタン1を終了させていないためか,ボタン2を押しても反応しません.  ボタン2の中で,ssh.Disconnectを行うと,現在のコンテキストに"ssh"という名前は存在しませんというエラーメッセージが表示されてしまいます.

 該当のソースコード

sing System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using Renci.SshNet;
using System.Diagnostics;


namespace sw20180626App
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        // コネクション情報
        int i = 0;

        private void button1_Click(object sender, EventArgs e)
        {
            try
            {

                while (i == 0)
                {
                    // 接続先のホスト名またはIPアドレス
                    var hostNameOrIpAddr = "raspberrypi.local";

                    // 接続先のポート番号
                    var portNo = 22;

                    // ログインユーザー名
                    var userName = "pi";

                    // ログインパスワード
                    var passWord = "raspberry";

                    // コネクション情報
                    ConnectionInfo info = new ConnectionInfo(hostNameOrIpAddr, portNo, userName,
                    new AuthenticationMethod[] {
                        new PasswordAuthenticationMethod(userName, passWord)
                        /* PrivateKeyAuthenticationMethod("キーの場所")を指定することでssh-key認証にも対応 */
                    }
                    );

                    // クライアント作成
                    SshClient ssh = new SshClient(info);

                    // 接続開始
                    ssh.Connect();

                    if (ssh.IsConnected)
                    {
                        // 接続に成功した(接続状態である)
                        Debug.WriteLine("[OK] SSH Connection succeeded!!");
                    }
                    else
                    {
                        // 接続に失敗した(未接続状態である)
                        Debug.WriteLine("[NG] SSH Connection failed!!");
                        return;
                    }
                    // 送信したいコマンドを変数に入れる
                    var commandString = "gpio -g read 4 ";
                    var commandString2 = "gpio -g read 9";
                    var commandString3 = "gpio -g read 27";


                    // コマンドを作成する
                    SshCommand cmd = ssh.CreateCommand(commandString);
                    SshCommand cmd2 = ssh.CreateCommand(commandString2);
                    SshCommand cmd3 = ssh.CreateCommand(commandString3);

                    // コマンドを実行する

                    Console.WriteLine("[CMD] {0}", commandString);
                    Console.WriteLine("[CMD] {0}", commandString2);
                    Console.WriteLine("[CMD] {0}", commandString3);
                    cmd.Execute();
                    cmd2.Execute();
                    cmd3.Execute();
                    // 結果を変数に入れる
                    var stdOut = cmd.Result;
                    var stdErr = cmd.Error;
                    var stdOut2 = cmd2.Result;
                    var stdErr2 = cmd2.Error;
                    var stdOut3 = cmd3.Result;
                    var stdErr3 = cmd3.Error;

                    // 終了コードを表示する
                    Console.WriteLine("終了コード:{0}", cmd.ExitStatus);
                    Console.WriteLine("終了コード:{0}", cmd2.ExitStatus);
                    Console.WriteLine("終了コード:{0}", cmd3.ExitStatus);


                    // 標準出力を表示する
                    if (stdOut != string.Empty)
                    {
                        Console.WriteLine("標準出力:");
                        Debug.WriteLine(stdOut);
                        label3.Text = "OK";
                        Console.WriteLine("---------");
                    }
                    if (stdOut2 != string.Empty)
                    {
                        Console.WriteLine("標準出力:");
                        Debug.WriteLine(stdOut2);
                        label4.Text = "OK";
                        Console.WriteLine("---------");
                    }
                    if (stdOut3 != string.Empty)
                    {
                        Console.WriteLine("標準出力:");
                        Debug.WriteLine(stdOut3);
                        label5.Text = "OK";
                        Console.WriteLine("---------");
                    }


                    // エラー出力を表示する
                    if (cmd.ExitStatus != 0 && stdErr != string.Empty)
                    {
                        Console.WriteLine("標準エラー出力:");
                        Debug.WriteLine(stdErr);
                        Console.WriteLine("----------------");
                    }
                    if (cmd2.ExitStatus != 0 && stdErr != string.Empty)
                    {
                        Console.WriteLine("標準エラー出力:");
                        Debug.WriteLine(stdErr2);
                        Console.WriteLine("----------------");
                    }
                    if (cmd3.ExitStatus != 0 && stdErr != string.Empty)
                    {
                        Console.WriteLine("標準エラー出力:");
                        Debug.WriteLine(stdErr3);
                        Console.WriteLine("----------------");
                    }
                    ssh.Disconnect();
                }

            catch (Exception ex)
            {
                // エラー発生時
                Console.WriteLine(ex);
                throw ex;
            }
        }

        private void button2_Click(object sender, EventArgs e)
        {
            i = 1;
            label3.Text = "------";
            label4.Text = "------";
            label5.Text = "------";

        }
    }    

}

 補足情報(FW/ツールのバージョンなど)

VSは2017,言語はC#,raspberry piは3のModel Bを使用しております.初心者でプログラム自体がすごく汚いと思います.3つの値を取得することと,ボタン1でssh接続を開始したらボタン2が押されるまで,ずっと値を取得し続けるという条件を満たせるプログラムの書き方がわかりません.. どなたか詳しい方アドバイスいただけたら嬉しいです.よろしくお願いいたします!

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 1

checkベストアンサー

0

  1. まず、タイマコンポーネントを追加し、インターバルをデータ取得間隔、例えば500(ms)とかに設定
  2. 開始ボタンを押したら、SSH接続を開始し、タイマを起動させます
    このとき、繰り返し開始ボタンを押されるとワケワカメになるので、ボタンをディセーブルにするなどします
  3. タイマイベントではデータ取得、表示処理を行います
  4. で、もう一つのボタンで、そのタイマを止め、SSH接続を切る処理を行います
    当然ながら、このボタンを繰り返し押されるとワケワカメになるのでそれなりの処理を。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/06/25 14:36

    回答ありがとうございます! タイマを使うという考えは浮かびませんでした... ありがとうございます!! このボタンを2つ使って,開始と終了を分ける処理を行いたいと思い,プログラムを作成しているときからわからなかったことが1つあります. button1でtry~catchの部分のssh接続部分 + this.timer1.Start();でタイマーイベントの発生を書きました. そしてタイマイベントの中では,先ほどのプログラムのコマンド作成や実行,値の取得,表示を書きました.最後にbutton2にthis.timer1.Stop(); + ssh.Disconnect();と書き込みました. コマンド作成や,接続終了の部分で,SshCommand cmd = ssh.CreateCommand(commandString);やssh.Disconnect();の行のsshと部分にエラーが表示されてしまいます. エラー内容は,現在のコンテキストにsshという名前は存在しませんです. この部分以外はエラーが出ていないのですが,この部分の改善ができません. もしよろしければアドバイスいただきたいです. よろしくお願いいたします.

    キャンセル

  • 2018/06/25 22:53

    > SshClient ssh = new SshClient(info);

    これは、そのブロックの中だけしか有効ではありません。

    > public partial class Form1 : Form
    > {

    の直下に書いてください

    キャンセル

  • 2018/06/26 10:18

    回答ありがとうございます! public partial class Form1 : Form
    {
    SshClient ssh = new SshClient(info); と記述したのですが,infoの部分がエラーになってしまいます. ConnectionInfo info のコネクション情報も直下においてみたのですが,今度はコネクション情報の中の(userName,password)などがエラーになってしまうという状態です... 置く場所が間違っていますでしょうか?

    キャンセル

  • 2018/06/26 10:27

    SshClient ssh;
    だけを関数の外に出して、インスタンスの生成を関数の中ですればいいですが、
    その他のところもいろいろ問題がありそうなソースとなってます

    C#の基本的な知識がおぼつかないようなんで、入門サイトなどで学び直されてはどうでしょう。

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 90.34%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

同じタグがついた質問を見る

  • C#

    7680questions

    C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

  • Visual Studio

    1987questions

    Microsoft Visual StudioはMicrosoftによる統合開発環境(IDE)です。多種多様なプログラミング言語に対応しています。

  • SSH

    588questions

    SSH(Secure Shell)は、セキュアチャネルを通してデータを交換するためのネットワークプロトコルです。リモートサーバーへのコマンド実行やファイル転送を行う時に一般的に使用されます。