Skip to content

Commit

Permalink
Merge pull request #527 from gemini-testing/HERMIONE-1330.merge_repor…
Browse files Browse the repository at this point in the history
…ts_send_headers

feat(merge-reports): ability to pass headers for databaseUrls.json files
  • Loading branch information
DudaGod authored Jan 17, 2024
2 parents 8b4a458 + a367122 commit e6db7b9
Show file tree
Hide file tree
Showing 8 changed files with 239 additions and 160 deletions.
13 changes: 11 additions & 2 deletions docs/en/html-reporter-commands.md
Original file line number Diff line number Diff line change
Expand Up @@ -83,14 +83,23 @@ The command accepts paths to database files or to `databaseUrls.json` files from

### Usage

The `merge-reports` command supports the following required option:
The `merge-reports` command supports the following options:

| **Option** | **Description** |
| --------- | ------------ |
| -d, --destination <folder> | The path to the folder where you want to save the final report. |
| -h, --header <header> | Http header for databaseUrls.json files from source paths. |

Usage example:

```bash
npx hermione merge-reports path-to-database.db path-to-databaseUrls.json -d dest-report
npx hermione merge-reports path-to-database.db path-to-databaseUrls.json -d dest-report -h foo=bar
```

Http headers can also be send using the environment variable - `html_reporter_headers` (has a higher priority than the cli option `--header'). Example:

```bash
html_reporter_headers='{"foo":"bar"}' npx hermione merge-reports path-to-database.db path-to-databaseUrls.json -d dest-report -h baz=qux
```

As a result, the `path-to-databaseUrls.json` will be requested with headers: `{foo: 'bar', baz: 'qux'}`.
13 changes: 11 additions & 2 deletions docs/ru/html-reporter-commands.md
Original file line number Diff line number Diff line change
Expand Up @@ -83,14 +83,23 @@ npx hermione remove-unused-screens --help

### Использование

Команда `merge-reports` поддерживает следующую обязательную опцию:
Команда `merge-reports` поддерживает следующие опции:

| **Опция** | **Описание** |
| --------- | ------------ |
| -d, --destination <folder> | Путь к папке, в которую нужно сохранить итоговый отчет. |
| -h, --header <header> | Http-хедер для загрузки databaseUrls.json из переданных исходных отчетов. |

Пример использования:

```bash
npx hermione merge-reports path-to-database.db path-to-databaseUrls.json -d dest-report
npx hermione merge-reports path-to-database.db path-to-databaseUrls.json -d dest-report -h foo=bar
```

Http-хедеры можно так же передавать с помощью переменной окружения - `html_reporter_headers` (имеет приоритет выше, чем cli-опция `--header`). Пример:

```bash
html_reporter_headers='{"foo":"bar"}' npx hermione merge-reports path-to-database.db path-to-databaseUrls.json -d dest-report -h baz=qux
```

В итоге `path-to-databaseUrls.json` будет запрошен с хедерами: `{foo: 'bar', baz: 'qux'}`.
8 changes: 4 additions & 4 deletions docs/ru/html-reporter-setup.md
Original file line number Diff line number Diff line change
Expand Up @@ -133,7 +133,7 @@ module.exports = {

По умолчанию «не сохранять»: `false`.

Любой плагин гермионы может добавить какие-либо подробности в объект ошибки при её возникновении. Эти подробности могут помочь пользователю в отладке проблем, которые возникли в тесте. Html-reporter сохраняет эти детали в папке `error-details` в файле с именем: `<хэш от полного названия теста>-<браузер>_<номер ретрая>_<временная метка>.json`.
Любой плагин гермионы может добавить какие-либо подробности в объект ошибки при её возникновении. Эти подробности могут помочь пользователю в отладке проблем, которые возникли в тесте. Html-reporter сохраняет эти детали в папке `error-details` в файле с именем: `<хэш от полного названия теста>-<браузер>_<номер ретрая>_<временная метка>.json`.

Под стектрейсом html-reporter добавляет раздел `Error details` со ссылкой `<title>`, указывающей на json-файл. Пользователь может открыть этот файл либо в браузере, либо в любой IDE.

Expand Down Expand Up @@ -238,7 +238,7 @@ throw err;
{
'<опция-1>': 'значение опции 1',
'<опция-2>': 'значение опции 2',
// и т. д.
// и т. д.
}
```

Expand Down Expand Up @@ -275,7 +275,7 @@ throw err;

### plugins

Список плагинов с их настройками.
Список плагинов с их настройками.

Смотрите подробнее в разделе «[Плагины для отчета](./html-reporter-plugins.md)».

Expand Down Expand Up @@ -304,7 +304,7 @@ customScripts: [

Также в интерфейсе Яндекс.Метрики необходимо перейти в разделе настроек на вкладку _«Счетчик»_, нажать кнопку _«Скопировать»_ и вставить код счетчика в поле [customScripts](#customscripts).

С помощью метрики вы сможете узнать как разработчики взаимодействуют с вашим отчетом и с какого рода проблемами они сталкиваются.
С помощью метрики вы сможете узнать как разработчики взаимодействуют с вашим отчетом и с какого рода проблемами они сталкиваются.

Отчет поддерживает следующие [цели для метрики][yandex-metrika-goals]:

Expand Down
9 changes: 8 additions & 1 deletion lib/cli-commands/merge-reports.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,19 @@ module.exports = (program, pluginConfig, hermione) => {
.allowUnknownOption()
.description('merge reports')
.option('-d, --destination <destination>', 'path to directory with merged report', pluginConfig.path)
.option('-h, --header <header>', 'http header for databaseUrls.json files from source paths', collect, [])
.action(async (paths, options) => {
try {
await mergeReports(pluginConfig, hermione, paths, options);
const {destination: destPath, header: headers} = options;

await mergeReports(pluginConfig, hermione, paths, {destPath, headers});
} catch (err) {
logError(err);
process.exit(1);
}
});
};

function collect(newValue, array = []) {
return array.concat(newValue);
}
38 changes: 29 additions & 9 deletions lib/merge-reports/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,24 @@ const _ = require('lodash');
const serverUtils = require('../server-utils');
const dbServerUtils = require('../db-utils/server');

module.exports = async (pluginConfig, hermione, srcPaths, {destination: destPath}) => {
validateOpts(srcPaths, destPath);
module.exports = async (pluginConfig, hermione, srcPaths, {destPath, headers}) => {
validateOpts({srcPaths, destPath, headers});

const resolvedUrls = await tryResolveUrls(srcPaths);
let headersFromEnv;

try {
headersFromEnv = JSON.parse(process.env.html_reporter_headers || '{}');
} catch (e) {
throw new Error(`Couldn't parse headers from "html_reporter_headers" env variable: ${e.message}`);
}

const headersFromCli = headers.reduce((acc, header) => {
const [key, ...values] = header.split('=');
return _.set(acc, key, values.join('='));
}, {});
const parsedHeaders = {...headersFromCli, ...headersFromEnv};

const resolvedUrls = await tryResolveUrls(srcPaths, parsedHeaders);

await Promise.all([
serverUtils.saveStaticFilesToReportDir(hermione.htmlReporter, pluginConfig, destPath),
Expand All @@ -18,19 +32,25 @@ module.exports = async (pluginConfig, hermione, srcPaths, {destination: destPath
await hermione.htmlReporter.emitAsync(hermione.htmlReporter.events.REPORT_SAVED, {reportPath: destPath});
};

function validateOpts(srcPaths, destPath) {
function validateOpts({srcPaths, destPath, headers}) {
if (!srcPaths.length) {
throw new Error('Nothing to merge, no source reports are passed');
}

if (srcPaths.includes(destPath)) {
throw new Error(`Destination report path: ${destPath}, exists in source report paths`);
}

for (const header of headers) {
if (!header.includes('=')) {
throw new Error(`Header must has key and value separated by "=" symbol, but got "${header}"`);
}
}
}

async function tryResolveUrls(urls) {
async function tryResolveUrls(urls, headers) {
const resolvedUrls = [];
const results = await Promise.all(urls.map(tryResolveUrl));
const results = await Promise.all(urls.map(url => tryResolveUrl(url, headers)));

results.forEach(({jsonUrls, dbUrls}) => {
resolvedUrls.push(...jsonUrls.concat(dbUrls));
Expand All @@ -39,22 +59,22 @@ async function tryResolveUrls(urls) {
return resolvedUrls;
}

async function tryResolveUrl(url) {
async function tryResolveUrl(url, headers) {
const jsonUrls = [];
const dbUrls = [];

if (serverUtils.isDbUrl(url)) {
dbUrls.push(url);
} else if (serverUtils.isJsonUrl(url)) {
try {
const {data} = await axios.get(url);
const {data} = await axios.get(url, {headers});
const currentDbUrls = _.get(data, 'dbUrls', []);
const currentJsonUrls = _.get(data, 'jsonUrls', []);

const preparedDbUrls = dbServerUtils.prepareUrls(currentDbUrls, url);
const preparedJsonUrls = dbServerUtils.prepareUrls(currentJsonUrls, url);

const responses = await Promise.all(preparedJsonUrls.map(tryResolveUrl));
const responses = await Promise.all(preparedJsonUrls.map(url => tryResolveUrl(url, headers)));

dbUrls.push(...preparedDbUrls);

Expand Down
Loading

0 comments on commit e6db7b9

Please sign in to comment.