Skip to content

Commit

Permalink
Merge branch 'KelvinTegelaar:main' into main
Browse files Browse the repository at this point in the history
  • Loading branch information
luke255 authored Feb 8, 2024
2 parents 41005c4 + 9d1698e commit 3ff36f0
Show file tree
Hide file tree
Showing 42 changed files with 45,109 additions and 28,982 deletions.
6,379 changes: 3,952 additions & 2,427 deletions package-lock.json

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion public/version_latest.txt
Original file line number Diff line number Diff line change
@@ -1 +1 @@
4.9.1
5.1.1
7 changes: 6 additions & 1 deletion src/_nav.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -173,7 +173,7 @@ const _nav = [
},
{
component: CNavItem,
name: 'Geo IP Lookup',
name: 'IP Database',
to: '/tenant/tools/geoiplookup',
},
{
Expand Down Expand Up @@ -239,6 +239,11 @@ const _nav = [
name: 'Deploy CA Policies',
to: '/tenant/conditional/deploy',
},
{
component: CNavItem,
name: 'CA Vacation Mode',
to: '/tenant/conditional/deploy-vacation',
},
{
component: CNavItem,
name: 'CA Templates',
Expand Down
8 changes: 8 additions & 0 deletions src/components/forms/RFFComponents.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -137,10 +137,17 @@ export const RFFCFormInput = ({
disabled = false,
spellCheck = true,
autoFocus = false,
onChange,
}) => {
return (
<Field name={name} validate={validate}>
{({ input, meta }) => {
const handleChange = onChange
? (e) => {
input.onChange(e)
onChange(e)
}
: input.onChange
return (
<div className={className}>
{label && <CFormLabel htmlFor={name}>{label}</CFormLabel>}
Expand All @@ -155,6 +162,7 @@ export const RFFCFormInput = ({
placeholder={placeholder}
spellCheck={spellCheck}
autoFocus={autoFocus}
onChange={handleChange}
/>
<RFFCFormFeedback meta={meta} />
</div>
Expand Down
11 changes: 1 addition & 10 deletions src/components/layout/AppHeader.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,17 +16,8 @@ import {
} from '@coreui/react'
import { AppHeaderSearch } from 'src/components/header'
import { TenantSelector } from '../utilities'
import cyberdrainlogolight from 'src/assets/images/CIPP.png'
import cyberdrainlogodark from 'src/assets/images/CIPP_Dark.png'

import { FontAwesomeIcon } from '@fortawesome/react-fontawesome'
import {
faBars,
faCaretSquareLeft,
faCaretSquareRight,
faHamburger,
faStroopwafel,
} from '@fortawesome/free-solid-svg-icons'
import { faBars } from '@fortawesome/free-solid-svg-icons'
import { setCurrentTheme, setUserSettings, toggleSidebarShow } from 'src/store/features/app'
import { useMediaPredicate } from 'react-media-hook'
import { useGenericGetRequestQuery, useLoadAlertsDashQuery } from 'src/store/api/app'
Expand Down
13 changes: 7 additions & 6 deletions src/components/layout/AppSidebar.jsx

Large diffs are not rendered by default.

59 changes: 59 additions & 0 deletions src/components/tables/CellMathFormatter.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
import React from 'react'
import { CBadge, CTooltip } from '@coreui/react'
import CellBoolean from 'src/components/tables/CellBoolean.jsx'
import cellTable from './CellTable'

export function CellTip(cell, overflow = false) {
return (
<CTooltip content={String(cell)}>
<div className="celltip-content-nowrap">{String(cell)}</div>
</CTooltip>
)
}
export const cellMathFormatter =
({ col } = {}) =>
(row) => {
const evaluateCalculation = (calculation, row) => {
try {
const formattedCalculation = calculation.replace(/\b\w+(\.\w+|\[\d+\])*\b/g, (key) => {
if (!isNaN(key)) {
return parseFloat(key)
}

const path = key.split(/\.|\[(\d+)\]/).filter(Boolean) // Splits keys and array indices
let currentObject = row
for (const prop of path) {
if (currentObject && prop in currentObject) {
currentObject = currentObject[prop]
} else if (!isNaN(prop)) {
// Checks if the prop is an array index
currentObject = currentObject[parseInt(prop, 10)]
} else {
throw new Error(`Property '${prop}' not found in row`)
}
}

return parseFloat(currentObject)
})

return Number(eval(formattedCalculation))
} catch (e) {
console.error(e)
return null
}
}

const result = evaluateCalculation(col.value, row)

if (result === null) {
return 'N/A'
}

if (col.showAs === 'percentage') {
return `${result.toFixed(2)}%`
} else {
return result.toFixed(2)
}
}

export default cellMathFormatter
55 changes: 53 additions & 2 deletions src/components/tables/CippTable.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,9 @@ import PropTypes from 'prop-types'
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome'
import {
faCheck,
faClipboard,
faColumns,
faCopy,
faFileCsv,
faFilePdf,
faSearch,
Expand All @@ -38,6 +40,7 @@ import { useLazyGenericGetRequestQuery, useLazyGenericPostRequestQuery } from 's
import { ConfirmModal } from '../utilities/SharedModal'
import { debounce } from 'lodash-es'
import { useSearchParams } from 'react-router-dom'
import CopyToClipboard from 'react-copy-to-clipboard'

const FilterComponent = ({ filterText, onFilter, onClear, filterlist, onFilterPreset }) => (
<>
Expand Down Expand Up @@ -571,6 +574,14 @@ export default function CippTable({
}
filtered = filtered.map((item) => flatten(item))

let dataFlat

if (Array.isArray(data)) {
dataFlat = data.map((item) => flatten(item))
} else {
dataFlat = []
}

if (!disablePDFExport) {
if (dynamicColumns === true) {
const addColumn = (columnname) => {
Expand Down Expand Up @@ -675,7 +686,7 @@ export default function CippTable({
<CDropdownItem>
<ExportCsvButton
key="export-csv-action-all"
csvData={data}
csvData={dataFlat}
reportName={reportName}
nameText="Export All Columns"
/>
Expand Down Expand Up @@ -748,6 +759,12 @@ export default function CippTable({
filteredItems,
])
const tablePageSize = useSelector((state) => state.app.tablePageSize)
const [codeCopied, setCodeCopied] = useState(false)

const onCodeCopied = () => {
setCodeCopied(true)
setTimeout(() => setCodeCopied(false), 2000)
}

return (
<div className="ms-n3 me-n3 cipp-tablewrapper">
Expand Down Expand Up @@ -777,6 +794,20 @@ export default function CippTable({
{message.data?.Metadata?.Heading}
</CAccordionHeader>
<CAccordionBody>
<CopyToClipboard text={results} onCopy={() => onCodeCopied()}>
<CButton
color={codeCopied ? 'success' : 'info'}
className="cipp-code-copy-button"
size="sm"
variant="ghost"
>
{codeCopied ? (
<FontAwesomeIcon icon={faClipboard} />
) : (
<FontAwesomeIcon icon={faCopy} />
)}
</CButton>
</CopyToClipboard>
{results.map((line, i) => {
return <li key={i}>{line}</li>
})}
Expand All @@ -790,7 +821,27 @@ export default function CippTable({
massResults.map((message, idx) => {
const results = message.data?.Results
const displayResults = Array.isArray(results) ? results.join(', ') : results
return <li key={`message-${idx}`}>{displayResults}</li>
return (
<>
<li key={`message-${idx}`}>
{displayResults}
<CopyToClipboard text={displayResults} onCopy={() => onCodeCopied()}>
<CButton
color={codeCopied ? 'success' : 'info'}
className="cipp-code-copy-button"
size="sm"
variant="ghost"
>
{codeCopied ? (
<FontAwesomeIcon icon={faClipboard} />
) : (
<FontAwesomeIcon icon={faCopy} />
)}
</CButton>
</CopyToClipboard>
</li>
</>
)
})}
{loopRunning && (
<li>
Expand Down
55 changes: 43 additions & 12 deletions src/components/utilities/CippActionsOffcanvas.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ import {
COffcanvasTitle,
CSpinner,
} from '@coreui/react'
import { CippOffcanvas, ModalService } from 'src/components/utilities'
import { CippCodeBlock, CippOffcanvas, ModalService } from 'src/components/utilities'
import { CippOffcanvasPropTypes } from 'src/components/utilities/CippOffcanvas'
import { CippOffcanvasTable } from 'src/components/tables'
import { useLazyGenericGetRequestQuery, useLazyGenericPostRequestQuery } from 'src/store/api/app'
Expand All @@ -38,6 +38,34 @@ export default function CippActionsOffcanvas(props) {
}
const handleModal = useCallback(
(modalMessage, modalUrl, modalType = 'GET', modalBody, modalInput, modalDropdown) => {
const handlePostConfirm = () => {
const selectedValue = inputRef.current.value
console.log(inputRef)
let additionalFields = {}

if (inputRef.current.nodeName === 'SELECT') {
const selectedItem = dropDownInfo.data.find(
(item) => item[modalDropdown.valueField] === selectedValue,
)
if (selectedItem && modalDropdown.addedField) {
Object.keys(modalDropdown.addedField).forEach((key) => {
additionalFields[key] = selectedItem[modalDropdown.addedField[key]]
})
}
}
const postRequestBody = {
...modalBody,
...additionalFields,
input: selectedValue,
}
// Send the POST request
genericPostRequest({
path: modalUrl,
values: postRequestBody,
})
}

// Modal setup for GET, codeblock, and other types
if (modalType === 'GET') {
ModalService.confirm({
body: (
Expand Down Expand Up @@ -82,12 +110,7 @@ export default function CippActionsOffcanvas(props) {
</div>
),
title: 'Confirm',
onConfirm: () => [
genericPostRequest({
path: modalUrl,
values: { ...modalBody, ...{ input: inputRef.current.value } },
}),
],
onConfirm: handlePostConfirm,
})
}
},
Expand All @@ -99,7 +122,6 @@ export default function CippActionsOffcanvas(props) {
modalContent,
],
)

useEffect(() => {
if (dropDownInfo.isFetching) {
handleModal(
Expand Down Expand Up @@ -282,14 +304,23 @@ export default function CippActionsOffcanvas(props) {
<CSpinner>Loading</CSpinner>
</CCallout>
)}
{postResults.isSuccess && <CCallout color="info">{postResults.data?.Results}</CCallout>}
{postResults.isSuccess && (
<CippCodeBlock
code={postResults.data?.Results}
callout={true}
calloutCopyValue={getResults.data?.Results}
/>
)}
{postResults.isError && (
<CCallout color="danger">Could not connect to API: {postResults.error.message}</CCallout>
)}
{getResults.isSuccess && (
<CCallout color={getResults.data?.colour ? getResults.data?.colour : 'info'}>
{getResults.data?.Results}
</CCallout>
<CippCodeBlock
code={getResults.data?.Results}
callout={true}
calloutColour={getResults.data?.colour ? getResults.data?.colour : 'info'}
calloutCopyValue={getResults.data?.Results}
/>
)}
{getResults.isError && (
<CCallout color="danger">Could not connect to API: {getResults.error.message}</CCallout>
Expand Down
33 changes: 19 additions & 14 deletions src/components/utilities/CippCodeBlock.jsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import React, { useState } from 'react'
import PropTypes from 'prop-types'
import { CopyToClipboard } from 'react-copy-to-clipboard'
import { CButton } from '@coreui/react'
import { CButton, CCallout } from '@coreui/react'
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome'
import { faCopy, faClipboard } from '@fortawesome/free-regular-svg-icons'
import SyntaxHighlighter from 'react-syntax-highlighter'
Expand All @@ -13,6 +13,9 @@ function CippCodeBlock({
showLineNumbers = true,
startingLineNumber,
wrapLongLines = true,
callout = false,
calloutColour = 'info',
calloutCopyValue = false,
}) {
const [codeCopied, setCodeCopied] = useState(false)

Expand All @@ -23,7 +26,7 @@ function CippCodeBlock({

return (
<div className="cipp-code">
<CopyToClipboard text={code} onCopy={() => onCodeCopied()}>
<CopyToClipboard text={calloutCopyValue || code} onCopy={() => onCodeCopied()}>
<CButton
color={codeCopied ? 'success' : 'info'}
className="cipp-code-copy-button"
Expand All @@ -33,18 +36,20 @@ function CippCodeBlock({
{codeCopied ? <FontAwesomeIcon icon={faClipboard} /> : <FontAwesomeIcon icon={faCopy} />}
</CButton>
</CopyToClipboard>

<SyntaxHighlighter
language={language}
showLineNumbers={showLineNumbers}
startingLineNumber={startingLineNumber}
wrapLongLines={wrapLongLines}
wrapLines={wrapLongLines}
style={atomOneDark}
className="cipp-code-block"
>
{code}
</SyntaxHighlighter>
{callout && <CCallout color={calloutColour}>{code}</CCallout>}
{!callout && (
<SyntaxHighlighter
language={language}
showLineNumbers={showLineNumbers}
startingLineNumber={startingLineNumber}
wrapLongLines={wrapLongLines}
wrapLines={wrapLongLines}
style={atomOneDark}
className="cipp-code-block"
>
{code}
</SyntaxHighlighter>
)}
</div>
)
}
Expand Down
Loading

0 comments on commit 3ff36f0

Please sign in to comment.