Paketbaurichtlinien für R

R ist eine Programmiersprache und Umgebung für statistische Berechnungen und Grafiken. R ähnelt dem preisgekrönten S-System, das von John Chambers et al. bei den Bell Laboratories entwickelt wurde. Es bietet eine Vielzahl statistischer und grafischer Verfahren (lineare und nichtlineare Modellierung, statistische Tests, Zeitreihenanalyse, Klassifizierung, Clustering usw.).

R ist als vollwertige Programmiersprache mit Kontrollstrukturen für Iteration und Alternation konzipiert und ermöglicht es Benutzern, durch die Definition neuer Funktionen zusätzliche Funktionalität hinzuzufügen. Für rechenintensive Aufgaben kann C-, C++- und Fortran-Code eingebunden und zur Laufzeit aufgerufen werden. Weitere Informationen finden Sie hier.

Dieses Dokument beschreibt, wie R-Add-on-Pakete für die Aufnahme in die Fedora-Paketquellen gehandhabt werden. Ein vollständiges Beispiel finden Sie in der unten stehenden [Beispiel-Spezifikationsdatei].

Benennung

Die zentrale Quelle für R-Pakete ist CRAN, das „Comprehensive R Archive Network“. Daneben gibt es weitere CRAN-ähnliche Repositories für spezifische Fachgebiete, wie beispielsweise Bioconductor (kurz Bioc) für Bioinformatik. Da diese jedoch als Ergänzung konzipiert sind, kommt es nicht zu Namenskonflikten zwischen den Paketen.

R-Add-ons MÜSSEN mit R-$pkg als Quellpaketnamen paketiert werden, wobei $pkg der Name des Projekts im CRAN-ähnlichen Upstream-Repository ist, d. h. das Feld Package des Pakets unter DESCRIPTION entspricht. Dieser $pkg-Name MUSS exakt mit der Schreibweise im Upstream-Repository übereinstimmen, einschließlich Groß- und Kleinschreibung sowie Punkten. Außerdem:

  • Das Feld Summary der Spec-Datei SOLLTE mit dem Feld Title der Paketbeschreibung (DESCRIPTION) übereinstimmen.

  • Das Feld DEscription der Spec-Datei SOLLTE mit dem Feld Description der Paketbeschreibung (DESCRIPTION) übereinstimmen.

Versionierung

Da Upstream-Versionen Zeichen enthalten können, die in RPM-Versionszeichenketten unzulässig sind, MÜSSEN sie in RPM-kompatible Zeichenketten umgewandelt werden. Insbesondere ist es üblich, dass R-Pakete Patch-Versionen mit einem Bindestrich als Trennzeichen angeben, z. B. 1.2-3. Solche Bindestriche MÜSSEN in einen Punkt umgewandelt werden. Diese Umwandlung SOLLTE mithilfe des Makros %R_rpm_version wie folgt erfolgen:

Version: %R_rpm_version 1.2-3

Abgesehen davon, dass in diesem Fall %{version} als 1.2.3 definiert wird, setzt dieses Makro außerdem %__R_upstream_version, um die Upstream-Version für die URL-Generierung weiterführen zu können.

Lizenz

Gemäß der CRAN-Richtlinie enthalten R-Pakete üblicherweise keine Lizenzdateien. R erlaubt und liefert eine Reihe von Open-Source-Lizenzen aus; R-Pakete geben in der DESCRIPTION-Datei lediglich an, welche Lizenz sie verwenden. Ausnahmsweise und gemäß den allgemeinen Lizenzrichtlinien verlangen wir nicht, dass zu den Upstream-R-Paketen zusätzliche Lizenzdateien hinzugefügt werden.

Die vollständigen Lizenztexte finden Sie unter /usr/share/R/licenses. Diese Texte können auch in der R-Konsole mit der Funktion RShowDoc() angezeigt werden.

Quellen

Projekte aus Standard-CRAN-ähnlichen Repositories MÜSSEN aus den dort veröffentlichten Quellen paketiert werden. Pakete aus den folgenden Repositories MÜSSEN die bereitgestellten Makros zur automatischen Generierung der Projekt-URL und der Quell-URL des Pakets verwenden:

  • CRAN: %{cran_url} und %{cran_source}

  • Bioc: %{bioc_url} und %{bioc_source}

Architekturen

Pakete, die keinen architekturspezifischen Code enthalten (d.h. keine kompilierten Teile), MÜSSEN BuildArch: noarch setzen.

Dies wirkt sich auf den Installationspfad aus:

  • %{_datadir}/R/library/$pkg für architekturunabhängige Pakete;

  • %{_libdir}/R/library/$pkg anderenfalls;

aber dies wird, wie unten beschrieben, von RPM automatisch verarbeitet.

Abhängigkeiten

Automatisch standardisierte Namen

Alle R-Pakete erzeugen automatisch standardisierte Requires- und Provides-Einträge mithilfe eines Generators in R-rpm-macros:

  • Provides haben die Form R($pkg) = $version;

  • Requires haben die Form R($pkg), wobei optional >= $version gemäß den Metadaten des Pakets angegeben ist, falls vorhanden;

wobei $pkg der Name des Upstream-Pakets und $version die RPM-kompatible Version ist, wie unter [Versioning] beschrieben.

Der Paketierer MUSS die generierten Requires-Einträge auf Korrektheit prüfen. Alle harten Abhängigkeiten (LinkingTo, Depends, Imports von R) MÜSSEN in der Zielversion von Fedora auflösbar sein.

BuildRequires

Pakete MÜSSEN BuildRequires: R-devel deklarieren, wodurch die notwendigen R-rpm-macros eingebunden und die Entwicklungsumgebung (Compiler, Bibliotheken usw.) eingerichtet wird.

Beachten Sie, dass R-Pakete ihre Kompilierungsflags vom Haupt-R-Paket erben, welches diese in %{_libdir}/R/etc/Makeconf speichert. R ist so konzipiert, dass alle R-Erweiterungspakete dieselben Optimierungsflags verwenden, mit denen das Haupt-R-Paket kompiliert wurde. Daher übergeben R-Erweiterungspakete nicht %{optflags}.

Falls für den Bauvorgang weitere Bibliotheken und Hilfsprogramme (z.B. cmake) benötigt werden, MÜSSEN diese explizit als BuildRequires deklariert werden.

Bauabhängigkeiten von anderen R-Paketen werden automatisch durch das Makro %R_buildrequires behandelt, das im Scriptlet %generate_buildrequires aufgerufen werden MUSS.

  • Alle harten Abhängigkeiten (LinkingTo, Depends, Imports von R) werden als BuildRequires unter Verwendung standardisierter Namen deklariert (siehe [Automatic standardized names]).

  • Weiche Abhängigkeiten (Suggests, Enhances von R) werden übersprungen, außer bei Paketen, die zur Entwicklung der Testsuite verwendet werden (derzeit testthat, tinytest oder RUnit).

Gebündelte Abhängigkeiten

Gemäß den allgemeinen Richtlinien SOLLTEN Pakete nach Möglichkeit andere Abhängigkeiten aus den R-Paketquellen extrahieren. Werden gebündelte Abhängigkeiten verwendet, MÜSSEN diese als virtuelles Provides deklariert werden.

Teilpakete

Manche R-Pakete stellen Header-Dateien unter dem Standardpfad R/library/$pkg/include bereit (definiert von CRAN und von R erwartet), so dass andere Pakete über LinkingTo darauf verlinken können. Das Paket Rcpp ist ein bekanntes Beispiel. Manchmal werden diese Header zur Bauzeit benötigt, manchmal sowohl zur Bau- als auch zur Laufzeit, und sind daher für die korrekte Funktion unerlässlich. Aus diesen und weiteren Gründen dürfen diese Header NICHT in ein -devel-Teilpaket ausgelagert werden.

Wenn ein bestimmtes Paket eine große Anzahl von Beispielen oder Dokumentationen enthält, die für die Funktionalität des Pakets nicht notwendig sind, KÖNNEN diese in ein Teilpaket ausgelagert werden, aber von Teilpaketen wird generell dringend abgeraten.

Durchlauf

Vorbereitung der Quellen

Die übrigen Scriptlets erwarten, dass die Paketquellen in einem nach dem Paket benannten Unterverzeichnis extrahiert werden. Daher MUSS in %prep beim Aufruf von %setup oder %autosetup die Option -c gesetzt werden.

%prep
%autosetup -c

Weiterer Code für Entbündelung, Fehlerbehebungen und Workarounds DARF hier platziert werden.

Dynamische BuildRequires

Das Makro %R_buildrequires MUSS im Scriptlet %generate_buildrequires aufgerufen werden, um die dynamischen BuildRequires zu erzeugen.

%generate_buildrequires
%R_buildrequires

Testpakete wie testthat, die in Suggests deklariert sind, werden in %{__R_whitelist} auf die Whitelist gesetzt und von %R_buildrequires als BuildRequires hinzugefügt.

Bau und Installation

R-Pakete werden in einem einzigen Schritt über R CMD INSTALL erstellt und installiert. Daher MUSS der Abschnitt %build leer sein.

Es werden zwei Makros bereitgestellt, die im Abschnitt %install aufgerufen werden MÜSSEN. Zuerst erstellt %R_install das Paket und installiert es, dann generiert %R_save_files eine Liste der Dateien, die dem angegebenen importierbaren Modul entsprechen, und speichert diese als %{R_files}.

%build

%install
%R_install
%R_save_files

Das Makro %R_install gewährleistet die Reproduzierbarkeit, indem es den Bau-Zeitstempel des Pakets auf $SOURCE_DATE_EPOCH setzt.

Die Installation des R-Pakets erzeugt eine neue R.css-Datei, die mit der im Haupt-R-Paket enthaltenen Master-R.css-Datei in Konflikt steht. Das Makro %R_install löscht diese Datei.

Das Makro %R_install ruft %_R_libdir_check auf, um sicherzustellen, dass ein architekturunabhängiges Paket keine gemeinsam genutzte Bibliothek erzeugt hat oder ein architekturabhängiges Paket tatsächlich eine gemeinsam genutzte Bibliothek enthält. Anderenfalls schlägt es mit einer aussagekräftigen Fehlermeldung fehl. Wenn der Paketierer diese Prüfung nicht wünscht, kann %_R_libdir_check beispielsweise auf eine leere Zeichenkette gesetzt werden.

Testen

Das Makro %R_check MUSS im Abschnitt %check aufgerufen werden, um R-Paketprüfungen durchzuführen.

%check
%R_check

Gemäß den CRAN-Richtlinien MÜSSEN R-Pakete ohne weiche Abhängigkeiten funktionieren. Wenn Paketprüfungen fehlschlagen, weil weiche Abhängigkeiten bedingungslos verwendet werden (z.B. in Beispielen oder Tests), gilt dies als Fehler und SOLLTE an die Entwickler gemeldet werden. In der Zwischenzeit MUSS etwas implementiert werden, das das Problem umgeht:

  • Wenn der Fehler in einem Beispiel auftritt, KANN das Flag --no-examples an %R_check angehängt werden.

  • Wenn der Fehler in einem Test auftritt, kann an der entsprechenden Stelle ein skip()-Aufruf eingefügt werden, um den Test zu überspringen, oder eine Testdatei kann entfernt werden, oder in komplizierteren Fällen kann sogar das Flag --no-tests an %R_check angehängt werden.

Auflisten der Dateien

Moduldateien MÜSSEN über die Option -f wie folgt hinzugefügt werden:

%files -f %{R_files}

Falls erforderlich, SOLLTEN alle zusätzlichen Dateien, die sich außerhalb des Paketpfads befinden, anschließend explizit hinzugefügt werden.

Beispiel-Spec-Datei

Dies ist eine Beispiel-Spec-Datei für ein hypothetisches R-Paket namens „foo“ mit der Upstream-Version 1.2-3:

Name:           R-foo
Version:        %R_rpm_version 1.2-3
Release:        %autorelease
Summary:        Adds foo functionality for R

License:        GPL-2.0-or-later
URL:            %{cran_url}
Source:         %{cran_source}

# BuildArch:      noarch
BuildRequires:  R-devel
# BuildRequires:  somelib-devel

%description
R Interface to foo, enables bar!

%prep
%autosetup -c

%generate_buildrequires
%R_buildrequires

%build

%install
%R_install
%R_save_files

%check
%R_check

%files -f %{R_files}

%changelog
%autochangelog