Migracja
Doconut.NETFramework 26.8.0 (.NET Framework 4.7) do 26.9.0 (.NET Framework 4.7.2)
Ta strona opisuje aktualizację istniejącej aplikacji ASP.NET z Doconut.NETFramework 26.8.0 lub wcześniejszej (.NET Framework 4.7) do 26.9.0 i nowszej (.NET Framework 4.7.2). Pakiet próbek Doconut zawiera kompletny przewodnik migracji oraz klasyczne próbki przeniesione do nowego API — MVC 5, farmę serwerów i Web Forms. Porównanie (diffowanie) Twojej aplikacji z próbką, od której zaczęła, jest najszybszą drogą.
Jeden pakiet, dwie wersje
Obie biblioteki publikowane są pod tym samym identyfikatorem pakietu, Doconut.NETFramework. Wersja je odróżnia:
| Wersja | Docelowy | API |
|---|---|---|
| 26.8.0 i wcześniejsze | .NET Framework 4.7 | poprzednie API |
| 26.9.0 i nowsze | .NET Framework 4.7.2 | nowe API |
Aktualizacja pakietu to aktualizacja. Nie ma osobnego pakietu do zainstalowania ani warstwy kompatybilności: 26.9.0 ma inną powierzchnię API, więc po aktualizacji spodziewaj się błędów kompilacji — reszta tej strony. Linia .NET Framework 4.7 została wycofana, a 26.8.0 jest jej ostatnim wydaniem. Możesz pozostać przy niej — nic tutaj nie jest poprawką bezpieczeństwa, którą byś przegapił — ale nowe wydania, wtyczki, tryb rozproszony i gotowe widgety pojawiają się tylko w wersji 26.9.0 i nowszych.
1. Zmiana docelowej wersji i aktualizacja pakietu
Najpierw zmień docelową wersję projektu webowego na .NET Framework 4.7.2: projekt, który nadal celuje w 4.7, nie może zainstalować 26.9.0, a NuGet odrzuca aktualizację. Następnie zaktualizuj Doconut.NETFramework i dodaj pakiety wtyczek, których używasz (Doconut.NETFramework.Converter, Doconut.NETFramework.Dicom, …). Każda wtyczka wymaga licencji, która ją uprawnia.
Jeśli projekt używa packages.config, aktualizacja uruchamia krok odinstalowywania poprzedniej wersji, który usuwa obsługę DocImage z Web.config, a 26.9.0 nie dodaje jej ponownie. Zarejestruj ją ponownie, jak pokazano w kroku 3; dopóki tego nie zrobisz, DocImage.axd zwraca 404 i żadna strona nie jest renderowana.
2. Przestrzenie nazw: prawie wszystko przeniesiono do korzenia
| Przed | Teraz |
|---|---|
using Doconut.Configs.View; | using Doconut; |
using Doconut.Models; | using Doconut; |
using Doconut.Configs; | using Doconut; |
using Doconut.Configs.Cloud; | using Doconut.Clouds; |
using Doconut.Configs.Conversion; | bez zmian |
Nazwy typów nie uległy zmianie: WordConfig, PdfConfig, ExcelConfig, CssConfig, ScriptConfig, FileShareConfig i reszta nadal istnieje. W większości plików cała edycja polega na usunięciu linii using.
3. Uruchamianie: DoconutHost.Initialize i dwa wpisy w Web.config
Klasyczny pakiet budował swój podgląd przy każdym żądaniu, z opcjami jako właściwościami tej instancji. Nowy pakiet ma korzeń kompozycji, tworzony raz w Application_Start, a podgląd jest usługą, którą rozwiązujesz:
// Wcześniej - Doconut.NETFramework 26.8.0 i wcześniejsze, na żądanie
var viewer = new Viewer
{
ID = "ctlDoc",
IncludeJQuery = true,
BasePath = "/",
FitType = "width"
};// Doconut.NETFramework 26.9.0\u002B - Viewer rozwiązany z DoconutHost, licencja skonfigurowana raz w DoconutHost.Initialize()
var viewer = Doconut.DoconutHost.Services.GetRequiredService<Viewer>();
var token = await viewer.OpenDocumentAsync(path, new PdfConfig { AllowSearch = true });DoconutHost.Initialize trafia do Application_Start, a DoconutHost.Shutdown do Application_End, i Web.config uzyskuje obsługę DocImage.axd oraz moduł zasobów — oba znajdują się w Installation. Ustawienia wyglądu per‑strona (FitType, FixedZoom, ShowHyperlinks, …) przeniesiono z instancji podglądu do opcji widgetu, lub do ViewerConfig przekazywanego do Viewer.RenderViewer (zobacz ViewerConfig). new Viewer() nadal kompiluje się po uruchomieniu DoconutHost.Initialize, więc zmigrowany kod‑behind może zachować tę linię, podczas gdy przenosisz ustawienia.
Bezpieczeństwo działa jak dotąd. Otwarcie dokumentu przyznaje bieżącej sesji ASP.NET dostęp do jego stron, a DocImage.axd odrzuca wszystkich innych. Ustawienie aplikacji DoconutUnSafeMode, które wyłączało to, jest teraz options.UnsafeMode w DoconutHost.Initialize — pozostaw je false. Zobacz Sessions & Security.
Błąd uruchamiania, który wyłącza całą witrynę. Zarejestrowana wtyczka, której funkcjonalność nie jest objęta licencją, rzuca wyjątek w
Application_Start, a aplikacja odpowiada pustym500na każde żądanie — brak strony błędu, nic w logu IIS, tylko wpis w dzienniku zdarzeń Windows (źródło ASP.NET). Licencje są odczytywane zwwwrootw katalogu głównym witryny i nigdzie indziej, a podstawowyDoconut.Viewer.licmusi być obecny, w przeciwnym razie licencje wtyczek obok niego nie są odczytywane. Zobacz License Setup.
4. Web farm: od flagi do trybu rozproszonego
Klasyczny model to viewer.IsWebfarm = true plus ExportToPng(path). Nowy model jest rejestrowany raz: każdy węzeł współdzieli jeden magazyn i jeden klucz podpisujący, a podpisany bilet powiązany z przeglądarką zastępuje „dowolny węzeł odpowiadający”:
Doconut.DoconutHost.Initialize(
options => options.UnsafeMode = false,
services => services.AddDoconutDistributed(d =>
{
d.Store = CloudLocation.FileShare;
d.FileShareRootPath = @"\\fileserver\doconut-shared"; // WebfarmPath jest aliasem
d.SigningKey = farmKey; // >= 32 bytes, takie same na każdym węźle
}));Następnie otwieraj dokumenty normalnie, wiążąc przeglądarkę (DocOptions.BrowserId = DoconutFarmBinding.EnsureBrowserId(...)) i przekazując viewer.AccessToken do widżetu z tokenem. Sesje i bezpieczeństwo zawiera kroki; przykład web-farm jest pełnym węzłem. IsWebfarm i WebfarmPath nadal się kompilują, ale już nic nie włączają.
Dwie rzeczy, które wyglądają na sukces, ale tak nie jest: DistributedDocumentPublisher.PublishAsync zapisuje wyrenderowane pliki dokumentu, ale nie otwiera sesji, więc przeglądarka skierowana na opublikowany token otrzymuje ~2 KB obrazek błędu ze statusem 200; oraz klient testowy bez ciasteczka doconut-client otrzymuje ten sam obrazek, a nie 401. Rozróżnij prawdziwą stronę od obrazu błędu po rozmiarze.
5. Konwersja to wtyczka i jest znacznie mniejsza
Enum SourceFormatConverter, dwanaście klas *ConfigConverter oraz ich zagnieżdżone enumy docelowe zostały zastąpione jednym enumem, ConversionTarget, i jednym wywołaniem:
using System.IO;
using System.Threading;
using Doconut;
using Doconut.Configs.Conversion;
// Załóż, że DoconutHost jest już zainicjowany i dostępny jest CancellationToken o nazwie ct.
var provider = DoconutHost.Services;
var converter = (DocumentConverter)provider.GetService(typeof(DocumentConverter));
Stream source = /* twój strumień wejściowy */;
var result = await converter.ConvertAsync(source, ".dwg", ConversionTarget.Pdf, null, ct);Format źródłowy pochodzi z przekazanego rozszerzenia. Nie ma warstwy kompatybilności: każde odwołanie do SourceFormatConverter jest błędem kompilacji, który rozwiązujesz usuwając je. Obiekty opcji per-format nie przetrwały — WordConfigConverter.HtmlOptions i CadConfigConverter.CadOptions.ShowColor nie mają odpowiednika w ConvertAsync. W Web Forms nigdy nie blokuj ConvertAsync — zobacz Wtyczka konwertera.
6. Przechowywanie w chmurze: uzyskaj dostęp jako folder współdzielony
Typy konfiguracji chmury zostały przeniesione do Doconut.Clouds bez zmian. Obsługa żądań chmurowych jest jednak komponentami ASP.NET Core i klasyczna aplikacja nie ma potoku, w którym można je uruchomić. Z witryny System.Web uzyskaj dostęp do przechowywania w chmurze jako folder współdzielony — w Azure, udział Azure Files zamontowany na każdym węźle — dostępny przez FileShareConfig.
7. Zmiany po stronie klienta, które zawodzą cicho
Każdy element poniżej się kompiluje, uruchamia, nie zapisuje logów i robi niewłaściwą rzecz:
| Poprzednio | Teraz |
|---|---|
ResPath: 'doconut-res' | ResPath: 'doconut-res/images' — w przeciwnym razie każda ikona zwraca 404 podczas renderowania dokumentu |
function ctlDoc_ViewerReady() { } | docViewer({ onViewerReady: function () { } }) — wywołania zwrotne przeglądarki są teraz opcjami |
var viewer = $(el).docViewer({...}).View(token) | Najpierw przypisz docViewer(...), potem wywołaj viewer.View(token) osobno |
viewer.Refit() aby dopasować do strony | viewer.FitType('width') — Refit() tylko przelicza układ |
var n = viewer.Search(kw, exact) | viewer.Search(kw, exact, function (n) { … }) — liczba przychodzi w wywołaniu zwrotnym |
if (viewer.SaveAnnotations()) { … } | docViewer({ onAnnSaved: …, onAnnSaveError: … }) |
function ctlDoc_Created() { } (annotations) | Nie zmienione — funkcje zdarzeń adnotacji są nadal globalne, znajdowane po nazwie |
Trzy kolejne: przeglądarka nie rysuje własnego paska narzędzi (twoja strona podłącza Zoom, Next, GotoPage i resztę do własnych przycisków); przeglądarka utworzona wewnątrz ukrytego modala Bootstrap ma wymiary 0×0 i nic nie rysuje, dopóki nie nadasz jej kontenerowi wyraźnej wysokości i nie dopasujesz go ponownie przy shown.bs.modal; oraz AllowSearch domyślnie używa false dla PDF, więc dokument renderuje się perfekcyjnie, podczas gdy każde wyszukiwanie nie zwraca wyników.
8. Co znika
| Zniknęło | Zamiast |
|---|---|
DocumentSearch / TextSearch.cs | Nic — wyszukiwanie działa na tekście, który wyodrębniają przeglądarki formatu |
Viewer.WatermarkInfo | Brak odpowiednika |
WordConfigConverter.HtmlOptions | Brak obiektów opcji przez ConvertAsync |
SourceFormatConverter, klasy *ConfigConverter | ConversionTarget i ConvertAsync |
Doconut.Configs.Editor | Usunięto |
viewer.IsWebfarm + ExportToPng(path) | AddDoconutDistributed i zwykłe otwieranie |
Sugerowana kolejność pracy
- Zmienić cel, zamienić pakiet i sprawić, by
Global.asaxkompilował się zDoconutHost.Initializeoraz dwoma rejestracjamiWeb.config. Strona powinna się uruchomić. - Jedna strona przeglądarki: uzyskaj dokument do renderowania, a następnie przejdź przez sekcję 7, aż pasek narzędzi, wyszukiwanie i adnotacje będą działać. Zweryfikuj w prawdziwej przeglądarce — nic w tej sekcji nie generuje błędu.
- Konwersja (sekcja 5): mechaniczna, oraz większość błędów kompilacji.
- Pozostałe strony, używając przeniesionych przykładów jako celu różnicy.
- Farma sieciowa (sekcja 4), jeśli ją masz. Przetestuj z dwoma węzłami i przeglądarką lub klientem, który zachowuje ciasteczka.
Czy ta strona była pomocna?