Använda transaktioner för att uppdatera modellen

Transaktioner ser till att ändringar som har gjorts i lagringen behandlas som en grupp. Ändringar som är grupperade kan committeras eller återställas som en enda enhet.

När programkoden ändrar, lägger till eller tar bort ett element i Store i Visual Studio Visualization and Modeling SDK måste den göra det i en transaktion. Det måste finnas en aktiv instans av Transaction associerad med Store när ändringen sker. Detta gäller för alla modellelement, relationer, former, diagram och deras egenskaper.

Transaktionsmekanismen hjälper dig att undvika inkonsekventa tillstånd. Om ett fel uppstår under en transaktion återställs alla ändringar. Om användaren utför ett Ångra-kommando behandlas varje ny transaktion som ett enda steg. Användaren kan inte ångra delar av en nyligen genomförd ändring, såvida du inte uttryckligen placerar dem i separata transaktioner.

Öppna en transaktion

Den mest praktiska metoden för att hantera en transaktion är med en using instruktion som omges av en try...catch instruktion:

Store store; ...
try
{
  using (Transaction transaction =
    store.TransactionManager.BeginTransaction("update model"))
    // Outermost transaction must always have a name.
  {
    // Make several changes in Store:
    Person p = new Person(store);
    p.FamilyTreeModel = familyTree;
    p.Name = "Edward VI";
    // end of changes to Store

    transaction.Commit(); // Don't forget this!
  } // transaction disposed here
}
catch (Exception ex)
{
  // If an exception occurs, the Store will be
  // rolled back to its previous state.
}

Om ett undantag som förhindrar den sista Commit() inträffar under ändringarna återställs Store till sitt tidigare läge. Detta hjälper dig att se till att felen inte lämnar modellen i ett inkonsekvent tillstånd.

Du kan göra valfritt antal ändringar i en transaktion. Du kan öppna nya transaktioner i en aktiv transaktion. De kapslade transaktionerna måste bekräftas eller rullas tillbaka innan den transaktion som innehåller dem avslutas. Mer information finns i exemplet för egenskapen TransactionDepth .

Om du vill göra ändringarna permanenta bör Commit du göra transaktionen innan den tas bort. Om ett undantag inträffar som inte fångas i transaktionen återställs Store till dess tillstånd före ändringarna.

Återställa en transaktion

För att säkerställa att Store förblir i eller återgår till dess tillstånd före transaktionen kan du använda någon av dessa taktiker:

  1. Upphöj ett undantag som inte fångas inom transaktionens omfång.

  2. Återställ uttryckligen transaktionen:

    this.Store.TransactionManager.CurrentTransaction.Rollback();
    

Transaktioner påverkar inte objekt som inte är lagrade

Transaktioner styr endast tillståndet för butiken. De kan inte ångra partiella ändringar som har gjorts i externa objekt, till exempel filer, databaser eller objekt som du har deklarerat med vanliga typer utanför DSL-definitionen.

Om ett undantag kan göra en sådan ändring inkonsekvent med Store bör du hantera den möjligheten i undantagshanteraren. Ett sätt att se till att externa resurser förblir synkroniserade med Store-objekten är att koppla varje externt objekt till ett element i arkivet med hjälp av händelsehanterare. Mer information finns i Händelsehanterare sprider ändringar utanför modellen.

Regler aktiveras i slutet av en transaktion

Innan transaktionen avslutas, utlöses de regler som är kopplade till elementen i lagringen i slutet av en transaktion. Varje regel är en metod som tillämpas på ett modellelement som har ändrats. Det finns till exempel regler för "korrigering" som uppdaterar tillståndet för en form när dess modellelement har ändrats och som skapar en form när ett modellelement skapas. Det finns ingen angiven avfyrningsordning. En ändring som görs av en regel kan utlösa en annan regel.

Du kan definiera dina egna regler. Mer information om regler finns i Svara på och sprida ändringar.

Regler aktiveras inte efter ett ångra, ett göra om, eller ett återgångskommando.

Transaktionskontext

Varje transaktion har en ordlista där du kan lagra all information du vill:

store.TransactionManager

.CurrentTransaction.TopLevelTransaction

.Context.Add(aKey, aValue);

Detta är särskilt användbart för överföring av information mellan regler.

Transaktionstillstånd

I vissa fall måste du undvika att sprida en ändring om ändringen orsakas av att en transaktion ångras eller görs om. Detta kan till exempel inträffa om du skriver en egenskapsvärdehanterare som kan uppdatera ett annat värde i Store. Eftersom ångra-åtgärden återställer alla värden i Store till deras tidigare tillstånd är det inte nödvändigt att beräkna uppdaterade värden. Använd den här koden:

if (!this.Store.InUndoRedoOrRollback) {...}

Regler kan utlösas när lagringen först håller på att läsas in från en fil. Om du vill undvika att svara på dessa ändringar använder du:

if (!this.Store.InSerializationTransaction) {...}