Skip to content

Commit

Permalink
Merge pull request #31479 from gsmet/2.16.4-backports-2
Browse files Browse the repository at this point in the history
2.16.4 backports 2
  • Loading branch information
gsmet authored Mar 1, 2023
2 parents 62c22c1 + 770ca5a commit 2c5a92c
Show file tree
Hide file tree
Showing 27 changed files with 525 additions and 189 deletions.
8 changes: 7 additions & 1 deletion .github/ci-prerequisites.sh
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,14 @@
# alpine 3.14 dd53f409bf0b 4 months ago 5.6MB
# alpine 3.15 c4fc93816858 4 months ago 5.58MB

time docker rmi node:14 node:16 node:18 buildpack-deps:buster buildpack-deps:bullseye
time docker rmi node:14 node:16 node:18 node:14-alpine node:16-alpine node:18-alpine buildpack-deps:buster buildpack-deps:bullseye
# That is 979M
time sudo rm -rf /usr/share/dotnet
# That is 1.7G
time sudo rm -rf /usr/share/swift
# Remove Android
time sudo rm -rf /usr/local/lib/android
# Remove Haskell
time sudo rm -rf /opt/ghc
# Remove pipx
time sudo rm -rf /opt/pipx
14 changes: 14 additions & 0 deletions .github/workflows/doc-build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ on:
- 'docs/src/main/asciidoc/**'
- '.github/workflows/doc-build.yml'
pull_request:
types: [opened, synchronize, reopened]
paths:
- 'docs/src/main/asciidoc/**'
- '.github/workflows/doc-build.yml'
Expand Down Expand Up @@ -58,3 +59,16 @@ jobs:
- name: Build Docs
run: |
./mvnw -e -B --settings .github/mvn-settings.xml clean package -pl docs
- name: Store PR id
run: echo ${{ github.event.number }} > pr-id.txt

- name: Persist documentation
uses: actions/upload-artifact@v3
with:
name: documentation
path: |
pr-id.txt
docs/
target/asciidoc/generated/config/
retention-days: 1
22 changes: 22 additions & 0 deletions .github/workflows/preview-teardown.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
name: Surge.sh Preview Teardown

on:
pull_request_target:
types: [closed]

jobs:
preview-teardown:
runs-on: ubuntu-latest
steps:
- name: Teardown surge preview
id: deploy
run: npx surge teardown https://quarkus-io-pr-main-${{ steps.pr.outputs.id }}-preview.surge.sh --token ${{ secrets.SURGE_TOKEN }}
- name: Update PR status comment
uses: actions-cool/[email protected]
with:
token: ${{ secrets.GITHUB_TOKEN }}
body: |
🙈 The PR is closed and the preview is expired.
<!-- Sticky Pull Request Comment -->
body-include: '<!-- Sticky Pull Request Comment -->'
number: ${{ github.event.number }}
100 changes: 100 additions & 0 deletions .github/workflows/preview.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
name: Surge.sh Preview

on:
workflow_run:
workflows: ["Quarkus Documentation CI"]
types:
- completed

jobs:
preview:
runs-on: ubuntu-latest
if: github.event.workflow_run.event == 'pull_request' && github.event.workflow_run.conclusion == 'success'
steps:
- name: Download PR Artifact
uses: dawidd6/action-download-artifact@v2
with:
workflow: ${{ github.event.workflow_run.workflow_id }}
workflow_conclusion: success
name: documentation
path: documentation
- name: Store PR id as variable
id: pr
run: |
echo "id=$(<documentation/pr-id.txt)" >> $GITHUB_OUTPUT
rm -f pr-id.txt
- uses: actions/checkout@v3
with:
repository: quarkusio/quarkusio.github.io
path: quarkusio
- name: Sync documentation
shell: bash
run: |
chmod 755 ./documentation/docs/sync-web-site.sh
./documentation/docs/sync-web-site.sh main ../../quarkusio/
- name: Set up ruby
uses: ruby/setup-ruby@v1
with:
ruby-version: 2.7 # can change this to 2.7 or whatever version you prefer
- name: Build Jekyll site
uses: limjh16/jekyll-action-ts@v2
with:
enable_cache: true
### Enables caching. Similar to https://github.com/actions/cache.
#
format_output: false
### Uses prettier https://prettier.io to format jekyll output HTML.
#
# prettier_opts: '{ "useTabs": true }'
### Sets prettier options (in JSON) to format output HTML. For example, output tabs over spaces.
### Possible options are outlined in https://prettier.io/docs/en/options.html
#
prettier_ignore: '*'
### Ignore paths for prettier to not format those html files.
### Useful if the file is exceptionally large, so formatting it takes a while.
### Also useful if HTML compression is enabled for that file / formatting messes it up.
#
# jekyll_src: sample_site
### If the jekyll website source is not in root, specify the directory. (in this case, sample_site)
### By default, this is not required as the action searches for a _config.yml automatically.
#
gem_src: quarkusio
### By default, this is not required as the action searches for a _config.yml automatically.
### However, if there are multiple Gemfiles, the action may not be able to determine which to use.
### In that case, specify the directory. (in this case, sample_site)
###
### If jekyll_src is set, the action would automatically choose the Gemfile in jekyll_src.
### In that case this input may not be needed as well.
#
# key: ${{ runner.os }}-gems-${{ hashFiles('**/Gemfile.lock') }}
# restore-keys: ${{ runner.os }}-gems-
### In cases where you want to specify the cache key, enable the above 2 inputs
### Follows the format here https://github.com/actions/cache
#
# custom_opts: '--future'
### If you need to specify any Jekyll build options, enable the above input
### Flags accepted can be found here https://jekyllrb.com/docs/configuration/options/#build-command-options
- name: Publishing to surge for preview
id: deploy
run: npx surge ./quarkusio/_site --domain https://quarkus-io-pr-main-${{ steps.pr.outputs.id }}-preview.surge.sh --token ${{ secrets.SURGE_TOKEN }}
- name: Update PR status comment on success
uses: actions-cool/[email protected]
with:
token: ${{ secrets.GITHUB_TOKEN }}
body: |
🎊 PR Preview ${{ github.sha }} has been successfully built and deployed to https://quarkus-io-pr-main-${{ steps.pr.outputs.id }}-preview.surge.sh/version/main/guides/
<img width="300" src="https://user-images.githubusercontent.com/507615/90250366-88233900-de6e-11ea-95a5-84f0762ffd39.png">
<!-- Sticky Pull Request Comment -->
body-include: '<!-- Sticky Pull Request Comment -->'
number: ${{ steps.pr.outputs.id }}
- name: Update PR status comment on failure
if: ${{ failure() }}
uses: actions-cool/[email protected]
with:
token: ${{ secrets.GITHUB_TOKEN }}
body: |
😭 Deploy PR Preview failed.
<img width="300" src="https://user-images.githubusercontent.com/507615/90250824-4e066700-de6f-11ea-8230-600ecc3d6a6b.png">
<!-- Sticky Pull Request Comment -->
body-include: '<!-- Sticky Pull Request Comment -->'
number: ${{ steps.pr.outputs.id }}
Original file line number Diff line number Diff line change
Expand Up @@ -2,27 +2,16 @@

import static io.quarkus.deployment.pkg.steps.LinuxIDUtil.getLinuxID;

import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.LinkOption;
import java.nio.file.Path;
import java.time.Duration;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.Objects;
import java.util.Set;
import java.util.function.Predicate;
import java.util.stream.Collectors;

import org.apache.commons.lang3.SystemUtils;
import org.jboss.logging.Logger;

import io.quarkus.deployment.OutputFilter;
import io.quarkus.deployment.pkg.NativeConfig;
import io.quarkus.deployment.util.ExecUtil;
import io.quarkus.deployment.util.FileUtil;
import io.quarkus.runtime.util.ContainerRuntimeUtil;

Expand All @@ -34,14 +23,16 @@ public NativeImageBuildLocalContainerRunner(NativeConfig nativeConfig, Path outp
super(nativeConfig, outputDir);
if (SystemUtils.IS_OS_LINUX) {
ArrayList<String> containerRuntimeArgs = new ArrayList<>(Arrays.asList(baseContainerRuntimeArgs));
if (isDockerRootless(containerRuntime)) {
if (containerRuntime == ContainerRuntimeUtil.ContainerRuntime.DOCKER
&& containerRuntime.isRootless()) {
Collections.addAll(containerRuntimeArgs, "--user", String.valueOf(0));
} else {
String uid = getLinuxID("-ur");
String gid = getLinuxID("-gr");
if (uid != null && gid != null && !uid.isEmpty() && !gid.isEmpty()) {
Collections.addAll(containerRuntimeArgs, "--user", uid + ":" + gid);
if (containerRuntime == ContainerRuntimeUtil.ContainerRuntime.PODMAN) {
if (containerRuntime == ContainerRuntimeUtil.ContainerRuntime.PODMAN
&& containerRuntime.isRootless()) {
// Needed to avoid AccessDeniedExceptions
containerRuntimeArgs.add("--userns=keep-id");
}
Expand All @@ -51,63 +42,6 @@ public NativeImageBuildLocalContainerRunner(NativeConfig nativeConfig, Path outp
}
}

private static boolean isDockerRootless(ContainerRuntimeUtil.ContainerRuntime containerRuntime) {
if (containerRuntime != ContainerRuntimeUtil.ContainerRuntime.DOCKER) {
return false;
}
String dockerEndpoint = fetchDockerEndpoint();
// docker socket?
String socketUriPrefix = "unix://";
if (dockerEndpoint == null || !dockerEndpoint.startsWith(socketUriPrefix)) {
return false;
}
String dockerSocket = dockerEndpoint.substring(socketUriPrefix.length());
String currentUid = getLinuxID("-ur");
if (currentUid == null || currentUid.isEmpty() || currentUid.equals(String.valueOf(0))) {
return false;
}

int socketOwnerUid;
try {
socketOwnerUid = (int) Files.getAttribute(Path.of(dockerSocket), "unix:uid", LinkOption.NOFOLLOW_LINKS);
} catch (IOException e) {
LOGGER.infof("Owner UID lookup on '%s' failed with '%s'", dockerSocket, e.getMessage());
return false;
}
return currentUid.equals(String.valueOf(socketOwnerUid));
}

private static String fetchDockerEndpoint() {
// DOCKER_HOST environment variable overrides the active context
String dockerHost = System.getenv("DOCKER_HOST");
if (dockerHost != null) {
return dockerHost;
}

OutputFilter outputFilter = new OutputFilter();
if (!ExecUtil.execWithTimeout(new File("."), outputFilter, Duration.ofMillis(3000),
"docker", "context", "ls", "--format",
"{{- if .Current -}} {{- .DockerEndpoint -}} {{- end -}}")) {
LOGGER.debug("Docker context lookup didn't succeed in time");
return null;
}

Set<String> endpoints = outputFilter.getOutput().lines()
.filter(Objects::nonNull)
.filter(Predicate.not(String::isBlank))
.collect(Collectors.toSet());
if (endpoints.size() == 1) {
return endpoints.stream().findFirst().orElse(null);
}
if (LOGGER.isDebugEnabled()) {
LOGGER.debugf("Found too many active Docker endpoints: [%s]",
endpoints.stream()
.map(endpoint -> String.format("'%s'", endpoint))
.collect(Collectors.joining(",")));
}
return null;
}

@Override
protected List<String> getContainerRuntimeBuildArgs() {
List<String> containerRuntimeArgs = super.getContainerRuntimeBuildArgs();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,8 @@ private boolean runUpxInContainer(NativeImageBuildItem nativeImage, NativeConfig
String gid = getLinuxID("-gr");
if (uid != null && gid != null && !uid.isEmpty() && !gid.isEmpty()) {
Collections.addAll(commandLine, "--user", uid + ":" + gid);
if (containerRuntime == ContainerRuntimeUtil.ContainerRuntime.PODMAN) {
if (containerRuntime == ContainerRuntimeUtil.ContainerRuntime.PODMAN
&& containerRuntime.isRootless()) {
// Needed to avoid AccessDeniedExceptions
commandLine.add("--userns=keep-id");
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
package io.quarkus.runtime.util;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
import java.util.function.Predicate;

import org.jboss.logging.Logger;

Expand Down Expand Up @@ -59,15 +63,60 @@ private static String getVersionOutputFor(ContainerRuntime containerRuntime) {
}
}

private static boolean getRootlessStateFor(ContainerRuntime containerRuntime) {
Process rootlessProcess = null;
try {
ProcessBuilder pb = new ProcessBuilder(containerRuntime.getExecutableName(), "info")
.redirectErrorStream(true);
rootlessProcess = pb.start();
int exitCode = rootlessProcess.waitFor();
if (exitCode != 0) {
log.warnf("Command \"%s\" exited with error code %d. " +
"Rootless container runtime detection might not be reliable.",
containerRuntime.getExecutableName(), exitCode);
}
try (InputStream inputStream = rootlessProcess.getInputStream();
InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
BufferedReader bufferedReader = new BufferedReader(inputStreamReader)) {
Predicate<String> stringPredicate;
// Docker includes just "rootless" under SecurityOptions, while podman includes "rootless: <boolean>"
if (containerRuntime == ContainerRuntime.DOCKER) {
stringPredicate = line -> line.trim().equals("rootless");
} else {
stringPredicate = line -> line.trim().equals("rootless: true");
}
return bufferedReader.lines().anyMatch(stringPredicate);
}
} catch (IOException | InterruptedException e) {
// If an exception is thrown in the process, assume we are not running rootless (default docker installation)
log.debugf(e, "Failure to read info output from %s", containerRuntime.getExecutableName());
return false;
} finally {
if (rootlessProcess != null) {
rootlessProcess.destroy();
}
}
}

/**
* Supported Container runtimes
*/
public enum ContainerRuntime {
DOCKER,
PODMAN;

private final boolean rootless;

ContainerRuntime() {
this.rootless = getRootlessStateFor(this);
}

public String getExecutableName() {
return this.name().toLowerCase();
}

public boolean isRootless() {
return rootless;
}
}
}
2 changes: 1 addition & 1 deletion docs/src/main/asciidoc/qute-reference.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -665,7 +665,7 @@ And must be used in a form of `{item_hasNext}` inside a `{#for}` section with th
{#for item in items}
{item_count}. {item.name} <1>
{#if item_hasNext}<br>{/if} <2>
{/each}
{/for}
----
<1> `item_count` represents one-based index.
<2> `<br>` is only rendered if the iteration has more elements.
Expand Down
Loading

0 comments on commit 2c5a92c

Please sign in to comment.