2 Migration from Poland to Norway
3.1 Considerations about future mobility
3.1.1 Summary of employment trajectories in Norway
Este módulo foi customizado para atender ao processo de desenvolvimento do SIGAA, onde cada versão validada contém as modificações de um conjunto de tarefas finalizadas, cada tarefa é implementada no trunk do SVN Repository, e quando todas as tarefas que constituem uma versão são finalizadas, as modificações são copiadas uma por uma para o branch de produção, registrando sempre o número da tarefa copiada nos logs. Quando todas as tarefas são copiadas para produção, testadas e validadas, é feita uma cópia para uma nova
tag, onde a versão ficará registrada. É possível observar este processo de
controle de versões em no exemplo de um sistema fictício apresentado nas Tabelas 3 e 4.
A Tabela 3 descreve três diferentes versões de um sistema, discriminando cada uma das tarefas que são requeridas para que o sistema evolua de uma versão para a seguinte. Cada tarefa por sua vez necessitará de uma ou mais revisões no trunk para que seja dada como finalizada, quando todas as tarefas de uma versão forem concluídas, cada modificação realizada será transferida para o branch de produção, onde as modificações serão postas a prova pela equipe de testes e validada pelos projetistas e arquitetos. Ao finalizar a validação, a versão pode então ser copiada para uma tag, recebendo o nome do sistema e o número da versão.
Tabela 3. Exemplo de sistema: versões e suas tarefas necessárias. version required tasks
1 1 and 2 2 3 and 4 3 5 and ...
A Tabela 4 exemplifica a evolução do sistema através das revisões, cada revisão representa um commit de código submetido ao SVN Repository em seus diferentes diretórios (trunk, branch e tag). Notem que foram necessárias duas revisões (1 e 2) para finalizar a tarefa 1 e mais outra revisão (3) para finalizar a última tarefa necessária à versão 1 do sistema. Neste ponto, as modificações de cada tarefa são copiadas individualmente para o branch de produção nas
revisões 4 e 5 e, após copiar e validar todas as modificações, uma nova cópia é feita para a tag da versão 1 (revisão 6). A versão da tag geralmente é um número a mais que a revisão do branch, por exemplo as revisões 6 e 5 respectivamente, entretanto, pode acontecer de um outro commit ser realizado depois da validação e antes da cópia do sistema para a tag, como o commit da revisão 13, sendo assim, a forma correta de se obter a revisão no branch que possua código equivalente ao da revisão na tag, é procurando pela última revisão no branch que ocorreu antes da revisão na tag.
Tabela 4. Exemplo de commits em um repositório SVN.
trunk branch tag commit log
rev isi o n s 1 changes of task 1 2 changes of task 1 3 changes of task 2
4 copy of changes on trunk 2 task 1 finished 5 copy of changes on trunk 3 task 2 finished 6 copy of branch 5 version 1 finished 7 changes of task 3
8 changes of task 4 9 changes of task 5 10 changes of task 3
11 copy of changes on trunk 8 task 4 finished 12 copy of changes on trunk 10 task 3 finished 13 changes of task 5
14 copy of branch 12 version 2 finished
O History Miner funciona da seguinte forma, as versões inicial e final do sistema, informadas pelo usuário ao Executer, estão registradas em duas tags
distintas, entretanto, nelas não há registo algum de quais tarefas foram atendidas
para que uma versão evoluísse até a outra. Tais informações serão encontradas apenas no branch de produção. Desta forma, é preciso obter, para cada tag, sua revisão correspondente no branch de produção, isto é feito através do método
HistoryMiner.getHeadRevision(...). Como a tag é uma cópia no tempo do
branch de produção, é possível concluir que a revisão no branch é algum número
inferior a revisão da tag, bastando consultar qual foi o último commit no branch antes da cópia, através do método HistoryMiner.getPreviousRevision(...). E
versão do sistema. Vale observar que a revisão inicial corresponde ao sistema antes das modificações, sendo assim, as modificações não serão procuradas nesta revisão, por isso serão analisadas as revisões a partir da subsequente da revisão inicial, para obtê-la é utilizado o método
HistoryMiner.getNextRevision(...).
Para que o History Miner obtenha as tarefas realizadas entre as revisões, ele consulta todos os logs das operações de commit no branch de produção entre as duas revisões, onde é possível encontrar os números de identificação de cada tarefa, registrados pelos próprios desenvolvedores, através do método
HistoryMiner.getTaskNumberFromLogMessage(...).
Após recuperar todos os números das tarefas, o History Miner utiliza a biblioteca do JDBC para consultar o CMT Data Base, onde pode encontrar as tarefas válidas a partir de seus identificadores, recuperando, também, outras informações relevantes ao estudo como seus tipos e logs de andamento. É a partir destes logs que serão extraídos os números das revisões no trunk, onde as modificações foram de fato realizadas. O identificador das revisões também são registrados pelos próprios desenvolvedores, à medida que concluem suas tentativas de atender a tarefa. Esta função está disponível através do método
HistoryMiner.populateTasksTypeById(...).
Como visto, as revisões das modificações se encontram no trunk, desta forma, o History Miner pode consultar tais revisões para obter cada uma das linhas modificadas em cada arquivo de classe Java do sistema, utilizando a operação SVNDiffClient.doDiff(...) do SVNKit. Além das modificações, ele
analisa cada classe Java modificada para obter as linhas de início e fim de cada método, assim é possível inferir a quais métodos pertencem cada uma das linhas incluídas, na nova versão da classe, e das excluídas, na versão antiga da classe. Ao analisar todas as revisões de cada tarefa o History Miner obtém a relação dos métodos modificados entre as duas versões, função, esta, implementada pelo método HistoryMiner.getChangedMethodsSignaturesFromProjects(...).
Outra operação desempenhada pelo History Miner é a de baixar os projetos com base numa revisão informada pelo Executer, através do método
HistoryMiner.checkouOrUpdateProjects(...), que por sua vez, ao ser
solicitado, executa o método SVNUpdateClient.doCheckout(...) do SVNKit para
cada um dos projetos que compõem o sistema. Cada projeto do sistema que deve ser rastreado recebe a instrumentação do TTracker através do método
HistoryMiner.configureAspectJ(...), em seguida, todos os projetos são
convertidos em projetos eclipse, e posteriormente importado para o Project
Explorer do Eclipse, através do método HistoryMiner.importProject(...). A
partir deste ponto o usuário é capaz de, utilizando o próprio eclipse para compilar, rodar e executar os testes no sistema.
A seguir serão descritas as associações entre as classes deste módulo conforme apresentadas na Figura 5. A classe SVNConfig recebe do Executer as
informações da URL, do usuário e da senha para acesso ao SVN Repository. A classe ChangedAssetsMinerUtil implementa os ativos modificados dos projetos,
sendo capazes de fornecer as UpdatedLines, que representam as linhas
alteradas de cada classe. O conjunto das UpdatedLines de uma classe
constituem uma ClasseUpdates, várias destas, por sua vez, constituem o
conjunto de atualizações de um mesmo projeto, o ProjectUpdates. A classe MethodLimitBuilder é capaz de determinar, a partir das classes modificadas,
quais são as linhas limite dos métodos, isto é, linhas de início e de fim de cada método, os chamados MethodLimits, que permitem que o UpdatedMethod
descubra a quais MethodLimits as UpdatedLines pertencem, consequentemente
descobrindo quais foram os métodos modificados.