Введення в. NET Framework, HTML, XML, DHTML, Інтернет-технології, статті

Один з ключових елементів архітектури Microsoft. NET – середа. NET Framework. Вона відповідає за реалізацію нового режиму виконання (а значить, і розробки) додатків на локальному комп’ютері. Мова йде про додаткової сполучною середовищі між додатками і ОС, з одного боку, і між програмними компонентами однієї програми – з іншого.


У цій статті мені хотілося б зробити загальний огляд архітектури. NET Framework, щоб показати основну логіку роботи на концептуальному рівні, не дуже вдаючись у деталі її реалізації. Більш детальне вивчення середовища ще попереду.


З точки зору розробника ОС Windows – це в першу чергу набір базових функцій Win API, реалізованих у вигляді DLL. До 1993 р. в Windows основною моделлю створення багатокомпонентних програм було саме використання допоміжних модулів підтримки у вигляді DLL (свого часу прийшли на зміну класичному варіанту, який передбачає створення єдиного виконуваного модуля шляхом включення до нього процедур з двійкових LIB-бібліотек). У 1993 р. Microsoft запропонувала нову модель багатокомпонентних додатків – COM (Common Object Model). За великим рахунком, головна ідея тут полягає в застосуванні на додаток до виконуваного коду метаданих, що забезпечують автоматичний контроль за передачею параметрів (а також уніфікація форматів параметрів).


Звичайно, можна говорити про достоїнства COM в порівнянні з традиційними DLL (хоча гідності завжди супроводжуються і недоліками, в даному випадку у вигляді зниження продуктивності), але я категорично незгодний з висловлюваннями деяких авторів, сенс яких зводиться до наступного: “Після виходу COM розробники зрозуміли, що їм більше не треба писати весь код програм з нуля”. Якщо вдуматися, використання готових компонентів – ключова технологія програмування протягом всієї історії цього виду діяльності.


Чесно кажучи, я ніколи не відчував особливого захоплення від конкретної реалізації ідей COM і ще кілька років тому висловлював думку, що вона несе в собі серйозну загрозу втрати керованості Windows-додатків (Див., наприклад “Проблеми компонентної моделі ПО”, PC Week / RE № 32/97). Представляючи першу бета-версію. NET Framework, корпорація Microsoft відкрито заявила, що одна з цілей реалізації цього середовища – рішення проблеми DLL Hell (“пекло DLL”), пов’язаної з використанням загальних DLL і OCX, які неконтрольованим чином змінюють версії, видаляються і т. п. Інші ключові завдання. NET Framework – уніфікація бібліотек функцій для різних мов, а також підвищення контролю за додатками з точки зору безпеки та ефективного використання ресурсів.


Структура і логіка роботи


Структура. NET Framework представлена ​​на рис. 1. Як видно, мова йде фактично про єдину середовищі виконання програм та підтримки їх розробки. Саме тут зібрано базові класи для всіх мов програмування, реалізовані у вигляді бібліотеки ядра System, а також великої кількості (понад 20) спеціалізованих бібліотек з іменами System.Data, System.XML і т. д. Над ними розташовується набір засобів формування виконуваних модулів різного типу (знову ж єдиний для різних мов).

Рис. 1. Структурна схема. NET Framework.


Власне, з точки зору розробки додатків саме в цьому полягає новизна (але лише відносна, для Windows-програмування) даного рішення: допоміжні функції відокремлені від бізнес-логіки додатків, що реалізується за допомогою конкретних мов. Крім очевидної переваги такої уніфікації функцій (навіщо писати окремі функції, що обчислюють синус, для різних мов?), Це створює хороші передумови для поліпшення управління оперативною пам’яттю. Адже, як відомо, величезне число проблем надійності програм пов’язано з використанням різних механізмів динамічного розподілу простору в різних мовах.


Зверху розташовуються самі інструменти розробки, представлені в даному випадку системою Visual Studio. NET, в якій кожен з мов взаємодіє с. NET Framework через загальний мовний інтерфейс. Докладне вивчення VS.NET ще попереду, а зараз обмежимося кількома зауваженнями.


З одного боку, такий механізм дозволяє досить просто підключати до розглянутої середовищі різні мови. В даний час про створення таких коштів (COBOL, FORTRAN, Perl і т. п.) оголосили вже більше 20 незалежних розробників. У той же час майже у всіх цих інструментів є альтернативні варіанти середовища, які працюють поза VS.NET і безпосередньо взаємодіють с. NET Framework.


З іншого боку, така уніфікація автоматично нівелює функціональні можливості різних мов, в значній мірі зводячи проблеми вибору конкретного інструменту до прихильності конкретних людей того чи іншого синтаксису. Це сьогодні особливо добре видно на прикладі VB.NET і C #. Оскільки, говорячи про платформу. NET, нам ніяк не уникнути порівняння її з Java 2 Platform, то зауважимо, що відмінність між ними в тому, що в першому випадку є різні синтаксичні форми для єдиного. NET-мови. Якою мірою виправданий відмова від специфіки мов (яка виявлялася в різній їх ефективність для вирішення різних предметних завдань) – на цю тему можна подискутувати окремо.


Common Language Runtime


Вище ми говорили про компоненти. NET Framework, що відносяться до процесу розробки додатків. CLR (Common Language Runtime, загальна для мов середовище виконання) – це наріжний камінь у фундаменті організації обчислювальних процесів всієї концепції. NET. Саме тут повинні вирішуватися основні завдання підвищення надійності та безпеки програм, а також платформної незалежності. CLR – це окрема велика тема, тому ми розглянемо її лише тезово.


Всі виконувані модулі. NET-додатків (будемо називати їх CLR-модулями) реалізуються не у вигляді машинного коду (native, “рідного” для даного комп’ютера), а за допомогою так званого байт-коду за специфікаціями проміжної мови Microsoft Intermediate Language (MSIL). Іншими словами, кожен сумісний с. NET-компілятор повинен перетворити вихідний код на мові високого рівня в двійковий MSIL-код, який вже потім буде виконуватися в середовищі CLR. Ідея та реалізація подібного підходу зовсім не нові, для Basic і Virtual Pascal це робилося ще в 1970-х, а про Java відомо і нинішньому поколінню розробників.


Однак, на відміну від Java, CLR буде виконувати код не в режимі класичного інтерпретатора, а шляхом попередньої компіляції в машинний код окремих фрагментів програми або цілого програми (рис. 2). Перший варіант – основний, при цьому застосовується так званий Just-In-Time компілятор, який виконує перетворення MSIL в машинний код у міру звернення до відповідних процедур (тобто невикористовувані фрагменти програми зовсім не компілюються). Даний підхід також добре відомий; він, зокрема, вже більше шести років використовується в платформі “1С: Підприємство”.

Рис. 2. Схема компіляції. NET-додатків.

Як відомо, режим інтерпретації має дві головні переваги в порівнянні з використанням машинного коду: підвищення безпеки програм (точніше, захищеності системи в цілому від дії конкретних програм) і спрощення адаптації програм до конкретної апаратній платформі. З урахуванням цього розглянемо структуру CLR-модулів.


CLR-модулі складаються з виконуваного коду і метаданих. Метадані (наприклад, різні декларації полів, методів, властивостей і подій) широко застосовуються і в COM-технології, що і складає її основна відмінність від звичайних двійкових DLL. У CLR складу метаданих значно розширений, що дозволяє більш ефективно контролювати версії, перевіряти надійність джерел надходження програм і т. п.


Виконуваний код в основному представлений у вигляді “керованого коду” (можливі й фрагменти “некерованого коду”, але вони будуть відтепер великою рідкістю). Це означає, що CLR не просто перетворює MSIL в машинні інструкції, а виконує ці дії з урахуванням певних зовнішніх установок. Наприклад, модуль1 може задати свій власний набір прав, наданий викликуваному їм Модулю2, заборонивши, зокрема, будь-які операції зміни файлів.


Ця можливість широко використовується в багатокористувацької Інтернет-грі для програмістів “Тераріум”, анонсованої на форумі PDC 2001. У ній кожен може написати програмні модулі, що реалізують вибрані стратегії, які інші учасники завантажують на свої комп’ютери. Безпека тут забезпечується саме завдяки чіткому контролю за допустимими діями “чужорідних тіл”. Загалом, в CLR ми бачимо реалізацію ідей Інтернет-браузерів, які представляють проміжну середу виконання програм, але тільки зі значно більш високим рівнем керованості прав.


Що стосується платформної незалежності, то CLR, здавалося б, має для цього всі передумови, оскільки передбачає наявність JIT-компілятора (як і в Java). Але я не поділяю оптимізму деяких експертів, які говорять про можливість появи найближчим часом подібних засобів, наприклад, для Linux. По-перше, CLR спочатку досить істотно задіє базові служби Windows. По-друге, Microsoft зовсім інакше, ніж Java-спільнота, трактує поняття багатоплатформності: JIT-компілятори з’являться для різних типів апаратури (кишенькові ПК, мобільні телефони тощо), але працювати вони будуть тільки в середовищі Windows. NET.


Об’єкти COM і. NET


Чесно кажучи, я поки не до кінця зрозумів, в чому якісна відмінність цих двох типів об’єктів, по крайней мере, в рамках локального комп’ютера. Можливо, є якісь радикальні зміни в протоколах взаємодії, але внешне.NET зараз є лише модернізований варіант COM, мабуть, лише з двома видимими відмінностями.


По-перше, реалізована ієрархічна система імен об’єктів типу, що отримала назву “простір імен”. Тепер замість плоского ідентифікатора “ІмяПріложенія.ІмяКласса” можна використовувати “ІмяПріложенія.Імя1.Імя2 …. ІмяКласса”.


По-друге, змінено порядок реєстрації об’єктів, що безпосередньо пов’язано з появою ще одного нового терміна – складання (Assembly).


Як відомо, COM-модулі можуть перебувати в будь-якому каталозі і стають доступними іншим програмам допомогою реєстрації в Реєстрі (де виконується зв’язка ідентифікаторів ProgID, GUID і фізичного адреси файлу). У разі. NET реєстрація об’єктів фактично виконується індивідуально для кожного розробляється, при цьому файл компонента просто копіюється в локальну збірку (окремий каталог даного проекту). Аналогічним чином. NET-додаток завантажує до себе копію COM-об’єкта, зареєстрованого в Реєстрі, і, в свою чергу,. NET-об’єкт може бути зареєстрований як модуля COM. Загальні. NET-компоненти (Shared Assemblies) для різних додатків зберігаються в області Global Assembly Cache, яка представляє собою просто каталог з фіксованим іменем WINNTassembly.


Здавалося б, такий підхід повинен надійно вирішити згадану вище проблему DLL Hell, але я б не поспішав з виявлення захоплення. Мене насторожує можливість появи на одному комп’ютері величезного числа різних версій по суті одного і того ж компонента, що в цілому суперечить класичним принципам програмування. Наприклад, ви виявили тривіальну помилку в компоненті і перекомпілювати його. А як тепер внести зміни у всі збірки, де він використовується? Не кажучи вже про те, що тепер один і той же розширення DLL використовується вже не для двох, а для трьох абсолютно різних типів бібліотек: звичайні бібліотеки, COM і. NET.


Приклад взаємодії компонентів


Тепер спробуємо подивитися на прикладі, як же працює модель взаємодії. NET-компонентів. У середовищі Visual Studio. NET відкриємо новий проект типу Class Library для мови Visual Basic і введемо наступний код для реалізації функції, яка повертає поточний час відповідно до заданого форматом:








Public Class MyClass1
     Public Function NowTime _
                    ByVal ShowSeconds As Boolean) _
                    As String
“Отримуємо поточний час
            If ShowSeconds Then
“Повернення” довгого “формату часу
                    Return Now.ToLongTimeString
Else “” короткий “формат
                    Return Now.ToShortTimeString
             End If
     End Function
End Class


В цілому ця маніпуляція нічим не відрізняється від створення COM-об’єкта у VB 6.0, за винятком лише синтаксису операції повернення значення функції (раніше ми б просто написали NowTime = Now).


Подивимось тепер на структуру проекту у вікні Solution Explorer (рис. 3). Зазначимо, що фізично наш проект називається ClassLibrary3, а логічне ім’я бібліотеки – MyClassLibrary (сенс цих компонентів проясниться в подальшому). Крім модуля класу, тут в явному вигляді описані три посилання на базові класи, підключені до проекту за замовчуванням. Втім, насправді підключених класів набагато більше (Наприклад, в їх число входять всі класи бібліотеки Microsoft.Visual Basic). Тут же видно новий модуль з описом даної збірки AssemblyInfo.vb, вміст якого можна не тільки подивитися, але і відредагувати (Рис. 4). Крім того, видно, що до проекту були автоматично підключені ще два базових класу (див. ключове слово Imports) і що дану бібліотеку можна зареєструвати і в якості COM-об’єкта – тут прописаний її GUID.

Рис. 3. Структура проекту ClassLibrary.

Рис. 4. Опис збірки проекту.

Тепер створимо DLL і подивимося каталог ClassLibrary3, куди записані файли проекту (рис. 5). Результуючий файл ClassLibrary3.dll знаходиться в підкаталозі BIN, а в OBJ – ще кілька копій цієї ж DLL, отриманих в результаті налагодження.

Рис. 5. Склад файлів проекту.

Для налагодження сервера створимо клієнтську програму у вигляді Console Application, в якій за допомогою сформованого раніше компонента спробуємо отримати поточний час. Для цього відкриємо вікно Add Reference і за допомогою кнопки Browse підключимо до проекту бібліотеку ClassLibrary3.dll (рис. 6). Введемо такий код:








Module Module1
     Sub Main()
          Dim tc As New ClassLibrary3.MyClass1()
           tc = New ClassLibrary3.MyClass1()
          MsgBox(tc.NowTime(True))
     End Sub
End Module

Рис. 6. Підключення. NET-компонентів.

Запустимо його на виконання і переконаємося, що все працює, як задумано. Принаймні, зовні все не відрізняється від того, як ми раніше працювали з COM-об’єктами (тільки всі тепер робиться помітно повільніше). Але відзначимо один цікавий момент. Знову відкриємо проект ClassLibrary3 і замінимо в ньому старий код на такий варіант:








Namespace MyTimeComponent
     Public Class MyClass2
          Public Function HelloAll() As String
Return “Привіт усім!”
          End Function
     End Class
End Namespace

Відкомпілюємо його, повністю замінивши стару DLL. Але якщо ми зараз зайдемо в каталог ConsoleApplication2Bin, де зберігається створений раніше виконуваний файл клієнтського проекту, і запустимо його на виконання, то він буде працювати без проблем у старому варіанті. Чому? Та тому, що в цьому ж каталозі ви виявите попередній варіант ClassLibrary3.dll, яка була автоматично переписана при підключенні відповідної посилання.


Тепер знову відкриємо проект ConsoleApplication2 в середовищі VB.NET – і тут ми відразу побачимо по виділенню помилок синтаксису, що він не може знайти об’єкт з ім’ям ClassLibrary3.MyClass1. Виправимо код для роботи з новим варіантом створеного компоненти:








Module Module1
     Sub Main()
          Dim tc As New _
                    ClassLibrary3.MyTimeComponent.MyClass2()
          tc = New _
                    ClassLibrary3.MyTimeComponent.MyClass2()
          MsgBox(tc.HelloAll)
     End Sub
End Module


Стає зрозумілим сенс операторних дужок Namespace, використаних у коді класу, – з їх допомогою описується ієрархічна система імен об’єктів. Підправимо цей код, щоб можна було застосовувати більш компактне звернення до імен об’єктів:








Imports ClassLibrary3.MyTimeComponent
Module Module1
     Sub Main()
          Dim tc As New MyClass2()
          tc = New MyClass2()
          MsgBox(tc.HelloAll)
     End Sub
End Module


Тепер “сухий залишок”: що ж нового ми побачили на цьому простому прикладі в порівнянні з традиційним використанням COM-об’єктів?


По-перше, проблема узгодження версій застосовуваних компонентів вирішується тривіальним копіюванням потрібних файлів в каталог клієнтського додатка (в тому числі за допомогою створення спеціальної копії COM-бібліотек). По-друге, за допомогою операторних дужок Namespace ми можемо створювати ієрархічну систему імен об’єктів на відміну від двухзвенной DllName.ClassName, прийнятої в COM, яка тепер є окремим випадком.


Покажемо детальніше, як створити таку систему імен, на прикладі проекту типу Class Library та імені ClassLibraryN:








“Це об’єкти першого рівня
Public Class Class1
“Набір функцій і методів класу
End Class


Namespace MyTimeComponent
“Об’єкти другого рівня
      Public Class Class1
“Набір функцій і методів класу
      End Class
            Public Class Class2
“Набір функцій і методів класу
      End Class
      Namespace MyComp2
“Об’єкти третього рівня
            Public Class Class1
“Набір функцій і методів класу
      End Class
   End Namespace
End Namespace


Відповідно, в клієнтському додатку використовуються нами класи будуть описані наступним чином:








Dim t1 As ClassLibraryN.Class1
Dim t2 As ClassLibraryN.MyTimeComponent.Class1
Dim t3 As ClassLibraryN.MyTimeComponent.Class2
Dim t4 As ClassLibraryN.MyTimeComponent.MyComp2.Clas


Зверніть увагу, що тут ми спеціально використовували однакове ім’я Class1 для різних об’єктів (що знаходяться в зоні дії різних просторів імен).


Звичайно, ці нововведення корисні, але я б поки уникав використання епітетів “революційні”. До того ж треба подивитися, як це все працює в реальних проектах.


Добре забуте старе


Отже, ідея. NET Framework зрозуміла: уніфікувати набір базових програмних функцій (бібліотеки класів) і підвищити керованість додатків, у тому числі з точки зору взаємодії їх компонентів (CLR). Все це дуже похвально, так як дійсно може допомогти вирішити існуючі сьогодні проблеми створення складних програмних комплексів. Однак важко позбутися думки про те, що всю цю “новизну” ми десь вже бачили …


Дійсно, за розмовами про DLL, об’єктних бібліотеках і збірках та інше ми якось призабули, що проблема повторного використання програмних компонентів і їх уніфікація виникла не 10 років тому. Саме для вирішення цього завдання ще років 40 тому була реалізована ідея поділу процедур компіляції (трансляція вихідних модулів у об’єктні) і компонування (об’єднання об’єктних модулів в один завантажувальний), яка передбачала, зокрема, що для створення однієї програми можна застосовувати різні мови програмування, у тому числі з використанням єдиних бібліотек підпрограм.


При цьому ще в часи MS-DOS широко застосовувалася технологія, яка дозволяла або виділити допоміжні функції програми у вигляді автономного модуля підтримки (повного аналога нинішніх DLL), або включити їх до складу єдиного виконуваного файлу. І ніякого DLL Hell!


Звичайно, такі паралелі досить умовні, але все ж залишається деякий почуття занепокоєння: чому реалізація загалом досить простих ідей тягне за собою настільки швидке зростання вимог до апаратних ресурсів? Може бути, для того, щоб ефективніше завантажити додаткові обчислювальні потужності, які постійно з’являються в результаті дії закону Мура?


До речі, що ось що з цього приводу говориться в книзі Девіда Платта “Знайомство з Microsoft. NET”: “. NET Framework змусить Intel випускати більш швидкі процесори і більше чіпів пам’яті. Дехто з відділу маркетингу Microsoft стверджує, що. NET-програми по швидкості не поступаються іншим, але це не так і ніколи так не буде “.


Схожі статті:


Сподобалася стаття? Ви можете залишити відгук або підписатися на RSS , щоб автоматично отримувати інформацію про нові статтях.

Коментарів поки що немає.

Ваш отзыв

Поділ на параграфи відбувається автоматично, адреса електронної пошти ніколи не буде опублікований, допустимий HTML: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

*

*