Pemrograman Qt 9 – QProcess dan Menjalankan Perintah Linux


Bismillahirrahmanirrahim.

qt-creator-logoKita bisa mengomando Linux melalui GUI. Bagaimana caranya? Ada banyak cara. Lihat dulu contoh semisal Ubuntu Tweak. Aplikasi tersebut menggantikan ratusan perintah Terminal dengan beberapa tombol saja. Jika Anda menekan satu tombol di Ubuntu Tweak, maka itu berarti menjalankan perintah tertentu. Konsep ini (GUI front-end) sangat berguna jika kita ingin membuat aplikasi yang melakukan otomatisasi perintah Terminal yang biasa kita kerjakan. Misalnya kita ingin mengganti alamat sumber repositori Ubuntu. Apa yang kita lakukan? Ubah sources.list secara manual, ketik sendiri alamat-alamat yang banyak itu dari hafalan Anda, lakukan update. Hal yang seperti ini bisa dibuatkan GUI supaya otomatis dengan menyimpan alamat-alamat sumber repositori lalu menambahkan tombol untuk masing-masing repositori. Jadi, cukup satu klik untuk mengganti repositori kita ke server Kambing atau UGM atau yang lain. Ini contoh saja. Sekarang kita akan membuat yang lebih sederhana dari itu. Kita akan memakai QProcess (sebagai ganti method system() kemarin) untuk menjalankan perintah Linux lebih canggih lagi di dalam Qt. Mengapa kita beralih ke QProcess? Nanti kita akan tahu, insya Allah.

Spesifikasi Sistem

  1. Ubuntu 12.04
  2. Qt Creator 2.4.1
  3. Qt 4.8.0 (32 bit)

Daftar Kelas

  1. QProcess
  2. QStringList
  3. QByteArray

Daftar Method

  • start() milik QProcess.
  • waitForFinished() milik QProcess.
  • readAll() milik QProcess.
  • printf() method standar iostream dari C++.

Arah Tulisan Ini

Saya hanya ingin menunjukkan bagaimana aplikasi Qt bisa dibuat seperti contoh di atas, seperti Ubuntu Tweak yang satu tombolnya menggerakkan beberapa perintah Terminal. Dan saya bilang kali ini lebih canggih karena kita bisa menangkap keluaran dari perintah yang dijalankan. Ini penting untuk mewujudkan aplikasi-aplikasi yang dapat mengeksekusi perintah Terminal, menangkap keluarannya, memroses keluaran tersebut, lalu membuat keluaran baru. Contoh nyatanya adalah aplikasi pengganti sources.list otomatis pada paragraf pertama di atas.

Kode

mainwindow.h

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QtGui>

class Dialog : public QDialog
{
    Q_OBJECT

public:
    Dialog();
    QVBoxLayout *layout;
    QPushButton *tombola;
    QPushButton *tombolb;
    QPushButton *tombolc;

public slots:
    void perintah_cat();
    void perintah_mkdir();
    void perintah_ls();

private:

};

#endif // MAINWINDOW_H

mainwindow.cpp

#include <iostream>
#include <QtGui>
#include <mainwindow.h>

Dialog::Dialog()   //kagak usah dikasih void
{
    layout  = new QVBoxLayout;
    tombola = new QPushButton("cat");
    tombolb = new QPushButton("mkdir");
    tombolc = new QPushButton("ls");

    tombola->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
    tombolb->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
    tombolc->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);

    tombola->setMinimumSize(88,55);
    tombolb->setMinimumSize(88,55);
    tombolc->setMinimumSize(88,55);

    layout->addWidget(tombola);
    layout->addWidget(tombolb);
    layout->addWidget(tombolc);

    setLayout(layout);

    connect(tombola, SIGNAL(clicked()), this, SLOT(perintah_cat()));
    connect(tombolb, SIGNAL(clicked()), this, SLOT(perintah_mkdir()));
    connect(tombolc, SIGNAL(clicked()), this, SLOT(perintah_ls()));
}

void Dialog::perintah_cat()
{
    QProcess *cat = new QProcess;
    cat->start("/bin/bash -c \"rm isifolder.txt\"");
}

void Dialog::perintah_mkdir()
{
    QProcess sh;
    sh.start("sh", QStringList() << "-c" << "ifconfig | grep inet");

    sh.waitForFinished(-1);
    QByteArray output = sh.readAll();
    printf(output);
}

void Dialog::perintah_ls()
{
    QStringList options;
    options << "-c" << "ls -l | grep a | sort > isifolder.txt";

    QProcess process;
    process.start("/bin/sh", options);
    process.waitForFinished(-1);
}

Qt Creator dan Kode

ngite-kesembilan8

Panel sebelah kiri berisi mainwindow.cpp dan sebelah kanan mainwindow.h.

Hasil Kode

Tampilan program kali ini sama dengan sebelumnya. Bedanya, isi perintah untuk masing-masing tombol saya ubah. Saya akan jelaskan satu per satu hasil perintah mulai dari tombol ketiga.

Tombol ls

Isi tombol ls adalah perintah untuk mendaftar isi folder tempat si program berada, menyaring supaya hanya informasi yang memiliki huruf a saja yang ditampilkan, lalu menuliskannya ke sebuah berkas teks bernama isifolder.txt.

ngite-kesembilan1 ngite-kesembilan2

Jika tombol ls ditekan, maka perintah ls -l | grep -a > isifolder.txt dijalankan. Maka jadilah satu berkas teks bernama isifolder.txt.

ngite-kesembilan3

Demikian isi dari berkas isifolder.txt.

ngite-kesembilan9

Demikian keluaran (standard output) dari perintah yang sama tetapi dijalankan dari Terminal. Sama persis dengan isi teks. Ini berarti program valid.

Tombol mkdir

Isi tombol mkdir adalah perintah untuk mengeluarkan informasi jaringan pada baris yang memiliki teks inet saja (membuang semua baris yang lain) dan informasi itu dicetak di dalam Terminal saja. Perintahnya adalah ifconfig | grep inet.

ngite-kesembilan6

Keluaran (standard output) hanya muncul setelah program ditutup.

ngite-kesembilan7

Sama keluarannya (standard output di Terminal asli dengan Terminal di Qt Creator). Valid.

Tombol cat

Isi tombol cat adalah perintah untuk menghapus berkas isifolder.txt yang sudah ada. Karena inilah saya jelaskan dari bawah ke atas.

Pembahasan

mainwindow.h

Sama seperti tulisan sebelumnya. Jika Anda belum mengerti model deklarasi dalam header ini, silakan merujuk ke sini.

mainwindow.cpp

Pada berkas .cpp proyek ini, ada 3 fungsi buatan yang perlu diperhatikan karena inilah inti program. Kita punya 3 model eksekusi perintah Terminal di Qt, setidaknya dalam program ini. Jika Anda belum mengerti bagaimana membangun elemen-elemen GUI dengan Qt, silakan merujuk ke sini.

  • Model Eksekusi Perintah Pertama
QProcess *cat = new QProcess;
cat->start("/bin/bash -c \"rm isifolder.txt\"");

Kita membuat sebuah objek bernama cat (dari nama cat (concatenate) bukan kucing) dari kelas QProcess. Lalu, dengan objek ini, kita panggil fungsi start(). Di dalam start() ini kita masukkan string yang merupakan perintah Terminal. Perhatikanlah, kita tidak langsung menulis perintah rm isifolder.txt seperti biasa dilakukan di Terminal. Kita mesti mengawali string perintah dengan /bin/bash. Lalu gunakanlah argumen -c (artinya membaca perintah bash dari string) milik /bin/bash tersebut. Lalu barulah kita tuliskan perintah yang ingin dilakukan. Perhatikan, ada sedikit perbedaan. Di sini, ada escape character \” yakni membuat yang diapit keduanya sebagai string. Ya, argumen -c itu tadi sebabnya. Kita memasukkan string ke dalam bash tetapi ia sanggup menerimanya sebagai perintah karena argumen -c. Yang paling penting, inilah model paling ringkas menggunakan QProcess untuk mengeksekusi perintah Terminal.

  • Model Eksekusi Perintah Kedua
QProcess sh;
sh.start("sh", QStringList() << "-c" << "ifconfig | grep inet");

sh.waitForFinished(-1);
QByteArray output = sh.readAll();
printf(output);

Inti dari model kedua ini adalah pemanfaatan method start() milik QProcess yang memiliki bentuk umum: start(command, argument);. Perintah kita taruh di command, argumen kita taruh di argument. Sekadar catatan, rm -rf ubuntu.png berarti rm itu perintah sedangkan -rf ubuntu.png itu argumen. Di sini, perintah yang digunakan adalah sh (pasti ada di /bin/ Anda) sedangkan argumen yang digunakan adalah -c dan ifconfig | grep inet. Istimewanya, di sini penggunaannya tidak sesederhana itu. Kita menggunakan kelas tambahan bernama QStringList di dalam argumen start(). QStringList ini adalah kelas yang bisa menampung beberapa string sekaligus. Oleh karena itu, ia dipakai untuk menampung string yang berisi argumen-argumen perintah. Ia sangat praktis, maka ia sering digunakan. Di sini, QStringList dipakai dengan deklarasi langsung QStringList() << “-c” << “ifconfig | grep inet”. Terlihat aneh, terlihat tidak biasa. Namun ini gunanya supaya kita tidak usah membuat satu objek baru.

Teristimewa untuk QByteArray output = sh.readAll(), ini maksudnya memanggil method readAll() milik objek QProcess, yang menghasilkan keluaran dari perintah yang dijalankan oleh QProcess, lalu keluaran itu disimpan pada objek output yang dibuat dari kelas QByteArray. Pendek kata, baris deklarasi ini mengambil standard output dari perintah di dalam objek QProcess. Oleh karena itu, ia akan mengeluarkan output dari perintah ifconfig | grep inet ke Terminal di dalam Qt Creator. Apakah ini tidak penting? Tidak, justru ini (standard output dan standard error) penting sekali untuk membangun aplikasi sebagaimana ditulis di paragraf pertama tulisan ini.

  • Model Eksekusi Perintah Ketiga
QStringList options;
options << "-c" << "ls -l | grep a | sort > isifolder.txt";

QProcess process;
process.start("/bin/sh", options);
process.waitForFinished(-1);

Model ketiga ini adalah yang paling mudah dipahami. Pertama-tama kita membuat objek QStringList dahulu yang menampung seluruh argumen yang dibutuhkan. Objek ini bernama options. Lalu kita buat objek QProcess yang menampung perintah /bin/sh (bisa diganti /bin/bash atau /bin/zsh jika Anda punya zsh). Objek ini bernama process. Lalu, kita panggil start(“/bin/sh”, options); untuk process. Maka jadilah program seperti yang saya tampilkan di bagian Hasil Kode di atas.

Inti dari ketiga jenis eksekusi perintah Terminal dari dalam Qt di atas adalah pemakaian kelas QProcess. Ada beberapa hal penting yang patut diperhatikan:

  1. Kita bisa menggunakan pipeline (|) dan redirection (>, <, >>, <<) setelah mereka dimasukkan sebagai string sekaligus argumen pada QProcess. Pipeline dan redirection adalah the ultimate power di sistem operasi Linux.
  2. Tidak seperti biasanya, di sini, yang disebut command itu malah /bin/bash (shell) kita bukan langsung pada command yang biasa kita ketik di Terminal. Justru command yang biasa kita pakai itu menjadi argument di sini.
  3. Adanya method waitForFinished(-1) di sini. Arti nilai -1 ini adalah menunggu sampai objek QProcess selesai mengerjakan tugasnya. Tanpa method ini, program tidak berjalan semestinya.
  4. Seluruh kode yang ada di sini adalah dasar kita untuk membuat aplikasi yang selain mampu mengeksekusi perintah Terminal, juga mampu membaca keluaran dari perintah yang dieksekusi bahkan mampu memrosesnya.

Unduh Kode Sumber

Program kali ini bernama Embrio-Metamorfosa juga. Saya menggunakan Git jadi tidak khawatir kode rusak. Silakan unduh dan buka di Qt Creator Anda.

Tautan: http://otodidak.freeserver.me/tarball/Embrio-Metamorfosa_Edisi_2.tar.gz
Ukuran: 3 KB

Kesimpulan

  • Eksekusi perintah Linux dengan Qt bisa dilakukan dengan QProcess selain dengan method system().
  • QProcess bisa dimanfaatkan untuk membaca standard output dan standard error dari segala perintah Linux.
  • Ada beberapa model eksekusi perintah Linux di dalam Qt tetapi seluruhnya tidak keluar dari bentuk umum qprocess.start(command, argument).
  • Kita beralih ke QProcess karena ia praktis dan memiliki semua perlengkapan untuk memanggil perintah Linux serta membaca dan mengolah standard output-nya.
  • Inti dari semua ini adalah pembuatan sebuah proses baru lalu proses itu memanggil perintah Linux.

Rujukan

One thought on “Pemrograman Qt 9 – QProcess dan Menjalankan Perintah Linux

  1. Ping balik: Kumpulan Ebook Tutorial & Source Code Pemrograman C++ dengan Qt Framework Edisi 1 – 11 | Ade Malsasa Akbar

Dilarang menggunakan emotikon

Isikan data di bawah atau klik salah satu ikon untuk log in:

Logo WordPress.com

You are commenting using your WordPress.com account. Logout / Ubah )

Gambar Twitter

You are commenting using your Twitter account. Logout / Ubah )

Foto Facebook

You are commenting using your Facebook account. Logout / Ubah )

Foto Google+

You are commenting using your Google+ account. Logout / Ubah )

Connecting to %s