diff --git a/.gitignore b/.gitignore index 70bfceac2cfdcf7123581062913923cea3df44a1..b4161d80e502c256f02d457b82e8dded6b351566 100644 --- a/.gitignore +++ b/.gitignore @@ -13,3 +13,5 @@ downloads/* *.html *.orig apostila-git.Rproj +/apostila_git.toc +/cap05.md diff --git a/apostila_git.tex b/apostila_git.tex new file mode 100644 index 0000000000000000000000000000000000000000..99b616b8f7b8ab440471df67a1462d4e3d9f77e9 --- /dev/null +++ b/apostila_git.tex @@ -0,0 +1,216 @@ +\documentclass[ + a5paper, + pagesize, + 9pt, + % bibtotoc, + pointlessnumbers, + normalheadings, + % DIV=9, + twoside=false +]{book} + +\usepackage[brazil]{babel} +\usepackage[utf8]{inputenc} +\usepackage[T1]{fontenc} + +\usepackage[sc]{mathpazo} +% \usepackage{palatino} +% \linespread{1.05} +\usepackage[scaled=0.85]{beramono} + +%----------------------------------------------------------------------- + +\usepackage{amssymb, amsmath} +\usepackage{ifxetex, ifluatex} + +\usepackage{fixltx2e} % provides \textsubscript +\ifnum 0\ifxetex 1\fi\ifluatex 1\fi=0 % if pdftex + \usepackage[T1]{fontenc} + \usepackage[utf8]{inputenc} +\else % if luatex or xelatex + \ifxetex + \usepackage{mathspec} + \usepackage{xltxtra,xunicode} + \else + \usepackage{fontspec} + \fi + \defaultfontfeatures{Mapping=tex-text,Scale=MatchLowercase} + \newcommand{\euro}{€} +\fi + +% use upquote if available, for straight quotes in verbatim environments +\IfFileExists{upquote.sty}{\usepackage{upquote}}{} +% use microtype if available +\IfFileExists{microtype.sty}{% +\usepackage{microtype} +\UseMicrotypeSet[protrusion]{basicmath} % disable protrusion for tt fonts +}{} + +%----------------------------------------------------------------------- +% knitr. + +\usepackage{color} +\usepackage{fancyvrb} +\newcommand{\VerbBar}{|} +\newcommand{\VERB}{\Verb[commandchars=\\\{\}]} +\DefineVerbatimEnvironment{Highlighting}{Verbatim}{commandchars=\\\{\}} +% Add ',fontsize=\small' for more characters per line +\usepackage{framed} +\definecolor{shadecolor}{RGB}{248,248,248} +\newenvironment{Shaded}{\begin{snugshade}}{\end{snugshade}} +\newcommand{\KeywordTok}[1]{\textcolor[rgb]{0.13,0.29,0.53}{\textbf{{#1}}}} +\newcommand{\DataTypeTok}[1]{\textcolor[rgb]{0.13,0.29,0.53}{{#1}}} +\newcommand{\DecValTok}[1]{\textcolor[rgb]{0.00,0.00,0.81}{{#1}}} +\newcommand{\BaseNTok}[1]{\textcolor[rgb]{0.00,0.00,0.81}{{#1}}} +\newcommand{\FloatTok}[1]{\textcolor[rgb]{0.00,0.00,0.81}{{#1}}} +\newcommand{\CharTok}[1]{\textcolor[rgb]{0.31,0.60,0.02}{{#1}}} +\newcommand{\StringTok}[1]{\textcolor[rgb]{0.31,0.60,0.02}{{#1}}} +\newcommand{\CommentTok}[1]{\textcolor[rgb]{0.56,0.35,0.01}{\textit{{#1}}}} +\newcommand{\OtherTok}[1]{\textcolor[rgb]{0.56,0.35,0.01}{{#1}}} +\newcommand{\AlertTok}[1]{\textcolor[rgb]{0.94,0.16,0.16}{{#1}}} +\newcommand{\FunctionTok}[1]{\textcolor[rgb]{0.00,0.00,0.00}{{#1}}} +\newcommand{\RegionMarkerTok}[1]{{#1}} +\newcommand{\ErrorTok}[1]{\textbf{{#1}}} +\newcommand{\NormalTok}[1]{{#1}} + +%----------------------------------------------------------------------- + +\usepackage{graphicx} +\makeatletter +\def\maxwidth{ + \ifdim\Gin@nat@width>\linewidth\linewidth + \else + \Gin@nat@width\fi} +\def\maxheight{ + \ifdim\Gin@nat@height>\textheight\textheight + \else + \Gin@nat@height\fi} +\makeatother +% Scale images if necessary, so that they will not overflow the page +% margins by default, and it is still possible to overwrite the defaults +% using explicit options in \includegraphics[width, height, ...]{} +\setkeys{Gin}{width=\maxwidth,height=\maxheight,keepaspectratio} + +\ifxetex + \usepackage[setpagesize=false, % page size defined by xetex + unicode=false, % unicode breaks when used with xetex + xetex]{hyperref} +\else + \usepackage[unicode=true]{hyperref} +\fi + +\hypersetup{breaklinks=true, + bookmarks=true, + pdfauthor={}, + pdftitle={}, + colorlinks=true, + citecolor=blue, + urlcolor=blue, + linkcolor=magenta, + pdfborder={0 0 0}} +\urlstyle{same} % don't use monospace font for urls + +\setlength{\parindent}{0pt} +\setlength{\parskip}{6pt plus 2pt minus 1pt} +\setlength{\emergencystretch}{3em} % prevent overfull lines + +\setcounter{secnumdepth}{5} + +%%% Use protect on footnotes to avoid problems with footnotes in titles +\let\rmarkdownfootnote\footnote% +\def\footnote{\protect\rmarkdownfootnote} + +%%% Change title format to be more compact +\usepackage{titling} + +% Create subtitle command for use in maketitle +\newcommand{\subtitle}[1]{ + \posttitle{ + \begin{center}\large#1\end{center} + } +} + +\setlength{\droptitle}{-2em} + +\title{Apostila Git} +\pretitle{\vspace{\droptitle}} +\posttitle{} + +\author{PET Estatística UFPR} +\preauthor{}\postauthor{} + +\date{2015} +\predate{}\postdate{} + +\usepackage{wrapfig} + +%----------------------------------------------------------------------- + +\begin{document} + +% \maketitle + +%----------------------------------------------------------------------- +% Capa. + +\begin{titlepage} + \centering{{\fontsize{40}{48}\selectfont \thetitle}}\\ + + \vspace{10mm} + \centering{\Large{\theauthor}}\\ + \vspace{\fill} \centering \large{\thedate} +\end{titlepage} + +%----------------------------------------------------------------------- +% Dedicatórias. + +\newpage{} +\thispagestyle{empty} +\vspace*{2cm} + +\begin{center} + \Large{ + \parbox{10cm}{ + \begin{raggedright} + {\Large + \textit{Não é a vontade de vencer que ganha o jogo, e sim a + vontade de se preparar para vencê-lo.} + } + + \vspace{.5cm}\hfill{---Paul ``Bear'' Bryant} + \end{raggedright} + } + } +\end{center} + +\newpage + +%----------------------------------------------------------------------- +% Agradecimentos. + +%----------------------------------------------------------------------- +% Tabela de conteúdo. + +{ +\hypersetup{linkcolor=black} +\setcounter{tocdepth}{2} +\tableofcontents +} + +%----------------------------------------------------------------------- +% Capítulos. + +% \input{cap01.tex} +% \input{cap02.tex} +% \input{cap03.tex} +% \input{cap04.tex} +% \chapter{Serviços Web para Projetos Git} +% \input{cap05.tex} +% \input{cap06.tex} +% \input{cap07.tex} +% \input{cap08.tex} +% \input{cap09.tex} + +\end{document} + +%----------------------------------------------------------------------- \ No newline at end of file diff --git a/cap05.Rmd b/cap05.Rmd index 395b3470496c1ae4bcf5570833956ad21caeeb96..049812dba810ac380edfdaa4e8663036a9a68deb 100644 --- a/cap05.Rmd +++ b/cap05.Rmd @@ -1,12 +1,16 @@ --- title: "Serviços Web para Projetos Git" author: "PET Estatística UFPR" +graphics: yes +header-includes: \usepackage{wrapfig} output: pdf_document: + template: template.tex highlight: default toc: true toc_depth: 2 keep_tex: true + number_sections: true --- ```{r, include=FALSE} @@ -14,6 +18,8 @@ library(knitr) opts_chunk$set(comment=NA) ``` +\chapter{Serviços Web para Projetos Git} + # Serviços Web para Git # No capítulo anterior vimos como configurar um repositório remoto em um @@ -26,9 +32,9 @@ discussão. Para que um desenvolvedor saiba o que os outros fizeram, ele terá que periodicamente dar `fetch`, navegar no histórico, ver *diffs*, etc. -O Git tem muitos serviços web voltados justamente para ter um local que -centralize o projeto bem como ofereça recursos administrativos e -colaborativos. Esses serviços possuem contas *free* etc... +O Git tem vários serviços web voltados para ter um local que centralize +o projeto bem como ofereça recursos administrativos ecolaborativos. +Esses serviços possuem contas *free*, entre outros. O objetivo desse capítulo é apresentar os serviços web para repositórios Git, descrever suas principais características, indicar como criar e @@ -38,12 +44,17 @@ as funcinalides desses serviçõs voltados à colaboração. ## GitHub ## - +\begin{wrapfigure}{r}{0.4\textwidth} + \begin{center} + \includegraphics[width=5cm]{./images/github-octocat.png} + \end{center} + \caption{Octocat é o mascote do GitHub.} +\end{wrapfigure} O [GitHub] é um serviço Web para hospedagem, gestão e compartilhamento de repositórios Git que oferece recursos para desenvolvimento e -colaboração. A principal slogam do GitHub é: *"Build software better, -together."* que justamente enfatiza o compromisso principal que é dar +colaboração. O principal slogam do GitHub é: *"Build software better, +together."* que justamente enfatiza o principal compromisso que é dar suporte ao desenvolvimento colaborativo. O GitHub foi fundado em 8 de Fevereiro de 2008, em São Francisco, por @@ -55,15 +66,15 @@ trimestre de 2014 haviam 22 milhões de repositórios. A linguagem total de *pushes* enquanto que a linguagem `R` foi a com maior número de novas cópias por repositório (6.45). -Diferente da forma tradicional de usar o Git, por linha de comando, que -fizemos até agora, o GitHub é um serviço web com interface gráfica -repleta de funções para o desenvolvimento e acompanhamento de um projeto -Git. Tais recursos vão desde administrar tarefas até a permitir a -colaboração de outras pessoas, até mesmo desconhecidos. Dentre os -principais recursos disponíveis, tem-se: +Diferente da forma tradicional de usar o Git por linha de comando, o GitHub +é um serviço web com interface gráfica repleta de funções para o +desenvolvimento e acompanhamento de um projeto Git. Tais recursos vão +desde administrar tarefas até permitir a colaboração de outras pessoas, +mesmo sendo desconhecidos. Dentre os principais recursos disponíveis, +tem-se: * README: é um arquivo texto escrito em liguagem de marcação - (Markdown, RST, Textile, Org, etc) que é renderizada para + (Markdown, RST, Textile, Org, etc) no qual é renderizada para exibição. O README é a capa do seu repositório, ou seja, o conteúdo apresentado na *home* do projeto e serve para informar o visitante dos objetivos do repositório, seus desenvolvedores e pode conter @@ -71,12 +82,12 @@ principais recursos disponíveis, tem-se: * Wiki: a Wiki de cada repositório serve para divulgação e documentação. Também é escrita em linguagem de marcação, tornando fácil e rápido a escrita pelo desenvolvedor e simples a leitura e a - navegação pelo visitante. Como a Wiki é também um repositório Git, + navegação pelo visitante. Como a Wiki é um repositório Git, ela pode inclusive ser editada por meios dos recursos de edição do - prórpio GitHub, além de versionada, claro. Com isso, não diferente + próprio GitHub, além de ser versionada. Com isso, não diferente do restante, a edição da Wiki também é colaborativa. - * *Issues*: Por *issues* é que se faz a correção de bugs e agendamento - de tarefas. Usuários criam *issues* para notificar um bug encontrado + * *Issues*: Pelos *issues* é que se faz a correção de bugs e agendamento + de tarefas. Os usuários criam *issues* para notificar um bug encontrado de forma que ele possa ser rapidamente corrigido. Criar *issues* também serve como ferramenta de admistração de tarefas nas quais os *issues* descrevem algo a ser feito e por quem. @@ -86,9 +97,9 @@ principais recursos disponíveis, tem-se: prazo para conclusão, por exemplo. * *Pull request* ou *merge request* (MR): é uma requisição de fusão. Os membros da equipe fazem suas contribuições em ramos de - desenvolvimento e ao concluir pedem um MR pela interface. O + desenvolvimento e ao concluir, pedem um MR pela interface. O responsável por avaliar o MR pode ver os *diffs* nos arquivos e - fazer o merge direto pela interfaçe, de dentro do serviço sem + fazer o merge direto pela interface, de dentro do serviço sem precisar baixar o ramo, aplicar o merge e subí-lo. * *Fork*: é uma forma de se fazer uma cópia do projeto de alguém para livremente experimentar modificações sem afetar o projeto @@ -100,8 +111,8 @@ principais recursos disponíveis, tem-se: De acordo com [Klint Finley], *fork* e MR são o que tornam o GitHub tão poderoso. Quando o mantenedor recebe um MR ele pode ver o perfil do -contribuidor onde estão listados todos os projetos no qual este deu -contribuição. Ao aceitar o MR, é acrescentado mais uma colaboração a +contribuidor onde estão listados todos os projetos no qual este +contribuiu. Ao aceitar o MR, é acrescentado mais uma colaboração a reputação do colaborador. Esse mecanísmo, então, beneficia as duas partes. @@ -118,8 +129,8 @@ ver as modificações no código (*diffs*) comaprando *commits* e O GitHub não hospeda apenas código fonte mas sim todo e qualquer arquivo que você tenha sob versionamento. É possível hospedar dados, por exemplo, em formato texto (csv), e disponibilizá-los por meio da URL -para download ou leitura direta. Para nós que somos usuários de R, essa -é uma característica que permite não só disponibilizar dados, mas também +para download ou leitura direta. Para usuários de R, essa é uma +característica que permite não apenas disponibilizar dados, mas também coleções de funções que podem ser carregadas com um `source()`. Com o plano *free* do GitHub, você pode ter inúmeros repositórios @@ -129,8 +140,8 @@ ter repositórios privados, o plano mais básico custa U$ 7 e dá direito a 5 repositórios. Existem outros planos individuais, e também planos organizacionais, para todos os tamanhos de projeto e equipe. Além dessas formas, pode-se ter o GitHub em um servidor próprio, o -[GitHub Interprise], que tem vantagens além das já mencionadas, no -entanto, tal como qualquer plano privado, tem seu custo. +[GitHub Interprise], que tem suas vantagens além das já mencionadas, e +terá seu custo como qualquer plano privado. É uma fonte de conhecimento onde você encontra *scripts* nas mais diferentes linguagens de programação. Você pode livremente estudar o @@ -143,29 +154,32 @@ JSON, SQL, XML, csv) e aplica os realces (highlights) que facilitam a leitura do código. O GitHub é o serviço web para Git mais popular quanto ao número de -projetos hospedados. No entanto, existem serviços com as mesmas e até -com funcionalidades que o GiHub não oferece no plano básico. O GitLab e -o Bitbucket estão entre os 5 mais populares e permitem, por exemplo, ter -alguns repositórios privados com a conta *free*. +projetos hospedados. No entanto, existem serviços com as mesmas +funcionalidades e até com outras que o GiHub não oferece no plano básico. +O GitLab e o Bitbucket estão entre os 5 mais populares e permitem, +por exemplo, ter alguns repositórios privados com a conta *free*. ## GitLab ## - - -FIGURA O guaxinim (*raccoon* em inglês) é o macote do GitLab. +\begin{wrapfigure}{r}{0.4\textwidth} + \begin{center} + \includegraphics[width=5cm]{./images/gitlab-raccoon.jpg} + \end{center} + \caption{O guaxinim (*raccoon* em inglês) é o macote do GitLab.} +\end{wrapfigure} Assim como o GitHub, o [GitLab] é um serviço Web para repositórios Git. O GitLab é um projeto *open source* desenvolvido em Ruby que deu -início em 2011 pelo Ucrâniano Dmitriy Zaporozhets. Em 2013, a Companhia +início em 2011 pelo ucrâniano Dmitriy Zaporozhets. Em 2013, a Companhia GitLab tinha 11 membros e mais de 10 mil organizações. -O GitLab, além de ser um serviço gratuíto (com planos extras) +O GitLab, além de ser um serviço gratuito (com planos extras) colaboração, é também um programa que você pode instalar em servidor local para ter seus repositórios na intraweb, se for o caso. Como serviço web, o GitLab oferece basicamente todos os recursos do -GitHub e do BitBucket [^1]. No entanto, com uma conta gratuíta no -<http://gitlab.com> você pode ter, além dos repositórios públicos e +GitHub e do BitBucket [^1]. No entanto, com uma conta gratuita no +<http://gitlab.com> você pode ter, os repositórios públicos e colaboradores, ilimitados repositórios privados sem pagar por nada. Isso faz do GitLab.com o lugar certo para pequenas equipes com pouco recurso ou que desenvolvem trabalhos sem fins lucrativos, como é o caso de @@ -175,11 +189,11 @@ Atualmente existem mais de 69 mil projetos públicos e 5840 grupos abertos no GitLab.com (https://gitlab.com/explore) A versão paga do GitLab, a *Enterprise Edition* (EE), tem um preço -muitas vezes menor que a equivalente do GitHub. +menor que a equivalente do GitHub. -A versão gratuíta do GitLab para servidores, a *Community Edition* (CE), -pode ser instalada em servidores Linux, Windows, máquinas vituais e -servidores na núvem, além de outras opções. Os serviços +A versão gratuita do GitLab para servidores, a *Community Edition* (CE), +pode ser instalada em servidores Linux, Windows, máquinas virtuais e +servidores na nuvem, além de outras opções. Os serviços <https://gitlab.c3sl.ufpr.br/explore> e <http://git.leg.ufpr.br/explore> são o GitLab CE para servidores rodando no C3SL (Centro de Computação Científica e Software Livre) e LEG (Laboratório de Estatística e @@ -187,11 +201,11 @@ Geoinformação). Estes serviços dão suporte à colaboração em código dentro dos departamentos de Informática e Estatística para alunos e professores (C3SL) e para a equipe e colaboradores do LEG (LEG). -Em termos finaceiros, vale mais a pena pagar por um servidor na núvem da +Em termos finaceiros, vale mais a pena pagar por um servidor na nuvem da [Digital Ocean] com o GitLab CE (U$ 5/mês) do que ter uma conta para -repositórios privados no GitHub (U$ 7/mes por 5 repositórios +repositórios privados no GitHub (U$ 7/mês) por 5 repositórios privados). No entanto, conforme já mencionamos, pequenas equipes podem -ter repositórios privados na conta gratuíta do GitLab.com. +ter repositórios privados na conta gratuita do GitLab.com. Além das características essenciais ou comuns aos demais serviços, como *issues*, *fork*, *merge requests*, *wiki* e *snippets*, o @@ -206,7 +220,7 @@ adição de *web hooks*. # Criar um perfil # -Criar uma conta no Github é tão simples como uma conta de email ou de +Criar uma conta no Github é tão simples como uma conta de email ou numa rede social. Acesse o endereço <https://github.com/join> para preencher seus dados pessoais e escolher um plano. Nenhum dos planos tem limitação quanto ao número de repositórios ou colaboradores. O que muda é a @@ -219,7 +233,7 @@ Ao preencher o formulário de criação de conta, você receberá um email com uma ulr de ativação. Se optar por planos pagos, terá informar número do cartão de crédito para que seja feito o pagamento mensalmente. -Para criar uma conta gratuíta no GitLab, acesse +Para criar uma conta gratuita no GitLab, acesse <https://gitlab.com/users/sign_in>. Os serviços GitLab que usamos são instalações em servidoras próprias (do C3SL e do LEG), no entanto, a interface do usuário é a mesma, com excessão de alguns privilégios @@ -266,10 +280,14 @@ chave. Use, por exemplo, `laptop` ou `trabalho` para facilitar o reconhecimento. É comum trabalhar-se com mais de um máquina, como uma em casa e outra no trabalho. - - -FIGURA XXX: *Printscreen* da página de configurações pessoais do -GitHub. No menu `SSH Keys` pode-se ver e adicionar chaves públicas. +\begin{figure} + \begin{center} + \includegraphics{./images/github_sshkeys.png} + \end{center} + \caption{\textit{Printscreen} da página de configurações pessoais do + GitHub. No menu \texttt{SSH Keys} pode-se ver e adicionar chaves + públicas.} +\end{figure} Para testar a comunição entre o GitHub e a sua máquina, execute: ```{r, engine="bash", eval=FALSE} @@ -284,6 +302,7 @@ No GitLab, o cadastro de chaves públicas é um processo semelhante. Uma vez autenticado, acesse <https://gitlab.c3sl.ufpr.br/profile/keys> para adicionar chaves públicas. Para testar a comunição entre o GitHub e a sua máquina, execute: + ```{r, engine="bash", eval=FALSE} ## Testa comunição. Retorna um "Welcome!" em caso positivo. ssh -T git@gitlab.c3sl.ufpr.br @@ -312,23 +331,25 @@ descrição à ele (Figura XXX). Na etapa seguinte, defina o nível de visibilidade: público ou privado. Lembre-se que os planos *free* só permitem repositórios públicos. - - -FIGURA XXX: Janela para a criação de um novo repositório no GitHub. +\begin{figure} + \begin{center} + \includegraphics{./images/github_new_repo.png} + \end{center} + \caption{Janela para a criação de um novo repositório no GitHub.} +\end{figure} Para criar o projeto dentro de uma Organização, selecione a Organização -na *drop list* que fica no no campo Owner, a esquerda do campo para o +na *drop list* que fica no campo Owner, a esquerda do campo para o nome do repositório. Você pode inicilizar o repositório com um arquivo `README.md`, o que é altamente recomendado. Como já mencionamos, esse arquivo é a capa do seu -repositório e serve para documentar o seu objetivo, formas de -colaboração, colaboradores, formas de instalação do software, caso seja -um. +repositório e serve para documentar o seu objetivo, formas de colaboração, colaboradores, formas de instalação do software, caso seja um informativo +do projeto. Você pode editar o arquivo `README.md` (ou qualquer outro) no GitHub. As moficações que fizer devem ser *commitadas* para serem salvas. O arquivo -de `README.md`, que é linguagem de marcação MarkDown, é automaticamente +`README.md`, que é linguagem de marcação MarkDown, é automaticamente renderizado pelo GitHub fazendo com que urls sejam clicáveis e códigos estejam em ambientes de fonto monoespaço, além de ter títulos com tamanho de fonte apropriado e as demais renderizações. @@ -344,7 +365,7 @@ git clone git@github.com:fulano/ola-mundo.git ``` Pode-se clonar repositórios pelo protocolo `http` (*Hypertext Transfer -Protocol*) também. Em geral, para clonar repositórios de outros usuários +Protocol*). Em geral, para clonar repositórios de outros usuários e fazer testes, usa-se `http`. Embora você possa usar `http` nos seus repositórios, prefira o *SSH*. Com `http`, o endereço para a ser: @@ -378,23 +399,30 @@ git push -u origin master ``` O seu projeto é configurado em -<https://github.com/walmes/emacs/settings/>. Para renomear, deletar ou -trasferir o projeto para outro usuário ou organização, vá em +<https://github.com/walmes/emacs/settings/>. Para renomear, deletar ou +transferir o projeto para outro usuário ou organização, vá em *Options*. Em *Collaborators* você administra os colaboradores do projeto. Para genrenciar os ramos de trabalho, como proteger ou remover ramos, vá em *Branches*. O uso de de serviços web é configurado no *Webhooks & services*. O *Deploy keys* permite adicionar chaves públicas. - +\begin{figure} + \begin{center} + \includegraphics{./images/github_repo_home.png} + \end{center} + \caption{\textit{Home} de um repositório no GitHub.} + \label{github_repo_home} +\end{figure} -Vamos considerar um repositório de bastante atividade para conhecermos +Vamos considerar um repositório com várias atividades para conhecermos um pouco mais dos recursos do GitHub. O repositório <https://github.com/yihui/knitr> é o sítio de desenvolvimento do pacote `knitr` do R, o principal pacote para a geração de relatórios dinâmicos. Nesse repositório tem-se acesso aos fontes. -Na figura XXX, logo abaixo do título, tem-se quatro quantificadores: +Na figura \ref{github_repo_home}, logo abaixo do título, tem-se quatro +quantificadores: * *commits*: ao clinar neste tem-se o histórico de *commits* com autor, mensagem e sha1. É possível comparar estados dos arquivos @@ -402,7 +430,7 @@ Na figura XXX, logo abaixo do título, tem-se quatro quantificadores: * *branches*: este lista os *branches* do projeto, permite comparar ramos. * *releases*: documenta as modificações de uma versão para outra e - lista os *commits* que tem *tags*. Essa é uma fonte importate. + lista os *commits* que tem *tags*. Essa é uma fonte importante. * *contributors*: dá um resumo das atividades dos colaboradores do projeto. Na aba *members* tem-se uma lista de todos os usuários que fizeram o *fork* do seu projeto. Falaremos de *fork* adiante. @@ -424,7 +452,7 @@ No menu da direita existem links para acessos a mais coisas: mescla. Nesta página pode submeter uma requisição e navegar nas existentes. * wiki: na Wiki de um repositório normalmente é feita uma documentação - mais detalhada do projeto. Páginas Wiki de um repositório são também + mais detalhada do projeto. Páginas Wiki de um repositório também são repositórios Git, portanto, versionáveis. * pulse: dá um resumo sobre s quantidade issues presentes, fechados e abertos bem como para requisções de mescla. Mostra também um resumo @@ -434,7 +462,7 @@ No menu da direita existem links para acessos a mais coisas: maior colaboração, etc. Existem ainda mais coisas sobre o GitHub que não podemos deixar de -comentar que são os recursos disníveis para colaboração. Nas sessões à +comentar que são os recursos disponíveis para colaboração. Nas sessões à frente, trataremos do recurso de *fork*, *issue* e requisições de mescla. Antes, no entanto, vamos conhecer um pouco GitLab, um serviço web para projetos Git que pode ser instalado no seu servidor. @@ -442,29 +470,29 @@ web para projetos Git que pode ser instalado no seu servidor. O GitLab é o serviço que nós do PET usamos para colaboração em nossos projetos. Além disso, é o que os alunos usam para fazerem seus trabalhos e desenvolverem o TCC. O uso do Git como ferramenta de trabalho passou -ser estimulado nesse semestre (2015/2). +ser estimulado no segundo semestre de 2015. **GitLab** Basicamente, o GitLab tem os mesmos recursos, só estão organizados de forma diferente. -O GitLab concentra os acessos à outras páginas em um meno do lado +O GitLab concentra os acessos à outras páginas em um menu do lado esquerdo. Do lado direito pode haver informações extras. O botão para -criar um novo repositório fica no canto superior direit. Ao lado deste +criar um novo repositório fica no canto superior direito. Ao lado deste tem botões para ir para página de configurações, sair, ajuda e explorar o GitLab. No menu da direita tem-se acesso aos projetos do usuário, ao projetos -favoritos e aos grupos que parcipa. As extradas *Milestones*, *Issues* e +favoritos e aos grupos que participa. As extras, *Milestones*, *Issues* e *Merge request* reúnem as informações sobre todos os projetos do qual o usuário participa. -Assim como acontece com outros serviços web, na página inical do projeto +Assim como acontece com outros serviços web, na página inicial do projeto é exibido o arquivo de capa, o `README.md`. Centralizado na página encontra-se o endereço para clonar o repositório por SSH ou HTTPS. No -menu da direita estão as principais informações sobre o -projeto. *Project* é a página inicial; *Activity* e *Commits* listam a +menu da direita estão as principais informações sobre o projeto. +*Project* é a página inicial; *Activity* e *Commits* listam a atividade (predominantemente *commits*); *Files* apresenta diretórios e arquivos com opção de mudar o ramo. *Network* o estado de desenvolvimento dos ramos do projeto com uma lista de todos os @@ -476,7 +504,7 @@ requisições de mescla; *Members* faz a gestão da equipe de trabalho como adição e redefinição dos níveis de acesso; *Labels* são usados para classificar os *issues* - é comum usar *bug*, *fix*, *review*. *Wiki* vai para a página Wiki do repositório, útil para divulgação e -documentação; Finalmente, em *Settings* são feitas as configurações +documentação. Finalmente, em *Settings* são feitas as configurações gerais do projeto como definição de nome, descrição, nível de visibilidade e adição e *Web Hooks*. Nessa mesma página pode-se renomear, transferir ou remover o projeto. @@ -487,9 +515,232 @@ Científica e Software Livre - da UFPR. # Fluxo de trabalho # -<https://www.atlassian.com/git/> +TODO Deixar os chunks dessa sessão reproduzíveis! TODO + +O fluxo de trabalho de um projeto Git local e usando um servidor remoto +já foram apresentados. O fluxo com um repositório Git mantido em um +serviço, como o GitHub ou Gitlab, não muda muito. A maior diferença não +é sobre o uso de novas instruções Git mas sim a adoção de uma estratégia +de trabalho (*workflow*) baseada nos recursos desses serviços, como as +*milestones* e *issues*. Esse modelos de trabalho seráo descritos em um +capítulo à frente. + +Em termos de comandos, acrescenta-se aqueles necessários para se +comunicar com um repositório remoto. Alguns desses comandos, senão +todos, já foram apresentados no capítulo anterior a esse. + +Ao considerar um seviço web, você pode começar um repositório novo de +duas formas: localmente ou pelo serviço. + +Pelo serviço, qualquer que seja, crie um novo repositório. GitHub e +GitLab dão instruções resumidas de como proceder logo que você cria um +novo repositório, inclusive, incluem opções como criar um repositório +com arquivo de `README`. Assim que criar, seu repositório terá um +endereço (ssh e http). Na sessão anterior, **Gerenciar repositórios**, +descremos o processo de criar e *clonar* o repositório e também de criar +local e adicionar um endeço do `origin`. + +Localmente o repositório segue o ciclo normal de desenvolvimento que +minimamente contém das intruções `git add` e `git commit`. Os fluxos de +trabalho em geral preconizam o desenvolvimento a partir de *branches* de +demanda cujo conteúdo será incorporado aos ramos permanentes (`master`, +`devel`) quando forem concluídos. Abaixo ilustramos a sequência de criar +um ramo, desenvolvê-lo e por fim subir o seu conteúdo para o repositório +remoto, que nesse caso é mantido em um servido web. + +```{r, engine="bash", eval=FALSE} +## Cria um ramo chamado issue#10. +git branch issue#10 + +## Muda do ramo atual para o recém criado. +git checkout issue#10 + +## Segue a rotina. +git add <arquivos> +git commit -m <mensagem> + +## Sempre que quiser, suba o trabalho. +git push origin issue#10 +``` + +Nessa rotina, consideramos `issue#10` um *issue* criado na interface +para atender uma demanda, como por exemplo, corrigir um *bug*. Da mesma +forma que o ramo default do Git é o `master`, o repositório remoto é por +default chamado de `origin`, então subimos o conteúdo desse ramo para o +servidor que mantém o repositório sob o serviço web. + +Não há limites para o número de ramos. Ramos podem ser locais, remotos +ou ambos. Quando você cria um ramo, como nos comandos acima, ele é um +ramo remoto. Quando você sobre esse ramo, ele passa ter sua parte remota +também. E quando você clona um repositório, você traz todos os ramos que +ele possui, que são ramos remotos. Ao escolher um ramos desse para +trabalhar, ele passar ser também um ramo local. Abaixo formas de listas +os ramos do projeto. + +```{r, engine="bash", eval=FALSE} +## Lista os ramos locais. +git branch -l + +## Lista os remostos. +git branch -r + +## Lista todos (all). +git branch -a +``` + +Você pode notar que ramos locais não tem prefixo e que ramos remotos tem +o prefixo `origin/`. Você pode remover um ramo local mas manter sua +parte remota e pode também excluir esse ramo por completo de todo o +sistema, localmente e no servidor, conforme ilustram os códigos abaixo. + +```{r, engine="bash", eval=FALSE} +## Remove um ramo local (não mais útil). +git branch -d issue#10 + +## Remove sua cópia remota (não mais útil também). +git branch -dr origin/issue#10 + +## Remove um ramo remoto na origem (duas formas). +git push origin --delete issue#10 +git push origin :issue#10 +``` + +Até aqui, nos referimos ao repositório remoto como `origin` que é o nome +default. No entanto, um projeto Git pode ter mais de um repositório +remoto. Considere o caso simples de um repositório para arquivos de uma +disciplina. Esse repositório contém tanto lista de exercícios para os +alunos como também as provas com as soluções. Para não entregar as +provas de bandeija, o diretório de provas existe no ramo `secret` e é +enviado somente para um repositório privado chamado `provas`. Já o +conteúdo restante (lista de exercícios, notas de aula, scripts) +disponibilizado para os alunos fica no ramo `master`, mantido em um +repositório aberto chamado de `origin`. + +Dois repositórios remotos tem endereços distintos pois são projetos +distintos no serviço web. Você pode ter a parte pública do projeto +(`origin`) no GitHub e a parte privada, as provas (`secret`) no GitLab +de forma privada. Abaixo tem-se uma série de comandos para listar, +renomear, remover e adicionar endereços para remotos. + +```{r, engine="bash", eval=FALSE} +## Lista os remotos. +git remote -v + +## Renomeia para um nome melhor +git remote rename origin profs + +## Remove. +git remote rm profs + +## Adiciona um endereço de remoto (origin) +git remote add origin <url> +git remote add profs <url> -clone, add, commit, branch, push, fetch, pull. +## Adiciona/remove URLs ao origin. +git remote set-url origin --add <url> +git remote set-url origin --delete <url> +``` + +Quando você trabalha em colaboração ou em mais de uma máquina, vai +sempre precisar atualizar os repositórios com o conteúdo existente no +remoto. Existem duas instruções Git para isso: `git fetch` e `git pull`. + +As duas traduções mais frequentes do verbo *to fetch* são buscar e +trazer. A documentação oficial do comando `git fetch` +(<https://git-scm.com/docs/git-fetch>) indica que esse comando serve +para trazer objetos e referências dos repositórios remotos. Abaixo o +comando padrão considerando um remoto de nome `origin` e algumas +variações. + +```{r, engine="bash", eval=FALSE} +## Traz todos os ramos do remoto origin. +git fetch origin + +## Traz só do ramo devel. +git fetch origin devel + +## Traz de todos os remotos: origin, profs. +git fetch --all +``` + +O comando *fetch* traz os ramos e atualiza a parte remota, por exemplo, +o `origin/devel`. O ramo local `devel` não tem seu conteúdo modificado +após o `fetch`. Para transferir o conteúdo o `origin/devel` para o +`devel` tem-se que usar o `git merge`. No entanto, sempre que haver +necessidade, antes o *merge* pode-se verificar as diferenças que existem +entre local e remoto, principalmente quando esse remoto traz +contribuições de algum colaborador. Os comandos abaixos exibem as +diferenças entre os ramos e aplicam o merge entre eles. + +```{r, engine="bash", eval=FALSE} +## Muda para o ramo devel. +git checkout devel + +## Mostra as diferenças entre devel local e remoto no terminal. +git diff devel origin/devel + +## Faz o merge do devel remoto no devel local. +git merge origin/devel +``` + +Como você já sabe, os merges podem apresentar conflito. Já vimos como +fazer isso e no capítulo a seguir apresentaremos interfaces gráficas +para trabalhar com o Git e dentre elas algumas são para auxiliar a +resolvê-los. + +Em resumo, para passar o conteúdo de um ramo remoto para um local temos +que fazer `git fetch` e em seguida `git merge`. O comando `git pull` são +esses dois em um. A documentação do `git pull` +(<https://git-scm.com/docs/git-pull>) dá uma descrição detalhada do seu +uso enquanto que os exemplos abaixo ilustram o uso mais simples +possível. + +```{r, engine="bash", eval=FALSE} +## Traz e junta todos os ramos do remoto origin para os locais. +git pull origin + +## Traz e justa só do ramo devel. +git pull origin devel +``` + +Por fim, para subir o trabalho feito em um ramo, usa-se a intrução `git +push`. Enviar o seu trabalho com frequência é a melhor forma de ter +*backups*, exibir e disponibilizar suas contribuições para os seus +colaboradores. A documentação do `git push` é rica em variações +(<https://git-scm.com/docs/git-push>) mas a maneira mais simples de +usá-lo é para subir um ramo para o repositório remoto. + +```{r, engine="bash", eval=FALSE} +## Sobe o ramo issue#10 para o repositório remoto origin. +git push origin issue#10 + +## Sobe todos os ramos. +git push --all origin +``` + +Quando você sobe pela primeira vez um ramo local, a sua parte remota é +criada. Assim, a instrução que colocamos acima criou um ramo remoto +chamado `origin/issue#10`. Essa é a forma mais natural, e até +despercebida, de criar ... + +Outras maneiras existem. Abaixo fazemos a criação do remoto a partir do +local sem ser usando o *push*. Esses comandos precisam ser usados uma +vez apenas. + +```{r, engine="bash", eval=FALSE} +## Duas formas de conectar o local e remoto. +git branch --set-upstream issue#10 origin/issue#10 +git branch -u issue#10 origin/issue#10 + +## Cria o ramo issue#11 a partir e vinculado ao devel remoto. +git checkout -b issue#11 origin/devel + +## Cria ramo local issue#12 a partir do remoto com vínculo. +git checkout --track origin/issue#12 + +## Mostra as ligações entre pares de ramos: locais e remotos. +git branch -vv +``` # Macanísmos de colaboração # @@ -527,7 +778,7 @@ tarefas. Combinado com as *milestones*, cada membro cria um *issue* correspondente ao que vai fazer no projeto no período de uma semana. Com isso, todos os demais membros são notificados de que alguém já vai trabalhar na tarefa A do projeto, eliminando foco duplicado. O *issue* é -parte do fluxo de trabalho do PET Estatística que será descrito em outro +parte do fluxo de trabalho do PET-Estatística que será descrito em outro capítulo. As *milestones* são uma espécie de coleção de *issues* que tenham algo @@ -551,7 +802,7 @@ serviços web até tem formas de fazer *hiperlinks* facilmente para os A palavra *fork*, como substantivo, representa forquilha, bifurcação. Como verbo, representa bifurcar. Esse recurso está presente -nas interfaces web para permitir que usuários facam cópias livres de +nas interfaces web para permitir que usuários façam cópias livres de projetos de outras pessoas. Como essa cópia é do projeto em determinado instante, há grande chance de divergência entre cópia e original a partir desse instante, por isso é apropriado a palavra bifurcamento. @@ -611,7 +862,7 @@ para incorporar algo ao projeto e, portanto, não são permanentes - uma vez incorporados, são removidos. Nos esquemas de trabalho, os membros são instruídos a fazerem o -desenvolvimentos nos ramos de demandae jamais nos ramos permanentes. Ao +desenvolvimentos nos ramos de demanda e jamais nos ramos permanentes. Ao concluir essa unidade de trabalho, esse *branch* é enviado para o servidor com um `push` @@ -621,14 +872,14 @@ git push origin issue#33 ``` Na interface web, o membro faz um *merge request* desse ramo para um -ramo permamente, que em projetos simples é o *master* mas em projetos +ramo permamente, no qual em projetos simples é o *master* mas em projetos maiores é usualmente o *devel*. Em ambos os serviços, o *merge resquest* leva para um página na qual você escolhe que ramo de demanda (doador) será incorporado a um ramo permamente (receptor). Ao confirmar os ramos envolvidos, tem-se uma -caixa de texto destinada as informações sobre o que as modificações a -serem incorporadas. Elas servem para justificar, esclarecer e informar o +caixa de texto destinada as informações sobre quais as modificações devem +ser incorporadas. Elas servem para justificar, esclarecer e informar o responsável pelo *merge* sobre a incorporação. Quando o projeto é coletivo e não individual, um membro pode ser indicado como responsável pelo *merge*. @@ -646,11 +897,11 @@ ou 2) incorporar ao *master* do original. Outra opção é incorporar ao para o *master* do original. Essa última é útil quando a quantidade de modificações é maior e portanto, o trabalho vai levar mais tempo. -O próprio serviço Web tem recurso para a apliação do *merge* sem +O próprio serviço Web tem recurso para a aplicação do *merge* sem precisar copiar os ramos envolvidos. Isso facilita bastante o trabalho. Porém, não haver conflito de *merge* não significa que as modificações incorparadas estão funcionais, ou seja, as modificações -feitas precisam ser testadas localmente para verificar de tiveram +feitas precisam ser testadas localmente para verificar surgiram efeito. É possível habilitar o serviço Git para checar se o projeto é executável, em caso de softwares. Esse recurso se chama intergração contínua e veremos na próxima sessão. @@ -664,9 +915,9 @@ que já reconheçe que o *merge* foi feito e fecha a requisição. Recomenda-se que os ramos de demanda sejam removidos após a incorporação nos ramos permanentes. Isso torna o projeto mais claro e concentrado em -ramos definitivos colhedores de desenvolvimento. Pode-se exluir o ramo +ramos definitivos colhedores de desenvolvimento. Pode-se excluir o ramo de demanda incorporado direto pela interface. Por linha de comando -também é possível +também é possível. ```{r, engine="bash", eval=FALSE} ## Deleta o branch issue#33 no servidor (origin). @@ -693,8 +944,359 @@ git tag -a v1.0 -m "Versão 1.0 do software" # Integração contínua # -Permite chegar se o projeto, no caso de softwares, está -funcionando/instalando sem erros. +Quando você está trabalhando em um projeto Git, cada *commit*, cada +*branch*, contém algum desenvolvimento. Solucionar conflitos de *merge* +não é um atarefa complicada, principalmente se forem consideradas as +ferramentas certas para isso, como será visto no próximo capítulo. No +entanto, para cada *commit* tem-se a preocupação: será que o projeto +está funcional? + +Reprodutibilidade é uma questão de fundamental importância em projetos +coletivos ou públicos. Existe a preocupação constante de que seu código +(programa) seja executado (instalado) sem erros nos ambientes dos seus +colaboradores ou usuários. É claro que o desenvolvimento do projeto visa +aperfeiçoá-lo mas o tempo todo estamos sujeitos fazer modificações que +induzem erros e alguém encontra erros não esperados (*bugs*). + +Monitorar erros no projeto em desenvolvimento não é uma tarefa fácil, +principalmente em trabalhos coletivos nos quais cada colaborator tem um +ambiente de trabalho. Em uma situação ideal, alguém teria que testar se +o projeto corre sem erros (código executa, software instala) em uma +máquina cliente (com os requisitos mínimos exigidos), toda vez que um +*commit* fosse feito, já que o *commit* indica que modificações foram +feitas. Então, se correu sem erros, avisar à todos que podem prosseguir, +mas se falhou, informar a equipe, encontrar e resolver a falha. + +Não é raro algo ser bem sucedido no ambiente em que foi desenvolvido e +apresentar falhas na ambiente de outra pessoa. O melhor jeito de +antecipar erros é testar em um ambiente virgem, uma máquina cliente que +contenha apenas os requisitos mínimos necessários ao projeto. + +A Integração Contínua (IC) é a solução desse problema. A ideia é manter +o repositório Git continuamente integrado à um ambiente cliente que faz +verificações no projeto a cada novo *push*. + +Fazer integração contínua no GitHub e GitLab, embora o conceito seja o +mesmo, tem algumas diferenças. Paro o GitHub existem diversos serviços +de IC, é algo terceirizado. Já o GitLab CE têm o serviço próprio de +IC desde a versão 8.0. Apresentaremos cada um deles na sessão seguinte. + +Independe do serviço web, as principais vantagens da IC são: + + 1) Economia de tempo com supervisão de código e procura de falhas; + 2) Verificação em um ambiente virgem sem efeito de variáveis de + ambiente locais; + 3) Verificação em vários ambientes (sistemas operacionais, + arquiteturas, dependências e versões); + 4) Informação coletiva e imediata à equipe da causa de falha na hora + que ela ocorre; + 5) Indicação de sucesso ou não na home do projeto; + 6) Entrega de versões estáveis, documentação e arquivos acessórios com + *continuous deployment*. + 7) Custo computacional reduzido já que é feito em um servidor + dedicado. + 8) Verificação a cada *push* feito. + 9) Status exibido para cada branch e requisição de merge. + 10) Aumenta a visilibidade facilitanto a comunicação e reunião de + esforços. + 12) Menos tempo na correção de bug, que devem ser menores, assim + deixando mais tempo para desenvolver o que interessa. + 13) É barato, até mesmo quando custa algo, porque parar o projeto por + erro pode custar inclusive mais caro. + 14) Reduz os problemas com usuários fora dos colaboradores pois testa + em máquinas virgens. + 15) Facilita para os usuários saberem se a última versão é executável. + 16) Pode automatizar a disponibilização do projeto aos usuários. + +A integração contínua não elinima erros, mas faz com que eles sejam mais +fáceis de identificar e remover. + +Sem a automação, os espaços entre verificações podem ficar longos, +encontrar um bug em tantos commits é mais difícil, encontrar no código é +mais ainda. Pode atrasar a entrega do projeto e comprometer a receita e +popularidade. Integrações periodicas são mais fáceis e leves. + +O build é automático, faz um self-testing a cada commit. + +O fluxo de trabalho de um repositório com IC é basicamente assim: + + 1) Os desenvolvedores trabalham no projeto em seu workspace + privado/local; + 2) Periodicamente fazem *commits* e *push* para o repositório remoto; + 3) O serviço de IC monitora o repositório toda vez que modificações + ocorrem; + 4) O serviço de IC corre todos os testes de inspeção que foram + configurados (instala dependendencias, executa scripts, + cria/tranfere arquivos, etc); + 5) O serviço de IC disponibiliza produtos da verificação, como + binários de instalação e documentação (no caso de sucesso) ou log + de execussão (no caso de falha); + 6) O serviço de IC assinalá no repositório Git o *status* da + verificação: sucesso/fracasso; + 7) O serviço de IC informa a equipe dos resultados por mensagem de + email ou webhooks, como o Slack; + 8) A equipe toma das providências cabiveis na primeira oportunidade, + como corrigir a falha ou anunciar o sucesso; + 9) O serviço aguarda por mais modificações; + +## GitHub ## + +http://www.codeaffine.com/2014/09/01/travis-continuous-integration-for-github-projects/ + +Embora exista uma lista grande de serviços de integração contínua +disponíveis para repositórios GitHub, um dos mais usados é o +[Travis CI]. Travis CI (*continuous integration*) é um serviço free e +open source destinado à integração contínua para projeto **públicos** no +GitHub. + +Para vincular um projeto no GitHub com IC no Travis CI, você precisa +logar no <https://travis-ci.org/> com a sua conta do GitHub. Assim que +você logar, dê autorização para acessar seus repositórios e em uma lista +você deve marcar os que usarão o serviço. A próxima etapa é criar um +arquivo `.travis.yml` na raíz do seu repositório Git. Esse arquivo +oculto especifica todas as instruções que devem ser feitas a fim de +verificar seu repositório. Se seu repositório é um pacote R, por +exemplo, esse arquivo vai ter instruções de instalação do pacote. + +Cada projeto, cada linguagem, têm uma forma particular de ser +testada. Para pacotes R, o Travis CI tem uma documentação de orientação: +<https://docs.travis-ci.com/user/languages/r/>. Além disso, uma boa +prática em ver exemplos em uso, como o `.travis.yml` dos pacotes R +`knitr` (<https://github.com/yihui/knitr>) e `devtools` +(<https://github.com/hadley/devtools>) que estão na lista dos mais +utilizados. + +Para todas as liguagens e objetivos têm-se exemplos de arquivos +`.trevis.yml`. Para o Emacs e biblitecas visite +<https://github.com/rolandwalker/emacs-travis>, +<https://github.com/Malabarba/elisp-bug-hunter> e +<https://github.com/abo-abo/tiny>. Para projetos em `C++` e `phyton`, +assim como o R, o Travis CI tem uma documentação introdutória. Visite +<https://docs.travis-ci.com/user/language-specific/> para ver a lista de +documentações. + +Além do linguagens de programação, é possível testar inclusive a +compilação de um documento Latex: +<http://harshjv.github.io/blog/setup-latex-pdf-build-using-travis-ci/>. + +*branch build flow* +*pull request build flow* + +`after_failure` (information, error report) +`after_success` (deployment, uploads de documentação e versões estáveis) + +exibir build status no README +fazer *webhook* com Slack + +## GitLab ## + +https://about.gitlab.com/gitlab-ci/ +https://about.gitlab.com/2015/02/03/7-reasons-why-you-should-be-using-ci/ + +A Integração Contínua passou fazer parte do GitLab CE na [versão 8.0], +lançada em setembro de 2015. Diferente do GitHub, essa versão do GitLab +tem o IC de forma nativa. Você pode configurar servidores externos para +executarem as verificações ou pode fazê-las no mesmo servidor que roda o +GitLab. + +[Alan Monger] descreve como configurar um servidor Ubuntu no +[Digital Ocean] parar verificar repositórios hospedados no +<https://gitlab.com/>. + +TODO Definir *runner*, *build*, *YAML*. + +Segundo ele, o primeiro passo é acessar <https://gitlab.com/ci/> para +adicionar o projeto à integração contínua. Isso vai gerar um *token* de +registro que será passado para o *runner* que deve estar em uma +máquina. Na sua matéria, Alan Monger descreve como instalar um *Virtual +Private Server* com Ubuntu 14.04 no Digital Ocean. Em seguida instala o +*runner* (`gitlab-ci-multi-runner`), configura e passa o *token*, cria +uma imagem - algo que executa coisas no sistema mas que propositalmente +perdidas no final, o sistema é sempre restaturado ao estado virgem. O +*runner* é então habilitado e por fim o arquivo `.gitlab-ci.yml` é +criado na home do *repositório*. + +As especificação são feitas em um arquivo `.gitlab-ci.yml` na home do +projeto. + +O [GitLab do LEG] tem o CI embutido pois é a versão mais recente do +serviço. Essa servidora é na realidade um *desktop* com Ubuntu Server. É +patrimônio da UFPR de responsabilidade do LEG mas tem uso compartilhado +com o PET Estatística e colaboradores do Laboratório. Desde a +disponibilização do GitLab, em julho de 2015, mantemos artigos, +materiais de ensino (aulas, provas, scripts), tutoriais e materias de +blog em devolvimento colaborativo, além de pacotes R. + +Nessa servidora, criamos um usuário chamado `gitlab-runner` com o qual +fazemos as integrações contínuas. Toda vez que um projeto com o arquivo +`.gitlab-ci.yml` recebe um *push*, as instruções nesse arquivo executam +a IC com o usuário `gitlab-runner`. Tecnicamente podemos correr todo +tipo de comando ou programa disponível no servidor em questão, um Ubuntu +Server 14.04. Até então, os repositórios com IC são só dois: [legTools] +e [mcglm], dois pacotes R. + +### O arquivo `.gitlab-ci.yml` ### + +A documentação oficial sobre como usar o arquivo `.gitlab-ci.yml` +encontra-se em <http://doc.gitlab.com/ce/ci/yaml/README.html>. + +O arquivo `.gitlab-ci.yml` fica na raíz do projeto. Seu conteúdo define +todo o processo de verificação do seu repositório a partir de uma série +de instruções, como execução de comandos diretos ou execução de +scripts. Abaixo tem-se um exemplo simples de `.gitlab-ci.yml`. + +``` +job1: + script: "teste_instalacao.sh" + +job2: + script: + - pwd + - ls -a +``` + +Neste exemplo existem dois *jobs* (tarefas). Cada um deles corre +independente e podem ser executados simultâneamente. O primeiro executa +um *script* shell e o segundo comandos *shell* em uma lista. Porém, tais +arquivos podem ser bem mais complexos, com campos além do `script:`. Os +campos a seguir são todos opcionais: + + * `image`: para especificar uma imagem [*docker*]. O tutorial de + [Alan Monger] considera esse campo. + * `services`: também refere ao *docker*. Tais campos são de uso menos + frequênte, porém existe uma séria de vantagens neles. A documentação + oficial sobre isso encontra-se em + <http://doc.gitlab.com/ce/ci/docker/README.html>. + * `before_script`: define comandos/scripts a serem executados antes + dos principais. São instruções de preparação das quais não se espera + falhas pois não deve depender do projeto. + * `stages`: define a ordem de excecução dos *jobs* que estabalecer uma + cadeia de execução condicional. Jobs de mesma ordem ou do mesmo + estágio são executados paralelamente mas àqueles à frente só são + executados se houver sucesso dos predecessores. + ``` + stages: + - construcao + - teste + - entrega + + job_contrucao: + script: "construcao.sh" + stage: construcao + + job_test: + script: "teste_codigofonte.sh" + script: "teste_documentacao.sh" + stage: teste + + job_entrega: + script: "compacta_transfere.sh" + stage: entrega + ``` + * `variables`: serve para criar variaveis de ambiente que podem ser + usados por todos os comandos e scripts. + * `cache`: indica os diretórios e arquivos que serão mantidos entre os + *jobs* (builds), possivelmente porque são aproveitados futuramente. + +Com excessão dos nomes listados acima, um *job* pode ter qualquer nome, +desde que seja exclusivo. Dentro de um *job* tem-se também uma lista de +campos disponíveis para configurá-lo: + + * `script`: especifica script *shell* ou uma lista de comandos a serem + executados. + * `stage`: já mencionado anteriormente, serve para dar a ordem de + execução dos *jobs*. Vários *jobs* podem ser do mesmo estágio e + nesse caso são executados paralelamente. + * `only` e `except`: servem para restringir a execução do *job*, + incluindo ou excluindo, para uma lista de referências git, como + *branches* ou *tags*. Esse campo permite expressões regulares, úteis + para incluir (excluir) ramos representáveis por *regex*, como são os + ramos de desenvolvimento do nosso workflow, iniciados com *issue*. + ``` + job_test: + script: "teste_codigofonte.sh" + script: "teste_documentacao.sh" + stage: teste + only: + - /^issue.*$/ ## Os que começam com issue + ``` + * `tags`: são usadas para indicar o *runner* da lista de + disponíveis. Na configuração dos *runners* pode-se atribuir *tags* + que servem justamente para esse tipo de pareamento. + * `allow_failure`: indica jobs que mesmo que falhem, não serão + considerados para dar estampa de sucesso ou falha. + * `when`: é um comando que dispara excussões condicionais ao sucesso + do *job* anterior + * `on_failure`: são instruções executadas quando algum o *job* do + estágio anterior falhou. + * `on_success`: são instruções executadas quando todos os *jobs* do + estágio anterior foram bem sucedidos. + * `always`: excutados sempre. + * `cache`: especifica arquivos e diretório mantidos entre um *build* e + outro. + +No caso do pacote LegTools, o arquivo `.gitlab-ci.yml` do repositório +tem o seguinte conteúdo: + +```{r, eval=FALSE, engine="sh"} +job_R: + script: + - echo $HOME + - Rscript -e 'getwd(); .libPaths(); sessionInfo()' + - Rscript -e 'library(devtools); check()' + - Rscript -e 'library(devtools);\ + .libPaths(new = path.expand("~/R-tests/legTools"));\ + install(local = FALSE)' +``` + +Estas são instruções em *shell* que chamam o R com expressões passadas +para `Rscript -e` que executam a instalação do pacote. Na ocorrência da +primeira falha, o processo é logicamente interrompido e os +colaboradoradores podem ver a causa em +<http://git.leg.ufpr.br/leg/legTools/builds>. No caso do *build* correr +sem falhas, tem-se uma estampa de *success*. Essa estampa também vai +aparecer no README.md na página de rosto do projeto, basta para isso +colocar + +``` + +``` + +Caso queira a estampa para outros ramos, é só acrescentá-los. + +### Runners ### + +Em poucas palavras, um *runner* é uma máquina que executa o build por +meio do GitLab CI. Um *runner* pode ser específico de um projeto ou pode +ser um *runner* compartilhado, disponível à todos os projetos. Estes +últimos são úteis à projetos que tem necessidades similares, como todos +àqueles projetos que são pacotes R, por exemplo. Isso facilita a +administação e atualização. Os específicos, por outro lado, atendem +projetos com demandas particulares. + +Apenas usuários com permissões de *admin* podem criar runners +compartilhados. + +Ir em Settings > Services e marcar *active*. Isso vai criar 6 novas +entradas no menu da esquerda + + * *Runners*: contém instruções de como usar um *runner* específicos e + compartilhados. + * *Variables*: define variáveis que são omitidas no *log* do *build*, + útil para passar senhas. + * *Triggers*: servem para ?? + * *CI Web Hooks*: esse *web hook* pode ser usado para criar eventos + quando o build é concluido. + * *CI Settings*: configurações gerais + * *CI Services*: permite integrar o CI com outros serviços, como email + e Slack. + +Para habilitar um *runner*, é necessário instalar o +`gitlab-ci-multi-runner`. O [repositório oficial do *GitLab Runner*] +contém as instruções de instalação e configuração e a documentação +oficial sobre +*runners*\footnote{\url{http://doc.gitlab.com/ce/ci/runners/README.html}} +indica como tirar melhor proveito do recurso. <!---------------------------------------------------------------------- --> @@ -707,3 +1309,12 @@ funcionando/instalando sem erros. [Digital Ocean]: https://www.digitalocean.com/community/tutorials/how-to-use-the-gitlab-one-click-install-image-to-manage-git-repositories [GitLab]: https://about.gitlab.com/ [Macmillan]: http://www.macmillandictionary.com +[TRavis CI]: https://travis-ci.org/ +[versão 8.0]: https://about.gitlab.com/2015/09/22/gitlab-8-0-released/ +[Digital Ocean]: https://www.digitalocean.com/ +[Alan Monger]: http://alanmonger.co.uk/php/continuous/integration/gitlab/ci/docker/2015/08/13/continuous-integration-with-gitlab-ci.html +[GitLab do LEG]: http://git.leg.ufpr.br/ +[legTools]: http://git.leg.ufpr.br/leg/legTools +[mcglm]: http://git.leg.ufpr.br/wbonat/mcglm +[*docker*]: https://www.docker.com/ +[repositório oficial do *GitLab Runner*]: https://gitlab.com/gitlab-org/gitlab-ci-multi-runner diff --git a/plano.md b/plano.md index 8659646b0da3327b5b0a010dfa10be1755b27b66..fa6dd6b25f82f9d8395036d47e835b2125713f53 100644 --- a/plano.md +++ b/plano.md @@ -145,6 +145,31 @@ concluir sobre Sistemas de Controle de Versão, *Cheat Sheet* e uso de Git no RStudio. 6. 2015-12-01: + + TODOS: colocar as figuras em ambiente Latex (`center > figure > + includegraphics + caption`). Controlar o tamanho das figuras para + não ultrapassarem as margens nem ficarem pequenas demais. Colocar + os links com âncoras (os não presentes no texto, como + `[google](http://www.google.com)`) em + `google\footnote{\url{http://www.google.com}}` para aparecer no + rodapé das páginas. Usar seções numeradas. Considerar como exemplo + o YAML do arquivo `cap05.Rmd`. + + Walmes: Fazer revisão completa do capítulo 5 até sexta para o + Alcides. Disponibilizar o template para cada um fazer os ajustes + finais no seu capítulo. + + Alessandra: Corrigir o capítulo 1. + + Daniel: Concluir o capítulo de RStudio e o *Cheat Sheet* + (**pendencias**). Revisar o dicionário de termos e exemplos de + rotinas. + + Gabriel: Fazer revisão e acréscimos no capítulo 3 e disponibilizar + até sexta para o Eduardo. + + Jhenifer: Corrigir o capítulo do Eduardo que será disponibilizado + na sexta. + + Ângela: Corrigir o capítulo de RStudio disponibilizado na sexta. + + Eduardo: Revisar o capítulo 6 até sexta para a Jhenifer. Corrigir o + capítulo 3 depois de sexta. + + Alcides: Corrigir o capítulo 5 disponibilizado na sexta. + + Quem se interessar: Pensar numa capa para a apostila, fazer esboço, + *brainstorm*. 7. 2015-12-08: 8. 2015-12-15: Apostila Git concluída! diff --git a/template.tex b/template.tex new file mode 100644 index 0000000000000000000000000000000000000000..fcfc62bb751128e19d7d2ef77dba4560cc173427 --- /dev/null +++ b/template.tex @@ -0,0 +1,276 @@ +% \documentclass[ +% $if(fontsize)$$fontsize$, +% $endif$$if(lang)$$lang$, +% $endif$$if(papersize)$$papersize$, +% $endif$$for(classoption)$$classoption$$sep$, +% $endfor$]{$documentclass$} + +\documentclass[ + a5paper, + pagesize, + 9pt, + % bibtotoc, + pointlessnumbers, + normalheadings, + % DIV=9, + twoside=false +]{book} + +\usepackage[brazil]{babel} +\usepackage[utf8]{inputenc} +\usepackage[T1]{fontenc} + +\usepackage[sc]{mathpazo} +% \usepackage{palatino} +% \linespread{1.05} +\usepackage[scaled=0.85]{beramono} + +%----------------------------------------------------------------------- + +\usepackage{amssymb, amsmath} +\usepackage{ifxetex, ifluatex} + +\usepackage{fixltx2e} % provides \textsubscript +\ifnum 0\ifxetex 1\fi\ifluatex 1\fi=0 % if pdftex + \usepackage[T1]{fontenc} + \usepackage[utf8]{inputenc} +$if(euro)$ + \usepackage{eurosym} +$endif$ +\else % if luatex or xelatex + \ifxetex + \usepackage{mathspec} + \usepackage{xltxtra,xunicode} + \else + \usepackage{fontspec} + \fi + \defaultfontfeatures{Mapping=tex-text,Scale=MatchLowercase} + \newcommand{\euro}{€} +$if(mainfont)$ + \setmainfont{$mainfont$} +$endif$ +$if(sansfont)$ + \setsansfont{$sansfont$} +$endif$ +$if(monofont)$ + \setmonofont[Mapping=tex-ansi]{$monofont$} +$endif$ +$if(mathfont)$ + \setmathfont(Digits,Latin,Greek){$mathfont$} +$endif$ +\fi + +% use upquote if available, for straight quotes in verbatim environments +\IfFileExists{upquote.sty}{\usepackage{upquote}}{} +% use microtype if available +\IfFileExists{microtype.sty}{% +\usepackage{microtype} +\UseMicrotypeSet[protrusion]{basicmath} % disable protrusion for tt fonts +}{} +$if(geometry)$ +\usepackage[$for(geometry)$$geometry$$sep$,$endfor$]{geometry} +$endif$ + +$if(lang)$ +\ifxetex + \usepackage{polyglossia} + \setmainlanguage{$mainlang$} +\else + \usepackage[shorthands=off,$lang$]{babel} +\fi +$endif$ + +$if(natbib)$ +\usepackage{natbib} +\bibliographystyle{$if(biblio-style)$$biblio-style$$else$plainnat$endif$} +$endif$ + +$if(biblatex)$ +\usepackage{biblatex} +$if(biblio-files)$ +\bibliography{$biblio-files$} +$endif$ +$endif$ + +$if(listings)$ +\usepackage{listings} +$endif$ + +$if(lhs)$ +\lstnewenvironment{code}{\lstset{language=Haskell,basicstyle=\small\ttfamily}}{} +$endif$ + +$if(highlighting-macros)$ +$highlighting-macros$ +$endif$ + +$if(verbatim-in-note)$ +\usepackage{fancyvrb} +\VerbatimFootnotes +$endif$ + +$if(tables)$ +\usepackage{longtable,booktabs} +$endif$ + +$if(graphics)$ +\usepackage{graphicx} +\makeatletter +\def\maxwidth{\ifdim\Gin@nat@width>\linewidth\linewidth\else\Gin@nat@width\fi} +\def\maxheight{\ifdim\Gin@nat@height>\textheight\textheight\else\Gin@nat@height\fi} +\makeatother +% Scale images if necessary, so that they will not overflow the page +% margins by default, and it is still possible to overwrite the defaults +% using explicit options in \includegraphics[width, height, ...]{} +\setkeys{Gin}{width=\maxwidth,height=\maxheight,keepaspectratio} +$endif$ + +\ifxetex + \usepackage[setpagesize=false, % page size defined by xetex + unicode=false, % unicode breaks when used with xetex + xetex]{hyperref} +\else + \usepackage[unicode=true]{hyperref} +\fi + +\hypersetup{breaklinks=true, + bookmarks=true, + pdfauthor={$author-meta$}, + pdftitle={$title-meta$}, + colorlinks=true, + citecolor=$if(citecolor)$$citecolor$$else$blue$endif$, + urlcolor=$if(urlcolor)$$urlcolor$$else$blue$endif$, + linkcolor=$if(linkcolor)$$linkcolor$$else$magenta$endif$, + pdfborder={0 0 0}} +\urlstyle{same} % don't use monospace font for urls + +$if(links-as-notes)$ +% Make links footnotes instead of hotlinks: +\renewcommand{\href}[2]{#2\footnote{\url{#1}}} +$endif$ + +$if(strikeout)$ +\usepackage[normalem]{ulem} +% avoid problems with \sout in headers with hyperref: +\pdfstringdefDisableCommands{\renewcommand{\sout}{}} +$endif$ + +\setlength{\parindent}{0pt} +\setlength{\parskip}{6pt plus 2pt minus 1pt} +\setlength{\emergencystretch}{3em} % prevent overfull lines + +$if(numbersections)$ +\setcounter{secnumdepth}{5} +$else$ +\setcounter{secnumdepth}{0} +$endif$ + +$if(verbatim-in-note)$ +\VerbatimFootnotes % allows verbatim text in footnotes +$endif$ + +%%% Use protect on footnotes to avoid problems with footnotes in titles +\let\rmarkdownfootnote\footnote% +\def\footnote{\protect\rmarkdownfootnote} + +%%% Change title format to be more compact +\usepackage{titling} + +% Create subtitle command for use in maketitle +\newcommand{\subtitle}[1]{ + \posttitle{ + \begin{center}\large#1\end{center} + } +} + +\setlength{\droptitle}{-2em} + +$if(title)$ + \title{$title$} + \pretitle{\vspace{\droptitle}\centering\huge} + \posttitle{\par} +$else$ + \title{} + \pretitle{\vspace{\droptitle}} + \posttitle{} +$endif$ + +$if(subtitle)$ +\subtitle{$subtitle$} +$endif$ +$if(author)$ + \author{$for(author)$$author$$sep$ \\ $endfor$} + \preauthor{\centering\large\emph} + \postauthor{\par} +$else$ + \author{} + \preauthor{}\postauthor{} +$endif$ + +$if(date)$ + \predate{\centering\large\emph} + \postdate{\par} + \date{$date$} +$else$ + \date{} + \predate{}\postdate{} +$endif$ + +$for(header-includes)$ +$header-includes$ +$endfor$ + +\begin{document} + +\maketitle + +$if(abstract)$ +\begin{abstract} +$abstract$ +\end{abstract} +$endif$ + +$for(include-before)$ +$include-before$ + +$endfor$ +$if(toc)$ +{ +\hypersetup{linkcolor=black} +\setcounter{tocdepth}{$toc-depth$} +\tableofcontents +} +$endif$ + +$if(lot)$ +\listoftables +$endif$ + +$if(lof)$ +\listoffigures +$endif$ + +$body$ %%--------------------------------------------------------------- + +$if(natbib)$ +$if(biblio-files)$ +$if(biblio-title)$ +$if(book-class)$ +\renewcommand\bibname{$biblio-title$} +$else$ +\renewcommand\refname{$biblio-title$} +$endif$ +$endif$ +\bibliography{$biblio-files$} + +$endif$ +$endif$ +$if(biblatex)$ +\printbibliography$if(biblio-title)$[title=$biblio-title$]$endif$ + +$endif$ +$for(include-after)$ +$include-after$ + +$endfor$ +\end{document}