Menulis Plugin IntelliJ IDEA

1. Perkenalan

Selama beberapa tahun terakhir, IntelliJ dari JetBrains dengan cepat menjadi IDE teratas untuk pengembang Java. Dalam laporan State of Java terbaru kami, IntelliJ adalah IDE pilihan bagi 55% responden, naik dari 48% tahun sebelumnya.

Salah satu fitur yang membuat IntelliJ begitu menarik bagi pengembang Java adalah kemampuannya untuk memperluas dan membuat fungsionalitas baru menggunakan plugin. Dalam tutorial ini, kita akan melihat penulisan plugin IntelliJ untuk mendemonstrasikan beberapa cara memperluas IDE.

Dan perhatikan bahwa meskipun artikel ini difokuskan pada plugin IntelliJ, semua IDE JetBrains memiliki kode yang sama. Oleh karena itu, banyak teknik yang digunakan di sini dapat diterapkan ke IDE JetBrain lain seperti PyCharm, RubyMine, dan lainnya.

2. Fungsi Plugin

Fungsionalitas plugin untuk IntelliJ biasanya termasuk dalam salah satu dari 4 kategori:

  • Bahasa khusus : kemampuan untuk menulis, menafsirkan, dan menyusun kode yang ditulis dalam bahasa berbeda
  • Kerangka : dukungan untuk kerangka pihak ketiga seperti Spring
  • Alat : integrasi dengan alat eksternal seperti Gradle
  • Add-on antarmuka pengguna : item menu baru, jendela dan tombol alat, dan banyak lagi

Plugin sering kali termasuk dalam beberapa kategori . Misalnya, plugin Git yang disertakan dengan IntelliJ, berinteraksi dengan git yang dapat dieksekusi yang diinstal pada sistem. Plugin menyediakan jendela alat dan item menu popup, sementara juga mengintegrasikannya ke dalam alur kerja pembuatan proyek, jendela preferensi, dan banyak lagi.

3. Membuat Plugin

Cara termudah untuk memulai dengan plugin IntelliJ adalah menggunakan Plugin DevKit mereka. Ini dapat diakses dari menu New > Project :

Catatan kita harus menggunakan JetBrains JDK untuk memastikan kelas plugin yang diperlukan tersedia di classpath. IntelliJ seharusnya datang dengan JDK yang sesuai secara default, tetapi jika tidak kita dapat mendownloadnya dari sini.

Saat tulisan ini dibuat, kita hanya dapat menggunakan Java 8 untuk menulis plugin IntelliJ . Ini karena JetBrains saat ini tidak menyediakan JDK resmi untuk Java 9 atau lebih tinggi.

4. Contoh Plugin

Untuk mendemonstrasikan penulisan plugin IntelliJ, kami akan membuat plugin yang menyediakan akses cepat ke situs web Stack Overflow populer dari berbagai area di IDE. Kami akan menambahkan:

  • Item menu Alat untuk mengunjungi halaman Ajukan Pertanyaan
  • Item menu popup di editor teks dan output konsol untuk menelusuri Stack Overflow untuk teks yang disorot.

4.1. Membuat Tindakan

Tindakan adalah komponen inti yang digunakan untuk menulis plugin IntelliJ . Tindakan dipicu oleh peristiwa di IDE, seperti mengklik item menu atau tombol toolbar.

Langkah pertama dalam membuat tindakan adalah membuat kelas Java yang memperluas AnAction . Untuk plugin Stack Overflow kami, kami akan membuat 2 tindakan.

Tindakan pertama membuka halaman Ajukan Pertanyaan di jendela browser baru:

public class AskQuestionAction extends AnAction { @Override public void actionPerformed(AnActionEvent e) { BrowserUtil.browse("//stackoverflow.com/questions/ask"); } }

Kami menggunakan kelas BrowserUtil bawaan karena menangani semua nuansa membuka halaman web pada sistem operasi dan browser yang berbeda.

Tindakan kedua membuka halaman pencarian Stack Overflow dan meneruskan teks pencarian sebagai string kueri. Kali ini kami akan menerapkan dua metode.

Metode pertama yang kami terapkan sama seperti tindakan pertama kami dan menangani pembukaan browser web.

Namun, pertama-tama, kita perlu mengumpulkan dua nilai untuk StackOverflow. Salah satunya adalah tag bahasa, dan yang lainnya adalah teks yang akan dicari.

Untuk mendapatkan tag bahasa, kita akan menggunakan Antarmuka Struktur Program. API ini mem-parsing semua file dalam sebuah proyek dan menyediakan cara terprogram untuk memeriksanya.

Dalam hal ini, kami menggunakan PSI untuk menentukan bahasa pemrograman file:

PsiFile file = e.getData(CommonDataKeys.PSI_FILE); Language lang = e.getData(CommonDataKeys.PSI_FILE).getLanguage(); String languageTag = "+[" + lang.getDisplayName().toLowerCase() + "]";

Perhatikan bahwa PSI juga memberikan detail khusus bahasa tentang file. Misalnya, kita bisa menggunakan PSI untuk menemukan semua metode publik di kelas Java.

Untuk mendapatkan teks yang akan dicari, kami akan menggunakan API Editor untuk mengambil teks yang disorot di layar:

final Editor editor = e.getRequiredData(CommonDataKeys.EDITOR); CaretModel caretModel = editor.getCaretModel(); String selectedText = caretModel.getCurrentCaret().getSelectedText();

Meskipun tindakan ini sama untuk jendela editor dan konsol, mengakses teks yang dipilih bekerja dengan cara yang sama.

Sekarang, kita bisa menggabungkan semuanya dalam deklarasi actionPerformed :

@Override public void actionPerformed(AnActionEvent e) { PsiFile file = e.getData(CommonDataKeys.PSI_FILE); Language lang = e.getData(CommonDataKeys.PSI_FILE).getLanguage(); String languageTag = "+[" + lang.getDisplayName().toLowerCase() + "]"; Editor editor = e.getRequiredData(CommonDataKeys.EDITOR); CaretModel caretModel = editor.getCaretModel(); String selectedText = caretModel.getCurrentCaret().getSelectedText() String query = selectedText.replace(' ', '+') + languageTag; BrowserUtil.browse("//stackoverflow.com/search?q=" + query); } 

Tindakan ini juga menggantikan metode kedua bernama update . Ini memungkinkan kami untuk mengaktifkan atau menonaktifkan tindakan dalam kondisi berbeda.

Dalam kasus ini, kami menonaktifkan tindakan pencarian jika tidak ada teks yang dipilih:

@Override public void update(AnActionEvent e) { Editor editor = e.getRequiredData(CommonDataKeys.EDITOR); CaretModel caretModel = editor.getCaretModel(); e.getPresentation().setEnabledAndVisible(caretModel.getCurrentCaret().hasSelection()); } 

4.2. Mendaftarkan Tindakan

Setelah tindakan kami ditulis, kami perlu mendaftarkannya dengan IDE . Ada dua cara untuk melakukannya.

The first way is using the plugin.xml file, which is created for us when we start a new project.

By default the file will have an empty element, which is where we will add our actions:

Using the XML file to register actions will ensure they register during IDE startup, which is usually preferable.

The second way to register actions is programmatically using the ActionManager class:

ActionManager.getInstance().registerAction("StackOverflow.SearchAction", new SearchAction());

This has the advantage of letting us dynamically register actions. For example, if we write a plugin to integrate with a remote API, we might want to register a different set of actions based on the version of the API that we call.

The disadvantage to this approach is that actions do not register at startup. We have to create an instance of ApplicationComponent to manage actions, which requires more coding and XML configuration.

5. Testing the Plugin

As with any program, writing an IntelliJ plugin requires testing. For a small plugin like the one we have written, it's sufficient to ensure the plugin compiles and that the actions we created work as expected when we click them.

We can manually test (and debug) our plugin by using a Plugin run configuration:

This will launch a new instance of IntelliJ with our plugin activated. This allows us to click the different menu items we created and ensure the proper Stack Overflow pages open up.

If you wish to do more traditional unit testing, IntelliJ provides a headless environment to run unit tests. We can write tests using any test framework we want, and the tests run using real, unmocked components from the IDE.

6. Deploying the Plugin

The plugin DevKit provides a simple way to package plugins so we can install and distribute them. Simply right-click the plugin project and select “Prepare plugin module for Deployment”. This will generate a JAR file inside the project directory.

The generated JAR file contains the code and configuration files needed to load into IntelliJ. You can install it locally, or publish it to a plugin repository for use by others.

The screenshot below shows one of the new Stack Overflow menu items in action:

7. Conclusion

Di artikel ini, kami mengembangkan plugin sederhana yang menyoroti hanya beberapa cara kami dapat menyempurnakan IntelliJ IDE.

Meskipun kami terutama bekerja dengan tindakan, SDK plugin IntelliJ menawarkan beberapa cara untuk menambahkan fungsionalitas baru ke IDE. Untuk bacaan lebih lanjut, lihat panduan resmi memulai.

Seperti biasa, kode lengkap untuk plugin sampel kami dapat ditemukan di repositori GitHub kami.