追加読書

追加読書

Raspberry Pi(Stretch)を再起動すると、デーモンが/run/user/1000存在しないため起動しません。これは私のユニットファイルです:

[Unit]
Description=SBFspot Upload Daemon

[Service]
User=pi
Type=forking
TimeoutStopSec=60
ExecStart=/usr/local/bin/sbfspot.3/SBFspotUploadDaemon -p /run/user/1000/sbfspotupload.pid 2>&1> /dev/null
PIDFile=/run/user/1000/sbfspotupload.pid
Restart=no
RestartSec=15
SuccessExitStatus=SIGKILL

[Install]
WantedBy=default.target

数回やり直してから正しく動作するように設定しましたが、Restart=on-failure実際には私が望むものではありません。デーモンは/run/user/1000インストールを待ちたいです。試しましたが、After=run-user-1000.mountまだ失敗しました。

これは可能ですか、それともこだわるべきですかRestart=on-failure

ベストアンサー1

/run/user/1000もちろん、ユーザー#1000がログインするまで、または明示的にxyrユーザー固有のサービス管理を開始するまでは存在しません。これを使用するための完全なメカニズムが存在してはいけません。

このプログラムのバグ #215あなたが思うよりもはるかに深いです。このサービス単位ファイルは非常に間違っています。プログラム自体の動作も同様である。。システム化されたサービスユニットの基本を実際に理解していないことに基づいている貨物愛好家のプログラミングがたくさんあります。

  • サービスユニットはシェルスクリプトではありません。 システムマニュアルする説明する。ここで設定すると、サービスプログラムはいくつかの追加パラメータでExecStart実行されます。2>&1>/dev/null
  • サービス管理者は、1つのサービスのみが実行されていることを確認しました。 ここに追加されたコードはすべて不要なゴミです。
  • 不安定で危険なPIDファイルメカニズムはいいえ使用。 適切なサービス管理には席がありません。
  • サービスマネージャはデーモンコンテキストでサービスコールも処理します。 他の多くのコードmain()は次のとおりです。返品悪魔化エラーに基づく不要なゴミ。
    • プログラムをfork()まったく実行してはならず、サービス準備メカニズムを指定してはいけませんType=forking。現実世界の多くのプログラムと同様に、いいえまず、フォーク準備プロトコルについて話しましょう。
    • 計画はすでにスーパーユーザーとして実行します。 User=root不要で、サービスを実際に再設計する必要があります。いいえスーパーユーザー権限で実行する必要がありますが、代わりに権限のない専用サービスアカウントのスポンサーとして実行されます。
    • サービスマネージャーすでに標準出力とエラーを記録し、このプログラムよりも優れた操作を行います。この独自のロギングシステムは、ファイルシステム全体が満たされるまでログファイルを増やし、スーパーユーザー用に予約されているすべての緊急スペースを消費します。
    • あなたのログは標準エラーであり、C ++でstd::clog
    • 実際、fork()標準エラーにリダイレクトされるすべてのコード使用しないでください。サービス管理ハンドルみんなセッションリーダーから作業ディレクトリへ、umaskから標準I / Oに移動し、正しく実行されます。このアプリはそうしませんし、それを試してはいけません。どのサービスマネージャで使用したときの様子です。

      Boostから得たすべてが間違っています。

  • 3つのサービスユニットは不要なメンテナンスコストです。 設定だけがAfter異なり、1つにマージできます。
  • 失礼な解雇は成功ではありません。 あることを考えるとすでにシャットダウン時のファイルクリーンアップに関する問題SuccessExitStatus=SIGKILLはバグです。通常の終了は正常に渡され、例外的なものと見なされるべきですSIGTERMSIGKILL(もちろん、outputすでに説明したように、完全なファイルメカニズムは正しく実装されていないローカルロギングメカニズムなので、サービス管理では使用しないでください。)これはsystemdのデフォルト設定です。
  • データベースオブジェクトやその他のコンテンツに対してデストラクタを実行する必要があります。main()去らないでくださいexit()

正しく実装され、サービスマネージャ(daemontools、runit、s6、nosh、systemdなど)で実行されるデーモンははるかに短いです。

//今までと同じ
無効 pvo_upload(無効)
{
    std::clog << "デーモンプロセスの開始..." << std::endl;

    公共サービスコード();

    std::clog << "デーモンの停止..." << std::endl;
}

int main(int argc, char *argv[])
{
    整数c;
    const char *config_file = "";

    /* コマンドラインの解析*/
    同時に(1)
    {
        静的構造オプション long_options[] =
        {
            {"設定ファイル",required_argument,0,'c'},
            {0、0、0、0}
        };

        intオプションインデックス= 0;
        c = getopt_long(argc, argv, "c:", long_options, &option_index);

        if(c == -1)割り込み;

        スイッチ(c)
        {
            ケース「c」:
                構成ファイル= optarg;
                残り;
            基本:
                EXIT_FAILUREを返します。
                残り;
        }
    }

    if (cfg.readSettings(argv[0], config_file) != 構成::CFG_OK)
        EXIT_FAILUREを返します。

    std::clog << "SBFspotUploadDaemon バージョンの開始中" << バージョン << std::endl;

    // データベースにアクセスできることを確認する
    db_SQL_Base db = db_SQL_Base();
    db.open(cfg.getSqlHostname(), cfg.getSqlUsername(), cfg.getSqlPassword(), cfg.getSqlDatabase());
    if(!db.isopen())
    {
        " std::clog << "データベースを開けませんでした。設定を確認してください。" << std::endl;
        EXIT_FAILUREを返します。
    }

    // データベースバージョンの確認
    intスキーマ_バージョン= 0;
    db.get_config(SQL_SCHEMAVERSION、スキーマ_バージョン);
    db.close();

    if(schema_version < SQL_MINIMUM_SCHEMA_VERSION)
    {
        std::clog << "データベースをバージョンにアップグレードする" << SQL_MINIMUM_SCHEMA_VERSION << std::endl;
        EXIT_FAILUREを返します。
    }

    //信号ハンドラをインストールします。
    // サービスマネージャが送信したサービス停止信号に応答します。
    signal(SIGTERM、ハンドラ);

    //デーモンループの開始
    pvo_upload();

    return終了_成功。
}

そして、サービスユニットも短いです。

[単位]
説明=SBFspotアップロードデーモン
以降=mysql.service mariadb.service network.target

[提供する]
タイプ=シンプル
タイムアウト停止秒=10
ExecStart=/usr/local/bin/sbfspot.3/SBFspotUploadDaemon
再開=成功

[インストールする]
WantedBy =マルチユーザー。ターゲット

systemctl statusログ出力を使用して表示できますjournalctl-u必要に応じてオプションとサービス名を含む)。

追加読書

おすすめ記事