Skip to content

Commit

Permalink
Merge pull request #1 from RedHatProductSecurity/OSIDB-3712
Browse files Browse the repository at this point in the history
OSIDB-3712: Create container image
  • Loading branch information
MrMarble authored Nov 25, 2024
2 parents 77f3d1e + 4c28b98 commit f7518c8
Show file tree
Hide file tree
Showing 14 changed files with 191 additions and 26 deletions.
3 changes: 3 additions & 0 deletions .github/workflows/lint.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ on:
push:
branches:
- main
pull_request:
branches:
- main

jobs:
type-check:
Expand Down
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -6,3 +6,4 @@ node_modules/
/playwright/.auth/
.vscode
.env
*.keytab
12 changes: 12 additions & 0 deletions docker/.dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
.gitignore
*.md
.git
.vscode
.github
.husky
test-results
playwright-report
user.json
Dockerfile
node_modules
.env
48 changes: 48 additions & 0 deletions docker/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
FROM registry.redhat.io/ubi9/ubi:9.5 as base

ENV LANG=C.UTF-8
ENV LC_ALL=C.UTF-8
ENV KRB5CCNAME=/tmp/cache

COPY docker/krb5.conf /etc/krb5.conf
COPY docker/install-certs.sh /install-certs.sh
COPY docker/auth.sh /auth.sh

RUN ./install-certs.sh $RH_CERT_URL \
&& yum update -y \
&& yum install -y wget git krb5-workstation \
# Playwright dependencies
libxcb libXdamage libXcursor libXext libXcomposite libXrandr \
libXi pango cairo cairo-gobject libXrender gtk3 atk gdk-pixbuf2 \
# NodeJS
&& yum module install -y nodejs:20/common \
&& yum clean all \
&& npm install -g yarn \
&& mkdir -p /krb5 \
&& chmod 755 /krb5 \
&& mkdir -p /var/lib/sss/pubconf/krb5.include.d \
&& chmod 755 /etc/krb5.conf.d \
&& chown -R 1001:0 /etc/krb5.conf.d \
&& chown 1001:0 /etc/krb5.conf \
&& chown -R 1001:0 /krb5

FROM base as build

WORKDIR /app
ENV PLAYWRIGHT_BROWSERS_PATH=0

COPY --chown=1001 package.json /app/package.json
COPY --chown=1001 yarn.lock /app/yarn.lock
COPY --chown=1001 playwright.config.ts /app/playwright.config.ts
COPY --chown=1001 tsconfig.json /app/tsconfig.json
COPY --chown=1001 docker/krb5.conf.d /etc/krb5.conf.d
COPY --chown=1001 docker/krb5.keytab /krb5/krb5.keytab

RUN yarn install --frozen-lockfile \
&& yarn playwright install chromium firefox

COPY --chown=1001 . /app

USER 1001

CMD ["/bin/sh"]
62 changes: 62 additions & 0 deletions docker/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
# OSIM UI + Kerberos Tests Container

This is the container that is used to run the tests on the CI/CD pipeline. It is based on redhat's ubi9 image and has the necessary dependencies to run the tests.

## Building the container
Before building the container, you need to prepare some files.

1. Create a `krb5.keytab` file in the `docker` directory. This file is used to authenticate with kerberos.
```bash
$ ktutil
ktutil: addent -password -p <principal> -k 1 -e aes256-cts-hmac-sha1-96 -f
ktutil: wkt krb5.keytab
ktutil: quit
```
2. Create a `crypto-policies` file in the `krb5.conf.d` directory. You should have this file in `/etc/krb5.conf.d/` or `/usr/bin/krb5-conf/` on your machine.


3. Provide the correct realm configuration in a file inside the `krb5.conf.d` directory. You should have this file in `/etc/krb5.conf` on your machine.


That should look like this:
```bash
|-- docker
| |-- krb5.conf.d
| | |-- crypto-policies
| | |-- realm # name of the file is not important
| |-- krb5.keytab
| |-- krb5.conf
| |-- Dockerfile
```

After preparing the files, you can build the container using the following command:

> [!IMPORTANT]
> Make sure to run the command from the root of the project.
> (outside of the docker folder)
```bash
podman build -t osim-ui-tests -f docker/Dockerfile --ignorefile docker/.dockerignore .
# to install RH certificates add --env RH_CERT_URL=<url> to the command
```

## Running the container
Make sure to provide the required [environment variables](/README.md#required-environment-variables) when running the container:

```bash
podman run --rm -it --env-file .env osim-ui-tests
```

## Running the tests

You need to authenticate with kerberos before running the tests. You can do this by running the script **inside the container**:

```bash
sh /auth.sh
```

After authenticating, you can run the tests using the following command:

```bash
yarn test
```
6 changes: 6 additions & 0 deletions docker/auth.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#!/bin/sh

principal="$( klist -kt /krb5/krb5.keytab | grep -Eo -m1 '\w+@[A-Z.]+' )"

kinit -k -t /krb5/krb5.keytab $principal
klist -c /tmp/cache
10 changes: 10 additions & 0 deletions docker/install-certs.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
#!/bin/sh

if [[ -z "${1}" ]]; then
echo -e "\e[1;33mWARNING: RH_CERT_URL environment variable not set, internal RH resources won't be accessible\e[0m"
else
curl "${1}/certs/Current-IT-Root-CAs.pem" -o /etc/pki/ca-trust/source/anchors/Current-IT-Root-CAs.pem
mkdir -p /etc/ipa
curl "${1}/chains/ipa-ca-chain-2015.crt" -o /etc/ipa/ipa.crt
update-ca-trust
fi
31 changes: 31 additions & 0 deletions docker/krb5.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# To opt out of the system crypto-policies configuration of krb5, remove the
# symlink at /etc/krb5.conf.d/crypto-policies which will not be recreated.
includedir /etc/krb5.conf.d/

[logging]
default = FILE:/var/log/krb5libs.log
kdc = FILE:/var/log/krb5kdc.log
admin_server = FILE:/var/log/kadmind.log

[libdefaults]
dns_lookup_realm = false
ticket_lifetime = 24h
renew_lifetime = 7d
forwardable = true
rdns = false
pkinit_anchors = FILE:/etc/pki/tls/certs/ca-bundle.crt
spake_preauth_groups = edwards25519
dns_canonicalize_hostname = fallback
qualify_shortname = ""
# default_realm = EXAMPLE.COM
default_ccache_name = KEYRING:persistent:%{uid}

[realms]
# EXAMPLE.COM = {
# kdc = kerberos.example.com
# admin_server = kerberos.example.com
# }

[domain_realm]
# .example.com = EXAMPLE.COM
# example.com = EXAMPLE.COM
2 changes: 2 additions & 0 deletions docker/krb5.conf.d/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
*
!.gitignore
8 changes: 3 additions & 5 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,6 @@
"private": true,
"devDependencies": {
"@faker-js/faker": "^9.2.0",
"@playwright/browser-chromium": "^1.48.2",
"@playwright/browser-firefox": "^1.48.2",
"@playwright/test": "^1.48.2",
"@stylistic/eslint-plugin": "^2.10.1",
"@types/eslint__js": "^8.42.3",
Expand All @@ -26,9 +24,9 @@
"undici": "^6.21.0"
},
"scripts": {
"test": "playwright test --reporter=list",
"test:chrome": "playwright test --reporter=list --project=chrome",
"test:firefox": "playwright test --reporter=list --project=firefox",
"test": "playwright test",
"test:chromium": "playwright test --project=chromium",
"test:firefox": "playwright test --project=firefox",
"dev": "playwright test --ui",
"lint": "eslint . ",
"lint:fix": "eslint . --fix",
Expand Down
2 changes: 1 addition & 1 deletion playwright.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ export default defineConfig({
forbidOnly: !!process.env.CI,
retries: process.env.CI ? 2 : 0,
workers: process.env.CI ? 1 : undefined,
reporter: 'html',
reporter: process.env.CI ? [['dot'], ['junit', {outputFile: 'results.xml'}]] : 'list',
use: {
storageState: 'playwright/.auth/user.json',
ignoreHTTPSErrors: true,
Expand Down
12 changes: 9 additions & 3 deletions playwright/helpers.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
import { Agent, setGlobalDispatcher } from 'undici';
import { GSS_MECH_OID_KRB5, initializeClient } from 'kerberos';
import { type BrowserContextOptions } from '@playwright/test';
import { readFile, writeFile } from 'fs/promises';
import { readFile, writeFile, mkdir } from 'fs/promises';
import dayjs_base from 'dayjs';
import utc_plugin from 'dayjs/plugin/utc';
import { existsSync } from 'fs';

dayjs_base.extend(utc_plugin);

Expand All @@ -20,6 +21,8 @@ interface JSONResponse {
refresh: string;
}

const storagePath = 'playwright/.auth/';

export async function authenticate(): Promise<{ refresh: string; access: string }> {
const client = await initializeClient(`HTTP@${process.env.OSIDB_URL}`, {
mechOID: GSS_MECH_OID_KRB5,
Expand All @@ -42,12 +45,15 @@ type Optional<T, K extends keyof T> = Pick<Partial<T>, K> & Omit<T, K>;
type Storage = Exclude<BrowserContextOptions['storageState'], undefined | string>;

export async function loadStorage(): Promise<Storage> {
const storage = JSON.parse(await readFile('playwright/.auth/user.json', 'utf8')) as Storage;
const storage = JSON.parse(await readFile(`${storagePath}/user.json`, 'utf8')) as Storage;
return storage;
}

export async function saveStorage(storage: Optional<Storage, 'cookies'>): Promise<void> {
await writeFile('playwright/.auth/user.json', JSON.stringify(storage, null, 2));
if (!existsSync(storagePath)) {
await mkdir(storagePath, { recursive: true });
}
await writeFile(`${storagePath}/user.json`, JSON.stringify(storage, null, 2));
}

export const { utc: dayjs } = dayjs_base;
6 changes: 3 additions & 3 deletions tests/flaw.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -55,8 +55,8 @@ test.describe('flaw creation', () => {
test.slow();
await flawCreatePage.createFlaw({ type, full: true });

await expect.soft(page.getByText('Flaw created')).toBeVisible();
await expect(page).toHaveURL(/flaws\/(?!new)\w+/);
await expect.soft(page.getByText('Flaw created')).toBeVisible({ timeout: 60_000 });
await expect(page).toHaveURL(/flaws\/(?!new)\w+/, { timeout: 60_000 });
});
});
// TODO: Add tests for specific fields and special cases.
Expand Down Expand Up @@ -88,7 +88,7 @@ test.describe('flaw edition', () => {
await flawEditPage.submitButton.click();

await expect(page.getByText('Flaw saved')).toBeVisible();
await expect(page.getByText(newTitle)).toBeVisible();
await expect(page.getByText(newTitle, { exact: true })).toBeVisible();
});

test.describe('affects', () => {
Expand Down
14 changes: 0 additions & 14 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -114,20 +114,6 @@
"@nodelib/fs.scandir" "2.1.5"
fastq "^1.6.0"

"@playwright/browser-chromium@^1.48.2":
version "1.48.2"
resolved "https://registry.yarnpkg.com/@playwright/browser-chromium/-/browser-chromium-1.48.2.tgz#7693eb46a4a5d5c7b1a5bf89b56b08b62c9963ab"
integrity sha512-TvYJ5PFaDPYNlKpvPSftBbPTnu75VdRKjoMjmkd7/P79rFIBD+v6K4wU8XR6PlAqqFdPcfLL5XXZnRwTRixbDQ==
dependencies:
playwright-core "1.48.2"

"@playwright/browser-firefox@^1.48.2":
version "1.48.2"
resolved "https://registry.yarnpkg.com/@playwright/browser-firefox/-/browser-firefox-1.48.2.tgz#ebbb4ca4ee6f5200218a856c211184dfc0a164a3"
integrity sha512-Cf0ZvgOCmmyqNbFLC2KQyV6RdTxfmuUzASnVhA7unT9xV3zK0TGv5xJZH4ACRMMdYeZ/pSK3SWyewmjMEvSo3g==
dependencies:
playwright-core "1.48.2"

"@playwright/test@^1.48.2":
version "1.48.2"
resolved "https://registry.yarnpkg.com/@playwright/test/-/test-1.48.2.tgz#87dd40633f980872283404c8142a65744d3f13d6"
Expand Down

0 comments on commit f7518c8

Please sign in to comment.