Teori Bash

/ bin / bash

0. Indeks

  1. Hal-hal yang terjadi pada kebanyakan orang
  2. Struktur naskah
  3. Cetak di layar
  4. Baca INPUT pengguna
  5. Perhitungan di bash
  6. Syarat
  7. Loop
  8. Funciones
  9. getops

1. Hal-hal yang terjadi pada kebanyakan orang

/ bin / bash atau / bin / sh

Salah satu hal pertama yang dilakukan mesin saat menjalankan skrip kami adalah melihat shell mana yang harus dilakukannya. Pada kebanyakan sistem linux saat ini / Bin / sh adalah tautan ke / bin / bash, tapi ini tidak selalu terjadi, misalnya pada distro yang menggunakan busybox membawa Sh dan biasanya mereka juga membawa Menampar, tetapi jika Anda menggunakan / Bin / sh, itu tidak akan berjalan dengan Bash. Itulah mengapa saya merekomendasikan untuk selalu menggunakan / bin / bash.

Unicode vs. ASCII

Pernahkah Anda bertanya-tanya mengapa Anda tidak dapat menggunakan "¿" atau "ñ" dalam skrip Anda? Atau gunakan aksen? Ini bisa sangat mengganggu dalam skrip interaktif. Itu karena pengkodean default Bash adalah ASCII, atau yang sama, kumpulan karakter bahasa Inggris. Untuk mengubahnya, kita hanya perlu memberi tahu skrip kita bahwa kita ingin menggunakan Unicode. Untuk itu Anda harus menambahkan baris tepat setelah command interpreter:

# - * - ENCODING: UTF-8 - * -

Hati-hati, ini penting agar baris ini berada di awal skrip.

Buat skrip dapat dieksekusi

Lucu sekali betapa banyak orang yang menjalankan skrip dengan «$ bashscript.sh" dari pada "$ ./script.sh'Lagipula, untuk inilah kita mendefinisikan shell.

Untuk menambahkan izin eksekusi, Anda harus menjalankan:

sudo + x script.sh
Jika skrip kami dapat dieksekusi, kami dapat menambahkannya ke PATH kami dan membuatnya dapat dieksekusi dari mana saja / folder di komputer kami. Untuk itu kita harus menambahkan baik ke .bashrc pengguna kita atau ke / etc / bashrc baris
BIN = "folder tempat kita memiliki skrip" PATH = "$ BIN $ PATH"
Ini adalah aturan Bash untuk menulis nama variabel dalam huruf besar semua. Banyak orang tidak mengikuti aturan ini, tetapi untuk skrip yang panjang itu dihargai karena mereka membuatnya lebih mudah dibaca

2. Struktur naskah

  1. Header
  2. Definisi variabel global
  3. Membantu
  4. Funciones
  5. Tubuh utama

Header adalah tempat kami menunjukkan shell mana yang ingin kami gunakan dan pengkodeannya. Kelebihan dari fungsinya adalah dapat menggunakan kembali kode yang diulang-ulang dengan menulisnya hanya sekali dan untuk memudahkan dalam memahami script, untuk kode yang melebihi 100 baris sangat berguna.

Untuk menggunakan fungsi, mereka harus didefinisikan dengan sebelum badan utama skrip kita. Dan jika kita ingin menggunakan variabel di tingkat global dari semua skrip kita, baik di badan utama maupun di fungsi, kita harus mendefinisikannya di awal segalanya, tepat setelah tajuk.

Terakhir, merupakan praktik yang baik untuk menulis fungsi helper saat skrip kita berjalan buruk atau dengan parameter yang buruk. Jelas, dalam kasus tersebut kami ingin segera keluar dari skrip, tanpa membaca fungsinya. Untuk itu kita bisa menggunakan:

function help () {echo "" "Teks bantuan kami yang diformat dengan baik." "" exit if [[-z $ 1 || $ 1 == "-h" || $ 1 == "--help"]]; kemudian bantu fi

Jika kita menambahkan "exit" ke fungsi bantuan, kita akan keluar dari skrip setiap kali kita menjalankan bantuan, misalnya setelah pesan kesalahan, dll. Kami menyimpan beberapa baris kode.

Kondisi tersebut menunjukkan bantuan tampilan di layar dan keluar jika skrip dijalankan tanpa parameter atau jika -h / –help ditentukan. Jika Anda melihatnya, itulah perilaku standar dari kebanyakan program linux.

Penggunaan 3 tanda kutip dengan gema memungkinkan untuk menggunakan jeda baris tanpa meninggalkan pesan untuk ditampilkan oleh gema. Untuk pesan multi-baris, jauh lebih nyaman menggunakan echo hanya sekali.

3. Cetak di layar

Ada 2 perintah utama untuk mencetak ke layar di bash: «gema"Y"Printf«. Keduanya sama cepatnya dan keduanya adalah bagian dari pesta. Perbedaan utama bagi pemula adalah gema menambahkan baris baru di akhir, sedangkan «Printf"Tidak.

Echo baik-baik saja dan itulah yang digunakan kebanyakan orang, namun ketika membaca INPUT pengguna, atau ketika Anda ingin mencetak variabel yang diambil dari file dengan pengolah kata, hal-hal aneh dapat terjadi. Mereka biasanya mudah diselesaikan, semudah mengubah tanda kutip ganda menjadi satu atau sebaliknya, atau menghilangkan referensi variabel dari tanda kutip. «Gema»Itu melakukan hal-hal aneh juga tergantung pada bagaimana ia telah dikompilasi, jika kita selalu menggunakan Ubuntu atau selalu Fedora, itu tidak mempengaruhi kita, tetapi jika kita mengubah distribusinya.

Itulah mengapa saya menggunakan «Printf«, Yang tidak membuatku pusing dan juga berperilaku lebih seperti«Printf»Dari C atau«mencetak»Dari Python, itu sangat penting jika Anda ingin memindahkan skrip Anda ke bahasa pemrograman lain.

Untuk pembahasan yang lebih luas, Anda dapat mengunjungi pertanyaan ini dari Unix & Linux di Stack Exchange.

4. Baca INPUT pengguna

Semua yang kita tulis setelah nama skrip kita dan sebelum menekan tombol ENTER secara otomatis disimpan dalam variabel khusus. Variabel ini berjenis $ X dengan X adalah angka.

«$0»Menunjukkan nama skrip kami dan dari«$1»Sampai tak terbatas semua yang telah kita tulis nanti adalah variabel. Sebagai contoh:

cat << EOF >> test.sh #! / bin / bash # - * - ENCODING: UTF-8 - * - printf "\ $ 0 = $ 0 \ n" printf "\ $ 1 = $ 1 \ n" printf "\ $ 2 = $ 2 \ n" EOF chmod + x script.sh ./script.sh file.txt saya

Kami membuat skrip pengujian, membuatnya dapat dieksekusi, dan menjalankannya dengan 2 parameter. Kami mendapatkan output layar dari:

$ 0 = ./script.sh $ 1 = $ 2 saya = file.txt

Menggunakan tanda kutip kita bisa saja meneruskan "file.txt saya" ke "$ 1".

Kita juga dapat membaca INPUT pengguna dengan perintah "read", yang secara langsung menunjukkan variabel tempat kita ingin menyimpan parameter. Sebagai contoh:

printf "Siapa namamu? \ n" baca NAMA printf "Halo, $ NAMA. \ n"
Hati-hati dengan penetapan variabel. "$ VAR = content" akan menghasilkan kesalahan, tidak ada spasi yang tersisa di antara tanda sama dengan, nama variabel, dan konten. Penggunaan yang benar adalah "VAR = konten"

5. Perhitungan di Bash

Untuk itu kita bisa menggunakan «cepat«, Selama kita tidak perlu melakukan perhitungan yang rumit. Ada dua hal yang harus diperhatikan, yang pertama adalah «cepat»Hanya menerima bilangan bulat, yang kedua adalah pembagian mengembalikan hasil keseluruhan, untuk melihat sisanya kita dapat menggunakan«%".

Biasanya kami ingin menetapkan hasil expr ke variabel. Kita dapat melakukannya dengan dua cara:

VAR2 = `expr $ VAR1 / 10` VAR2 = $ (expr $ VAR1 / 100)

Anda juga dapat melewati «cepat»Menggunakan tanda kurung ganda:

VAR2 = $ (($ VAR1 / 100))
Untuk penjelasan lebih lanjut tentang «cepat»Atau alternatif yang menggunakan bilangan bulat, Anda dapat melihat entri KZKG ^ gaara ini.

6 Kondisi

Ini telah ditulis secara ekstensif di «if«,«lain«,«elif»Dan kondisi. Anda dapat membacanya di:

Saya hanya ingin menyoroti perbedaan antara penggunaan tanda kurung siku sederhana, «[]«, Dan tanda kurung ganda,«[[]]«, Untuk kondisi. Dengan tanda kurung ganda kita dapat menggunakan kondisi tambahan:

  • «&&»Untuk dan
  • «||»Untuk atau

Menggunakan "&&"Y"||»Dengan tanda kurung siku sederhana, setiap bagian harus dipisahkan dalam tanda kurung siku terpisah. Contoh yang digunakan untuk bagian skrip yang terlihat untuk melihat apakah bantuan perlu dijalankan adalah:

jika [-z "$ 1"] || ["$ 1" == "-h"] || ["$ 1" == "--help"]]; kemudian bantu fi

Ini juga menyelamatkan kita dari keharusan menulis nama variabel dalam tanda kutip untuk mencegah kesalahan. Sebagai contoh:

jika [$ 1 = 1]; lalu printf "Parameternya sama dengan 1."; fi jika ["$ 1" = 1]; lalu printf "Parameternya sama dengan 1."; fi jika [[$ 1 = 1]]; lalu printf "Parameternya sama dengan 1."; fi

Jika script.sh dijalankan tanpa parameter apa pun, kasus pertama akan memberikan error:

bash: [: =: diharapkan operator unary
Dalam Bash "=" dan "==" keduanya diinterpretasikan dengan cara yang sama. Ini tidak terjadi dalam bahasa pemrograman lain di mana "=" hanya digunakan untuk menetapkan variabel.

Yang belum dibicarakan adalah «kasus«, Yang digunakan untuk menyederhanakan«if«. Mari kita mulai dari awal, ketika kita tidak memiliki «if»Semua kode akan dieksekusi. Jika kita menambahkan kondisi «if»Kami akan memiliki dua kasus, satu di mana blok kode yang ada di dalam«if»Dan kasus lain di mana blok ini tidak dijalankan.

Jika kita menambahkan «lain“Kami juga akan punya dua kasus, tapi dua kasus ini berbeda dari yang sebelumnya. Karena sekarang akan ada dua blok kode bersyarat, A dan B, dan blok C, yang merupakan sisa program. A atau B akan dieksekusi, dan C. Dalam kasus sebelumnya adalah A dan C atau hanya C.

Untuk menghindari kondisi penulisan «jika / lain"dalam"lain»Dan untuk menyederhanakan pembacaan kode, itu dibuat«elif«. Ketika kami memiliki banyak kondisi yang bergantung pada yang sebelumnya, misalnya kisaran angka atau jenis:

VAR1 = $ 1 jika [[$ VAR1 = 1]]; lalu printf "1 \ n" elif [[$ VAR1 = 2]]; lalu printf "2 \ n" elif [[$ VAR1 = 3]]; lalu printf "3 \ n" lain printf "tidak ada \ n" fi

Dalam kasus «terakhirelif»Banyak ketentuan yang akan terbaca. Dengan kasus ini, proses ini disederhanakan:

VAR1 = $ 1 kasus $ VAR dalam 1) printf "1 \ n" ;; 2) printf "2 \ n" ;; 3 | 4) printf "3 atau 4, itu tergantung \ n" ;; *) printf "tidak ada \ n" ;; itu C

Sebuah variabel akan dibaca, dalam hal ini VAR1, dan akan diperiksa apakah itu setara dengan kasus manapun, jika tidak, kasus default "*" akan dijalankan. Titik koma ganda sama dengan «istirahat", Mereka berkata"kasus»Itu harus diakhiri.

«Kasus»Bisa juga digunakan sebagai urutan«if«, Untuk itu Anda harus menggunakan« ;; & »(lanjutkan) daripada« ;; » (berhenti).

7. Perulangan

Sangat sedikit loop yang dikenal dalam bahasa pemrograman apa pun. Di Bash mereka adalah «sementara«,«sampai"Y"untuk«. Sudah ditulis di blog tentang ini:

Ada dua jenis loop «untuk«, Mereka yang merupakan tipe«$ untuk VAR di LOQUESEA»Dan apa tipe C«$ untuk ((I = 0; I <= 10; I ++))«. Jenis loop kedua «untuk»Sangat berguna, ini memiliki 3 bagian di awal perulangan:

  • Deklarasi dan inisiasi variabel (Dalam hal ini variabel bantu "I = 0").
  • Kondisi eksekusi (sampai I kurang dari atau sama dengan 10).
  • Peningkatan variabel bantu

Menurut pendapat saya, ini adalah putaran paling kuat dari semuanya. Contoh, yang mencetak semua angka dari 0 sampai 10, termasuk:

#! / bin / bash untuk ((I = 0; I <= 10; I ++)); lakukan printf "$ I \ n" selesai

8. Fungsi

Ada beberapa hal yang Bash tidak izinkan untuk kita lakukan, bukan? Sekilas, fungsi bash mencegah Anda melakukan 3 hal: mendeklarasikan variabel lokal dalam fungsi, meneruskan parameter ke fungsi, dan mengembalikan parameter. Semuanya punya solusi.

Jangan lakukan seperti:

#! / bin / bash VAR = 1 printc "$ VAR \ n" fungsi hello () {VAR = 2 printf "$ VAR \ n"} halo printf "$ VAR \ n"

Ini mencetak ke layar 1, 2 dan 2.

Untuk mendeklarasikan variabel lokal, tambahkan «lokal»Saat mendeklarasikan:

#! / bin / bash VAR = 1 printf "$ VAR1 \ n" fungsi foo () {local VAR1 = 2 printf "$ VAR1 \ n"} printf "$ VAR1 \ n" foo printf "$ VAR1 \ n"

Ini mencetak 1, 1, 2, 1 di layar.

Bagaimana Anda mengirimkan parameter ke suatu fungsi?

#! / bin / bash # - * - ENCODING: UTF-8 - * - function hello () {printf "Halo $ 1 \ n"}

printf "Siapa namamu? \ n"
membaca VAR1
halo $ VAR1

Bagaimana parameter dikembalikan?

#! / bin / bash # - * - ENCODING: UTF-8 - * - function hello () {printf "Hello holita"} printf "Siapa namamu? \ n" baca VAR1 VAR1 = $ (halo) # DI SINI printf "$ VAR1 $ VAR2 \ n"

Seperti yang Anda lihat, ini memiliki dua kekurangan, Anda hanya dapat mengembalikan satu parameter, yang dapat berupa vektor 😀, dan jika Anda ingin mengembalikan parameter, Anda tidak dapat lagi mencetak di layar dari fungsi itu.

Anda dapat menemukan lebih banyak hal tentang fungsi di [url=https://blog.desdelinux.net/programando-en-bash-parte-3/]artikel ini dari Usemoslinux[/url].

9. Getop

Salah satu hal terakhir yang perlu Anda ketahui tentang Bash untuk membuat skrip yang rumit adalah «getop«. Ini digunakan untuk meneruskan opsi ke skrip apa pun urutannya. Satu-satunya downside adalah bahwa itu hanya mempengaruhi opsi pendek:

#! / bin / bash # - * - ENCODING: UTF-8 - * - VARC = 0 function help () {printf "Help message \ n" exit} if [[-z $ 1]]; kemudian bantu fi saat getopts: ha: b: c OPT; lakukan case $ OPT in h) help ;; :) Tolong ;; a) VARA = $ OPTARG ;; b) VARB = $ OPTARG ;; c) VARC = 1 ;; \?) Tolong ;; esac done # Blok utama skrip yang # melakukan berbagai hal dengan VARA, VARB, dan VARC

«getopt»Membaca opsi satu per satu, jadi diperlukan putaran.

Ada 2 jenis opsi yang bisa dilalui menggunakan «getopt":

  • Parameter disebut flag, dalam hal ini -c atau -h. Mereka ditentukan dengan huruf yang ingin kita gunakan. Mereka seperti variabel Boolean, «benar»(Are) atau«palsu"(Mereka tidak ada di sini).
  • Parameter dengan argumen terkait, -a apa saja, -b apa saja. Mereka ditentukan dengan huruf yang kita inginkan dengan titik dua di bawah. Argumen disimpan dalam OPTARG (nama ini tidak dapat diubah).
Titik awal ganda untuk menunjukkan tidak ada kesalahan.

Apa fungsi skrip ini?

Menampilkan pesan bantuan ketika tidak ada opsi yang dilewatkan, ketika parameter "-h" dilewatkan, ketika parameter yang tidak valid dilewatkan (misalnya "-x", ini dilakukan oleh "\?") Atau ketika parameter valid tanpa argumen (":"). Dalam kasus lainnya, ini menyimpan keberadaan "-c" sebagai 1 di VARC, dan nilai yang diteruskan dengan "-a" dan "-b" di VARA dan VARB.


tinggalkan Komentar Anda

Alamat email Anda tidak akan dipublikasikan. Bidang yang harus diisi ditandai dengan *

*

*

  1. Penanggung jawab data: Miguel Ángel Gatón
  2. Tujuan data: Mengontrol SPAM, manajemen komentar.
  3. Legitimasi: Persetujuan Anda
  4. Komunikasi data: Data tidak akan dikomunikasikan kepada pihak ketiga kecuali dengan kewajiban hukum.
  5. Penyimpanan data: Basis data dihosting oleh Occentus Networks (UE)
  6. Hak: Anda dapat membatasi, memulihkan, dan menghapus informasi Anda kapan saja.

  1.   hidup dijo

    MAHIR. Saya tidak mengatakan lebih banyak U_U

  2.   Miguel dijo

    Halo, artikel yang sangat bagus.
    Hei, Anda memberi izin sudo + x alih-alih chmod + x

    1.    Henry dijo

      $ sudo chmod + x script.sh
      (Lebih tepatnya, hehe)

      Ah, selamat dan terima kasih!

  3.   api unggun dijo

    Pos yang sangat bagus, saya sangat mengucapkan selamat kepada Anda, pertahankan, Salam

  4.   Gustavo dijo

    Dan jika Anda ingin skrip terlihat saat dijalankan, langkah demi langkah, lihat misalnya bagaimana variabel, kondisi, dan semuanya berperilaku, Anda dapat menggunakan:

    skrip sh -x

    salam

  5.   dago dijo

    PIECE dari pengawasan. Luar biasa dan dijelaskan dengan sangat baik.
    Terima kasih.

  6.   gabriel dijo

    Posting yang bagus tentang masalah ini 😉

  7.   Mario Guillermo Zavala Silva dijo

    Sangat menarik dan sangat penting terima kasih atas informasinya….
    BERSULANG !!!

  8.   Bukan daribrooklyn dijo

    Terima kasih atas semua ucapan selamat Anda, untuk perintah Miguel, dia tidak mengizinkan saya mengubah entri setelah diterbitkan. Itu harus melakukan elav yang saya bayangkan.

  9.   Adrian dijo

    Baik sekali!

    Pertama-tama saya ingin mengucapkan selamat kepada Anda atas postingannya, saya merasa mudah untuk dipahami dan sangat membantu untuk mengikuti pedoman untuk memprogram dengan baik di bash, terutama untuk orang-orang yang baru memulai program.

    Namun saya menemukan beberapa detail yang menurut saya harus diperbaiki.

    Pertama: di bagian «2. STRUKTUR SKRIP »fungsi tidak ditutup, yang akan menimbulkan masalah saat menjalankannya dalam skrip.
    Solusinya adalah dengan menambahkan kurung kurawal tutup tepat setelah perintah "keluar".

    Kedua: di bagian «4. BACA INPUT PENGGUNA »Anda menegaskan bahwa parameter yang dapat dimasukkan pengguna mulai dari $ 0 hingga tak terbatas, namun," bash "hanya akan menerjemahkan dari $ 0 hingga $ 9, karena $ 10 akan sama dengan $ 1 + 0.
    Untuk mengatasi masalah ini, Anda dapat menggunakan perintah "shift" untuk mengambil variabel berikut. Atau tentukan variabel dalam tanda kurung kurawal "$ {10}", sehingga bash menggabungkan nilai, bukan sebagai $ 1 + 0.

    Tanpa basa-basi lagi, salam kenal!

    1.    Bukan daribrooklyn dijo

      Terima kasih atas komentar Anda. Itu benar-benar gagal untuk menjelaskan penggunaan exit yang benar, baik dalam skrip maupun dalam fungsi. Adapun $ {10} Saya belum pernah mewariskan sebanyak itu, jadi saya belum mengalami masalah itu, ada baiknya mengetahui bahwa ada solusi untuk itu (saya sudah mencoret hal baru yang dipelajari hari ini 😀).

  10.   chanio dijo

    Terima kasih banyak atas artikelnya! Beberapa hal yang Anda sebutkan masih kurang klarifikasi. Misalnya, getops.
    Di bagian keluaran layar, Anda harus menyebutkan kucing yang nanti Anda sebutkan ...
    kucing <
    ***************************************
    * FORMULIR INI SANGAT EKSPRESIF *
    ***************************************
    EOF

    Dalam contoh Anda:
    kucing << EOF >> test.sh
    Ada dua hal yang harus disebutkan ... >> itu adalah 'append' yaitu, jika Anda mengulangi perintah yang sama, Anda akan memiliki seluruh skrip dalam duplikat ... Anda hanya boleh menggunakan satu ...
    cat << EOF> script.sh
    Ya, itu juga harus disebut script.sh
    Lalu masuk
    jika [-z "$ 1"] || ["$ 1" == "-h"] || ["$ 1" == "–help"]]; kemudian
    membantu
    fi

    Saya pikir itu harus ditulis ...
    jika [[-z "$ 1"] || ["$ 1" == "-h"] || ["$ 1" == "–help"]]; kemudian
    ...

    Masih banyak lagi yang bisa ditemukan dari BASH.
    Bisakah Anda memberinya judul "DASAR"? 🙂
    Misalnya, parameter 'penguji' seperti -z untuk melihat apakah kosong, atau -f untuk mengetahui apakah ada sebagai file.

    Sekali lagi, terima kasih atas usaha Anda.
    alberto

  11.   clow_eriol dijo

    Tutorial skrip bash yang sangat bagus!

  12.   OCZ dijo

    -- ENCODING: UTF-8 --

    Ini pertama kalinya saya melihat baris itu untuk mengatur pengkodean karakter dalam skrip bash. Bagi saya ini lebih seperti Python daripada Bash. Apakah ini benar-benar perlu? Saya telah mencari referensi di Google tetapi saya tidak dapat menemukan apa pun, apakah Anda memiliki tautan di tangan yang membahas tentang masalah ini? Khususnya pada kesesuaian garis itu.

    Menurut saya, untuk menulis skrip di Bash menggunakan UTF-8, Anda hanya perlu menyimpan file teks seperti itu (tanpa BOM) dan memiliki variabel lingkungan tertentu, (LANG dan LC_ *), yang disetel dengan benar.
    Maka, jelas, perlu bahwa perintah yang dieksekusi disiapkan untuk pengkodean selain ASCII. Misalnya, jika kita ingin menggunakan huruf besar, ini sepertinya tidak berhasil:
    «Gema áéíóú | tr az AZ »
    o:
    «Gema áéíóú | tr [: bawah:] [: atas:] »
    dan lebih baik menggunakan:
    «Gema áéíóú | awk '{print toupper ($ 0)}' ».

    1.    Bukan daribrooklyn dijo

      Tentang "encoding»Telah disebutkan di blog ini sebelumnya:

      Bash: cara membuat skrip dapat dieksekusi
      Skrip utilitas pasca instalasi

    2.    borriquito seperti Anda dijo

      Seseorang mengoreksi saya, tetapi baris pengkodean itu (# -- ENCODING: UTF-8 --) Ini tidak ada hubungannya dengan bash atau shell: ini adalah baris komentar (dimulai dengan #) dan berfungsi untuk memberi tahu EDITOR yang kita gunakan untuk menulis skrip (vim, emacs ...) pengkodean file.

      Faktanya, bash tidak melihat baris seperti itu, karena ini adalah baris komentar.

  13.   JoRgE-1987 dijo

    Tutorial yang sangat bagus, karena Sysadmin mengetahui Scripting in Bash itu penting, ini berguna untuk semuanya.

    Sangat sangat baik!

    Salam!

  14.   Edward Cuomo dijo

    Jika ini berguna bagi siapa saja, berikut beberapa kegunaan dan contoh untuk membuat Skrip Anda sendiri: https://github.com/reduardo7/hsabx

  15.   Black Lito dijo

    Baik sekali. Hal-hal baru untuk ditambahkan ke skrip saya. Hal encodig dan printf tidak memilikinya.
    Terima kasih!!!

  16.   xxxtonixxx dijo

    Artikel yang sangat bagus! Saya menyimpan yang ini untuk favorit, alangkah baiknya untuk memperbaiki apa yang salah dan bahkan mengembangkannya dengan lebih banyak konten. Tepuk tangan untuk semua info ini !!!!