IntelliJ IDEA-plug-ins schrijven met Gradle

1. Inleiding

In de afgelopen jaren is IntelliJ van JetBrains snel uitgegroeid tot de beste IDE voor Java-ontwikkelaars. In ons meest recente State of Java-rapport was IntelliJ de IDE bij uitstek voor 61% van de respondenten, tegen 55% het jaar ervoor.

Een kenmerk dat IntelliJ zo aantrekkelijk maakt voor Java-ontwikkelaars is de mogelijkheid om uit te breiden en nieuwe functionaliteit te creëren met behulp van plug-ins.

In deze tutorial zullen we kijken naar het schrijven van een IntelliJ-plug-in met behulp van de nieuwe aanbevolen manier met Gradle om een ​​paar manieren te demonstreren waarop we de IDE kunnen uitbreiden. Dit artikel is een nieuwe mix van een vorig artikel waarin het maken van dezelfde plug-in wordt beschreven met behulp van de plug-in Devkit.

2. Belangrijkste soorten plug-ins

De meest voorkomende soorten plug-ins bevatten functionaliteit voor:

  • Aangepaste taalondersteuning: de mogelijkheid om code geschreven in verschillende talen te schrijven, interpreteren en compileren
  • Framework integratie: ondersteuning voor frameworks van derden, zoals Spring
  • Tool integratie: integratie met externe tools zoals Gradle
  • Add-ons voor gebruikersinterface: nieuwe menu-items, toolvensters, voortgangsbalken en meer

Plug-ins vallen vaak in meerdere categorieën. De Git-plug-in die bij IntelliJ wordt geleverd, werkt bijvoorbeeld samen met de git uitvoerbaar bestand geïnstalleerd op het systeem. De plug-in biedt zijn toolvenster en pop-upmenu-items, terwijl hij ook wordt geïntegreerd in de workflow voor het maken van projecten, het voorkeurenvenster en meer.

3. Maak een plug-in

Er zijn twee ondersteunde manieren om plug-ins te maken. We zullen de aanbevolen manier gebruiken voor nieuwe projecten met Gradle in plaats van hun Plugin Devkit te gebruiken.

Het maken van een Gradle-gebaseerde plug-in wordt gedaan met behulp van de Nieuw> Project menu.

Merk op dat we Java en de IntelliJ Platform-plug-in moeten opnemen om ervoor te zorgen dat de vereiste plug-in-klassen beschikbaar zijn op het klassenpad.

Op het moment van schrijven, we kunnen alleen JDK 8 gebruiken voor het schrijven van IntelliJ-plug-ins.

4. Voorbeeld plug-in

We zullen een plug-in maken die snelle toegang biedt tot de populaire Stack Overflow-website vanuit meerdere gebieden in de IDE. Het bevat:

  • een menu-item Tools om de pagina Stel een vraag te bezoeken
  • een pop-upmenu-item in zowel teksteditor als console-uitvoer om in Stack Overflow naar gemarkeerde tekst te zoeken

4.1. Acties maken

Acties zijn de meest gebruikelijke manier om toegang te krijgen tot een plug-in. Acties worden geactiveerd door gebeurtenissen in de IDE, zoals het klikken op een menu-item of een werkbalkknop.

De eerste stap bij het maken van een actie is het maken van een Java-klasse die uitbreidt Een actie. Voor onze Stack Overflow-plug-in maken we twee acties.

De eerste actie opent de pagina Stel een vraag in een nieuw browservenster:

openbare klasse AskQuestionAction breidt AnAction uit {@Override public void actionPerformed (AnActionEvent e) {BrowserUtil.browse ("// stackoverflow.com/questions/ask"); }}

We gebruiken de ingebouwde BrowserUtil klasse om alle nuances van het openen van een webpagina op verschillende besturingssystemen en browsers af te handelen.

We hebben twee parameters nodig om een ​​zoekopdracht op StackOverflow uit te voeren: de taal-tag en de tekst waarnaar moet worden gezocht.

Om de taalcode te krijgen, gebruiken we de Program Structure Interface (PSI). Deze API parseert alle bestanden in een project en biedt een programmatische manier om ze te inspecteren.

In dit geval gebruiken we de PSI om de programmeertaal van een bestand te bepalen:

Optioneel psiFile = Optioneel.ofNullable (e.getData (LangDataKeys.PSI_FILE)); String languageTag = psiFile.map (PsiFile :: getLanguage) .map (Taal :: getDisplayName) .map (String :: toLowerCase) .map (lang -> "[" + lang + "]") .orElse ("") ;

Om de tekst te vinden waarnaar moet worden gezocht, gebruiken we de Editor API om gemarkeerde tekst op het scherm op te halen:

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

Hoewel deze actie hetzelfde is voor zowel editor- als consolevensters, werkt het openen van de geselecteerde tekst op dezelfde manier.

Nu kunnen we dit allemaal samenvoegen in een actie uitgevoerd verklaring:

@Override public void actionPerformed (@NotNull AnActionEvent e) {Optioneel psiFile = Optioneel.ofNullable (e.getData (LangDataKeys.PSI_FILE)); String languageTag = psiFile.map (PsiFile :: getLanguage) .map (Taal :: getDisplayName) .map (String :: toLowerCase) .map (lang -> "[" + lang + "]") .orElse ("") ; Editor-editor = e.getRequiredData (CommonDataKeys.EDITOR); CaretModel caretModel = editor.getCaretModel (); String selectedText = caretModel.getCurrentCaret (). GetSelectedText (); BrowserUtil.browse ("// stackoverflow.com/search?q=" + languageTag + selectedText); }

Deze actie overschrijft ook een tweede methode met de naam bijwerken, waarmee we de actie onder verschillende omstandigheden kunnen in- of uitschakelen. In dit geval schakelen we de zoekactie uit als er geen geselecteerde tekst is:

Editor-editor = e.getRequiredData (CommonDataKeys.EDITOR); CaretModel caretModel = editor.getCaretModel (); e.getPresentation (). setEnabledAndVisible (caretModel.getCurrentCaret (). hasSelection ());

4.2. Acties registreren

Zodra we onze acties hebben geschreven, we moeten ze registreren bij de IDE. Dit kan op twee manieren.

De eerste manier is het gebruik van de plugin.xml bestand, dat voor ons wordt aangemaakt wanneer we een nieuw project starten.

Standaard heeft het bestand een leeg element, waar we onze acties aan toevoegen:

Als u het XML-bestand gebruikt om acties te registreren, zorgt u ervoor dat ze worden geregistreerd tijdens het opstarten van IDE, wat meestal de voorkeur heeft.

De tweede manier om acties te registreren is programmatisch met behulp van de ActionManager klasse:

ActionManager.getInstance (). RegisterAction ("StackOverflow.SearchAction", nieuwe SearchAction ());

Dit heeft het voordeel dat we acties dynamisch kunnen registreren. Als we bijvoorbeeld een plug-in schrijven om te integreren met een externe API, willen we misschien een andere reeks acties registreren op basis van de versie van de API die we aanroepen.

Het nadeel van deze aanpak is dat acties niet worden geregistreerd bij het opstarten. We moeten een instantie maken van Toepassing Component om acties te beheren, wat meer codering en XML-configuratie vereist.

5. Testen van de plug-in

Zoals bij elk programma, moet het schrijven van een IntelliJ-plug-in worden getest. Voor een kleine plug-in zoals degene die we hebben geschreven, is het voldoende om ervoor te zorgen dat de plug-in compileert en dat de acties die we hebben gemaakt werken zoals verwacht wanneer we erop klikken.

We kunnen onze plug-in handmatig testen (en debuggen) door het Gradle-toolvenster te openen en het runIde taak:

Hiermee wordt een nieuw exemplaar van IntelliJ gestart met onze plug-in geactiveerd. Hierdoor kunnen we op de verschillende menu-items klikken die we hebben gemaakt en ervoor zorgen dat de juiste Stack Overflow-pagina's worden geopend.

Als we meer traditionele unit-tests willen doen, biedt IntelliJ een headless-omgeving om unit-tests uit te voeren. We kunnen tests schrijven met elk testraamwerk dat we willen, en de tests worden uitgevoerd met echte, niet-geblokkeerde componenten van de IDE.

6. Implementatie van de plug-in

De Gradle-plug-in biedt een eenvoudige manier om plug-ins te verpakken, zodat we ze kunnen installeren en distribueren. Open gewoon het Gradle-toolvenster en voer het buildPlugin taak. Dit genereert een ZIP-bestand in het build / distributies directory.

Het gegenereerde ZIP-bestand bevat de code en configuratiebestanden die nodig zijn om in IntelliJ te laden. We kunnen het lokaal installeren of publiceren naar een plug-in-opslagplaats voor gebruik door anderen.

De onderstaande schermafbeelding toont een van de nieuwe menu-items van Stack Overflow in actie:

7. Conclusie

In dit artikel hebben we een eenvoudige plug-in ontwikkeld die laat zien hoe we de IntelliJ IDE kunnen verbeteren.

Hoewel we voornamelijk met acties werken, biedt de IntelliJ-plug-in SDK verschillende manieren om nieuwe functionaliteit aan de IDE toe te voegen. Raadpleeg hun officiële startgids voor meer informatie.

Zoals altijd is de volledige code voor onze voorbeeldplug-in te vinden op GitHub.