Пишемо ХабраКвест на ASP.NET Core і Angular2

Кожного разу з виходом нового фреймворку, хочеться спробувати його в справі і написати на ньому якийсь додаток. минулий раз відмінно зайшов формат квесту. З цього пропоную подивитися, що змінилося за майже півтора року і написати ще один квест— і фреймворки подивимося, і пограти можна.
Результат:
сорсы на гітхабі для тих, кому цікаво подивитися на исходники
лінк на квест для тих, кому цікаво що вийшло або витратити свій час на ще один логічний квест.

Під катом описаний повний процес від створення проекту до його розгортання.


Попередні вимоги
Для роботи з ASP.NET Core і Angular2 підійде майже будь-IDE або текстовий редактор. Звичайно для налагодження повноцінної ASP.NET потрібна Visual Studio, але з виходом нової Core версії для розробки вона не обов'язкова, можна працювати з кодом Sublime\Atom\… і запускати додаток (попередньо встановивши SDK) з командного рядка, за допомогою:
dotnet run

Вихідний код, інсталятор, документацію для інтерфейсу командного рядка .NET і SDK можна знайти на:
dotnet.github.io
При чому все це тепер доступно не тільки на Windows, але і на Max, Linux, а так само Docker.

Напевно, багато зазнають когнітивний дисонанс, побачивши
sudo apt-get install dotnet-dev-1.0.0-preview2-003121


Створюємо проект
Для створення нового ASP.NET core додатку є кілька шляхів:
1) З допомогою Visual Studio
2) З консолі — dotnet new
3) Використовуючи сторонні генератори.

Не будемо заглиблюватися у всі проблеми створення та конфігурування проекту, тим більше, що нам потрібно не пусте додаток, а вже з підключеним Angular2 і, бажано налаштованими білд скриптами.
Для цього ідеально підходить ASP.NET Core JavaScript Services github.com/aspnet/JavaScriptServices, який дозволяє створювати додатки для ASP.NET Core JavaScript фреймворком на вибір: Angular 2, React, і Knockout.
Для цього нам знадобиться: ASP.NET Core, Node.js і генератор yeoman з шаблоном aspnet-spa. Останній можна встановити з допомогою:
npm install -g yo generator-aspnetcore-spa

Тепер створення нового проекту зводиться до
cd <папка_для_проекта>
yo aspnetcore-spa



Вибираємо Angular2 шаблон, назву проекту та генератор сам створить всю структуру, залежності і т. д. (це може зайняти декілька хвилин).
Спочатку може здатися, що цей генератор використовує занадто багато бібліотек, особливо, якщо ви не любитель останніх або ж мало працювали з фронт-ендом. Але особисто моя думка — що це один з найбільш збалансованих шаблонів. Особливо хочеться виділити наступні властивості:

TypeScript

Звичайно ж розробляти програми на Angular2 можна і на простому JavaScript, TypeScript дає нам можливості типізації, автодоповнення, більш звичний (для більшості) синтаксис для ООП. А також команда Angular2 активно використовує TypeScript і схоже на те, що TypeScript буде (або вже є) не офіційною мовою за промовчанням для Angular2.

Webpack

Схоже, що webpack швидко стає фаворитом у битві інструментів для фронт-енду. Особливо важливо помітити його можливості при постійній зміні коду. Фактично розробнику можна забути про те, щоб постійно перезбирати проект і оновлювати сторінку з допомогою Гарячої Заміни Модулів (Hot module replacement — HMR). Після того, як спробували писати фронт-енд на одному моніторі, в той час як на другому він на очах змінюється вже не хочеться повертатися назад, на інструменти без можливості гарячої підміни.

Інші бонуси

Серверний пре-рендер, лінива завантаження, зручна робота з Development і Production билдами.
Більше можна дізнатися у блозі одного з розробників JavaScriptServices:
blog.stevensanderson.com/2016/05/02/angular2-react-knockout-apps-on-aspnet-core
або ж побачити реальний приклад в одному з останніх публічних стенд-апів команди ASP.NET:


Збираємо проект
Як вже говорилося раніше, щоб зібрати і запустити проект, можна скористатися консольною командою:
dotnet run


Як результат, сайт буде зібраний і запущений локально:


Або ж, зробити теж саме з Visual Studio.
Якщо після білду у вас буде повідомлення, що не всі модулі npm встановлено,

швидше за все це проблема з тим, що один з модулів не підтримується в Windows, але оскільки залежність не обов'язкова, додаток повинен працювати нормально.

В результаті у вас повинно запустити робочий додаток з трьома простими сторінками.


Приступаємо до роботи
Розглянемо головні відмінності в порівнянні з попередніми версіями фреймворків.

Структура проекту

Схоже, структура проекту JavaScriptServices webpack-орієнтована. Тобто це npm + webpack, відповідно відсутні gulp і bower. На скільки я розумію bower просто вирішили не додавати у стартовий проект, так як немає багато залежностей від бібліотек JavaScript, зі всім справляється npm. А всі функції gulp (або grunt) тепер виконує webpack.

Що стосується файлової структури, то по частині серверних файлів так само, як і раніше, а от на front-end є деякі відмінності. Наприклад, у папці зі статичними файлами wwwroot є папка dist, куди, фактично, компілюється весь JavaScript.
В порівнянні з першою версією Angular кидається в очі те, що немає ніяких уявлень і контролерів — все в компонентах і для кожної html частини компоненти є TypeScript частина.

Особливості в процесі

Webpack звичайно дуже радує в плані гарячої заміни модулів, розробка front-end частини з-за цього значно приємніше.
Варто так само відзначити, що помилки WebPack відмінно показуються вже на рівні ASP.NET дуже зручна інтеграція. Правда після помилкового стану (наприклад, підтягування не існуючої компоненти) гаряча заміна у мене не заробила, можливо в таких випадках треба оновлювати сторінку вручну.

Так само дуже зручно те, що дебажити в браузері можна TypeScript і все це вже вбудовано за замовчуванням


В першу чергу я переробив сторінки з прикладами на ті, що потрібні мені. Це виявилося дуже просто, незважаючи на те, що мої знання Angular2 і TypeScript близькі до нуля. Взагалі синтаксис нового Angular здається дуже читабельним, як мінімум з першого погляду. А можливість описувати інтерфейси, класи і типи TypeScript роблять його дуже зрозумілим.
Приклад простий компоненти:

Думаю більшість розробників, які бачать TypeScript в перший раз відразу зрозуміють що тут відбувається.

Entity Framework і база даних

Якщо ви знайомі з попередніми версіями Entity Framework то з Entity Framework Core проблем виникнути не повинно. У крайньому випадку можна переглянути документацію на docs.efproject.net/en/latest/intro.html

Спочатку ставимо nuget пакети для самого EF, а також для інструментів для роботи з базою (версія останнього поки не стабільна):
Install-Package Microsoft.EntityFrameworkCore.SqlServer
Install-Package Microsoft.EntityFrameworkCore.Tools –Pre

github.com/gbdrm/HabraQuest/commit/959f4cb6c253dad0cc5e6eb34756ee5cc9c920f9

Далі, додаємо команди інструментів у project.json, для цього відкриваємо його, знаходимо налаштування tools і додаємо
"Microsoft.EntityFrameworkCore.Tools": "1.0.0-preview2-final",

Можливо в вашому шаблоні інструменти вже будуть додані. Тоді нічого міняти не треба.

Додаємо класи моделі нашого додатка і DbContext і реєструємо їх у Startup.cs.
Ну і звичайно ConnectionString appsettings.json і так само додаємо код для конфігурації у Startup.cs.
github.com/gbdrm/HabraQuest/commit/7411eb4262bdef9f5fb810f6cf7d5a239221c0b5

Наступний крок, типова історія з міграціями — додаємо початкову міграцію і просимо базу оновитися.
Add-Migration Initial
Update-Database

Оскільки база ще не існує, після другої команди вона повинна бути створена. Це можна перевірити, подивившись, які бази даних існують якщо приєднатися до SQL-серверу з допомогою Visual або SQL Management студії.
github.com/gbdrm/HabraQuest/commit/09b42dc0a8e45da1f461b38c2b41d79c4fc0b88a

Давайте додамо простий метод Home контролер і спробуємо мінімально використовувати з'єднання з базою. Додамо метод створення нового гравця, який будемо повертати його токен.
github.com/gbdrm/HabraQuest/commit/e67a322184517aa929d1347f6fd638c6290bf9d3

Якщо тепер ми запустимо додаток, можна протестувати цей метод, додавши/home/registernewplayer в кінець адреси. У результаті ми повинні отримати токен нашого гравця.


Перші кроки в Angular 2

По скільки ми вже створили примітивний back-end, то можемо спробувати його використати на клієнті. Спробуємо зробити наступне:
коли новий користувач заходить на сторінку — перевірити, чи є у нього cookie з токеном і, якщо немає, попросити його з сервера. Щоб не створювати власний велосипед, спробуємо використовувати існуючу бібліотеку для роботи з cookie. Наприклад, ng2-cookies.
Для цього нам треба встановити і підключити в компоненті home.
github.com/gbdrm/HabraQuest/commit/8c7aadd9607a0c4d0a1039707b08b0c4b720112c

Складно описати мої наступні кілька годин наполегливої боротьби зі стереотипами JavaScript і першого Angular. Виявилося, що у другій версії фреймворку все абсолютно інакше. Можу лише сказати, що закінчилося це тим, що я вирішив поки не використовувати сервіси (спочатку вирішив краще розібратися з rxjs вами, який активно використовується в Angular 2), оновив пакети до наступного реліз кандидата (четвертого), додав нові форми (виявилося, що вони були сильно перероблені і цей процес ще не закінчений) і вирішив максимально спростити код (більшість логіки в одну компоненту). Для початку потрібно зробити що-то робочий, а потім будемо думати про хороших практиках. Так само додав кілька заглушок на серверну частину.
github.com/gbdrm/HabraQuest/commit/60c8239a89cae2357d0521973e091781027186ba

З цікавих особливостей — то студія то решарпер вміють підтягувати правильні імпорти для TypeScript, так само в більшості випадків працює штатна навігація по методах. З-за такого роду особливостей писати код для клієнтської частини ставати значно приємніше, немає більше почуття, що ви пишете якийсь скрипт, який може впасти де завгодно. Замість цього основні елементи синтаксису перевіряються автоматично і є впевненість, що все не поламається десь посередині. А навіть якщо і поламається, то виконається ще одна перевірка на рівні webpack і в результаті на сторінці буде показу помилка, навіть без перезапуску.


Правда, іноді, це починає напружувати, коли після збереження кожного файла — сторінка починає перерисовываться. Але думаю це питання звички.

Весь наступний код не представляє особливої важливості. В основному це реалізація заглушених моментів. Якщо вам все ж цікаво переглянути — вихідні коди доступні на github.com/gbdrm/HabraQuest

Розгортання

По скільки бек-енд написаний .Net то деплоить наше додаток будемо на Azure. До речі за останні рік-півтора тут теж змін хоч відбавляй, з першого разу не розберешся що і куди. Для нашого додатка нам достатньо буде створити самий базовий сайт з базою (Web App + SQL).
З деплойментом, як завжди, не дуже гладко. По-перше, він не проходить без помилок. Сам сайт працює, але в підсумку Visual Studio показує помилки в якихось зовнішніх модулях TypeScript. Поки так і не розібрався що це. По-друге, буває, що при відкритті сайту вилітає помилка «TaskCanceledException: A task was canceled». З цим теж поки не до кінця ясно, але схоже проблема десь на рівні хостингу. І крім цього, трохи погрався з міграціями.

Хоча, загалом, я цим кроком залишився задоволений. Дуже детальний і зрозумілий лог, все можна сконфігурувати (база, міграції). Перший раз, правда, треба почекати деякий час (кілька хвилин) поки все билдится, копіюється. Та й взагалі, схоже, що процес досить складний, на скільки я зрозумів спочатку все копіюється локально, а потім вже перекидається на Azure, але це вже деталі.

Результат, висновки

Все вийшло так, як планувалося. Новими фреймворками особисто я задоволений, з радістю б на них перейшов. Звичайно є ще не дуже стабільні моменти, Angular 2 ще й зовсім не випущений офіційно. Але виглядає все досить цікаво і, головне, працює.
Дуже радує розвиток інструментів, підходів у розробці які дозволяють робити менше рутинних завдань, типу оновлення станиці, контролювання структури бази даних.
Так само, дуже багато блогів, питань, документації в мережі, так що з рішенням типових завдань вже має бути все просто.

Всі результати можна знайти на:
github.com/gbdrm/HabraQuest
habraquest.azurewebsites.net

Вийшло досить сумбурно, так як багато різних тем. Які з них вам найбільш цікавими для опису в майбутньому?

Джерело: Хабрахабр

0 коментарів

Тільки зареєстровані та авторизовані користувачі можуть залишати коментарі.