Como publicar seu software no Copr, o Repositório de Usuários do Fedora

Christopher Engelhard, Jean-Baptiste Holcroft, Otto Urpelainen Versão unspecified Last review: 2022-02-05
Isso é um breve tutorial em como criar e manter um repositório Copr para seu software de forma automatizada. Será presumido alguma familiaridade básica com Git e como criar um pacote RPM.

Neste guia, nós vamos

  • criar um pacote RPM para um programa

  • criar um repositório Copr e publicar o programa no mesmo

  • configurar o gerenciamento automático da versão do programa, seu lançamento e das notas de atualização do pacote

  • configurar a construção automática de novas versões do pacote

O objetivo é lhe permitir manter seu software atualizado no Copr sem precisar interagir com nada além do repositório Git do seu programa.

Você pode configurar uma automação similar quando empacotar o programa de outra pessoa, ou seja, construir o programa a partir de uma tarball fonte baixada. As modificações necessárias são descritas no fim do tutorial.

Pré-requisitos

O seguinte é necessário:

  1. Our program’s source in a publicly available git repository somewhere. This tutorial uses a simple example program - hellocopr - to demonstrate the process. The program and all files referenced in this guide can be found in the project’s git repository. It’s a very simple (& pointless) python program with a setuptools installer:

    user@host ~/copr-tito-quickdoc % ls
    doc  LICENSE  README.md  requirements.txt  setup.py  src
    
    user@host ~/copr-tito-quickdoc % ls src/hellocopr
    colors.py  hellocopr.py  __init__.py
  2. A Fedora (FAS) account in order to be able to create repositories on Copr. This tutorial’s demo repository can be found here.

  3. The utility `tito` installed on your system. Tito is capable of a lot of advanced automation for package creation, most of which we won’t need here. Check out its documentation to learn more.

  4. A specfile for our program. For more information on how to create one, refer to Packaging Tutorial: GNU Hello or adapt this tutorial’s annotated example specfile.

Você pode seguir esse tutorial clonando ou fazendo um fork do repositório e conferindo a tag initial. Isso colocará o repositório neste estado logo antes do próximo passo. O histórico de commits do repositório deve ser igual aos passos seguidos nesse tutorial.

Primeiro passo: Criando o pacote usando o tito

Copie o arquivo spec no diretório base do projeto. Algumas mudanças devem ser feitas antes de prosseguir:

  1. Os valores de Version: e Release: não importam, já que esses serão gerenciados pelo tito. Faz sentido definí-los como Version: 0.0.0 e Release: 0%\{?dist} para marcar que esse pacote ainda não foi construído.

  2. tito will also handle the creation of the source tarball from the git repository, so change the `Source0:` URL to the filename %{name}-%{version}.tar.gz & add a comment to tell users how to get the tarball

  3. As notas de atualização também podem ficar vazias.

    Faça um commit das mudanças.
    
    A seguir, vamos inicializar o projeto para seu uso com o tito.
    
    ``` user@host ~/copr-tito-quickdoc % tito init Creating tito metadata in: ~/copr-tito-quickdoc/.tito
       - created ~/copr-tito-quickdoc/.tito
       - wrote tito.props
       - created ~/copr-tito-quickdoc/.tito/packages
       - wrote ~/copr-tito-quickdoc/.tito/packages/.readme
    committed to git Done! ```
    
    Isso cria link:https://pagure.io/copr-tito-quickdoc/c/7a6919d3dd56943bb988a755f8233157965aa9bb?branch=master[um subdiretório `.tito` com algumas configurações padrão], que pode ser deixado como está por agora.
    
    We can now do a test build of the package using _`tito build`_. Usually, tito will build from a tag, which we haven't created yet. However, using the `--test` flag, we can build from the most recent commit instead, which will be written to `/tmp/tito`:
    
    [source]
    ----
    user@host ~/copr-tito-quickdoc % tito build --rpm --test
    Creating output directory: /tmp/tito
    WARNING: unable to lookup latest package tag, building untagged test project
    WARNING: .tito/packages/hellocopr doesn't exist in git, using current directory
    Building package [hellocopr-0.0.0-0]
    Wrote: /tmp/tito/hellocopr-git-11.7a6919d.tar.gz
    ...
    
    Successfully built: /tmp/tito/hellocopr-0.0.0-0.git.11.7a6919d.fc32.src.rpm
    	- /tmp/tito/noarch/hellocopr-0.0.0-0.git.11.7a6919d.fc32.noarch.rpm
    ----
    
    Once we've fixed any issues with the package that might crop up, we can let _tito_ create a package release using `tito tag`. Since we haven't set a proper version yet, we need to pass it to tito for the first tag:
    
    [source]
    ----
    user@host ~/copr-tito-quickdoc % tito tag --use-version 1.0.0
    ----
    
    Isso abrirá o editor e mostrar uma nota de atualização pré-formatada construída com todos os commits desde o último lançamento, que podemos editar como for necessária. Já que não houve nenhum até agora, a nota vai conter apenas "- novo pacote construído com tito". Salve o arquivo, link:https://pagure.io/copr-tito-quickdoc/c/f44e81d695df669bcdb7237612baf41b80da98e0?branch=master[e o tito vai]
    
    . definir a versão (Version) do arquivo spec para 1.0.0
    
    . definir o lançamento (Release) no arquivo spec para 1
    
    . adicionar as notas de atualização na seção `%changelog` do arquivo spec
    
    . fazer um commit do resultado e adicionar uma tag ao mesmo com `<nome>-<versão>-<release>, nesse caso `hellocopr-1.0.0-1`
    +
    [source]
    ----
    user@host ~/copr-tito-quickdoc % tito tag --use-version 1.0.0
    Creating output directory: /tmp/tito
    Tagging new version of hellocopr: untagged -> 1.0.0-1
    Created tag: hellocopr-1.0.0-1
       View: git show HEAD
       Undo: tito tag -u
       Push: git push --follow-tags origin
    ----
    
    Faça um push dos commits e tags para o remoto usando `git push --follow-tags`, e com isso estamos prontos para lançar o pacote no Copr.
    
    
    == Segundo passo: Publicando o pacote em um repositório Copr
    
    . Vá para https://copr.fedorainfracloud.org/ e faça login. Uma vez que esteja logado, clique em _New Project_ (Novo Projeto) e comece a criar um repositório para nosso programa. Nas entradas de input a seguir,
    
    .. Em _1. Project information_ (Informações do projeto) -> _Project name_ (Nome do projeto) defina o nome de como você quer que seu repositório se chame - já que ele conterá apenas um único pacote, faz sentido usar nomedoprojeto = nomedopacote, nesse caso _hellocopr_. Essa é a única configuração que não pode ser modificada depois.
    
    .. Em _2. Build options_ (Opções de build) marque todas as distribuições para as quais você deseja criar repositórios - geralmente todas as versões do Fedora e talvez versões para o EPEL também
    
    .. Em _4. Other Options_ (Outras Opções) garanta que _Follow Fedora branching_ (Seguir ramificação do Fedora) está marcada, isso garantirá que seu repositório será automaticamente atualizado para cada novo lançamento do Fedora.
    
    . Vá para _Packages_ (Pacotes) -> _New Package_ (Novo Pacote)
    
    .. Em _1. Provide the source_ (Adicione a fonte), defina o nome do pacote e a URL do seu repositório git
    
    .. Em _2. How to build SRPM from the source_ (Como construir o SRPM a partir da fonte) selecione _tito_
    
    .. Em _3. Generic package setup_ (Configurações genéricas do pacote) marque a opção de _Auto-rebuild_ (Reconstrução automática)
    
    . Seu pacote aparecerá na lista de pacotes. Selecione _Rebuild_ para iniciar uma construção. A página a seguir lhe permite mudar quaisquer opções de build se necessário, mas iremos utilizar apenas os padrões, ou seja, as opções que configuramos no último passo. Clique em _Submit_ (Confirmar) e o Copr construirá o pacote a partir da tag do tito que criamos no Primeiro passo.
    
    Once the build has finished, you can test installing the package from Copr by activating your repository.
    [source]
    ----
    user@host ~/copr-tito-quickdoc % sudo dnf copr enable <username>/hellocopr
    
    user@host ~/copr-tito-quickdoc % sudo dnf install hellocopr
    ----
    
    == Terceiro passo: Automatizando a (re)construção do pacote
    
    Em seguida, vamos configurar o Copr para construir automaticamente uma nova versão do pacote quando criarmos uma, para que não precisemos fazer login e iniciar uma manualmente. Para fazer isso, precisamos simplesmente iniciar uma construção quando fizermos push de uma nova tag para o repositório.
    
    Isso requer uma certa configuração tanto do seu repositório Git e do seu projeto Copr.
    
    A configuração no Copr pode ser encontrada em _Settings_ (Configurações) -> _Integrations_ (Integrações), a página também explica os passos para configurar seu repositório git para todas as _forges_ Git mais comuns (Pagure, GitHub, GitLab e BitBucket).
    
    Agora, para testarmos, vamos fazer algumas mudanças no nosso programa que virão a calhar para a última camada de automação e criar uma nova atualização para nosso software.
    
    Atualmente o programa de exemplo tem sua versão manualmente definida em inúmeros lugares. link:https://pagure.io/copr-tito-quickdoc/c/61abf1cdf622d8c9fb4f03eb6b06c4ddc1677362?branch=master[Vamos mudar isso] para que a string de versão seja modificada por um único arquivo. Não importa que arquivo seja, mas idealmente a variável de versão deve ser a única coisa que provavelmente mudará. Nesse caso, vamos usar o arquivo `src/hellocopr/pass:[__]initpass:[__].py` que anteriormente estava vazio. Vamos nomear essa nova versão '1.0.1'.
    
    Commit the changes, and create a new release with tito
    
    [source]
    ----
    user@host ~/copr-tito-quickdoc % tito tag
    Creating output directory: /tmp/tito
    Tagging new version of hellocopr: 1.0.0-1 -> 1.0.1-1
    Created tag: hellocopr-1.0.1-1
       View: git show HEAD
       Undo: tito tag -u
       Push: git push --follow-tags origin
    ----
    
    Note that by ommiting the `--use-version` option, tito now updates the version automatically. It does so by
    
    . Aumentando o dígito final da versão em 1 - `1.0.0` -> `1.0.1`
    . Resetando o lançamento para 1 se já não foi feito antes.
    
    Se você quiser aumentar para uma versão diferente, por exemplo `1.1.0`, você pode fazê-lo passando novamente `--use-version`.
    
    Faça push do commit e da tag resultantes, e se você conferir a página do seu projeto no Copr, você verá que uma nova build do `hellocopr-1.0.1-1` foi iniciada por termos feito push da tag.
    
    == Quarto passo: Deixar o tito gerenciar a versão do programa
    
    Se você chegar o log do git, você vai descobrir que eu na verdade esqueci de atualizar a variável de versão do hellocopr para 1.0.1. Não queremos que isso aconteça novamente. Por sorte, já que fizemos o processo de modificação da versão para uma única fonte, podemos deixar o tito gerar esse arquivo automaticamente a partir de um template.
    
    First, copy the version source file `src/hellocopr/pass:[__]initpass:[__].py` to `.tito/templates/pass:[__]initpass:[__].py.template`. Then, open the template file and replace the version string with `$version`. It also makes sense to add a note that the file is managed by tito and should not be edited manually.
    [source]
    ----
    user@host ~/copr-tito-quickdoc % cat .tito/templates/__init__.py.template
    ...
    # This file is automatically created from a template by tito. Do not edit it manually.
    
    __version__ = '$version'
    ----
    
    Next, add the following to `.tito/tito.props`
    [source]
    ----
    [version_template]
    destination_file = src/hellocopr/__init__.py
    template_file = .tito/templates/__init__.py.template
    ----
    
    https://pagure.io/copr-tito-quickdoc/c/28600f6e41d5a4b60f2e47cf077f2fe2d9224e1d?branch=master[Commit the changes]. Now, when we tag a new release, tito will take the template, replace `$version` with whatever version was tagged, and copy the resulting file to `src/hellocopr/pass:[__]initpass:[__].py` before updating the spec file and commiting the changes.
    
    We can test this by tagging a new release:
    [source]
    ----
    user@host ~/copr-tito-quickdoc % % tito tag
    Creating output directory: /tmp/tito
    Tagging new version of hellocopr: 1.0.1-1 -> 1.0.2-1
    Created tag: hellocopr-1.0.2-1
       View: git show HEAD
       Undo: tito tag -u
       Push: git push --follow-tags origin
    
    user@host ~/copr-tito-quickdoc % cat src/hellocopr/__init__.py
    ...
    # This file is automatically created from a template by tito. Do not edit it manually.
    
    __version__ = '1.0.2'
    ----
    
    If you again push the tag to the remote repo, Copr will again automatically trigger a rebuild.
    
    == Procedimento de liberação em resumo
    A partir de agora, atualizar seu software no repositório Copr é tão simples quanto
    
    . Faça o commit de todas as alterações para a sua nova versão.
    . Realize uma compilação de teste usando `tito build --test`
    . Faça a marcação da versão com `tito tag` (adicione `--use-version` se necessário)
    . Faça o push da tag para o seu repositório git usando `git push --follow-tags`
    
    E o Copr cuidará do restante.
    
    == Empacotamento a partir de arquivos tarballs de origem
    
    Você pode usar um processo semelhante para gerenciar o software de outra pessoa no Copr, ou seja, construir a partir de um tarball baixado diretamente do desenvolvedor original.
    
    Para fazer isso, as seguintes alterações precisam ser feitas no procedimento descrito acima:
    
    . Em vez de descompactar as fontes, faça o download e faça commit do tarball de origem que deseja empacotar em seu repositório
    . Em vez de modificar diretamente a fonte, adicione quaisquer alterações que você precise fazer na forma de arquivos de patch. Liste esses patches como `PatchX:` no arquivo de especificação (spec file)
    . Também no arquivo de especificação (spec file), defina `Version:` de volta para a versão atual do programa e `Source0:` de volta para a URL do tarball. Você pode usar macros como `%{version}` para a última, a fim de seguir automaticamente as alterações de versão.
    . Modifique o arquivo `.tito/tito.props` do Tito para, em primeiro lugar, não tentar construir um tarball de origem e, em segundo lugar, incrementar o valor de `Release:` em vez de `Version:` ao criar tags
    +
    [source]
    ----
    [buildconfig]
    builder = tito.builder.NoTgzBuilder
    tagger = tito.tagger.ReleaseTagger
    ----
    
    . Não realize nenhum tipo de modelagem de tito
    
    O restante do procedimento permanece o mesmo. Se você fizer alterações no pacote sem modificar a fonte, basta criar uma nova tag de versão com o Tito. Se você atualizar o tarball de origem, precisará atualizar o campo `Version:` e redefinir `Release:` para `0%{?dist}` antes de criar a tag.
    
    TIP: A versão adaptada ao tarball do projeto pode ser encontrada no ramo `foreign-sources` do repositório git em `https://pagure.io/copr-tito-quickdoc/tree/foreign-sources`.