import { useTranslation } from 'react-i18next'; import { shallowEqual, useSelector } from 'react-redux'; import classNames from 'classnames'; import React from 'react'; import propTypes from 'prop-types'; import { getRulesToFilterList, formatElapsedMs, getFilterNames, getServiceName, } from '../../../helpers/helpers'; import { FILTERED_STATUS, FILTERED_STATUS_TO_META_MAP } from '../../../helpers/constants'; import IconTooltip from './IconTooltip'; const ResponseCell = ({ elapsedMs, originalResponse, reason, response, status, upstream, rules, service_name, cached, }) => { const { t } = useTranslation(); const filters = useSelector((state) => state.filtering.filters, shallowEqual); const whitelistFilters = useSelector((state) => state.filtering.whitelistFilters, shallowEqual); const isDetailed = useSelector((state) => state.queryLogs.isDetailed); const formattedElapsedMs = formatElapsedMs(elapsedMs, t); const isBlocked = reason === FILTERED_STATUS.FILTERED_BLACK_LIST || reason === FILTERED_STATUS.FILTERED_BLOCKED_SERVICE; const isBlockedByResponse = originalResponse.length > 0 && isBlocked; const statusLabel = t(isBlockedByResponse ? 'blocked_by_cname_or_ip' : FILTERED_STATUS_TO_META_MAP[reason]?.LABEL || reason); const boldStatusLabel = {statusLabel}; const upstreamString = cached ? t('served_from_cache', { value: upstream, i: }) : upstream; const renderResponses = (responseArr) => { if (!responseArr || responseArr.length === 0) { return ''; } return
{responseArr.map((response) => { const className = classNames('white-space--nowrap', { 'overflow-break': response.length > 100, }); return
{`${response}\n`}
; })}
; }; const COMMON_CONTENT = { encryption_status: boldStatusLabel, install_settings_dns: upstreamString, elapsed: formattedElapsedMs, response_code: status, ...(service_name && { service_name: getServiceName(service_name) } ), ...(rules.length > 0 && { rule_label: getRulesToFilterList(rules, filters, whitelistFilters) } ), response_table_header: renderResponses(response), original_response: renderResponses(originalResponse), }; const content = rules.length > 0 ? Object.entries(COMMON_CONTENT) : Object.entries({ ...COMMON_CONTENT, filter: '', }); const getDetailedInfo = (reason) => { switch (reason) { case FILTERED_STATUS.FILTERED_BLOCKED_SERVICE: if (!service_name) { return formattedElapsedMs; } return getServiceName(service_name); case FILTERED_STATUS.FILTERED_BLACK_LIST: case FILTERED_STATUS.NOT_FILTERED_WHITE_LIST: return getFilterNames(rules, filters, whitelistFilters).join(', '); default: return formattedElapsedMs; } }; const detailedInfo = getDetailedInfo(reason); return (
{statusLabel}
{isDetailed &&
{detailedInfo}
}
); }; ResponseCell.propTypes = { elapsedMs: propTypes.string.isRequired, originalResponse: propTypes.array.isRequired, reason: propTypes.string.isRequired, response: propTypes.array.isRequired, status: propTypes.string.isRequired, upstream: propTypes.string.isRequired, cached: propTypes.bool.isRequired, rules: propTypes.arrayOf(propTypes.shape({ text: propTypes.string.isRequired, filter_list_id: propTypes.number.isRequired, })), service_name: propTypes.string, }; export default ResponseCell;