Waarschijnlijk, heeft geen bijzondere introductie meer nodig. Veel mensen kennen Eclipse dankzij de Eclipse Java development tools (). Deze populaire open-source Java IDE wordt door de meeste ontwikkelaars geassocieerd met het woord “Eclipse”. Maar Eclipse is ook een uitbreidbaar platform voor de integratie van ontwikkeltools (Eclipse Platform), en een reeks IDE's die op deze basis zijn gebouwd, waaronder JDT. Eclipse omvat ook het Eclipse Project, een topniveau project dat de ontwikkeling van de Eclipse Platform en JDT coördineert, en de Eclipse SDK – het resultaat van deze ontwikkeling. Ten slotte is Eclipse een open-source Foundation met een enorme gemeenschap van projecten, waarvan niet alle in Java zijn geschreven of betrekking hebben op ontwikkeltools (bijvoorbeeld projecten en ). De wereld van Eclipse is zeer divers.
In dit artikel, dat een overzicht biedt, zullen we enkele basisprincipes van de architectuur van Eclipse als platform voor het bouwen van geïntegreerde ontwikkeltools bekijken en een eerste indruk geven van de componenten van Eclipse die de fundamenten van het technologische platform voor de ‘nieuwe Configurator’ 1C: Enterprise vormen, . Natuurlijk zal deze beschouwing onvermijdelijk grotendeels oppervlakkig en vrij beperkt zijn, ook omdat we ons niet alleen op Eclipse-ontwikkelaars als doelgroep richten. We hopen echter dat zelfs ervaren Eclipse-ontwikkelaars interessante informatie in dit artikel zullen vinden. Bijvoorbeeld, we zullen een van de 'geheimen van Eclipse' bespreken, een relatief nieuw en nog weinig bekend project , dat is opgericht en wordt ondersteund door het bedrijf 1C.

Inleiding tot de architectuur van Eclipse
Laten we eerst enkele algemene aspecten van de architectuur van Eclipse bekijken aan de hand van (JDT). De keuze voor juist JDT als voorbeeld is geen toeval. Dit is de eerste geïntegreerde ontwikkelomgeving die in Eclipse is verschenen. De andere *DT projecten van Eclipse, zoals Eclipse C/C++ Development Tooling (CDT), zijn later gecreëerd en hebben zowel basisarchitectuurprincipes als afzonderlijke fragmenten van de broncode uit JDT overgenomen. De architecturale fundamenten die in JDT zijn gelegd, zijn tot op de dag van vandaag relevant voor praktisch iedere IDE die op de Eclipse Platform is gebouwd, waaronder ook de 1C:Enterprise Development Tools.
Allereerst moet worden opgemerkt dat Eclipse een duidelijke architecturale scheiding kent, waarbij taal-onafhankelijke functionaliteit wordt gescheiden van functionaliteit die is bedoeld ter ondersteuning van specifieke programmeertalen, en waarbij UI-onafhankelijke 'kern' componenten worden gescheiden van componenten die verband houden met de ondersteuning van de gebruikersinterface.
De Eclipse Platform definieert zo een algemene, taal-onafhankelijke infrastructuur, terwijl de Java development tools een volledig functionele Java IDE aan Eclipse toevoegen. Zowel de Eclipse Platform als JDT bestaan uit verschillende componenten, elk van welke ofwel behoort tot de UI-onafhankelijke 'kern', ofwel tot de UI-laag (zie Figuur 1).

Figuur 1. Eclipse Platform en JDT
Laten we de belangrijkste componenten van de Eclipse Platform opsommen:
- Runtime — Bepaalt de infrastructuur van plugins. Eclipse heeft een modulaire architectuur. In wezen is Eclipse een verzameling 'uitbreidingspunten' en 'uitbreidingen'.
- Workspace — Beheert één of meerdere projecten. Een project bestaat uit mappen en bestanden die direct op het bestandssysteem worden weergegeven.
- Standard Widget Toolkit (SWT) — Biedt de basis gebruikerselementen die zijn geïntegreerd met de besturingssystemen.
- JFace — Biedt een reeks UI-frameworks die zijn gebouwd bovenop SWT.
- Werkruimte — Bepaalt de UI-paradigma van Eclipse: editors, weergaven, perspectieven.
Het moet worden gezegd dat de Eclipse Platform ook veel andere nuttige componenten biedt voor het bouwen van geïntegreerde ontwikkelingshulpmiddelen, waaronder Debug, Compare, Search, en Team. Bijzonder moet JFace Text worden genoemd - de basis voor het bouwen van 'slimme editors' van broncode. Helaas is een oppervlakkige beschouwing van deze componenten, evenals van de componenten van de UI-laag, niet mogelijk in het kader van dit artikel; daarom beperken we ons in het resterende deel van deze sectie tot een overzicht van de belangrijkste 'kern' componenten van de Eclipse Platform en JDT.
Core Runtime
De plugin-infrastructuur van Eclipse is gebaseerd op en wordt geleverd door het project . Elke Eclipse-plugin is een OSGi-bundel. De OSGi-specificatie definieert onder andere de mechanismen voor versiebeheer en afhankelijkheidsresolutie. Naast deze standaardmechanismen introduceert Equinox het concept van uitbreidingspunten. Elke plugin kan zijn eigen extensiepunten definiëren en extra functionaliteit toevoegen aan het systeem ("uitbreidingen"), gebruikmakend van de extensiepunten die door dezelfde of andere plugins zijn gedefinieerd. Een gedetailleerde beschrijving van de OSGi- en Equinox-mechanismen valt buiten het bereik van dit artikel. We willen alleen opmerken dat modulariteit in Eclipse totaal is (elke subsysteem, inclusief Runtime, bestaat uit een of meerdere plugins), en vrijwel alles in Eclipse is een uitbreiding. Bovendien zijn deze principes al in de architectuur van Eclipse vastgelegd voordat OSGi werd geïmplementeerd (toen werd een eigen technologie gebruikt, die in veel opzichten vergelijkbaar was met OSGi).
Kernwerkruimte
Bijna elke geïntegreerde ontwikkelomgeving die is gebouwd op basis van het Eclipse-platform, werkt met de Eclipse-werkruimte. De werkruimte bevat meestal de broncode van de applicatie die in de IDE wordt ontwikkeld. De werkruimte weerspiegelt direct het bestandssysteem en bestaat uit projecten die mappen en bestanden bevatten. Deze projecten, mappen en bestanden worden genoemd resources werkruimte. De implementatie van de werkruimte in Eclipse fungeert als een cache ten opzichte van het bestandssysteem, wat de navigatie door de boom van resources aanzienlijk versnelt. Bovendien biedt de werkruimte een aantal aanvullende diensten, waaronder en .
De ondersteuning van de werkruimte en zijn resources wordt verzorgd door de Core Resources-component (plugin org.eclipse.core.resources). Deze component biedt met name programmeertoegang tot de werkruimte in de vorm van een resource-model. Voor een effectieve omgang met dit model hebben clients een eenvoudige manier nodig om een verwijzing naar een resource voor te stellen. Het zou wenselijk zijn om het object dat de status van de resource in het model opslaat, voor directe toegang door de client te verbergen. Anders zou de client, bijvoorbeeld bij het verwijderen van een bestand, het object kunnen blijven vasthouden dat al niet meer in het model aanwezig is, wat leidt tot problemen. Eclipse lost deze taak op door het zogenaamde handle van de resource. Het handle fungeert als een sleutel (het kent alleen het pad naar de resource in de werkruimte) en controleert volledig de toegang tot het interne modelobject, dat rechtstreeks informatie over de status van de resource opslaat. Dit ontwerp is een variatie op het pattern .
Figuur 2 illustreert de idiom Handle/Body in verband met het model van bronnen. De interface IResource vertegenwoordigt de handle van de bron en is de API, in tegenstelling tot de klasse Resource die deze interface implementeert, evenals de klasse ResourceInfo die de body vertegenwoordigt, welke geen API is. We benadrukken dat de handle alleen het pad naar de bron weet ten opzichte van de wortel van de werkruimte en geen verwijzing naar de resource info bevat. Objecten van resource info vormen de zogenaamde "elementboom" (element tree). Deze datastructuur is volledig in het geheugen gematerialiseerd. Om een exemplaar van resource info te vinden dat overeenkomt met een bepaalde handle, wordt de elementboom doorlopen op basis van het pad dat in deze handle is opgeslagen.

Figuur 2. IResource en ResourceInfo
Zoals we later zullen zien, wordt het basale ontwerp van het model van bronnen (dat we handle-based kunnen noemen) ook in Eclipse gebruikt voor andere modellen. Laten we ondertussen enkele onderscheidende eigenschappen van dit ontwerp opsommen:
- Handle is een waarde-object (value object). Waarde-objecten zijn immutabele (immutable) objecten waarvan de gelijkheid niet is gebaseerd op identiteit. Dergelijke objecten kunnen veilig worden gebruikt als sleutels in gehasheerde containers. Meerdere exemplaren van handles kunnen naar dezelfde bron verwijzen. Voor hun vergelijking moet de methode equals(Object) worden gebruikt.
- Handle definieert het gedrag van de bron, maar bevat geen informatie over de toestand van de bron (de enige gegevens die het opslaat, zijn de "sleutel", het pad naar de bron).
- Handle kan verwijzen naar een niet-bestaande bron (of naar een bron die nog niet is gemaakt, of naar een bron die al is verwijderd). Het bestaan van de bron kan worden gecontroleerd met de methode IResource.exists().
- Sommige bewerkingen kunnen uitsluitend worden uitgevoerd op basis van de informatie die in de handle zelf is opgeslagen (de zogenaamde handle-only operaties). Voorbeelden hiervan zijn IResource.getParent(), getFullPath(), enzovoorts. De bron hoeft niet noodzakelijkerwijs te bestaan voor het succesvolle uitvoeren van een dergelijke bewerking. Bewerkingen waarvoor het vereist is dat de bron bestaat, gooien een uitzondering (CoreException) als de bron niet bestaat.
Eclipse biedt een efficiënt mechanisme voor notificatie over wijzigingen in de bronnen van de workspace (zie Figuur 3). Bronnen kunnen worden gewijzigd als gevolg van acties die binnen de Eclipse IDE worden uitgevoerd, of als gevolg van synchronisatie met het bestandssysteem. In beide gevallen ontvangen abonnees van de notificaties gedetailleerde informatie over de wijzigingen in de vorm van 'bronnen deltas' (resource delta). Delta beschrijft de wijzigingen tussen twee toestanden van (sub-)bomen van de workspace-bronnen en zelf is het een boom, waarbij elke knoop een wijziging van een bepaalde bron beschrijft en een lijst van deltas van het volgende niveau bevat, die de wijzigingen van de kindbronnen beschrijven.

Figuur 3. IResourceChangeEvent en IResourceDelta
Het notificatiemechanisme op basis van bronnen deltas heeft de volgende kenmerken:
- Zowel een enkele wijziging als meerdere wijzigingen worden beschreven met behulp van dezelfde structuur, aangezien de delta wordt opgebouwd volgens het principe van recursieve compositie. Abonnees kunnen wijzigingen in de bronnen verwerken door recursief door de delta-structuur te navigeren.
- De delta bevat volledige informatie over de wijziging van de bron, inclusief de verplaatsing en/of wijziging van de bijbehorende 'markers' (zoals fouten bij het compileren die in de vorm van markers worden weergegeven).
- Aangezien verwijzingen naar bronnen via een handle worden gemaakt, kan de delta op een natuurlijke manier verwijzen naar een externe bron.
Zoals we binnenkort zullen zien, zijn de belangrijkste componenten van het ontwerp van het notificatiemechanisme voor wijzigingen in het model van bronnen ook relevant voor andere handle-gebaseerde modellen.
JDT Core
Het model van de Eclipse workspace-bronnen is een fundamenteel taalonafhankelijk model. De JDT Core-component (plugin org.eclipse.jdt.core) biedt een API voor navigatie en analyse van de structuur van de workspace vanuit het perspectief van Java, het zogenaamde 'Java-model' (Java-model). Deze API is gedefinieerd in termen van Java-elementen, in tegenstelling tot de onderliggende API van het bronnenmodel, die is gedefinieerd in termen van mappen en bestanden. De belangrijkste interfaces van de boom van Java-elementen zijn weergegeven in Figuur 4.

Figuur 4. Elementen van het Java-model
Het Java-model gebruikt dezelfde handle/body-idiom als het resources-model (zie fig. 5). IJavaElement is de handle, terwijl JavaElementInfo de body vervult. De interface IJavaElement definieert een protocol dat gemeenschappelijk is voor alle Java-elementen. Sommige van zijn methoden zijn alleen handle: getElementName(), getParent(), enz. Het object JavaElementInfo slaat de toestand van het overeenkomstige element op: zijn structuur en attributen.

Figuur 5. IJavaElement en JavaElementInfo
Het Java-model wijkt op bepaalde punten af van de implementatie van het basisontwerp handle/body in vergelijking met het resources-model. Zoals eerder vermeld, ligt de element tree in het resources-model, waarvan de knooppunten objecten resource info zijn, volledig in het geheugen. Maar in het Java-model kan er een aanzienlijk groter aantal elementen zijn dan in de resources tree, omdat het ook de interne structuur van .java en .class bestanden omvat: types, velden en methodes.
Om te voorkomen dat de volledige materialisatie van de gehele element tree in het geheugen plaatsvindt, gebruikt de implementatie van het Java-model een beperkt LRU-cache element info, waarbij de sleutel de handle van IJavaElement is. De objecten element info worden op aanvraag gecreëerd terwijl de navigatie door de element tree plaatsvindt. Hierbij worden de minst vaak gebruikte elementen uit de cache verdrongen en blijft het geheugenverbruik van het model binnen de vastgestelde cachegrootte. Dit is weer een ander voordeel van het handle-gebaseerde ontwerp, dat dergelijke implementatiedetails volledig verbergt voor de klantcode.
Het mechanisme voor het notificeren van wijzigingen aan Java-elementen is in grote lijnen vergelijkbaar met het hierboven besproken mechanisme voor het volgen van wijzigingen in de resources workspace. Een klant die wijzigingen in het Java-model wil volgen, abonneert zich op notificaties die worden gepresenteerd als een ElementChangedEvent-object, dat IJavaElementDelta bevat (zie fig. 6).

Figuur 6. ElementChangedEvent en IJavaElementDelta
Het Java-model bevat geen informatie over de inhoud van methoden of naamresolutie, daarom biedt JDT Core een aanvullende (niet-handle-gebaseerde) model voor gedetailleerde code-analyse geschreven in Java: (abstract syntax tree, AST). De AST vertegenwoordigt het resultaat van de syntactische analyse van de broncode. De knooppunten van de AST komen overeen met de elementen van de structuur van de bronmodule (declaraties, operatoren, expressies, enz.) en bevatten informatie over de coördinaten van het overeenkomstige element in de broncode, evenals (optioneel) informatie over de naamresolutie in de vorm van verwijzingen naar zogenaamde bindings. Bindings zijn objecten die genummerde entiteiten vertegenwoordigen, zoals types, methoden en variabelen die de compiler kent. In tegenstelling tot AST-knooppunten die een boom vormen, ondersteunen bindings kruisverwijzingen en vormen ze in het algemeen een grafiek. De abstracte klasse ASTNode is de algemene basisclass voor alle AST-knooppunten. Subklassen van ASTNode komen overeen met bepaalde syntactische constructies van de programmeertaal Java.
Aangezien syntactische bomen aanzienlijke hoeveelheden geheugen kunnen verbruiken, cachet JDT slechts één AST voor de actieve editor. In tegenstelling tot het Java-model wordt de AST doorgaans beschouwd als een 'tussen-' of 'tijdelijk' model, waarvan klanten geen referenties buiten de context van de operatie die tot de creatie van de AST heeft geleid, moeten behouden.
De drie genoemde modellen (Java-model, AST, bindings) vormen samen de basis voor het bouwen van 'intelligente ontwikkeltools' in JDT, waaronder een krachtige Java-editor met diverse 'helpers', verschillende acties voor het verwerken van de broncode (waaronder het organiseren van de importlijst en het formatteren volgens de ingestelde stijl), zoek- en refactor-tools. Hierbij speelt het Java-model een bijzondere rol, omdat het als basis wordt gebruikt voor de visuele weergave van de structuur van de ontwikkelde applicatie (bijvoorbeeld in Package Explorer, Outline, Search, Call Hierarchy en Type Hierarchy).
Eclipse-componenten die worden gebruikt in 1C:Enterprise Development Tools
Figuur 7 toont de Eclipse-componenten die de fundamenten van het technologieplatform voor 1C:Enterprise Development Tools vormen.

Figuur 7. Eclipse als platform voor 1C:Enterprise Development Tools
Eclipse Platform biedt de basisinfrastructuur. We hebben enkele aspecten van deze infrastructuur in de vorige sectie behandeld.
(EMF) biedt algemene middelen voor het modelleren van gestructureerde gegevens. EMF is geïntegreerd met het Eclipse Platform, maar kan ook zelfstandig worden gebruikt in gewone Java-toepassingen. Vaak zijn beginnende Eclipse-ontwikkelaars al goed bekend met EMF, hoewel ze nog niet helemaal op de hoogte zijn van de fijne kneepjes van het Eclipse Platform. Een van de redenen voor zijn verdiende populariteit is het universele ontwerp, inclusief een geharmoniseerde meta-niveau API, waardoor op een generieke manier met elk EMF-model kan worden gewerkt. De basisimplementaties die EMF biedt voor modelobjecten en het modelcodegeneratiesysteem op basis van de metamodellen verhogen de ontwikkelingsefficiëntie aanzienlijk en verminderen het aantal fouten. EMF bevat ook mechanismen voor modelserialisatie, het bijhouden van wijzigingen in het model en meer.
Zoals elk echt veelzijdig hulpmiddel is EMF geschikt voor een breed scala aan modelleringstaken, maar bepaalde modelklassen (zoals de hierboven besproken op handle gebaseerde modellen) hebben mogelijk meer gespecialiseerde modelleringstools nodig. Het bespreken van EMF is een onbeloond karwei, vooral binnen de beperkte ruimte van één artikel, aangezien het onderwerp van een afzonderlijk boek is en een tamelijk dik boek bovendien. Laten we alleen opmerken dat het hoogwaardige genericiteitssysteem dat ten grondslag ligt aan EMF, de geboorte heeft gegeven aan een breed scala aan modelleringprojecten die deel uitmaken van het overkoepelende project. samen met EMF zelf. Een van dergelijke projecten is Eclipse Xtext.
biedt de infrastructuur voor "tekstmodellering". Xtext gebruikt voor de syntactische analyse van de brontekst en EMF voor de representatie van de resulterende ASG (abstracte semantische grafiek, die in wezen een combinatie is van AST en bindings), ook wel de "semantische model" genoemd. De grammatica van de met Xtext gemodelleerde taal wordt beschreven in de eigen Xtext-taal. Dit maakt het mogelijk om niet alleen een grammatika-beschrijving voor ANTLR te genereren, maar ook een mechanisme voor de serialisatie van de AST (d.w.z. Xtext biedt zowel een parser als een unparser), contextuele hints, en een aantal andere taalspecifieke componenten. Aan de andere kant is de grammatika beschrijvingstaal die in Xtext wordt gebruikt minder flexibel in vergelijking met de grammatika beschrijvingstaal in ANTLR. Daarom moet de implementeerbare taal soms "worden aangepast" voor Xtext, wat meestal geen probleem is als het gaat om een vanaf nul ontwikkelde taal, maar onaanvaardbaar kan zijn voor talen met een reeds gevestigde syntaxis. Desondanks is Xtext momenteel de meest mature, functioneel volledige, en veelzijdige tool in Eclipse voor het bouwen van programmeertalen en de bijbehorende ontwikkeltools. In het bijzonder is het ideaal voor snel prototyping. (domain-specific language, DSL). Naast de hierboven genoemde "taalkern" op basis van ANTLR en EMF, biedt Xtext tal van nuttige componenten van een hoger niveau, waaronder indexeringsmechanismen, incrementele bouw, een "slimme editor", en nog veel meer, maar laat taalkundige handle-gebaseerde modellen buiten beschouwing. Net als EMF is Xtext een onderwerp dat een apart boek waard is, en we zullen nu waarschijnlijk niet eens kort kunnen praten over al zijn mogelijkheden.
1C:Enterprise Development Tools maken zowel actief gebruik van EMF zelf, als van verschillende andere Eclipse Modeling-projecten. In het bijzonder is Xtext een van de basiscomponenten voor ontwikkeltools voor talen in 1C:Enterprise, zoals de ingebedde programmeertaal en de querytaal. Een andere basis van deze ontwikkeltools is het Eclipse Handly-project, waar we later dieper op in zullen gaan (van de genoemde Eclipse-componenten is het tot nu toe het minst bekend).
, het subproject van het bovenliggende project Eclipse Technology, is ontstaan uit de initiële bijdrage van code aan de Eclipse Foundation, geleverd door het bedrijf 1C in 2014. Sindsdien blijft het bedrijf 1C de ontwikkeling van het project ondersteunen: de committer'ers van Handly zijn medewerkers van het bedrijf. Het project is klein, maar vervult een unieke niche binnen Eclipse: de hoofddoelstelling is het ondersteunen van de ontwikkeling van handle-based modellen.
De belangrijkste architecturale principes van handle-based modellen, zoals de handle/body-idioma, zijn eerder besproken aan de hand van de resource model en het Java-model. Daar werd ook opgemerkt dat zowel het resource model als het Java-model belangrijke fundamenten zijn voor de Eclipse Java Development Tools (JDT). Aangezien vrijwel alle *DT-projecten van Eclipse een architectuur hebben die vergelijkbaar is met die van JDT, zou het geen grote overdrijving zijn om te zeggen dat handle-based modellen ten grondslag liggen aan vele, zo niet alle IDE's die bovenop het Eclipse Platform zijn gebouwd. Bijvoorbeeld, in de Eclipse C/C++ Development Tooling (CDT) is er een handle-based model voor C/C++, dat dezelfde rol vervult in de architectuur van CDT als het Java-model dat doet in JDT.
Voor de komst van Handly bood Eclipse geen gespecialiseerde bibliotheken voor het bouwen van taalhandle-based modellen. De huidige modellen werden voornamelijk gemaakt door directe aanpassing van de code van het Java-model (ook bekend als copy/paste), in de gevallen waarin dit is toegestaan door de Eclipse Public License (EPL). (Het is duidelijk dat, zeg, voor de projecten van Eclipse zelf dit meestal geen juridische problemen oplevert, in tegenstelling tot producten met gesloten broncode.) Naast de inherente chaotische aard van deze methode leidt het tot bekende problemen: duplicatie van code, fouten die bij de aanpassing ontstaan, enz. Wat nog erger is, de resulterende modellen blijven 'een op zichzelf staand iets' en benutten niet het bestaande potentieel voor unificatie. Het identificeren van gemeenschappelijke concepten en protocollen voor taalhandle-based modellen zou kunnen leiden tot de creatie van herbruikbare componenten voor hun verwerking, vergelijkbaar met wat er is gebeurd met EMF.
Het kan niet gezegd worden dat er binnen Eclipse geen begrip was voor deze problemen. Al in 2005 , generaliserend uit de ervaring van de ontwikkeling van het prototype CDT, de noodzaak om een gezamenlijke infrastructuur voor taalmodellen te creëren, inclusief handle-based modellen. Maar zoals vaak het geval is, kwamen deze ideeën door andere prioritaire taken niet tot uitvoering. Ondertussen blijft de factorisatie van code van *DT-projecten een van de onderwerpen die in Eclipse nog onvoldoende zijn uitgewerkt.
In zekere zin is het Handly-project bedoeld om vergelijkbare taken op te lossen als EMF, maar dan voor handle-based modellen, en in dit geval voor taalmodellen (d.w.z. die elementen van de structuur van een programmeertaal vertegenwoordigen). Hieronder staan de belangrijkste doelstellingen die zijn gesteld bij het ontwerpen van Handly:
- Het identificeren van de belangrijkste abstracties van het domein.
- Vermindering van inspanning en verbetering van de kwaliteit van de implementatie van taal handle-based modellen door codehergebruik.
- Het bieden van een uniforme API op meta-niveau voor de resulterende modellen, waardoor de creatie van algemene IDE-componenten mogelijk wordt die werken met taal handle-based modellen.
- Flexibiliteit en schaalbaarheid.
- Integratie met Xtext (in een aparte laag).
Om gemeenschappelijke concepten en protocollen te identificeren, zijn bestaande implementaties van taal handle-based modellen geanalyseerd. De belangrijkste interfaces en basisimplementaties die door Handly worden geleverd, worden weergegeven in fig. 8.

Figuur 8. Algemene interfaces en basisimplementaties van Handly-elementen
De interface IElement vertegenwoordigt de handle van een element en is gemeenschappelijk voor elementen van alle modellen die op Handly zijn gebaseerd. De abstracte klasse Element implementeert een gegeneraliseerd mechanisme handle/body (fig. 9).

Figuur 9. IElement en de gegeneraliseerde implementatie van handle/body
Bovendien biedt Handly een gegeneraliseerd mechanisme voor notificatie van veranderingen in model-elementen (fig. 10). Zoals zichtbaar is, lijkt het in grote lijnen op de notificatiemechanismen die zijn geïmplementeerd in het model voor middelen en het Java-model, en maakt gebruik van IElementDelta voor een uniforme weergave van informatie over de wijziging van een element.

Figuur 10. Algemene interfaces en basisimplementaties van het Handly-notificatiemechanisme
De eerder besproken onderdelen van Handly (fig. 9 en 10) kunnen worden gebruikt voor het weergeven van vrijwel alle handle-based modellen. Voor de creatie taal modellen biedt het project extra functionaliteit - in het bijzonder, algemene interfaces en basisimplementaties voor elementen van de structuur van de brontekst, de zogenaamde source elements (fig. 8). De ISourceFile-interface vertegenwoordigt het brondocument, terwijl ISourceConstruct een element binnen het brondocument is. De abstracte klassen SourceFile en SourceConstruct implementeren algemene mechanismen ter ondersteuning van de werking met brondocumenten en hun elementen, zoals het werken met tekstbuffers, het koppelen aan de coördinaten van een element in de oorspronkelijke tekst, het reconciliëren van het model met de huidige inhoud van de werkcopy-buffer, enzovoort. De implementatie van deze mechanismen is doorgaans een behoorlijk ingewikkelde taak, en Handly kan de ontwikkelinspanningen voor taalmodellen op basis van handles aanzienlijk verminderen door kwalitatieve basisimplementaties te bieden.
Naast de hierboven genoemde basismechanismen, biedt Handly een infrastructuur voor tekstbuffers en 'instanties' (snapshots), ondersteuning voor integratie met code-editors (inclusief de 'out-of-the-box' integratie met de Xtext-editor), evenals enkele algemene UI-componenten die werken met modellen op basis van Handly, zoals het outline-framework. Om zijn mogelijkheden te illustreren, biedt het project verschillende voorbeelden, waaronder de implementatie van een Java-model op Handly. (Vergeleken met de volledige implementatie van het Java-model in JDT, is dit model opzettelijk iets vereenvoudigd voor een betere overzichtelijkheid.)
Zoals eerder opgemerkt, is er tijdens het initiële ontwerp van Handly en de verdere ontwikkeling veel aandacht besteed aan schaalbaarheid en flexibiliteit.
In principe schalen handle-based modellen vrij goed 'by design'. Bijvoorbeeld, de handle/body-idioma maakt het mogelijk om het geheugengebruik van het model te beperken. Maar er zijn ook nuances. Tijdens tests van Handly op schaalbaarheid werd een probleem ontdekt in de implementatie van het notificatiemechanisme – bij het wijzigen van een groot aantal elementen vergde het opbouwen van deltas te veel tijd. Bleek dat hetzelfde probleem ook aanwezig was in het Java-model van JDT, waarvan op een gegeven moment de betreffende code was aangepast. We hebben de fout in Handly gecorrigeerd en een vergelijkbare patch voor JDT voorbereid, die met dank werd geaccepteerd. Dit is slechts een van de voorbeelden waarbij de implementatie van Handly in bestaande modelimplementaties potentieel nuttig zou kunnen zijn, aangezien in dat geval zo'n fout op slechts één plek zou kunnen worden gecorrigeerd.
Om de integratie van Handly in bestaande implementaties technisch mogelijk te maken, moet de bibliotheek aanzienlijke flexibiliteit bezitten. Het belangrijkste probleem is om de achterwaartse compatibiliteit van de API van het model te behouden. Deze uitdaging is opgelost in door een duidelijke scheiding aan te brengen tussen de model-specifieke API, gedefinieerd en volledig gecontroleerd door de ontwikkelaar, en de gestandaardiseerde API van het meta-niveau die door de bibliotheek wordt aangeboden. Dit maakt niet alleen de technische integratie van Handly in bestaande implementaties mogelijk, maar geeft de ontwikkelaar van het nieuwe model ook aanzienlijke vrijheid bij het ontwerpen van de API.
Flexibiliteit heeft ook andere aspecten. Bijvoorbeeld, Handly legt bijna geen beperkingen op aan de structuur van het model en kan worden gebruikt voor zowel het modelleren van algemene programmeertalen als domeinspecifieke talen. Bij het bouwen van de structuur van het bronbestand schrijft Handly geen specifieke vorm voor de representatie van de AST voor en vereist in principe niet eens de aanwezigheid van een AST, waardoor compatibiliteit met vrijwel alle parsingmechanismen wordt gegarandeerd. Tenslotte ondersteunt Handly volledige integratie met de Eclipse-workspace, maar kan ook rechtstreeks met bestandssystemen werken, dankzij de integratie met (EFS).
De huidige versie is uitgebracht in december 2016. Hoewel het project momenteel in de incubatiefase verkeert en de API nog niet definitief is vastgelegd, wordt Handly al gebruikt in twee grote commerciële producten die de risico's hebben genomen om als 'early adopters' op te treden, en tot nu toe hebben ze daar geen spijt van.
Zoals hierboven vermeld, is een van deze producten 1C:Enterprise Development Tools, waar Handly vanaf het begin wordt gebruikt voor het modelleren van de elementen van de high-level structuur van talen zoals 1С:Enterprise, waaronder de ingebouwde programmeertaal en de querytaal. Het andere product is minder bekend bij het grote publiek. Dit is , een geïntegreerde ontwerpoplossing voor probleemgerichte processors (application-specific instruction-set processors, ASIP), die zowel binnen het Tsjechische bedrijf Codasip als door hun klanten wordt gebruikt, waaronder , , , Codasip maakt sinds 2015 gebruik van Handly in productie, beginnend met versie Handly 0.2. De laatste versie van Codasip Studio gebruikt versie 0.5, die in juni 2016 is uitgebracht. Ondřej Ilčík, die het IDE-ontwikkelteam bij Codasip leidt, onderhoudt contact met het project en biedt cruciale feedback als "third-party adopter". Hij heeft zelfs wat tijd weten vrij te maken om persoonlijk bij te dragen aan het project door een UI-laag (~ 4000 regels code) te implementeren voor een van de Handly-voorbeelden, het Java-model. Meer gedetailleerde informatie "uit de eerste hand" over het gebruik van Handly door adopters is te vinden op de pagina van het project.
We hopen dat na de release van versie 1.0 met garantie voor API-stabiliteit en de exit uit de incubatiestatus, Handly nieuwe adopters zal hebben. Voorlopig blijft het project in de testfase en verbetert de API verder, met twee "grote" releases per jaar – in juni (op dezelfde datum als de gelijktijdige release van Eclipse) en in december, waardoor een voorspelbare schema ontstaat waarop adopters kunnen rekenen. Daarnaast is het vermeldenswaardig dat de bugrate van het project op een constant laag niveau blijft en dat Handly vanaf de allereerste versies betrouwbaar werkt in producten van vroege adopters. Voor verdere kennismaking met Eclipse Handly kan men gebruikmaken van en .
Bron: habr.com
