Microsoft Roslyn kontra CodeDom

111

Z wczorajszego komunikatu prasowego w InfoWorld dotyczącego nowego Microsoft Roslyn :

Najbardziej oczywistą zaletą tego rodzaju „zdekonstruowanego” kompilatora jest to, że umożliwia on wywołanie całego procesu kompilacji i wykonania z poziomu aplikacji .Net. Hejlsberg zademonstrował program C #, który przekazał kilka fragmentów kodu do kompilatora C # w postaci ciągów; kompilator zwrócił wynikowy kod assemblera IL jako obiekt, który został następnie przekazany do środowiska uruchomieniowego języka wspólnego (CLR) w celu wykonania. Voilà! Dzięki Roslyn C # zyskuje zdolność języka dynamicznego do generowania i wywoływania kodu w czasie wykonywania.

Byłem w stanie to zrobić od czasu wydania .NET 4, z CSharpCodeProvider.CompileAssemblyFromSourcektórym faktycznie używam w projekcie ASP.Net napisanym jakiś czas temu, który robi dokładnie to - umożliwia użytkownikowi wpisywanie kodu w polu tekstowym, wybieranie zestawów / przestrzeni nazw odwoływać się, a następnie wykonywać i wyświetlać dane wyjściowe z tego kodu w locie w celu testowania kodu środowiska na żywo w systemie Windows Azure.

Jest CodeDomczęścią / prekursorem Roslyna? Jaka jest szczególna korzyść z Roslyn CodeDom?

mellamokb
źródło

Odpowiedzi:

241

Zastrzeżenie : Pracuję dla firmy Microsoft w zespole Roslyn.

CodeDom jest prekursorem Roslyn, ale jest tylko nieznacznie powiązany. Zasadniczo CodeDom to prosty i (nieco) niezależny od języka sposób generowania kodu, który został dodany w .NET 1.0 do obsługi projektantów (a la WinForms). Ponieważ CodeDom było próbą dostarczenia ujednoliconego modelu, który może generować kod w C #, VB i innych językach, brakuje mu wysokiej wierności z żadnym z obsługiwanych języków (dlatego nie można utworzyć instrukcji przełącznika za pomocą CodeDom). CSharpCodeProvider.CompileAssemblyFromSource to po prostu otoka wokół wykonywania csc.exe.

Roslyn to zupełnie inne zwierzę. Jest to przepisanie zarówno kompilatorów C #, jak i VB od podstaw, przy użyciu kodu zarządzanego - C # w C # i VB w VB (wersje csc.exe i vbc.exe, które są obecnie dostarczane, są napisane w kodzie natywnym). Zaletą budowania ich w kodzie zarządzanym jest to, że użytkownicy mogą odwoływać się do rzeczywistych kompilatorów jako bibliotek z aplikacji .NET (nie są potrzebne otoki).

Podczas budowania każdego komponentu potoku kompilatora udostępniliśmy na wierzchu publiczne interfejsy API:

  • Parser -> Syntax Tree API
  • Import tabeli symboli / metadanych -> Symbol API
  • Binder -> Binding and Flow Analysis APIs
  • Emiter IL -> Emituj API

Roslyn może być używany jako wyrafinowany generator kodu źródłowego C # i VB, ale na tym kończy się podobieństwo do CodeDom. Interfejsy API Roslyn Compiler mogą służyć do analizowania kodu, wykonywania analiz semantycznych, dynamicznego kompilowania i oceniania kodu itp.

Oprócz kompilatorów zespół Roslyn przebudowuje również funkcje Visual Studio C # i VB IDE na podstawie publicznych interfejsów API kompilatora. Zatem interfejsy API kompilatora są wystarczająco bogate, aby tworzyć narzędzia czasu projektowania programu Visual Studio, takie jak IntelliSense i refaktoryzacja metody wyodrębniania. Ponadto na warstwach powyżej kompilatora Roslyn oferuje usługi analizy wyższego poziomu lub transformacji danych. Na przykład istnieją usługi do formatowania kodu przy użyciu reguł formatowania C # i VB lub znajdowania wszystkich odwołań do określonego symbolu w rozwiązaniu.

Naprawdę, nie ma jednej szczególnej korzyści z Roslyn w porównaniu z CodeDom. Tam, gdzie CodeDom spełniało bardzo specyficzną potrzebę generowania kodu, Roslyn zajmuje się całą przestrzenią narzędzi językowych, dostarczając strukturę umożliwiającą tworzenie dowolnego narzędzia języka C # lub VB, o którym możesz pomyśleć.

Dustin Campbell
źródło
2
@Dustin: Czy Roslyn będzie obsługiwał inne języki? Na przykład JavaScript (.NET)?
Diego Barros
@Dustin: Jest to idealne rozwiązanie do budowania pełnego środowiska IDE, które może wymusić jakość kodu w mojej organizacji, chociaż nie widzę całkowitego zastąpienia ręcznego przeglądu kodu, ale widzę znaczny wzrost jakości. Wkrótce!
Jerric Lyns John
Byłoby wspaniale, gdyby ktoś już utworzył narzędzie oparte na Roslyn do konwersji kodu używającego CodeDom na kod, który używa SyntaxFactory Roslyn ... (Częściowo dlatego, że .Net Core ma Roslyn, ale nie ma CodeDom i używam biblioteki zbudowanej wokół CodeDom )
Emyr
43

CodeDom pozwala na kompilację - ale nie daje możliwości uzyskania informacji o samym kodzie (poza błędami kompilatora). Zasadniczo jest to czarna skrzynka, w której mówisz „skompiluj to” i jest napisane „Udało mi się” lub „Nie udało mi się, tutaj są błędy”.

Roslyn umożliwia pełną inspekcję i tworzenie kodu w locie. Obejmuje to takie rzeczy, jak możliwość przeglądania / sprawdzania komentarzy w fragmencie kodu źródłowego, szczegółowych informacji o pełnej strukturze itp. Możesz przejść i pobrać całe drzewo składniowe źródła, które przekazujesz do Roslyn, i przeprowadzić szczegółową analizę lub przemiany na nim.

Biorąc pod uwagę pełne, bogate informacje o składni, masz ogromną ilość dodatkowej kontroli i elastyczności. W ten sposób na przykład działa przykład, który kopiuje blok kodu C # i wkleja go jako kod VB.NET. Dzięki Roslyn możesz zrobić więcej niż tylko kompilować - możesz także czysto manipulować samym kodem. Powinno to znacznie uprościć generowanie wielu narzędzi, ponieważ takie rzeczy jak refaktoryzacje można wykonać bardzo prosto, ponieważ narzędzie rozumie pełną składnię, w tym metainformacje (takie jak komentarze), i może po prostu pracować z nimi bezpośrednio.

Reed Copsey
źródło
12

Widzę jedną dużą różnicę: w CodeDom za każdym razem, gdy kompilujesz jakiś C # lub VB.NET, dzieje się to poza procesem. CSC.exe lub VBC.exe to prawdziwi pracownicy za kulisami.

Jeśli chcesz zbudować usługę, jeśli chodzi o architekturę, skalowalność, izolację itp. (Wspominasz o Azure), nie jest to zbyt dobre.

Z Roslyn to trwa.

Przypuszczam, że jest to jeden z powodów, dla których nazywają to „kompilatorem jako usługą”.

Ponadto CodeDom jest stosunkowo słabym interfejsem API, pomija wiele funkcji i nie jest tak naprawdę aktualny, ponieważ został zaprojektowany głównie do obsługi automatycznego generowania kodu przez projektantów interfejsu użytkownika Visual Studio. Myślę, że Roslyn poradzi sobie znacznie lepiej, ponieważ został napisany przez ludzi, którzy piszą kompilatory. Mam nadzieję, że to się zmieni.

PS: Jedna znacząca różnica w porównaniu z CSC.exe i VBC.exe: Roslyn wydaje się być czystym .NET (i używa CCI ).

Simon Mourier
źródło
8

Roslyn pozwala na znacznie dokładniejszą kontrolę całego procesu - na przykład można przeanalizować ciąg, a nawet wygenerować dodatkowy kod (w locie w ramach procesu kompilacji na podstawie analizy) itp.

CodeDom „po prostu używa kompilatora”, podczas gdy Roslyn jest „kompilatorem jako usługą z pełnym dostępem do (pod) części”… z Roslyn jesteś „wewnątrz kompilatora” i możesz zobaczyć, jak wygląda kod z perspektywy kompilatora umożliwiając zmianę rzeczy w sposób obecnie niemożliwy.

Na przykład można użyć Roslyn, aby rozszerzyć C # - coś bardzo przydatnego i znacznie lepszego niż bieżący stan implementacji AOP.

Aby uzyskać przegląd aktualnego stanu Roslyn i różnych poziomów dostępu i kontroli, które zapewnia, zobacz http://msdn.microsoft.com/en-us/hh500769

AKTUALIZACJA

Microsoft właśnie udostępnił nowy CTP z dodatkowymi funkcjami i wieloma zmianami / dodatkami API. Aby uzyskać szczegółowe informacje, zobacz tutaj .

Yahia
źródło
1
W rzeczywistości nie jest prawdą, że można użyć Roslyn do rozszerzenia C # o dodatkowe słowa kluczowe.
Dustin Campbell
dzięki ... poprawione ... chociaż nie w pierwszym wydaniu jestem śliczna, że ​​to będzie możliwe ...
Yahia
2
@DustinCampbell, co by było, gdybyś poradził sobie z jakimkolwiek błędem kompilatora, który pseudo słowo kluczowe spowodowało wygenerowanie kodu?
Rodrick Chapman
3
Przed przekazaniem go do kompilatora musisz wykonać przepisanie. Najpierw przeanalizuj kod za pomocą specjalnych słów kluczowych. Kod zostanie przeanalizowany i, o ile parser nie mógł go określić, nieprawidłowe słowa kluczowe pojawią się jako SkippedTokenTrivia w wynikowym drzewie. Następnie wykryj pominięte słowa kluczowe i przepisz drzewo z poprawnym kodem (np. Tkanie AOP). Na koniec przekaż nowe drzewo do kompilatora. Jest to jednak zdecydowanie hack i nie ma gwarancji, że będzie działać z przyszłymi wersjami Roslyn. Np. Parser może produkować nie to samo drzewo dla zepsutego kodu w przyszłych wydaniach.
Dustin Campbell
@DustinCampbell: ale czy będzie COŚ pozwalającego na tkanie AOP w finale Roslyn? Moje tkanie Mono.Cecil INPC działa dobrze tak jak jest, ale gdybym mógł napisać, public notifying string Name {get;set;}to byłoby jeszcze bardziej niesamowite
TDaver