Романов В.Ю.
МГУ им. М.В. Ломоносова, факультет ВМК, vromanov @ cs . msu . su, vladimir. romanov @ gmail . com
Моделирование и верификация архитектуры программного обеспечения, разработанного на языке Java
КЛЮЧЕВЫЕ СЛОВА:
Программное обеспечение, моделирование, верификация, Java. АННОТАЦИЯ:
В статье рассматриваются особенности реализации CASE-инструмента для моделирования свободно распространяемого программного обеспечения разработанного на языке Java. Данный инструмент предназначен для моделирования и визуализации такого программного обеспечения с помощью языка UML, верификации и рефакторинга его архитектуры. В качестве анализируемого исходного кода для такого CASE-инструмента предполагается использовать репозитории кода с унифицированной идентификаций распространяемых
программных библиотек. В статье описывается контекст, в котором предполагается работа данного инструмента. Рассмотрены типовые ошибки в проектировании логической и физической структуры программного обеспечения, методы верификации и рефакторинга для исправления таких ошибок проектирования.
1.Введение
Использование свободно распространяемых в сети Internet библиотек, разработанных на языке Java, получает все более широкое распространение. Многие такие библиотеки распространяются в исходных текстах, что дает возможность их развития независимыми группами разработчиков. Для распространения таких библиотек все чаще используются не только сайты разработчиков библиотек, но и централизованные хранилища (репозитории) со стандартизованным интерфейсом. Это позволяет ссылаться на библиотеки непосредственно по их уникальному адресу в репозитории. Разработка программного обеспечения в таком случае представляет собой сборку программного обеспечения с указанием уникального идентификатора группы (фирмы или команды разработчиков), уникального идентификатора артефакта (библиотеки) и номера версии артефакта. Заданная в проекте с помощью таких координат библиотека автоматически подгружается из глобального репозитория в интернете в локальный репозиторий проекта и
используется при сборке программы. Требуемые загруженной библиотекой другие библиотеки также рекурсивно подгружаются в локальный репозиторий и используются при сборке вновь разрабатываемого программного обеспечения на языке Java. Широкое распространение получили также инструменты [1, 2] позволяющие автоматизировать с помощью таких координат описание зависимостей между библиотеками и их сборку. Разработана унифицированная структура репозиториев для хранения таких библиотек [2] и программный интерфейс [3] для доступа к репозиториям артефактов из различного рода инструментов автоматизации сборки.
Вместе с тем использование свободно распространяемых через репозитории библиотек сопряжено с определенными трудностями. Существует множество различных библиотек с аналогичной функциональностью, либо множество версий той библиотеки с различными функциональными возможностями. Некоторые библиотеки со схожими возможностями развиваются параллельно независимыми группами разработчиков по своему усмотрению. Многие получившие популярность библиотеки уже никем не сопровождаются. При несогласованной совместной разработке библиотек зачастую совершались ошибки проектирования, что теперь затрудняет их последующее развитие и использование. Как следствие, использование свободных библиотек требует существенного времени на их сравнение, на выбор подходящих для конкретного проекта, на изучение функциональных возможностей этих библиотек. Существенную помощь в этом оказывает наличие моделей этих библиотек, представленных с помощью наглядной графической нотации языка UML.
2. Моделирование архитектуры программного обеспечения
Стандартизованная структура байт-кода библиотек, разработанных на языке Java, позволяет выполнить построение их UML[4,5,6] модели даже при отсутствии исходных текстов этих библиотек. Наличие UML-модели существенно облегчает и ускоряет понимание внутренней структуры изучаемой библиотеки. Графическая нотация языка UML позволяет представить на одной диаграмме в компактной форме информацию, которая зачастую рассредоточена во многих текстовых файлах написанных на языке Java. Вместе с тем, при большом размере хранимого в репозиториях и анализируемого для возможного использования программного кода, полная визуализация кода с помощью языка UML может оказаться затруднительной. Построение диаграмм, отражающих все связи между элементами программ, может потребовать слишком много времени. Восприятие графического представления при этом по-прежнему будет затруднено из-за чрезмерно большого числа UML-диаграмм. Поэтому необходима визуализация лишь наиболее существенной информации о программной системе - ее архитектуры.
В результате совместной работы международных организаций по стандартизации ISO и IEEE был принят стандарт, определяющий, что может считаться описанием архитектуры программного обеспечения [7]. Были также изданы книги [8,9] являющиеся хорошими комментариями к данному стандарту. В стандарте и упомянутых книгах формализованным образом описана метамодель архитектуры. С помощью языка UML в модели и соответствующих им диаграммах определяются элементы, из которых строится описание архитектуры (architectural elements), категории участников заинтересованных в реализации программной системы (stakeholders). Для каждой категории участников из элементов строится описание архитектуры учитывающей специфику этой категории. В стандарте определен также каталог проекций (views) и точек зрения на модель (viewpoint) с подмножествами типов элементов архитектуры, из которых они строятся. В стандарте регламентируется деятельность системного архитектора при построении им описания архитектуры. Частично работа архитектора по построению модели архитектуры программного обеспечения (элементов модели, их проекций и различных точек зрения участников проекта) и ее визуализации, выполняемая для хранимого в репозиториях свободного программного кода, может быть автоматизирована CASE-инструментом [10,11,12].
3. Верификация и рефакторинг библиотек
Многие библиотеки, предоставляющие проекту необходимую функциональность, требуют переработки (рефакторинга) исходного текста библиотеки. Зачастую это обусловлено ошибками проектирования совершенными при не согласованной работе многих разработчиков библиотеки меняющихся на протяжении нескольких лет. Такие ошибки проектирования приводят к необходимости подключения той функциональности, которая реально в проекте не используется. Не используемый в проекте код в свою очередь может требовать подключения других библиотек. В итоге размеры подключаемого и реально используемого программного кода могут отличаться в несколько раз.
Другой распространенной причиной, которая требует рефакторинга библиотек, является отсутствие исходных текстов у части используемых ими свободно распространяемых библиотек. Для некоторых проектов критичным является отсутствие в используемом коде так называемых «закладок», выполняющих непредсказуемые действия. Например, передачу информации об окружении исполняемой программы по сети интернет. Поэтому отсечение или замена кода, использующего библиотеки без исходных текстов, для таких проектов требует понимания архитектуры библиотеки показывающей связи исключаемого или заменяемого кода с остальным кодом библиотеки.
Для выявления ошибок проектирования библиотеки CASE-инструментом выполняется верификация архитектуры библиотеки.
Разработан ряд объектно-ориентированных метрик [13] позволяющих выявить критические участки в коде библиотеки. С помощью таких метрик измеряются сцепление классов, сцепление методов классов, глубина наследования и многие другие характеристики логической структуры библиотеки. Измерение проекта с помощью метрик позволяет также выявить нарушение основных принципов проектирования [14], получивших сокращенное наименование SOLID (Single responsibility, Open-closed, Liskov substitution, Interface segregation, Dependency inversion). Таким образом объектно-ориентированные метрики позволяют выявить ошибки проектирования в логической структуре проекта (в исходных текстах программ на языке Java) и выполнить рефакторинг структуры с помощью CASE-инструмента.
Большое значение для использования и сопровождения свободно распространяемых библиотек имеет также их физическая структура -декомпозиция библиотек на модули. В настоящий момент в языке Java отсутствует явно понятие модуля на уровне конструкций языка. Фактически роль модуля в языке Java выполняют упакованные в файлы с расширением jar исполняемые файлы (байт-код) классов языка Java (компоненты). Отсутствие модульности на уровне самого языка приводит к часто встречающимся ошибкам проектирования, когда классы из одной компоненты имеют непосредственные связи с классами из других компонент [15]. Это существенно затрудняет сопровождение, использование и развитие библиотек состоящих из таких модулей.
Для преодоления таких ошибок проектирования связи между компонентами системы в некоторых проектах явно описываются на основе получающей все более широкое распространение спецификации OSGi[16]. При использовании спецификации OSGi описание допустимых связей между компонентами включается в файл манифеста компоненты. Такие явно описанные связи используются CASE-инструментом при построении модели компонентов и ее визуализации.
В настоящее время ведется работа по расширению самого языка Java модульными конструкциями в рамках проекта JIGSAW[17]. Эти конструкции языка можно будет использовать, начиная с версии языка Java 8. Фирмой Oracle в версии языка Java 8 для декомпозиции платформы предполагается использовать компактные профили (Compact Profiles) [18]. Полностью модульные конструкции для декомпозиции самой платформе Java предполагается использовать, начиная с версии Java 9. В CASE-инструменте модульные конструкции Java предполагается использовать при переносе библиотек на платформу Java 8.
Для верификации взаимосвязей компонент библиотек выполняется анализ структуры компонент и выявление типовых ошибок проектирования [15, 14]. К таким ошибкам, например, можно отнести наличие циклических связей между компонентами, отсутствие разбиения архитектуры компонент на уровни, несоответствие уровней логической и
физической структуры, наличие сильного сцепления (cohesion) между компонентами, отсутствие разделения уровней компонент для интерфейсов, реализации и тестирования. Анализ физической структуры библиотек [15] позволил выявить множество хорошо зарекомендовавших шаблоны проектирования, выделив категории таких шаблонов. В частности, категории шаблонов для расширяемости библиотек, категории для уменьшения зависимости между компонентами библиотек, категории облегчающие используемость библиотек. В качестве примеров из категории расширяемости приведем замену зависимостей между классами модулей на зависимости только от абстрактных элементов структуры (интерфейсов и абстрактных классов), использование реализаций интерфейсов и абстрактных классов через фабрики реализаций.
Для выполнения преобразования программного кода CASE-инструментом предполагается использовать программный интерфейс платформы Eclipse[19] предназначенный для рефакторинга программного текста написанного на языке Java. Данный программный интерфейс предоставляет элементарные виды рефакторинга, применяемые к исходным текстам программ, из которых возможно построение более специализированных видов рефакторинга CASE-инструмента. В частности, такой полезный вид элементарного рефакторинга Eclipse, как порождение из существующего класса интерфейса, который данный класс будет реализовать, с включением в интерфейс части методов класса. Или выделение в абстрактный базовый класс части полей и методов выбранного для рефакторинга класса. Таким образом, возможно, например, выделение в отдельные уровни (компоненты) абстрактных классов, или замены зависимостей между классами компонент на зависимости классов от интерфейсов, выделенных в отдельные компоненты.
4. Заключение
В статье рассмотрены возможности CASE-инструмента для решения задачи обратного проектирования (reverse engineering) свободно распространяемого программного обеспечения. Описаны особенности работы этого инструмента с централизованными хранилищами свободно распространяемых библиотек. Рассмотрены возможности по моделированию и визуализации архитектуры библиотек с помощью языка UML с использованием стандартов на описание архитектуры программной системы. Описаны проблемы осложняющие использование таких библиотек. Показаны методы верификации логической и физической структуры библиотеки для ее последующего рефакторинга.
Литература
1. Ivy - The agile dependency manager, http://ant.apache.org/ivy/
2. Maven architecture, http://maven.apache.Org/ref/3.0.5/
3. Aether- the library for working with artifact repositories, http://www.eclipse.org/aether/
4. Object Management Group, UML 2.4 Superstructure Specification, OMG document.
http://www.omg.org/spec/UML/2A1/
5. Object Management Group, UML Diagram Interchange, OMG document, http://www.omg.Org/spec/UMLDI/1.0/PDF
6. Object Management Group, XML Metadata Interchange, OMG document, http: //www. omg. org/spec/XM I/2.4.1/
7. ISO/IEC/IEEE 42010:2011, Systems and software engineering — Architecture description, http://www.iso-architecture.org/ieee-1471/
8. Nick Rozanski, Software Systems Architecture: Working with Stakeholders Using Viewpoints and Perspectives, Second Edition, Addison-Wesley Professional, October 25, 2011, ISBN 978-0-32171833-4
9. Paul Clements; Felix Bachmann; Len Bass; David Garlan; James Ivers; Reed Little; Paulo Merson; Robert Nord; Judith Stafford, Documenting Software Architectures: Views and Beyond, Second Edition Publisher: Addison-Wesley Professional, October 05, 2010, ISBN 978-0-321-55268-6
10. Романов В. Ю. Моделирование свободно-распространяемого программного обеспечения с помощью языка UML //International Journal of Open Information Technologies. - 2013. - Т. 1. -№. 7. - С. 11-15.
11. Романов В.Ю. Реализация метамодели языка UML на основе хранилища данных фирмы Google. Сб. трудов VII Международной научно-практической конференции "Современные информационные технологии и ИТ-образование". М.:, 2012. c.605-610.
12. Романов В.Ю. Сервис анализа и визуализации кода и текстов на языках программирования как облачное приложение Google. Сб. трудов V Международной научно-практической конференции "Современные информационные технологии и ИТ-образование". М.:, 2011. c.743-748, 12-14 декабря 2011 г.
13. Michele Lanza, Radu Marinescu, S. Ducasse. Object-Oriented Metrics in Practice: Using Software Metrics to Characterize, Evaluate, and Improve the Design of Object-Oriented Systems. Springer 2006, ISBN 978-3540244295
14. Robert C. Martin, Designing Object Oriented Applications using UML, 2d. ed. Prentice Hall, 1999
15. Kirk Knoernschild , Java Application Architecture: Modularity Patterns with Examples Using OSGi, Addison-Wesley Professional, 2012, ISBN 978-0-321-24713-1
16. OSGi - The Dynamic Module System for Java, http://www.osgi.org
17. Standard module system for the Java SE Platform http://openjdk.java.net/projects/jigsaw/
18. Compact Profiles, http://openjdk.java.net/jeps/161
19. The Language Toolkit: An API for Automated Refactorings in Eclipse-based IDEs, http://www.eclipse.org/articles/Article-LTK/ltk.html