Przewodnik przejścia po integracji modeli logicznych dotyczący repozytorium

Aby zagwarantować pełną obsługę modeli logicznych, dostawca repozytorium może wykonać następujące czynności:

  1. Udostępnić odpowiednie operacje repozytorium elementom, które dopasowują się do klasy ResourceMapping.
  2. Zagwarantować, że operacje wykonywane na odwzorowaniach zasobów obejmują wszystkie odpowiednie elementy modelu oraz zasoby, wykorzystując interfejs ISynchronizationScope oraz obsługujący go interfejs API.
  3. Umożliwić dostawcom modeli uczestnictwo w beznagłówkowym scalaniu przez użycie interfejsu IMergeContext i obsługującego go interfejsu API.
  4. Umożliwić dostawcom modeli uczestnictwo w podglądach scalenia przez użycie punktu rozszerzenia teamContentProviders dla modeli zaangażowanych w scalenie. W zarządzaniu relacjami między treścią modelu, kontekstem scalenia oraz środowiskiem porównywania pomocna jest klasa ModelSynchronizeParticipant.
  5. Zapewnić dostęp do historii plików obszaru roboczego przez użycie interfejsu API IFileHistoryProvider.
  6. Zapewnić dostęp do zdalnych konfiguracji przy użyciu interfejsu API systemu plików Eclipse we wtyczce org.eclipse.core.filesystem oraz udostępnić dowiązanie do projektów obszaru roboczego przy użyciu klasy ProjectSetCapability.
  7. Obsługiwać dekoracje elementów modelu logicznego udostępniając mechanizm obszaru roboczego Subscriber, którego można użyć z interfejsem API SynchronizationStateTester.

W poniższych sekcjach opisano każdy z powyższych punktów nieco bardziej szczegółowo. Wtyczka org.eclipse.team.examples.filesystem zawiera przykład, który odnosi się do kilku z powyższych punktów. Odpowiedni projekt można pobrać z repozytorium CVS i używać jako odwołania podczas lektury tego kursu. Zastrzeżenie: kod źródłowy w przykładowej wtyczce może się zmieniać. Aby uzyskać kopię zgodną z tym przykładem, można pobrać projekt ze znacznikiem wersji 3.2 (najprawdopodobniej R3_2) lub znacznikiem daty 28 czerwca 2006 r.

Wnoszenie akcji do odwzorowań zasobów

Podstawowy interfejs API odwzorowywania zasobów

Interfejs API odwzorowywania zasobów składa się z następujących klas:

Istnieją dwa typy wtyczek, które mogą być interesujące z punktu widzenia odwzorowań zasobów. Są to takie wtyczki, które udostępniają model składający się z zasobów obszaru roboczego lub w nich utrwalony, a także takie, które mają wykonywać operacje na zasobach. Pierwszy przypadek będzie opisany w Przewodniku przejścia dotyczącym modelu, a drugi w następnej sekcji.

Odwzorowania zasobów i obiekty wnoszone przez kontrybutora

Wtyczki, które wnoszą rozszerzenia do dopasowywalnych punktów rozszerzeń, będą musiały zostać zmienione w dwóch aspektach, aby obsługiwać nowe interfejsy API ResourceMapping:

  1. Zaktualizuj wszystkie elementy objectContribution należące do punktu rozszerzenia popupMenu w odpowiadających im plikach plugin.xml tak, aby kierowały na klasę ResourceMapping zamiast interfejs IResource (w odpowiednich przypadkach).
  2. Zaktualizuj ich akcje tak, aby korzystały z klasy ResourceMapping zamiast interfejsu IResource i dostosowywały się do ograniczeń głębokości w ścieżkach przejścia.

Wtyczki, które wnoszą obiekty do interfejsu IResource, mogą teraz w zamian dodawać je do klasy ResourceMapping, jeśli akcja może dotyczyć wielu zasobów. Poniżej przedstawiono fragment kodu XML, który wnosi akcję menu do obiektów dopasowujących się do odwzorowań zasobów:

      <extension
       point="org.eclipse.ui.popupMenus">
     <objectContribution
            objectClass="org.eclipse.core.resources.mapping.ResourceMapping"
            adaptable="true"
            id="org.eclipse.team.ccvs.ui.ResourceMapperContributions">
<enablement>
<adapt type="org.eclipse.core.resources.mapping.ResourceMapping">
<test
property="org.eclipse.core.resources.projectPersistentProperty"
args="org.eclipse.team.core.repository,org.eclipse.team.cvs.core.cvsnature" />
</adapt>
</enablement>
<action
label="%UpdateAction.label"
definitionId="org.eclipse.team.cvs.ui.update"
class="org.eclipse.team.internal.ccvs.ui.actions.UpdateAction"
tooltip="%UpdateAction.tooltip"
menubarPath="team.main/group2"
id="org.eclipse.team.cvs.ui.update">
</action>
...
</objectContribution>
</extension>

Obiekty wnoszone do klasy ResourceMapping będą automatycznie stosowane do obiektów, które dopasowują się do interfejsuIResource. To przejściowe powiązanie jest obsługiwane przez środowisko robocze. Filtrowanie obiektów wnoszonych do odwzorowań zasobów można zrealizować przy użyciu wyrażeń włączających. Dodano wyrażenie do filtrowania przez właściwość trwałą projektu, co umożliwia dostawcom repozytorium wyświetlanie menu w projektach, które są odwzorowane na swoje repozytoria.

Akcje wnoszone do klasy ResourceMapping będą mogły korzystać z wyboru zawierającego jedną lub więcej klas ResourceMapping. Za przekształcenie odwzorowania zasobów na zbiór zasobów do operacji odpowiedzialne są akcje. Można to zrealizować wywołując metodę getTraversals, aby uzyskać ścieżki przejścia odwzorowania. Ścieżki przejścia są stosowane, aby umożliwić klientom ścieżki zoptymalizowanie operacji na podstawie głębokości zasobów, przez które dokonywane jest przejście. Klient może przejść przez zasób ręcznie lub użyć zasobu oraz głębokości jako danych wejściowych do operacji, której akcja deleguje wykonanie pracy. Jeśli na przykład użytkownik aktualizuje pakiet Java w systemie CVS, a odwzorowanie zasobów pakietu Java kieruje na folder o głębokości jeden, system CVS wykona odpowiednią komendę ("cvs update -l" dla zainteresowanych), która wykona płytką aktualizację folderu reprezentowanego przez pakiet.

Chociaż można uzyskać zbiór ścieżek przejścia bezpośrednio z wybranych odwzorowań zasobów, istnieją relacje modeli (lub relacje repozytoriów), które mogą wymagać dodania do operacji dodatkowych zasobów lub elementów modeli. W następnej sekcji opisano, jak zagwarantować, aby wszystkie niezbędne zasoby były uwzględnione w operacji.

Zasięg operacji

W przypadku operacji zespołowych należy dokonać konwersji wybranych odwzorowań na zestaw odwzorowań, których ma dotyczyć operacja. Ten proces wymaga sprawdzenia z wszystkimi dostawcami modeli, aby upewnić się, że będą uwzględnieni w operacjach na zasobach, które są zgodne z ich regułami włączania. Pełen zbiór odwzorowań zasobów, których ma dotyczyć operacja, określa się terminem zasięgu operacji. Powyższe działania można zrealizować za pomocą następującego interfejsu API:

Metoda initialize(IProgressMonitor) klasy SynchronizationScopeManager obsługuje cały proces przekształcania wejściowego zbioru odwzorowań zasobów w pełen zbiór odwzorowań, na których należy wykonać operację, a także pełen zbiór ścieżek przejścia, które odpowiadają tym odwzorowaniom. Dostawca repozytorium może dostosować ten proces, używając następujących sposobów:

  1. Udostępniając klasę RemoteResourceMappingContext, której można użyć przy uzyskiwaniu ścieżek przejścia po zasobach z odwzorowań zasobów.
  2. Przesłaniając klasę SynchronizationScopeManager, aby w odpowiedni sposób dostosować proces zarządzania zasięgiem.

W poniższych dwóch sekcjach opisano bardziej szczegółowo powyższe sposoby.

Kontekst odwzorowania zasobu zdalnego

Aby zagwarantować, że wszystkie niezbędne zasoby będą uwzględnione w operacji zespołowej, może zaistnieć potrzeba przejrzenia stanu jednego lub większej liczby zasobów w repozytorium. W przypadku niektórych modeli może to nie być konieczne. Na przykład pakiet Java jest kontenerem odwiedzanym do głębokości równej jeden, niezależnie od zdalnego stanu modelu. Z tego powodu dostawca repozytorium może w łatwy sposób określić, że usunięcia wychodzące powinny być uwzględnione przy zatwierdzaniu, zaś przychodzące elementy dodane powinny być uwzględnione przy aktualizacji. Zasoby, z których składają się niektóre modele logiczne, mogą jednak zmieniać się w czasie. Na przykład zasoby, z których składa się element modelu, mogą być zależne od pliku manifestu (lub podobnego mechanizmu). Aby odwzorowanie zasobów zwracało prawidłową ścieżkę przejścia, musi mieć dostęp do zdalnej treści pliku manifestu (jeśli jest ona różna od treści lokalnej), aby uzyskać informacje na temat tego, czy istnieją dodatkowe zasoby, które należy uwzględnić. Te dodatkowe zasoby mogą nie istnieć w obszarze roboczym, ale dostawca repozytorium powinien wiedzieć jak upewnić się, że istniały podczas wykonywania wybranej akcji.

Aby obsługiwać takie bardziej złożone modele, można przekazać klasę RemoteResourceMappingContext do metody ResourceMapping#getTraversals. Jeśli udostępniony jest kontekst, odwzorowanie może z niego skorzystać, aby zagwarantować, że wszystkie niezbędne zasoby są uwzględnione w ścieżce przejścia. Jeśli nie udostępniono kontekstu, odwzorowanie może założyć, że interesuje je tylko stan lokalny.

Kontekst odwzorowania zasobu zdalnego udostępnia trzy podstawowe zapytania:

Odpowiedź na pierwsze z powyższych pytań zależy od typu wykonywanej operacji. Aktualizacje i scalenia dotyczą zazwyczaj trzech elementów, zaś porównania i zastąpienia (przynajmniej w przypadku systemu CVS) dwóch.

Zespołowy interfejs API środowiska Eclipse zawiera klasę Subscriber, która określa interfejs API udostępniający stan synchronizacji między lokalnym obszarem roboczym i serwerem zdalnym. Dostępny jest kontekst SubscriberResourceMappingContext, który wykorzystuje klasę Subscriber do uzyskania dostępu do niezbędnego stanu zdalnego. Klienty, w których stosowana jest klasa Subscriber, nie muszą wykonywać żadnych dodatkowych czynności, aby uzyskać kontekst odwzorowania zasobów.

Tworzenie klas pochodnych klasy SynchronizationScopeManager

Klasa SynchronizationScopeManager może mieć klasy pochodne, które umożliwiają dostosowanie procesu generowania zasięgu i zarządzania. Dwa główne powody tworzenia klas pochodnych menedżera zasięgów to:

  1. Dostawca repozytorium musi uwzględnić dodatkowe zasoby ze względu na pewne relacje na poziomie repozytorium (np. zbiór zmian). Można to zrealizować przez przesłonięcie metody adjustInputTraversals(ResourceTraversal[]).
  2. Synchronizacja ma dłuższy cykl życia (np. widok Synchronizacja a okno dialogowe) i musi mieć możliwość zareagowania na zmiany zasięgu. Interfejs ISynchronizationScopeParticipant określa interfejs API, który może być używany przez dostawców modeli do brania udziału w procesie zarządzania zasięgiem. Klasa SubscriberScopeManager jest oparta na klasie Subscriber i stanowi podklasę klasy SynchronizationScopeManager. Uwzględnia ona uczestników w procesie zarządzania zasięgiem. Przykładem potrzeby zastosowania tego typu procesów są zbiory robocze. Jeśli zbiór roboczy jest jednym z odwzorowań zasobów w zasięgu, zbiór ścieżek przejścia obejmowanych przez ten zasięg zwiększyłby się, gdyby dodano do zbioru roboczego nowe zasoby.

Scalanie oparte na modelach

Głównym typem operacji repozytorium, który wymaga modeli, jest scalanie. W wielu przypadkach modele muszą uczestniczyć w operacji tylko na poziomie plików. Do obsługi tych przypadków wprowadzono interfejs API IStorageMerger, który umożliwia dostawcom modeli wnoszenie scaleń, które powinny być wykorzystywane do scalania plików z określonym rozszerzeniem lub typem treści. W niektórych przypadkach modele mogą jednak potrzebować dodatkowych kontekstów, aby móc prawidłowo uczestniczyć w scaleniu. W tym celu wprowadzone zostały interfejsy API IResourceMappingMerger oraz IMergeContext.

Operacje scalenia są nadal wywoływane przez akcje powiązane z dostawcą repozytorium. Gdy jednak użytkownik zażąda operacji będącej scaleniem, dostawca repozytorium musi uwzględnić dostawców modeli w procesie scalania, aby scalenie nie uszkodziło modelu.

Z obsługą scalania opartego na modelach związane są dwa główne elementy interfejsu API dostawcy repozytorium.

  1. Interfejs API do opisywania stanu synchronizacji zasobów uwzględnionych w scaleniu.
  2. Interfejs API umożliwiający dostawcom modeli scalanie elementów modelu.
Te dwa elementy są opisane w poniższych sekcjach.

Interfejs API do opisu stanu synchronizacji

Istotnym aspektem scalania opartego na modelach jest interfejs API wykorzystywany do przekazywania stanu synchronizacji uwzględnionych zasobów do dostawcy modelu. Do opisu stanu synchronizacji służą następujące interfejsy:

Dla wszystkich tych interfejsów udostępniono klasy abstrakcyjne. Ich konwencja nazewnictwa opiera się na usunięciu przedrostka "I" z nazwy interfejsu. Jedyną klasą, którą muszą przesłonić dostawcy repozytoriów, jest klasa ResourceDiff. Umożliwia to udostępnienie odpowiednich wersji plików sprzed zmian i po zmianach.

Interfejs API do scalania modeli

Interfejs IMergeContext rozszerza kontekst synchronizacji o dodatkowe metody obsługujące scalanie. Istnieją metody zwrotne umożliwiające:

Udostępniono klasę abstrakcyjną MergeContext, która zawiera domyślne implementacje większości zachowań związanych ze scalaniem, a także korzysta z interfejsu IStorageMerger do wykonywania scaleń trzech elementów. Udostępniono też klasę SubscriberMergeContext, która obsługuje wypełnianie i aktualizowanie opisu stanu synchronizacji związanego z kontekstem scalenia.

Udostępniono też klasę operacji ModelMergeOperation, która korzysta z interfejsu API IResourceMappingMerger do wykonywania operacji scalenia opartych na modelu. Podklasy muszą przesłonić metodę initializeContext(IProgressMonitor), aby zwrócić kontekst scalenia. Operacja wykorzystje ten kontekst do próby scalenia beznagłówkowego opartego na modelu. Jeśli wystąpią konflikty, podgląd scalenia zostaje pozostawiony podklasie. Jak zostanie przedstawione w następnej sekcji, istnieje klasa abstrakcyjna ModelParticipantMergeOperation, która udostępnia możliwość tworzenia podglądów przy użyciu klasy ModelSynchronizeParticipant.

Treść modeli w przeglądarkach zespołowych

Obsługa wyświetlania modeli logicznych w operacjach zespołowych jest udostępniana przez środowisko wspólnego nawigatora, wprowadzone w wersji 3.2 środowiska Eclipse. Modele logiczne mogą powiązać rozszerzenie treści z dostawcą modelu przy użyciu punktu rozszerzenia org.eclipse.team.ui.teamContentProvider. Dostawcy zespołu mają dostęp do tych dostawców treści przez interfejs ITeamContentProviderManager.

Istnieje kilka sytuacji, w których dostawca zespołu może chcieć wyświetlać modele logiczne:

Klasa ModelSynchronizeParticipant udostępnia integrację z widokiem Synchronizacja lub dowolnym innym kontenerem, który może wyświetlić iSynchronizePages. Uczestnik wykorzystuje zarówno istniejące, wstępne możliwości uczestnika synchronizacji, a także możliwości wspólnego nawigatora i dzięki nim umożliwia dostawcom zespołu i modelom dostosowanie paska narzędzi, menu kontekstowego i innych aspektów podglądu scalenia. Klasa ModelSynchronizeParticipant udostępnia następujące mechanizmy:

Poniżej przedstawiono listę kontrolną czynności związanych z dostosowaniem uczestnika synchronizacji modelu do potrzeb konkretnego dostawcy zespołu:

Poniższe fragmenty kodu XML pokazują, jak jest rejestrowana klasa uczestnika systemu CVS i jak definiowana jest jej przeglądarka.

   <extension point="org.eclipse.team.ui.synchronizeParticipants">
<participant
            name="CVS"
            icon="$nl$/icons/full/eview16/cvs_persp.gif"
            class="org.eclipse.team.internal.ccvs.ui.mappings.WorkspaceModelParticipant"
            id="org.eclipse.team.cvs.ui.workspace-participant">
      </participant>
    </extension>   
   <extension point="org.eclipse.ui.navigator.viewer">
       <viewer viewerId="org.eclipse.team.cvs.ui.workspaceSynchronization">
           <popupMenu
                allowsPlatformContributions="false"
                id="org.eclipse.team.cvs.ui.workspaceSynchronizationMenu"> 
             <insertionPoint name="file"/>
             <insertionPoint name="edit" separator="true"/>       
             <insertionPoint name="synchronize"/>
             <insertionPoint name="navigate" separator="true"/>
             <insertionPoint name="update" separator="true"/>
             <insertionPoint name="commit" separator="false"/>
             <insertionPoint name="overrideActions" separator="true"/>
             <insertionPoint name="otherActions1" separator="true"/>
             <insertionPoint name="otherActions2" separator="true"/>
             <insertionPoint name="sort" separator="true"/>
             <insertionPoint name="additions" separator="true"/>             
             <insertionPoint name="properties" separator="true"/>
          </popupMenu>
	</viewer>
    </extension>

Historia plików

Dodany został interfejs API historii plików, który umożliwia modelom dostęp do historii plików. Interfejs API historii plików składa się z następujących interfejsów:

Oprócz tego interfejsu API dodano ogólny widok Historia pliku. Umożliwia on dostawcom zespołów wyświetlanie historii swoich plików i zasobów we współużytkowanym widoku, a także umożliwia modelom wyświetlanie historii elementów modelu w zakresie elementów, które nie są odwzorowane bezpośrednio na pliki. Widok Historia jest widokiem opartym na stronach, który uzyskuje stronę dla konkretnego elementu w następujący sposób:

Możliwości zbioru projektów

Do klasy ProjectSetCapability dodano metody, które obsługują tłumaczenie łańcucha odwołania wykorzystywanego do identyfikowania odwzorowań między projektem i treściami zdalnymi, a także odsyłaczy URI identyfikujących schemat systemu plików zarejestrowany w punkcie rozszerzenia org.eclipse.core.filesystem.filesystems. Dostawcy zespołu mogą opcjonalnie udostępniać obsługę tego mechanizmu, aby umożliwić modelom logicznym zdalne przeglądanie i ładowanie projektów.

Dekorowanie elementów modelu

Dostawcy zespołu mogą dekorować elementy modelu, przekształcając ich proste dekoracje tak, aby działały dla odwzorowań zasobów, w ten sam sposób jak obiekty wnoszone przez kontrybutora są przekształcane, aby mogły działać z odwzorowaniami zasobów. Jest jednak pewien aspekt dekoracji elementów modelu logicznego, który sprawia problemy. Jeśli element modelu nie jest w relacji "jeden do jednego" z zasobem, element modelu może nie uzyskać aktualizacji etykiety, gdy zmienią się zasoby stanowiące jego podstawę.

Aby rozwiązać ten problem, wprowadzono interfejs ITeamStateProvider, umożliwiający dostawcom modeli dostęp do zmian stanu, które mogą mieć wpływ na dekoracje zespołu. Dodatkowo widoki modeli mogą wykorzystywać klasę SynchronizationStateTester, aby określić, kiedy trzeba zaktualizować etykiety elementów modelu logicznego. Ten interfejs API opiera się na interfejsie ITeamStateProvider i umożliwia określenie, kiedy stan zespołu danego zasobu został zmieniony, a także może być przekazywany do dekoracji zespołu jako część kontekstu IDecorationContext.