Lagring af arbejdsområde udløses, når arbejdsbænken lukkes af brugeren eller periodisk af platformen. Plugins kan deltage i arbejdsområdets lagringsproces, så kritiske plugin-data gemmes på disken, når resten af arbejdsområdets vedvarende data gemmes.
Lagring af arbejdsområdet kan også bruges til at spore ændringer, der finder sted mellem aktivering af plugins.
Du skal have tilføjet en gemt deltager til arbejdsområdet, for at denne kan deltage i lagring af arbejdsområdet. Dette gøres typisk under plugin'ens startmetode. Det er også her, at en tilstand, der er gemt, da plugin'en sidst blev lukket ned, læses.
Følgende simple plugin demonstrerer lagringsprocessen:
package com.example.saveparticipant; import org.eclipse.core.runtime.*; import org.eclipse.core.resources.*; import java.io.File; import java.util.*; public class MyPlugin extends Plugin { private static MyPlugin plugin; public MyPlugin(IPluginDescriptor descriptor) { super(descriptor); plugin = this; } public static MyPlugin getDefault() { return plugin; } protected void readStateFrom(fildestination) { } public void startup() throws CoreException { super.startup(); ISaveParticipant saveParticipant = new MyWorkspaceSaveParticipant(); ISavedState lastState = ResourcesPlugin.getWorkspace().addSaveParticipant(this, saveParticipant); if (lastState == null) return; IPath location = lastState.lookup(new Path("save")); if (location == null) return; // plugin-forekomsten skal læse en vigtig tilstand fra filen. File f = getStateLocation().append(location).toFile(); readStateFrom(f); } protected void writeImportantState(fildestination) { } }
ISaveParticipant definerer protokollen for en deltager i lagring af arbejdsområdet. Implementorer af denne grænseflade kan stille funktioner til rådighed for de forskellige trin i lagringsprocessen. I det følgende ses på trinene og på, hvordan klassen WorkspaceSaveParticipant implementerer hver af disse trin.
public void prepareToSave(ISaveContext kontekst) throws CoreException { }
public void saving(ISaveContext kontekst) throws CoreException { switch (context.getKind()) { case ISaveContext.FULL_SAVE: MyPlugin myPluginInstance = MyPlugin.getDefault(); // gemmer plugin'ens tilstand int saveNumber = context.getSaveNumber(); String saveFileName = "save-" + Integer.toString(saveNumber); File f = myPluginInstance.getStateLocation().append(saveFileName).toFile(); // hvis der ikke skrives, vises en undtagelse, og stien opdateres ikke myPluginInstance.writeImportantState(f); context.map(new Path("save"), new Path(saveFileName)); context.needSaveNumber(); break; case ISaveContext.PROJECT_SAVE: // henter det projekt, der er relateret til denne lagringsfunktion IProject project = context.getProject(); // gemmer oplysninger, hvis det er nødvendigt break; case ISaveContext.SNAPSHOT: // Denne funktion skal udføres meget hurtigt, fordi // arbejdsområdet ofte kan anmode om snapshots. break; } }
ISaveContext beskriver oplysninger om lagringsfunktionen. Der er tre typer lagringsfunktion: FULL_SAVE, SNAPSHOT og PROJECT_SAVE. Lagringsdeltagerne skal sørge for at udføre den funktion, der er relevant for den type lagringsaktivitet, der er underrettet om. Snapshot-aktiviteter kan f.eks. ofte finde sted, og hensigten er, at plugins skal kunne gemme deres kritiske tilstand. At bruge lang tid på at gemme en tilstand, som skal beregnes igen i tilfælde af et nedbrud, reducerer platformens ydeevne.
Ved oprettelsen af datalagringsfiler benyttes lagringsnumre, og disse numre er fortløbende (save-1, save-2 osv.) Hver lagringsfil knyttes til et logisk filnavn vha. mapping (save), der er uafhængigt af lagringsnummeret. Plugin-data skrives til den tilsvarende fil og kan hentes senere uden af have kendskab til det specifikke lagringsnummer på den seneste lagringsfunktion, der er udført uden fejl. Denne teknik benyttes også i plugin'ens startkode:
IPath placering = lastState.lookup(new Path("save"));Når dataene er gemt, og filnavnet er tilknyttet vha. mapping, kaldes needSaveNumber for at angive, at aktiv deltagelse i lagring af arbejdsområde har fundet sted, og at et nummer ønskes tildelt lagringsaktiviteten. Lagringsnumrene kan bruges til at oprette datafilen som ovenfor.
public void doneSaving(ISaveContext kontekst) { MyPlugin myPluginInstance = MyPlugin.getDefault(); // sletter den tidligere gemte tilstand, da den er overflødig int previousSaveNumber = context.getPreviousSaveNumber(); String oldFileName = "save-" + Integer.toString(previousSaveNumber); File f = myPluginInstance.getStateLocation().append(oldFileName).toFile(); f.delete(); }
Her er det muligt at rydde op i de oplysninger, der er gemt i den forrige lagringsfunktion. Vi bruger getPreviousSaveNumber til at hente lagringsnummeret, der er tildelt i den forrige lagringsfunktion (ikke den, der netop er afsluttet). Dette nummer bruges til at konstruere navnet på den fil, der skal slettes. Bemærk, at lagringstilstandens logiske fildefinition ikke benyttes, da det aktuelle lagringsfilnummer allerede er tilknyttet vha. mapping.
public void rollback(ISaveContext kontekst) { MyPlugin myPluginInstance = MyPlugin.getDefault(); // da lagringsfunktionen ikke er udført korrekt, skal den gemte tilstand, som netop er skrevet, slettes int saveNumber = context.getSaveNumber(); String saveFileName = "save-" + Integer.toString(saveNumber); File f = myPluginInstance.getStateLocation().append(saveFileName).toFile(); f.delete(); }
Du skal slette den tilstand, der netop er gemt. Bemærk, at det aktuelle lagringsnummer benyttes til at konstruere navnet på den fil, der netop er gemt. Du skal ikke tænke på, at du har tilknyttet dette filnavn vha. mapping til ISaveContext. Platformen skiller sig af med konteksten, når en lagringsfunktion ikke udføres korrekt.
Hvis plugin'en viser en undtagelse i løbet af lagringens livscyklus, fjernes den fra den aktuelle lagringsfunktion og modtager ingen af de resterende livscyklusmetoder. Hvis en lagringsmetode ikke udføres korrekt, vises en rollback- eller doneSaving-meddelelse.
Når du tilføjer en gemt deltager til arbejdsområdet, returneres et ISavedState-objekt, som beskriver, hvad plugin'en gemte under den seneste lagringsfunktion (eller null, hvis plugin'en ikke tidligere har gemt en tilstand). Dette objekt kan bruges til at få adgang til oplysninger fra den forrige lagringsfil (vha. lagringsnummeret og fildefinitionen) eller til at behandle ændringer, der har fundet sted mellem aktiveringer af en plugin.
Hvis en fildefinition bruges til at gemme filer, der er logisk navngivet iht. lagringsnummer, kan den samme definition bruges til at hente data fra den sidst kendte lagringstilstand.
ISaveParticipant saveParticipant = new MyWorkspaceSaveParticipant(); ISavedState lastState = ResourcesPlugin.getWorkspace().addSaveParticipant(myPluginInstance, saveParticipant); if (lastState != null) { String saveFileName = lastState.lookup(new Path("save")).toString(); File f = myPluginInstance.getStateLocation().append(saveFileName).toFile(); // plugin-forekomsten skal læse en vigtig tilstand fra filen. myPluginInstance.readStateFrom(f); }
Husk på, at et vilkårligt antal ressourceændringsaktiviteter kan finde sted i arbejdsområdet, inden plugin'en overhovedet aktiveres. Hvis du vil vide, hvilke ændringer har fundet sted, siden plugin'en sidst blev deaktiveret, kan du bruge lagringsmekanismen, selvom du ikke har brug for at gemme andre data.
Lagringsdeltageren skal anmode platformen om at opbevare en ressourcedelta på vegne af lagringsdeltageren. Dette sker som en del af lagringsfunktionen.
public void saving(ISaveContext kontekst) throws CoreException { // der er ingen tilstand, som plugin'en skal gemme, men anmod // om, at der benyttes en ressourcedelta ved næste aktivering. context.needDelta(); }
Under plugin-start kan der opnås adgang til den forrige gemte tilstand, og ændringsaktiviteter oprettes for alle ændringer, der har fundet sted, siden sidste lagring.
ISaveParticipant saveParticipant = new MyWorkspaceSaveParticipant(); ISavedState lastState = ResourcesPlugin.getWorkspace().addSaveParticipant(myPluginInstance, saveParticipant); if (lastState != null) { lastState.processResourceChangeEvents(new MyResourceChangeReporter()); }
Den leverede klasse skal implementere IResourceChangeListener som beskrevet i Spor ressourceændringer. De ændringer, der har fundet sted siden sidste lagring, rapporteres som en del af POST_AUTO_BUILD-ressourceændringsaktiviteten.
Bemærk: Markeringsændringer rapporteres ikke i de ændringsaktiviteter, der gemmes i en ISavedState. Du må antage, at en eller alle markeringer er ændret, siden den seneste tilstand blev gemt.