Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
112 commits
Select commit Hold shift + click to select a range
e434313
Update build-and-publish-image.yml for two images
iaine Jul 11, 2025
d7f0998
Update cache
iaine Jul 11, 2025
38e5386
Update build-and-publish-image.yml
iaine Jul 11, 2025
69fe205
Update build-and-publish-image.yml
iaine Jul 11, 2025
65e41cd
Update registry and added platform tags
iaine Jul 11, 2025
a7f491e
Update build-and-publish-image.yml
iaine Jul 11, 2025
70cddd6
Update build-and-publish-image.yml
iaine Jul 11, 2025
c450b56
Update build-and-publish-image.yml
iaine Jul 11, 2025
aed1515
Update build-and-publish-image.yml
iaine Jul 11, 2025
d068c98
Initial reusable flow
iaine Jul 25, 2025
6a912a2
Update call_jobs.yml and fix syntax
iaine Jul 25, 2025
4178cc3
Update call_jobs.yml and addd branch
iaine Jul 25, 2025
d04a92a
Removed version
iaine Jul 25, 2025
a231106
Change to gh token
iaine Jul 25, 2025
b1360ae
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
190dcf8
Update call_jobs.yml
iaine Jul 25, 2025
dc57ccc
Update call_jobs.yml
iaine Jul 25, 2025
0b1ad64
Update call_jobs.yml
iaine Jul 25, 2025
56ce47c
Added branch
iaine Jul 25, 2025
e2a20d7
Update call_jobs.yml
iaine Jul 25, 2025
38099d5
Update call_jobs.yml
iaine Jul 25, 2025
ebcfe0e
Fix path
iaine Jul 25, 2025
ae74c06
Update call_jobs.yml
iaine Jul 25, 2025
bfb32dd
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
e024c9a
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
5bb1553
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
bc36026
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
bb33732
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
9a0c245
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
296869c
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
dd76ce8
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
88d43b4
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
904140b
version number
iaine Jul 25, 2025
9dd190a
Update call_jobs.yml
iaine Jul 25, 2025
9527f69
Update call_jobs.yml
iaine Jul 25, 2025
be45553
Update call_jobs.yml
iaine Jul 25, 2025
3bbf9cb
Update call_jobs.yml
iaine Jul 25, 2025
cae7158
Update call_jobs.yml
iaine Jul 25, 2025
aed9f65
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
9569072
Update call_jobs.yml
iaine Jul 25, 2025
cbb235e
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
5c8400f
Update workflow name
iaine Jul 25, 2025
bd52755
Update reuse-build-and-publish.yml
iaine Jul 25, 2025
f4f5b12
Remove actor
iaine Jul 25, 2025
a1e77a4
Align call inputs with file inputs
iaine Jul 25, 2025
9b58474
Update call_jobs.yml
iaine Jul 25, 2025
0ad67e7
Cleaning up workflows
iaine Jul 28, 2025
3541281
Cleaning up workflows
iaine Jul 28, 2025
89135e9
Cleaning up workflows
iaine Jul 28, 2025
8cf5866
Cleaning up workflows
iaine Jul 28, 2025
ec32dee
Cleaning up workflows
iaine Jul 28, 2025
dd156dc
Cleaning up workflows
iaine Jul 28, 2025
9983aeb
Cleaning up workflows
iaine Jul 28, 2025
a863bec
Cleaning up workflows
iaine Jul 28, 2025
607c470
Merge branch 'r-devel:devel' into devel
iaine Jul 29, 2025
7bd0a7f
Update reuse-build-and-publish.yml
iaine Jul 29, 2025
9bdd697
Update call_jobs.yml
iaine Jul 29, 2025
f97403c
Update call_jobs.yml
iaine Jul 29, 2025
838c646
Update reuse-build-and-publish.yml
iaine Jul 29, 2025
47d4920
Update call_jobs.yml
iaine Jul 29, 2025
3098c53
Update call_jobs.yml
iaine Jul 29, 2025
fe6319c
Ref name fix to call
iaine Jul 29, 2025
26921c8
Update call_jobs.yml
iaine Jul 29, 2025
c67b970
Update call_jobs.yml
iaine Jul 29, 2025
b7a7f32
Update call_jobs.yml
iaine Jul 29, 2025
2fa7f05
Adding ref
iaine Jul 29, 2025
180861e
remove whitespace
iaine Jul 29, 2025
baae071
call locally
iaine Jul 29, 2025
3a11ab9
Update call_jobs.yml
iaine Jul 29, 2025
cd4ec5f
Update pull-request
iaine Jul 29, 2025
a03fa06
Testing if statement
iaine Jul 29, 2025
ab06202
Update call_jobs.yml with workflows
iaine Jul 29, 2025
bdb0f08
Update call_jobs.yml
iaine Jul 29, 2025
f99c69f
Initial manifest script
iaine Aug 11, 2025
ee8573d
Updated with manifest
iaine Aug 11, 2025
03a18d1
Merge branch 'devel' of github.com:iaine/r-dev-env into devel
iaine Aug 11, 2025
3bab5ac
Updated with manifest and added r-base to run
iaine Aug 11, 2025
b878155
Updated paths
iaine Aug 11, 2025
8db1e0c
Updated apt-get
iaine Aug 11, 2025
006d100
Updated apt-get
iaine Aug 11, 2025
982c2ea
Fixing R libraries
iaine Aug 11, 2025
c19fd29
Fixing R libraries
iaine Aug 11, 2025
454edb9
Fixing R libraries
iaine Aug 11, 2025
2d278dd
Fixing input variables
iaine Aug 11, 2025
1b5e470
Removed version
iaine Aug 11, 2025
871ef23
Updated histrory long line
iaine Aug 11, 2025
dced3fe
Updated bash run
iaine Aug 11, 2025
40450f0
Updated bash run
iaine Aug 11, 2025
7f02e95
Updated bash run
iaine Aug 11, 2025
28bb525
Updated bash run
iaine Aug 11, 2025
8655adc
Updated bash run
iaine Aug 11, 2025
908b7c2
Lookign at details
iaine Aug 11, 2025
2060707
Updated file details
iaine Aug 11, 2025
3816813
Added recursive in and altered file paths
iaine Aug 11, 2025
be9724d
Altered file paths
iaine Aug 11, 2025
8c4b8b1
Docker commands
iaine Aug 11, 2025
47fedb0
Update command
iaine Aug 11, 2025
ab84fe8
Update command
iaine Aug 11, 2025
ead2182
Update command
iaine Aug 11, 2025
0890893
Update command
iaine Aug 11, 2025
1c609cd
Update command wth bash
iaine Aug 11, 2025
c1e5eb1
Update command wth bash
iaine Aug 11, 2025
2403598
Update command wth bash
iaine Aug 11, 2025
259cc0e
Added platform variable
iaine Aug 12, 2025
2d85487
Added platform variable and altered manifest line'
iaine Aug 12, 2025
f5f3653
Added platform variable
iaine Aug 12, 2025
2f4b0cd
Merge branch 'devel' of github.com:iaine/r-dev-env into devel
iaine Aug 12, 2025
c486c8e
Added platform variable
iaine Aug 12, 2025
87e5fb2
Tidying test variable
iaine Aug 12, 2025
ad801a7
Tidy manifest name
iaine Aug 12, 2025
b1d20e4
Added platform to variable
iaine Aug 12, 2025
93558ff
Tidied name
iaine Aug 12, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 15 additions & 1 deletion .github/workflows/build-and-publish-image.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
# separate terms of service, privacy policy, and support
# documentation.


name: Build and publish Docker image

on:
Expand Down Expand Up @@ -41,7 +42,17 @@ jobs:
steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Set up QEMU
uses: docker/setup-qemu-action@v1
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Cache Docker layers
uses: actions/cache@v4
with:
path: /tmp/.buildx-cache
key: ${{ runner.os }}-buildx-${{ github.sha }}
restore-keys: |
${{ runner.os }}-buildx-
- name: Extract version number
run: |
VER=$(cat VERSION)
Expand Down Expand Up @@ -74,3 +85,6 @@ jobs:
build-args: |
CONTAINER_VERSION=${{ env.VERSION }}
labels: ${{ steps.meta.outputs.labels }}
platforms: linux/amd64,linux/arm64/v8
cache-from: type=local,src=/tmp/.buildx-cache
cache-to: type=local,dest=/tmp/.buildx-cache
29 changes: 29 additions & 0 deletions .github/workflows/call_jobs.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
name: Call reusable workflows

on:
pull_request:
branches:
- main
- devel
types:
- closed
paths:
- '.github/workflows/reuse-build-and-publish-amd.yml'
- '.devcontainer/devcontainer.json'
- 'Dockerfile'
- 'reinstall-cmake.sh'
- 'VERSION'

jobs:
call-workflow-amd64:
permissions:
contents: read
packages: write
uses: ./.github/workflows/reuse-build-and-publish.yml
with:
image_name: ${{ github.repository }}
ref_name: ${{ github.ref_name }}
actor: ${{ github.actor }}
registry: ghcr.io
platform: amd64
secrets: inherit
99 changes: 99 additions & 0 deletions .github/workflows/reuse-build-and-publish.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
# This workflow uses actions that are not certified by GitHub.
# They are provided by a third-party and are governed by
# separate terms of service, privacy policy, and support
# documentation.

name: Build and publish amd 64 Docker image

on:
workflow_call:
inputs:
image_name:
description: image name
required: true
type: string
ref_name:
description: ref name
required: true
type: string
actor:
description: actor
required: true
type: string
registry:
description: registry
required: true
type: string
platform:
description: platform
required: true
type: string
permissions:
contents: read
packages: write

jobs:
reuse-build-and-push:

runs-on: ubuntu-latest

steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Extract version number
run: |
VER=$(cat VERSION)
echo "VERSION=$VER" >> $GITHUB_ENV

- name: Log in to the Container registry
uses: docker/login-action@v3
with:
registry: ${{ inputs.registry }}
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}

- name: Extract metadata (tags, labels) for Docker
id: meta
uses: docker/metadata-action@v5
with:
images: ${{ inputs.registry }}/${{ inputs.image_name }}
tags: |
type=ref,event=branch
type=ref,event=pr
type=semver,pattern=${{ env.VERSION }}
type=sha

- name: Build and push Docker image
uses: docker/build-push-action@v5
with:
context: .
push: true
pull: true
tags: ${{ inputs.registry }}/${{ inputs.image_name }}:${{ inputs.ref_name }}
build-args: |
CONTAINER_VERSION=${{ env.VERSION }}
labels: ${{ steps.meta.outputs.labels }}
- name: Write manifest and build history file
run: |
sudo apt-get install r-base -y && sudo Rscript -e "install.packages('optparse')" \
&& Rscript scripts/manifest.R \
--registry ${{ inputs.registry }} \
--owner ${{ inputs.actor}} \
--image ${{ inputs.ref_name }} \
--historydir /tmp/r-devel/hist_lines \
--manifestdir /tmp/r-devel/manifests \
--repository ${{ inputs.image_name }}
shell: bash
- name: Upload manifest file
uses: actions/upload-artifact@v4
with:
name: ${{ inputs.platform }}-manifest
path: /tmp/r-devel/manifests/manifest-*.md
retention-days: 3
- name: Upload build history line
uses: actions/upload-artifact@v4
with:
name: ${{ inputs.platform }}-history_line
path: /tmp/r-devel/hist_lines/history-*.txt
retention-days: 3
228 changes: 228 additions & 0 deletions scripts/manifest.R
Original file line number Diff line number Diff line change
@@ -0,0 +1,228 @@
# manifest.R
#
# Files takes the container arguments and creates two files inside the
# given container. These are the build history and manifest files.
#
# The build history file has the locations of the manifest and git history
# files. This is stored in the location given in histlines argument.
#
# The manifest file has the installed apt and R packages written into it
# along with the build time and commit hash for this build. This is is stored
# in the manifestdir location.
#
# Both are stored as markdown files on the container itself.

library(optparse)

option_list <- list(
make_option(c("-r", "--registry"), type = "character", default = "ghcr.io",
help = "Registry name"),
make_option(c("-o", "--owner"), type = "character", default = "r-devel",
help = "Current owner of the Repository"),
make_option(c("-i", "--image"), type = "character", default = "devel",
help = "Provide the image name [default %default]"),
make_option(c("-t", "--historydir"), type = "character",
default = "/tmp/hist_lines/", help = "location of history lines"),
make_option(c("-m", "--manifestdir"), type = "character",
default = "/tmp/manifests/",
help = "Manifest file location [default %default]"),
make_option(c("-p", "--repository"), type = "character",
default = "r-dev-env", help = "Repository name [ %default]")
)

parser <- OptionParser(usage = "%prog [options] file",
option_list = option_list)

args <- parse_args(parser, positional_arguments = 0)
opt <- args$options

#set up constants
build_time <- as.numeric(Sys.time())
tm <- as.POSIXlt(build_time, "UTC")
utc_time <- strftime(tm, "%Y-%m-%dT%H:%M:%S%z")

manifest_filename <- paste("manifest-", build_time, ".md", collapse = NULL,
sep = "")

history_filename <- paste("history-", build_time, ".txt", collapse = NULL,
sep = "")

#set up docker
docker_id <- paste(opt$registry, "/", opt$repository, ":",
opt$image, collapse = NULL, sep = "")

#container_id = system2("docker", args = c("run", "-i -d", docker_id, "bash"),
# stdout = TRUE)

write_all <- function() {
write_manifest_details()
write_history_details()
}

write_manifest_details <- function() {
details <- get_manifest_details()
write_manifest(details, opt$manifestdir, manifest_filename)
}

write_history_details <- function() {
details <- get_build_history()
write_manifest(details, opt$historydir, history_filename)
}

write_manifest <- function(manifestdata, filepth, filename) {

my_directory <- file.path(filepth)
if (!dir.exists(my_directory)) {
dir.create(my_directory, recursive = TRUE)
}

file_conn <- file(manifest_filename)
writeLines(manifestdata, paste(my_directory, filename,
sep = "/", collapse = NULL))
close(file_conn)
}

get_manifest_details <- function() {

buildregistry <- paste("registry", opt$registry, sep = ":")
buildowner <- paste("owner", opt$owner, sep = ":")
buildimage <- paste("image", opt$image, sep = ":")
buildrepository <- paste("repository", opt$repository, sep = ":")
buildtime <- paste("timestamp", build_time, sep = ":")

r_ver <- r_version()
rbuildversion <- paste("### R Version: ", r_ver, sep = "\n")

r_package <- r_packages()
rbuildpackages <- paste("### R Packages: ", r_package, sep = "\n")

apt_package <- apt_packages()
aptbuildpackages <- paste("### APT Packages: ", apt_package, sep = "\n")

manifest_d <- manifest_string()

title <- paste(opt$owner, opt$repository, sep = "/")
build_title <- paste("# Build manifest for image ", title, ":", opt$image,
sep = "")

builds <- paste(build_title, buildregistry, buildrepository, buildowner,
buildimage, buildtime, manifest_d,
rbuildversion, rbuildpackages, aptbuildpackages, " ",
sep = "\n\n")

builds
}

get_build_history <- function() {

platform <- "amd64"

tags <- "default"

commit <- get_commit_hash()

diff_url <- paste("https://github.com/", opt$repository, collapse = NULL,
sep = "")

diff <- paste("[Git diff](", diff_url, "/commit/", commit, ")",
collapse = NULL, sep = "")
dockerfile <- paste("[Dockerfile](", diff_url, "/blob/", commit, ")",
collapse = NULL, sep = "")
manif <- paste("[Build manifest] (./", manifest_filename, ")",
collapse = NULL, sep = "")

build_history <- paste(diff, dockerfile, manif, sep = "<br />")

image_manifest <- paste("{", tags, ":", platform, "}", collapse = NULL,
sep = "")

build_conf <- paste(utc_time, image_manifest, build_history, sep = " | ")

build_conf
}


## Git helpers
get_commit_hash <- function() {
arguments <- c("rev-parse", "HEAD")
hash <- system2("git", args = arguments, stdout = TRUE)
hash
}

get_commit_hash_tag <- function() {
x <- get_commit_hash()
tag <- substr(x, nchar(x) - 12 + 1, nchar(x))
tag
}

##Linux Helper
get_linux_release <- function() {
os <- docker_command(c("lsb_release", "-a"))
release <- paste(os, sep = " ", collapse = "\n")
release
}

#packages
r_version <- function() {

r_version <- docker_command(c("R", "--version"))
details <- strsplit(r_version, "\r", fixed = TRUE)
#version <- paste(details[[1]], details[[3]], sep = " ", collapse = "\n\n")
version <- paste(details, sep = " ", collapse = "\n\n")
version
}

r_packages <- function() {

# from dockerstack
r <- docker_command(c("R", "--silent", "-e",
"'installed.packages(.Library)[, c(1,3)]'"))
#tidy the response by removing final > and the initial commands
package <- paste(unlist(strsplit(r, "\r", fixed = TRUE)[3:length(r) - 1]),
sep = " ", collapse = "\n")
package
}

apt_packages <- function() {
e <- docker_command(c("apt", "list", "--installed"))
#remove listing line and then clean up response
install <- paste(strsplit(e, "\r", fixed = TRUE)[2:length(e)], sep = " ",
collapse = " \n")
remove_local <- gsub("\\[installed,local\\]", "", install)
install1 <- gsub("\\[32m", "", remove_local)
installed <- unlist(paste(gsub("\\[0m/now", "", install1), sep = " ",
collapse = " \n"))
installed
}

# manifest
manifest_string <- function() {
m <- paste("default", get_commit_hash_tag(), utc_time, get_linux_release(),
collapse = NULL, sep = " ")
m
}

# Docker functions
docker_start <- function() {
args <- system2("docker", args = c("run", "-i -d", docker_id, "bash"),
stdout = TRUE)
args
}

docker_stop <- function() {
system2("docker", args = c("stop", container_id))
}

docker_command <- function(arguments) {
docker <- paste("exec", "-i", container_id, "bash", "-c",
sep = " ", collapse = "")

a <- paste('"', paste(arguments, sep = " ", collapse = " "), '"',
collapse = NULL)

cmd <- system2("docker", args = c(docker, a), stdout = TRUE)
cmd
}

container_id <- docker_start()
write_all()