Новий плагін від Stepik.org для IntelliJ IDEA

У вересні ми випустили плагін для IntelliJ IDEA з підтримкою Python і Java. Про процесі розробки, і про те, чому плагін спростить життя учнів програмування на Stepik.org розповімо в цій статті.



Плагін, як і у випадку з Stepik Telegram bot, мобільними додатками під iOS і Android, проектував наш новий стажист Петро Богданов, студент Computer Science Center в Санкт-Петербурзі.

Призначення плагіна
Навіщо ми його робили? Зрозуміло, щоб спростити життя студентам, не змушувати виконувати рутинні операції, дозволити повністю сконцентруватися на процесі навчання.

Перша складність, з якою стикається студент при проходженні курсу з програмування на платформі, це необхідність копіпаста в браузер з IDE. Програмувати в браузері нелегко: не можна запустити код і перевірити його локально, немає автодоповнення і рефакторинга і багато чого іншого. Також, програмуючи в IDE, необхідно постійно підглядати в браузер, щоб переглянути умови задачі або скопіювати Sample Input.

Друга проблема — це проблема організації коду у проекті. Студенти, набираючи код в пісочниці, як правило вирішують тільки поточну задачу і не замислюються над тим, де вони будуть вирішувати таку задачу. І швидше за все, студент або не зберігає попередні рішення, які файли у нього називаються кшталт «new_file» «new_file7» «new_file777». Все це ускладнює навігацію і ускладнює переиспользование коду.

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

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

Так як старий плагін був монолітним, раціональним чином додати підтримку нових мов і писати нові плагіни для інших IDE не було можливості. Тому, було вирішено перейти на ядро навчальних плагінів від команди PyCharm.

Розглянемо докладно:
  • Збереження даних
  • Авторизація і спілкування по мережі
  • Побудова дерева проекту
Збереження даних
Щоб користувальницькі дані не губилися при перезапуску, їх необхідно зберігати. Для цього в IDEA є інтерфейс PersistentStateComponent, за допомогою якого можна сериализации в .xml зацікавив вас клас. В документації це не зазначено, але мається на увазі, що клас, який реалізує PersistentStateComponent, — це одинак, який потрібно инстанцировать одним з трьох способів, за рівнем компоненти: Application level, Project level і Module level.

У першому випадку сінглтон буде єдиний на весь плагін, і розумно зберігати в ньому глобальні налаштування.
В інших випадках сінглтон може бути багато і сериализоваться вони будуть в ./.idea. Саме на рівні проекту ми зберігаємо дані (ім'я, токен та інше), і майже всю мета інформацію про курс.

Резонне питання — де тоді зберігати дані, якщо жоден проект не відкритий? На такий випадок в IDEA існує defaultProject, отримати який можна так:

ProjectManager.getInstance().getDefaultProject()

Звідти ми беремо credentials, коли створюємо проект, і саме тому просимо користувача закрити всі проекти перед тим, як залогуватися у налаштуваннях явно.

Реалізувати цей інтерфейс можна двома способами (детальніше див. документацію), крім цього потрібно обов'язково оголосити цю компоненту в plugin.xml (найголовніший .xml) у відповідності з рівнем, наприклад:

<projectService serviceInterface="com.jetbrains.edu.learning.StudyTaskManager"
serviceImplementation="com.jetbrains.edu.learning.StudyTaskManager"/>

Взагалі, реалізувавши будь інтерфейс з IntelliJ API, його необхідно оголосити в plugin.xml.

А для зберігання паролів можна використовувати вбудований менеджер паролів PasswordSafe. Саме через звернення до нього час від часу виникають такі вікна:




Авторизація і спілкування по мережі
Stepik.org підтримує повноцінну OAuth 2 авторизацію. Але в плагіні поки що реалізована тільки авторизація через логін і пароль. З іншими типами авторизації є проблема, в тому що доведеться піднімати сервер на localhost для прослуховування redirected_url.

Для спілкування з Стэпиком в ядрі вже існував клас EduStepicConnector, який містив великий набір статичних методів, і примірник HttpClient для виконання запитів. Цей клас було вирішено розбити на 4 класи:



У Client Init ініціалізується HttpClient і вирішується проблема з перевіркою сертифіката. У Стэпика сертифікат від let's Encrypt, а IdenTrus CA був доданий тільки в Java 8u101. StepikConnectorLogin відповідає за авторизацію. А інші класи вже можуть робити запити, що вимагають авторизації і немає.

У такій схемі може бути тільки один активний клієнт, але її не складно розширити на кілька, створюючи примірники авторизованих клієнтів. Однак, ми не хочемо потурати студентам, ведучим на Стэпике подвійне життя :)

Побудова дерева проекту
Побудова дерева проекту сильно змінилося щодо першої версії плагіна, але слабо щодо ядра.
Тепер курс скачується, кешується і тільки потім будується з кеша. Реалізовано це було із-за повільного побудови проекту: щоб скачати весь курс, потрібно зробити близько 100 запитів. Тут істотного прискорення вдалося досягти, поєднуючи багато id один запит до API.

Червнева версія плагіна підтримувала Яндекс.Перекладач, щоб перевести назви курсу, уроків та секцій на англійську. Це було потрібно для того, щоб імена пакетів для Java були англійською, а кроці відповідав конкретний файл. І було трохи незручно. Доводилося редагувати файл перед відправкою і накладало додаткові обмеження.

Зараз же в цьому немає такої необхідності, тому що рівень кроку тепер відповідає директорії, в якій знаходиться source. Але, тим не менш, директорії зараз носять робочі назви (lesson1/task1), і з допомогою TreeStructreProvider відбувається фіктивна підміна імен директорій і вони відображаються на мові курсу.


TreeStructureProvider включений / виключений.

За допомогою TreeStructureProvider ховається і директорія ./src/hide, в якій зберігаються шаблони кроку на різних мовах. А при зміні мови файли переміщуються.

Залежність плагінів



На картинці зображені всі відомі нам освітні плагіни від JetBrains, а також Стэпик плагін та його залежності. Бузковим показано плагіни для PyCharm. Видно, що нашому плагіну для роботи необхідно ще 3 плагіна. Залежність від Python ще правильно налаштована (тому його доводиться встановлювати вручну). Цікаво, що для Community і Ultimate IDEA покладаються різні плагіни. Edu-IntelliJ — це просто точка розширення для менеджера проектів. Можливо, цю залежність ми приберемо.

І залишається найголовніша залежність від ядра: поточні зміни в ядрі ще не залиті на офіційний репозиторій, тому доведеться встановлювати вручну нестабільну версію. І в такому випадку плагіни Edu-Java і Edu-Kotlin у вас поки що працювати не будуть.

Новий UI

Перше, що ми додали — це авторизацію в налаштуваннях, а-ля GitHub.



Але, якщо ви все-таки пропустіть цей крок, то зустрінете більше нав'язливу авторизацію.



При побудові проекту можна вибрати курс зі списку курсів, на які ви підписані. Але це не означає, що всі вони сумісні з плагіном. Щоб курс створився без помилок, у ньому повинен бути хоч один крок із завданням на програмування.



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

Ще є можливість вивантажити курс за посиланням, при цьому, якщо ви не були раніше підписані на курс, відбувається підписка. Поле для посилання можна вводити як id курсу, так і будь-яке посилання з курсу.

Статус кроку відображається в дереві проекту:



А основні дії знаходяться на панелі Task Description праворуч.



Серед них: відправка рішення, попередній/наступний крок, почати спочатку (поки що недоступно), завантаження останнього рішення і зміна мови.

Сумісність

У Stepik.org поки що немає API для того, щоб розуміти, чи сумісний конкретний курс зі стороннім додатком, тому корисно уявляти як все працює.

Після авторизації плагін викачує дерево проекту, для цього він збирає інформацію про всіх кроках у відкритій частині курсу. Потім він зберігає дані тільки для підтримуваних кроків. На даний момент це тільки завдання типу «code». Однак, даний тип завдань володіє особливістю — в ньому використовуються приховані шаблони. Приховані шаблони — це шматки коду, які додаються в початок і кінець файлу. І за визначенням вони недоступні для студента.

Розглянемо на прикладі Java. За допомогою шаблонів викладач може створювати завдання на реалізацію окремого методу, а обгортка методу в клас відбувається вже на сервері. Таким чином, у студента не буде компілюватися правильне рішення, тому що весь код Java зобов'язаний бути в класі.

Але хороші новини в тому, що таких задач не так вже й багато. Вони найчастіше зустрічаються у мовних курсах.
Тому плагін ідеально підходить для курси з алгоритмам і Hadoop.

Плани на майбутнє
У найближчій перспективі ми хочемо розвивати підтримку різних мов програмування. На даний момент досить легко Stepik Union можна додати R, Scala, але, наприклад, підтримка Haskell ще дуже сира. А з С++ складніше, тут доведеться писати окремий плагін для CLion.

Крім того, ми розглядаємо здійснення підтримки плагіном інших типів завдань.

Подяки
Висловлюємо подяку команді PyCharm за надану допомогу та якісне ядро.

Висновок
Будемо раді відповісти на питання, отримати зворотній зв'язок, пропозиції і конструктивну критику плагіну в коментарях і в обговоренні з автором плагіна ВК.

Посилання: Stepik.org plugins, StepikOrg/intellij-community, Stepik API doc, IntelliJ Platform SDK Documentation, Repository for IntelliJ Platform SDK Documentation.
Джерело: Хабрахабр

0 коментарів

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