O metamodelo arquitetural do Cosmos deve possibilitar a representação das aplicações por meio de seus componentes, suas propriedades e conexões. A definição original do metamodelo foi apresentada por Lopes (LOPES, 2006) e ele era composto em síntese pelos elementos:
Tabela 2: Metamodelo definido por Lopes. Elemento Descrição
CosmosComponent Representa um componente no Cosmos.
Port Representa as portas associadas aos componentes. Property Representa as propriedades dos componentes e portas.
Com a evolução do Cosmos, um outro metamodelo foi definido com o intuito de utilizar o estilo componente-conector, da engenharia de software. Pinto (PINTO, 2011) apresenta um metamodelo que, além de representar componentes e propriedades, introduz elementos para representar as interfaces. As ligações entre os componentes, que era realizada por meio das portas, passou a ser realizada através das interfaces, com isso, os componentes passaram a prover e requerer interfaces.
Em ambas as abordagens, (LOPES, 2006) e (PINTO, 2011), os metamodelos definidos somente eram capazes de representar o modelo das aplicações por meio de suas instâncias, não possibilitando sua representação estrutural, por meio dos seus elementos e tipo. O uso dessa separação nos possibilita ter, tanto uma visão da composição da aplicação, quanto dos seus componentes concretos. A separação dessas visões é importante por estarmos realizando a integração do Cosmos com o framework de geração de processos.
Em nossa abordagem estamos adotando o metamodelo definido pela linguagem xADL (DASHOFY; HOEK; TAYLOR, 2005). Essa adoção foi realizada tendo em vista os seguintes
pontos:
• A linguagem xADL tem a capacidade de representar modelos tanto por meio de tipos e estrutura, quanto por instâncias;
• A linguagem xADL possibilita que seja realizada extensões de maneira a torná-la específica ao domínio da aplicação;
• Essa linguagem foi adotada pelo framework de geração de processos;
• E por entender que a criação de uma nova ADL não é a nosso foco.
O novo metamodelo é apresentado pela Figura 8 onde encontramos a representação de arquiteturas de instancia (ArchInstance), arquiteturas de estrutura (ArchStructure) e tipos da estrutura (ArchTypes). A arquitetura de instância é composta pelas instâncias dos elementos componente (ComponentInstance), conector (ConnectorInstance), interface (InterfaceInstance) e link (LinkInstance). As interfaces são associadas aos componentes e conectores, e podem ser requeridas ou providas. A indicação de que a interface é re- querida ou provida é realizada através da direção (Direction) a qual está associada. A ligação entre duas interfaces se dá através links, que contêm pontos de ligação. A arqui- tetura estrutural é composta de maneira semelhante a arquitetura de instância por meio de componente (Component), conector (Connector), interface (Interface) e link (Link). A principal diferença entre a arquitetura de instância e estrutural é que nos elemen- tos componente, conector e interface são associados seus respectivos tipos; esses tipos são representados por: tipo de componente (ComponentType), tipo de conector (Connec- torType) e tipo de instância (InterfaceInstance). O elo de ligação entre a arquitetura de instância e de estrutura é realizada através dos elementos PrescribedComponentInstance, PrescribedInterfaceInstance e PrescribedConnectorInstance.
Além dos elementos existentes no metamodelo xADL introduzimos o elemento pro- priedade (Property) que pode ser associado aos componentes, conectores e interfaces. A associação de propriedades aos componentes é realizada através de sua estrutura (Virtual- Resource) e sua instância (VirtualResourceInstance) que são especializações dos elemen- tos Component e PrescribedComponentInstance. De maneira semelhante, as propriedades também podem ser associadas aos links através da especialização MyPrescribedInterfa- ceInstance.
A geração do metamodelo foi realizada com o auxílio do framework EMF1
. Esse fra- mework disponibiliza um conjunto de ferramentas gráficas que auxiliam a especificação de componentes e aplicações. A partir da especificação do metamodelo, gerada pelo fra- mework EMF, podemos gerar arquivos no formato XMI. A descrição simplificada de um componente é apresentada na Figura 9. Nela encontramos a definição do tipo de compo- nente MyVRType que é utilizado na definição do componente VR1. Também encontramos a definição do tipo da interface MyInterfaceType que define a interface MyInteface. As
instancias, vr e myInterface são estruturadas pelos elementos VR1 e MyInterface, respec- tivamente.
Figura 9: Descrição de um componente em nosso metamodelo.
3.2
Nova Arquitetura do Cosmos
Na reengenharia realizada, uma nova arquitetura foi projetada para atender as novas necessidades introduzidas, adaptação aberta e integração com a plataforma OSGi. Com isso, parte dos componentes que compunham o antigo framework foram substituídos por componentes especializados e novos componentes foram adicionados.
3.2.1
Visão Geral
A arquitetura original do Cosmos, apresentada no capítulo anterior pela Figura 2, é centrada no componente Configurator, o qual é responsável pelas atividades de adaptação, com o auxílio de monitores na coleta de informações. Com isso, o Configurator é o respon- sável por analisar os dados obtidos nos componentes e realizar as operações necessárias na realização da adaptação. Com a reengenharia realizada, as fases que compõem o feedback control loop foram extraídas do Configurator.
A nova arquitetura é apresentada na Figura 10, onde buscamos a integração do Cos- mos com componentes especializados. Esses componentes especializados são responsáveis
pelas fases do feedback control loop. A fase de coleta e analise é realizada pelo QoS Ma- nager através do gerenciamento da qualidade de serviços. A fase decidir é realizada pelo MoSAC através da seleção de novas arquiteturas. Por fim, as fases decidir, no que se refere a geração dos planos de adaptação, e atuar é realizada pelo Wf.Gen. A interação entre o Configurator e esses componentes é realizada com o uso das interfaces IQoSMa- nager, IArchSelector, IPlanGen. No contexto da geração dos planos, o Wf.Gen interage com o Configurator por meio da interface IAdaptable. Também destacamos que ocorreram mudanças e ajustes em alguns componentes. De forma a entender melhor a arquitetura, vamos descrever e destacar os principais elementos. Como componente central da arqui- tetura, temos o Configurator, que é o responsável por todos os processos do framework. Ao instanciar o Cosmos, o Configurator precisa, na sequencia, instanciar o gerenciador de modelos (ModelManager), que por sua vez utiliza o metamodelo (MetaModel) definido anteriormente. A criação de componentes, ou seja, recursos virtuais (VirtualResource) das aplicações que serão executadas no framework, é realizada pelo Configurator. Com a instanciação de um novo recurso virtual, o Configurator associa ao recurso virtual um Probe que tem como papel monitorar as propriedades relacionadas à qualidade de serviço do recurso virtual.
Figura 10: Visão geral do Cosmos.
Ao instanciar uma aplicação no Cosmos, o Configurator configura o gerenciador de QoS (Qos Manager ) com informações relacionadas as propriedades dos componentes que devem ser monitoradas. Essas informações são formadas por faixas de valores esperados durante a execução dos componentes. Uma vez que o gerenciador de QoS esteja confi- gurado, os Probes realizam a leitura do valor das propriedades monitoradas e informa ao gerenciador de QoS que verificará a existência da necessidade de adaptação. A inte-
gração com um gerenciador de QoS é realizada através da interface IQosManager que contem as seguintes atividades: adicionar um monitor (addMonitor), remover um Probe (removeMonitor) e avaliar dados(checkData), como apresentada pela Figura 11.
Figura 11: Interface IQoSManager.
Uma vez identificada a necessidade de adaptação, o Cosmos utiliza um componente de seleção arquitetural, o MoSAC (SILVA, 2011) para encontrar uma nova arquitetura; para tal, o Cosmos envia ao seletor de arquiteturas a configuração arquitetural atual, indicando os componentes que falharam. O seletor deve devolver uma nova arquitetura para ser instanciada no Cosmos. A integração entre o Cosmos e o componente seletor de arquiteturas é realizada através da interface IArchSelector que deve ser disponibilizada pelo componente especializado MoSAC. Essa interface pode ser observada na Figura 12 e contem o método getNewArch que deve retornar a nova arquitetura, para tal, deve-se informar a arquitetura de instância e de estrutura atuais.
Figura 12: Interface IArchSelector.
A partir da nova arquitetura, o Cosmos utiliza um gerador de planos de adaptação que tem a responsabilidade de gerar e executar as ações necessárias para a realização da adaptação. Para isso, o Cosmos necessita que o gerador de planos disponibilize a interface IPlanGen que é capaz de iniciar o processo de geração de planos (Figura 13). Essa interface apresenta o método generatePlan que é utilizado para indicar o início da geração do plano de adaptação ao gerador de processos, e receber como parâmetros a configuração atual (oldInstance) e a nova configuração (newInstance).
Uma vez que o plano seja gerado, o gerador de planos utiliza a interface IAdaptable para efetuar as ações de adaptação. A interface IAdaptable é apresentada pela Figura 14 e contem as ações disponíveis para adaptar o sistema. Essas ações correspondem aos templates de tarefas exigidos pelo framework de geração de processos durante a geração dos planos de adaptação. A seguir apresentamos as ações:
• start : solicita ao Cosmos que inicie o componente indicado; • stop: solicita ao Cosmos que pare o componente indicado;
• connectComponentToConnector : solicita ao Cosmos que conecte as interfaces do componentes e conector indicados;
• connectConnectorToComponent : solicita ao Cosmos que conecte as interfaces do conector e componente indicados;
• disconnectComponentToConnector : solicita ao Cosmos que desconecte as interfaces do componente e conector indicados;
• disconnectConnectorToComponent : solicita ao Cosmos que desconecte as interfaces do conector e componente indicados;
• block : solicita ao Cosmos que bloqueie o componente, o que indica que o componente está em processo de adaptação. Esse bloqueio ocorre em nível de modelo;
• unblock : solicita ao Cosmos que desbloqueie o componente;
Figura 14: Interface IAdaptable.
3.2.2
Modelo de Componentes
O modelo de componentes definido por (LOPES, 2006), Figura 15, apresentava seis in-
que foram realizadas na arquitetura e a integração com componentes especializados, foi realizada uma atualização das interfaces do modelo de componentes de maneira que as seguintes interfaces foram unidas: IMonitored com IBasicService e IPropertyConstranint com IPropertyInquiry.
Figura 15: Modelo de componentes original.
Com a união das interfaces mencionadas e o refinamento dos métodos, apresentamos na Figura 16 a assinatura das interfaces do novo modelo de componentes. Entendendo que obter o valor de uma determinada propriedade pode ser caracterizado por um ser- viço do componente, o método getValue foi movido da antiga interface IMonitored para IBasicService. O método actualizeSelectedValue foi retirado da interface IPropertyUpdate, uma vez que assumimos que mudanças de propriedades devem ser realizadas com base no ModelManager; as interfaces IPropertyInquiry e IPropertyConstraint foram unidas por tratarem de acesso as propriedades.
Figura 16: Interfaces do modelo de componentes.
A descrição das operações relacionadas com as interfaces apresentadas pela Figura 16 é listada na Tabela 3.
3.2.3
Gerenciador de Modelos
No contexto de sistemas de software autoadaptativos, o monitoramento do estado e controle do sistema pode ser realizado através do uso de modelos. Esses modelos represen- tam o sistema e devem espelhar o estado e comportamento dos componentes que compõem
Tabela 3: Descrição dos métodos das interfaces do componente. Método Descrição
Interface IBasicService
getName Retorna o nome do componente.
getInterfaces Retorna uma lista com as interfaces do componente. getValue Obtem o valor de uma propriedade.
Interface IPropertyUpdate
activate Ativa o componente. deactivate Desativa o componente.
activateAdaptation Indica ao componente que ele está em adaptação. changeStateTo Muda o estado de um componente
Interface IPropertyInquiry
getProperties Obtêm uma lista com todas as propriedades de um componente. getProperty Obtém uma propriedade especifica de um componente.
o sistema. Com isso, a mudança no modelo deve ser refletida no sistema e vice-versa, como indicado por (BLAIR; BENCOMO; FRANCE, 2009)(MORIN et al., 2009).
No Cosmos as aplicações são representadas por modelos, baseados no metamodelo apresentado anteriormente na Figura 8, e, esses modelos são gerenciados pelo ModelMa- nager. No gerenciamento, o ModelManager realiza toda a validação do modelo de instância baseado-se na estrutura e tipos, como também todas as operações de controle e gerencia- mento. A Figura 17 apresenta a interface que é seguida na construção do ModelManager. Nessa interface encontramos métodos de verificação do estado dos componentes e de con- trole do estado.
(c) Por fim, o Wf.Gen indica o fim da adaptação.
6. Uma vez que os componentes sejam criados, o Configurator instancia um Probe e o associa aos atributos que devem ser monitorados.
O processo de adaptação no Cosmos é apresentado pelo diagrama da Figura 18. Ele é iniciado quando o QoS Manager verifica a necessidade de adaptação, a partir dos dados que foram lido pelos Probes. Uma vez verificado que a leitura não está conforme, o QoS Manager indica ao Configurator que o processo de adaptação deve ser iniciado. A partir da notificação de inicio de adaptação, o Configurator obtém as arquiteturas de instância e de estrutura, cujas informações devem ser passadas para o seletor de arquitetura (Mo- SAC ). Uma vez selecionada a nova arquitetura pelo seletor de arquitetura, o Configurator encaminha essa configuração para o gerador de processos (ProcessGenerator) que irá gerar um plano de adaptação e irá executá-lo no Configurator. O processo é terminado quando o gerador de processo sinalizar com o fim da adaptação; com isso, o Configurator efetua as mudanças no ModelManager e replica as ações para serem executadas nos componentes concretos.
Figura 18: Processo de adaptação.
3.3
Integração com a Plataforma OSGi
A importância da integração com a plataforma OSGi é proporcionar o uso do Cosmos em um ambiente adotado pela indústria e assim, torná-lo mais atrativo. Nessa integração,
tomamos como princípio que as aplicações que foram desenvolvidas para serem executadas no framework Cosmos não necessitem de codificação extra quando o Cosmos estiver sendo executado sobre a plataforma OSGi.
Aplicações baseadas em componentes e baseadas em serviços utilizam conceitos dife- rentes, onde a principal diferença é que no modelo de componentes as ligações são estáti- cas enquanto que no modelo baseado em serviços as ligações são dinâmicas (DESERTOT; CERVANTES; DONSEZ, 2006). Ao realizar essa integração, assumimos que os componentes Cosmos serão mapeados como serviços na dessa plataforma.
Para usar o OSGi como suporte, foi criado uma extensão do Cosmos contendo fábri- cas de componentes, configurador, probe, e ativador específicos para o OSGi. A Figura 19 mostra a relação entre o framework e sua extensão onde apresentamos o componente Con- figuratorOSGi como responsável por efetuar as atividades do Configurator no ambiente OSGi; para dar suporte ao ConfiguratorOSGi foi necessário criar fábricas específicas (Fac- toryOSGi) que servem para criar os componentes concretos e publicá-los na plataforma OSGi. Foi introduzido também um novo tipo de Probe, ProbeOSGi que é implementado como uma especialização da interface OSGi ServiceTrackCustomizer. A interface Service- TrackCustomizer é utilizada para monitorar serviços, na plataforma OSGi, possibilitando adicionar ações quando um serviço é adicionado, alterado ou removido.
Figura 19: Especialização do Cosmos para OSGi.
Uma vez que o Cosmos esteja sendo instanciado na plataforma OSGi, o CosmosAc- tivator é o responsável por instanciar o ConfiguratorOSGi e torná-lo disponível, como serviço, na plataforma OSGi. Uma vez que o ConfiguratorOSGi esteja instanciado, ele criará o componente ModelManager a partir da realização da interface, descrita anteri- ormente na Figura 8. A Figura 20 mostra a implementação padrão ModelManagerImpl,
como também um implementação específica para para a plataforma OSGi.
Figura 20: Diagrama da implementação padrão.
Os componentes que compõem as aplicações, no Cosmos, são instanciadas e publica- das como serviços OSGi, por meio do ConfiguratorOSGi. As ligações entre os componentes Cosmos/serviços OSGi, são tratadas de maneiras distintas, enquanto que no Cosmos as li- gações são explícitas, no OSGi as ligações são implícitas. Para poder lidar com a diferença no tratamento das ligações, passamos a responsabilidade da ligação para o Configurato- rOSGi, o qual, utiliza o mecanismo de busca da plataforma OSGi. Na busca são utiliza- dos o tipo do componente/serviço e sua identificação. Essa identificação é adicionada ao serviço OSGi, no momento da publicação do serviço, e corresponde ao identificador do componente Cosmos.
O estado associado ao bundle, descrito no capítulo 2, influencia os componentes Cos- mos, pois, uma vez que um bundle é parado, todos os seus serviços também são parados. A Tabela 4 apresenta a relação entre o ciclo de vida de um bundle e um componente OSGi. Um componente é considerado Instantiated no Cosmos quando todas as dependências es- tão disponíveis e o componente pode ser instanciado, esse comportamento é semelhante a instalação de um bundle OSGi, nesse momento o componente é carregado na plataforma e o bundle passa por uma validação de suas dependências, estados Installed e Resolved respectivamente. Uma vez que o componente Cosmos seja instanciado, ele passa por uma etapa de configuração, a qual define todos os seus atributos, e por fim a alocação de todos os recursos necessários ao seu funcionamento; de maneira semelhante na plataforma OSGi a configuração do bundle é realizada no momento em que ele está sendo iniciado, estado Starting. Os estados Running e Active. no Cosmos e OSGi respectivamente, indicam que o componente está em execução. Os demais estados do Cosmos, Finishing e Released são análogos aos estados Stopping e Unistalled e são relacionados a parada e liberação dos componentes. Assim, procuramos encontrar uma relação direta dos estados do Cosmos com os da plataforma OSGi, dessa maneira podemos adicionar elementos que consigam
atualizar os componentes, a nível de modelo, e que indique a necessidade de adaptação ocasionada pela parada de um bundle.
Tabela 4: Relação entre os ciclos de vida do Cosmos e OSGi. Componente Cosmos Bundel OSGi
Instantiated Installed Resolved Configured Starting Allocated Running Active Finishing Stopping Released Unistalled
O monitoramento na mudança dos estados em um bundle é realizado através do Probe- OSGi. Assim, quando um bundle é parado na plataforma OSGi, o ProbeOSGi informa ao ConfiguratorOSGi que os componentes contidos no bundle também pararam. Uma vez que o ConfiguratorOSGi é informado da parada dos componentes, ele inicia uma adaptação da aplicação. De maneira semelhante, quando um bundle é desinstalado, o ProbeOSGi deve informar ao ConfiguratorOSGi que os componentes associados ao bundle foram removidos e o ConfiguratorOSGi deve iniciar uma adaptação da aplicação.