All files / app/assets/javascripts/pipelines/components/graph utils.js

87.23% Statements 41/47
77.27% Branches 17/22
91.67% Functions 11/12
86.67% Lines 39/45

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142                15x 10x           15x 13x   13x 2x     13x   13x 13x   13x 2x           13x       15x 252x                       15x 3x   3x                   15x 19x   19x 3x     16x       16x       16x         15x 114x 114x 114x           114x 114x     15x 10x     15x 34x       34x           34x   34x   34x                           80x                      
import { isEmpty } from 'lodash';
import Visibility from 'visibilityjs';
import { getIdFromGraphQLId } from '~/graphql_shared/utils';
import { reportToSentry } from '../../utils';
import { listByLayers } from '../parsing_utils';
import { unwrapStagesWithNeedsAndLookup } from '../unwrapping_utils';
import { beginPerfMeasure, finishPerfMeasureAndSend } from './perf_utils';
 
const addMulti = (mainPipelineProjectPath, linkedPipeline) => {
  return {
    ...linkedPipeline,
    multiproject: mainPipelineProjectPath !== linkedPipeline.project.fullPath,
  };
};
 
const calculatePipelineLayersInfo = (pipeline, componentName, metricsPath) => {
  const shouldCollectMetrics = Boolean(metricsPath);
 
  if (shouldCollectMetrics) {
    beginPerfMeasure();
  }
 
  let layers = null;
 
  try {
    layers = listByLayers(pipeline);
 
    if (shouldCollectMetrics) {
      finishPerfMeasureAndSend(layers.linksData.length, layers.numGroups, metricsPath);
    }
  } catch (err) {
    reportToSentry(componentName, err);
  }
 
  return layers;
};
 
/* eslint-disable @gitlab/require-i18n-strings */
const getQueryHeaders = (etagResource) => {
  return {
    fetchOptions: {
      method: 'GET',
    },
    headers: {
      'X-GITLAB-GRAPHQL-FEATURE-CORRELATION': 'verify/ci/pipeline-graph',
      'X-GITLAB-GRAPHQL-RESOURCE-ETAG': etagResource,
      'X-Requested-With': 'XMLHttpRequest',
    },
  };
};
 
const serializeGqlErr = (gqlError) => {
  const { locations = [], message = '', path = [] } = gqlError;
 
  return `
    ${message}.
    Locations: ${locations
      .flatMap((loc) => Object.entries(loc))
      .flat(2)
      .join(' ')}.
    Path: ${path.join(', ')}.
  `;
};
 
const serializeLoadErrors = (errors) => {
  const { gqlError, graphQLErrors, networkError, message } = errors;
 
  if (!isEmpty(graphQLErrors)) {
    return graphQLErrors.map((err) => serializeGqlErr(err)).join('; ');
  }
 
  Iif (!isEmpty(gqlError)) {
    return serializeGqlErr(gqlError);
  }
 
  Iif (!isEmpty(networkError)) {
    return `Network error: ${networkError.message}`;
  }
 
  return message;
};
 
/* eslint-enable @gitlab/require-i18n-strings */
 
const toggleQueryPollingByVisibility = (queryRef, interval = 10000) => {
  const stopStartQuery = (query) => {
    Eif (!Visibility.hidden()) {
      query.startPolling(interval);
    } else {
      query.stopPolling();
    }
  };
 
  stopStartQuery(queryRef);
  Visibility.change(stopStartQuery.bind(null, queryRef));
};
 
const transformId = (linkedPipeline) => {
  return { ...linkedPipeline, id: getIdFromGraphQLId(linkedPipeline.id) };
};
 
const unwrapPipelineData = (mainPipelineProjectPath, data) => {
  Iif (!data?.project?.pipeline) {
    return null;
  }
 
  const { pipeline } = data.project;
 
  const {
    upstream,
    downstream,
    stages: { nodes: stages },
  } = pipeline;
 
  const { stages: updatedStages, lookup } = unwrapStagesWithNeedsAndLookup(stages);
 
  return {
    ...pipeline,
    id: getIdFromGraphQLId(pipeline.id),
    stages: updatedStages,
    stagesLookup: lookup,
    upstream: upstream
      ? [upstream].map(addMulti.bind(null, mainPipelineProjectPath)).map(transformId)
      : [],
    downstream: downstream
      ? downstream.nodes.map(addMulti.bind(null, mainPipelineProjectPath)).map(transformId)
      : [],
  };
};
 
const validateConfigPaths = (value) => value.graphqlResourceEtag?.length > 0;
 
export {
  calculatePipelineLayersInfo,
  getQueryHeaders,
  serializeGqlErr,
  serializeLoadErrors,
  toggleQueryPollingByVisibility,
  unwrapPipelineData,
  validateConfigPaths,
};