Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: non-root user for video recorder #2122

Merged
merged 1 commit into from
Jan 31, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
8 changes: 5 additions & 3 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -397,11 +397,13 @@ test_firefox_standalone:
# Its main purpose is to check that a video file was generated.
test_video: video hub chrome firefox edge
# Running a few tests with docker-compose to generate the videos
rm -rf ./tests/videos; mkdir -p ./tests/videos
for node in NodeChrome NodeFirefox NodeEdge ; do \
cd ./tests || true ; \
echo VIDEO_TAG=$(FFMPEG_TAG_VERSION)-$(BUILD_DATE) > .env ; \
echo TAG=$(TAG_VERSION) >> .env ; \
echo NODE=$$node >> .env ; \
echo UID=$$(id -u) >> .env ; \
if [ $$node = "NodeChrome" ] ; then \
echo BROWSER=chrome >> .env ; \
echo VIDEO_FILE_NAME=chrome_video.mp4 >> .env ; \
Expand All @@ -418,9 +420,9 @@ test_video: video hub chrome firefox edge
done
# Using ffmpeg to verify file integrity
# https://superuser.com/questions/100288/how-can-i-check-the-integrity-of-a-video-file-avi-mpeg-mp4
docker run -v $$(pwd):$$(pwd) -w $$(pwd) $(FFMPEG_BASED_NAME)/ffmpeg:$(FFMPEG_BASED_TAG) -v error -i ./tests/videos/chrome_video.mp4 -f null - 2>error.log
docker run -v $$(pwd):$$(pwd) -w $$(pwd) $(FFMPEG_BASED_NAME)/ffmpeg:$(FFMPEG_BASED_TAG) -v error -i ./tests/videos/firefox_video.mp4 -f null - 2>error.log
docker run -v $$(pwd):$$(pwd) -w $$(pwd) $(FFMPEG_BASED_NAME)/ffmpeg:$(FFMPEG_BASED_TAG) -v error -i ./tests/videos/edge_video.mp4 -f null - 2>error.log
docker run -u $$(id -u) -v $$(pwd):$$(pwd) -w $$(pwd) $(FFMPEG_BASED_NAME)/ffmpeg:$(FFMPEG_BASED_TAG) -v error -i ./tests/videos/chrome_video.mp4 -f null - 2>error.log
docker run -u $$(id -u) -v $$(pwd):$$(pwd) -w $$(pwd) $(FFMPEG_BASED_NAME)/ffmpeg:$(FFMPEG_BASED_TAG) -v error -i ./tests/videos/firefox_video.mp4 -f null - 2>error.log
docker run -u $$(id -u) -v $$(pwd):$$(pwd) -w $$(pwd) $(FFMPEG_BASED_NAME)/ffmpeg:$(FFMPEG_BASED_TAG) -v error -i ./tests/videos/edge_video.mp4 -f null - 2>error.log

chart_setup_env:
./tests/charts/make/chart_setup_env.sh
Expand Down
58 changes: 53 additions & 5 deletions Video/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,14 @@ ARG BASED_TAG
FROM $NAMESPACE/ffmpeg:$BASED_TAG
LABEL authors="Selenium <selenium-developers@googlegroups.com>"

#Arguments to define the user running the container
ARG SEL_USER=seluser
ARG SEL_GROUP=${SEL_USER}
ARG SEL_PASSWD=secret
ARG UID=1200
ARG GID=1201

USER root
#================================================
# Customize sources for apt-get
#================================================
Expand All @@ -12,29 +20,69 @@ RUN echo "deb http://archive.ubuntu.com/ubuntu jammy main universe\n" > /etc/ap

# No interactive frontend during docker build
ENV DEBIAN_FRONTEND=noninteractive \
DEBCONF_NONINTERACTIVE_SEEN=true
DEBCONF_NONINTERACTIVE_SEEN=true \
PIP_ROOT_USER_ACTION=ignore

#========================
# Supervisor
#========================
RUN apt-get -qqy update \
&& apt-get upgrade -yq \
&& apt-get -qqy --no-install-recommends install \
supervisor x11-xserver-utils x11-utils curl jq python3-pip \
supervisor x11-xserver-utils x11-utils curl jq python3-pip tzdata acl \
&& python3 -m pip install --upgrade pip \
&& python3 -m pip install --upgrade setuptools \
&& python3 -m pip install --upgrade wheel \
&& python3 -m pip install psutil \
&& rm -rf /var/lib/apt/lists/* /var/cache/apt/*

#===================
# Timezone settings
# Possible alternative: https://github.com/docker/docker/issues/3359#issuecomment-32150214
#===================
ENV TZ "UTC"
RUN ln -fs /usr/share/zoneinfo/${TZ} /etc/localtime && \
dpkg-reconfigure -f noninteractive tzdata && \
cat /etc/timezone

#======================================
# Configure environement
#======================================
ENV SEL_USER=${SEL_USER}
ENV SEL_UID=${UID}
ENV SEL_GID=${GID}
ENV HOME=/home/${SEL_USER}

#========================================
# Add normal user and group with passwordless sudo
#========================================
RUN groupadd ${SEL_GROUP} \
--gid ${SEL_GID} \
&& useradd ${SEL_USER} \
--create-home \
--gid ${SEL_GID} \
--shell /bin/bash \
--uid ${SEL_UID} \
&& usermod -a -G sudo ${SEL_USER} \
&& echo 'ALL ALL = (ALL) NOPASSWD: ALL' >> /etc/sudoers \
&& echo "${SEL_USER}:${SEL_PASSWD}" | chpasswd

#======================================
# Add Supervisor configuration files
#======================================
COPY supervisord.conf /etc
COPY entry_point.sh video.sh video_ready.py /opt/bin/
RUN cd /opt/bin && pip install psutil
COPY --chown="${SEL_UID}:${SEL_GID}" entry_point.sh video.sh video_ready.py /opt/bin/

ENV SE_VIDEO_FOLDER /videos
RUN mkdir -p /var/run/supervisor /var/log/supervisor $SE_VIDEO_FOLDER
RUN mkdir -p /var/run/supervisor /var/log/supervisor $SE_VIDEO_FOLDER \
&& chown -R ${SEL_USER}:${SEL_GROUP} /var/run/supervisor /var/log/supervisor $SE_VIDEO_FOLDER $HOME \
&& chmod -R 775 /var/run/supervisor /var/log/supervisor $SE_VIDEO_FOLDER $HOME \
&& chgrp -R 0 /var/run/supervisor /var/log/supervisor $SE_VIDEO_FOLDER $HOME \
&& chmod -R g=u /var/run/supervisor /var/log/supervisor $SE_VIDEO_FOLDER $HOME \
&& setfacl -Rdm u:${SEL_USER}:rwx,g:${SEL_GROUP}:rwx /var/run/supervisor /var/log/supervisor $SE_VIDEO_FOLDER $HOME

USER ${SEL_UID}
VOLUME ${SE_VIDEO_FOLDER}

ENTRYPOINT ["/opt/bin/entry_point.sh"]
CMD ["/opt/bin/entry_point.sh"]
Expand Down
10 changes: 10 additions & 0 deletions Video/entry_point.sh
Original file line number Diff line number Diff line change
@@ -1,4 +1,14 @@
#!/usr/bin/env bash
#==============================================
# OpenShift or non-sudo environments support
# https://docs.openshift.com/container-platform/3.11/creating_images/guidelines.html#openshift-specific-guidelines
#==============================================

if ! whoami &> /dev/null; then
if [ -w /etc/passwd ]; then
echo "${USER_NAME:-default}:x:$(id -u):0:${USER_NAME:-default} user:${HOME}:/sbin/nologin" >> /etc/passwd
fi
fi

/usr/bin/supervisord --configuration /etc/supervisord.conf &

Expand Down
1 change: 0 additions & 1 deletion Video/supervisord.conf
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ pidfile=/var/run/supervisor/supervisord.pid ; (supervisord pidfile;default sup
nodaemon=true ; (start in foreground if true;default false)
minfds=1024 ; (min. avail startup file descriptors;default 1024)
minprocs=200 ; (min. avail process descriptors;default 200)
user=root ; (default is current user, required if root)

[program:video-recording]
priority=0
Expand Down
2 changes: 1 addition & 1 deletion Video/video.sh
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
#!/bin/sh
#!/usr/bin/env bash

VIDEO_SIZE="${SE_SCREEN_WIDTH}""x""${SE_SCREEN_HEIGHT}"
DISPLAY_CONTAINER_NAME=${DISPLAY_CONTAINER_NAME}
Expand Down
4 changes: 1 addition & 3 deletions charts/selenium-grid/configs/node/nodePreStop.sh
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,7 @@ if curl -sfk ${SE_SERVER_PROTOCOL}://127.0.0.1:${SE_NODE_PORT}/status; then
curl -k -X POST ${SE_SERVER_PROTOCOL}://127.0.0.1:${SE_NODE_PORT}/se/grid/node/drain --header "${HEADERS}"
while curl -sfk ${SE_SERVER_PROTOCOL}://127.0.0.1:${SE_NODE_PORT}/status -o /tmp/preStopOutput;
do
echo "Node preStop is waiting for current session to be finished if any.\nNode details: \
.value.message: $(jq -r '.value.message' /tmp/preStopOutput || "unknown"), \
.value.node.availability: $(jq -r '.value.node.availability' /tmp/preStopOutput || "unknown")"
echo "Node preStop is waiting for current session to be finished if any. Node details: message: $(jq -r '.value.message' /tmp/preStopOutput || "unknown"), availability: $(jq -r '.value.node.availability' /tmp/preStopOutput || "unknown")"
sleep 1;
done
else
Expand Down
1 change: 0 additions & 1 deletion charts/selenium-grid/values.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -1066,7 +1066,6 @@ videoRecorder:
cpu: "1"
# SecurityContext for recorder container
securityContext:
runAsUser: 0
extraEnvironmentVariables:
# - name: SE_VIDEO_FOLDER
# value: /videos
Expand Down
2 changes: 1 addition & 1 deletion tests/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
FROM python:3.8.6-buster
FROM python:3.10-slim

WORKDIR /usr/src/app

Expand Down
3 changes: 3 additions & 0 deletions tests/docker-compose-v3-test-video.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ version: "3"
services:
browser:
image: selenium/node-${BROWSER}:${TAG}
user: ${UID}
shm_size: 2gb
depends_on:
- selenium-hub
Expand All @@ -18,6 +19,7 @@ services:

browser_video:
image: selenium/video:${VIDEO_TAG}
user: ${UID}
volumes:
- ./videos:/videos
depends_on:
Expand All @@ -28,6 +30,7 @@ services:

selenium-hub:
image: selenium/hub:${TAG}
user: ${UID}
container_name: selenium-hub
ports:
- "4442:4442"
Expand Down
Loading