diff --git a/frontend/package.json b/frontend/package.json
index 6141cbf94..6b401f0ea 100644
--- a/frontend/package.json
+++ b/frontend/package.json
@@ -14,6 +14,8 @@
"@fortawesome/react-fontawesome": "^0.1.16",
"@monaco-editor/react": "^4.3.1",
"@mui/material": "^5.2.3",
+ "@opuscapita/react-filemanager": "^1.1.11",
+ "@opuscapita/react-filemanager-connector-node-v1": "^1.1.11",
"@testing-library/jest-dom": "^5.11.4",
"@testing-library/react": "^11.1.0",
"@testing-library/user-event": "^12.1.10",
@@ -33,6 +35,7 @@
"react-flow-renderer": "^9.7.3",
"react-hook-form": "^7.21.2",
"react-idle-timer": "^4.6.4",
+ "react-lazylog": "^4.5.3",
"react-lottie": "^1.2.3",
"react-router-dom": "5.2.0",
"react-scripts": "5.0.0",
diff --git a/frontend/src/App.js b/frontend/src/App.js
index 70f7f0b8e..ff912f105 100644
--- a/frontend/src/App.js
+++ b/frontend/src/App.js
@@ -27,9 +27,11 @@ import Settings from './pages/Settings';
import TeamDetail from './pages/TeamDetail';
import TeamGroup from './pages/TeamGroup';
import Teams from './pages/Teams';
+import PipelineEditor from './pages/Editor';
import RemoveLogs from './pages/RemoveLogs';
import PipelinesPermission from './pages/PipelinesPermission';
import createCustomTheme from './theme';
+import UseCheckTheme from './hooks/useCheckTheme';
export const ColorModeContext = React.createContext({
toggleColorMode: () => {},
@@ -92,6 +94,7 @@ function App() {
+
@@ -109,6 +112,10 @@ function App() {
+
+
+
+
{
+ return (
+
+ } />
+
+ );
+};
+
+export default LogsDrawer;
diff --git a/frontend/src/components/DrawerContent/ShowYAMLCodeDrawer/index.jsx b/frontend/src/components/DrawerContent/ShowYAMLCodeDrawer/index.jsx
index fed289bfc..f487687a2 100644
--- a/frontend/src/components/DrawerContent/ShowYAMLCodeDrawer/index.jsx
+++ b/frontend/src/components/DrawerContent/ShowYAMLCodeDrawer/index.jsx
@@ -72,6 +72,9 @@ const ShowYAMLCodeDrawer = ({ handleClose }) => {
path={file.name}
defaultLanguage={file.language}
defaultValue={file.value}
+ options={{
+ automaticLayout: true,
+ }}
/>
diff --git a/frontend/src/components/ThemeToggle/index.jsx b/frontend/src/components/ThemeToggle/index.jsx
index a2dea1d9f..1376b9158 100644
--- a/frontend/src/components/ThemeToggle/index.jsx
+++ b/frontend/src/components/ThemeToggle/index.jsx
@@ -83,18 +83,6 @@ const ThemeToggle = (props) => {
const theme = useTheme();
const colorMode = React.useContext(ColorModeContext);
- // Retrieve color mode on load
- React.useEffect(() => {
- const themeData = localStorage.getItem('theme');
-
- if (themeData) {
- if (themeData !== theme.palette.mode) {
- colorMode.toggleColorMode();
- }
- }
- // eslint-disable-next-line react-hooks/exhaustive-deps
- }, []);
-
// Toggle color mode on click
async function handleClick() {
const color = theme.palette.mode === 'light' ? 'dark' : 'light';
diff --git a/frontend/src/hooks/useCheckTheme.jsx b/frontend/src/hooks/useCheckTheme.jsx
new file mode 100644
index 000000000..c213bb2f7
--- /dev/null
+++ b/frontend/src/hooks/useCheckTheme.jsx
@@ -0,0 +1,25 @@
+import { useTheme } from '@mui/material';
+import { useEffect } from 'react';
+import { useContext } from 'react';
+import { ColorModeContext } from '../App';
+
+const CheckTheme = () => {
+ const theme = useTheme();
+ const colorMode = useContext(ColorModeContext);
+
+ useEffect(() => {
+ const themeData = localStorage.getItem('theme');
+
+ if (themeData) {
+ if (themeData !== theme.palette.mode) {
+ colorMode.toggleColorMode();
+ }
+ }
+
+ // eslint-disable-next-line react-hooks/exhaustive-deps
+ }, []);
+
+ return null;
+};
+
+export default CheckTheme;
diff --git a/frontend/src/pages/Editor.jsx b/frontend/src/pages/Editor.jsx
new file mode 100644
index 000000000..43686e467
--- /dev/null
+++ b/frontend/src/pages/Editor.jsx
@@ -0,0 +1,216 @@
+import { faPlayCircle } from '@fortawesome/free-regular-svg-icons';
+import { faCaretDown } from '@fortawesome/free-solid-svg-icons';
+import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
+import Editor from '@monaco-editor/react';
+import { AppBar, Box, Button, Chip, Drawer, FormControl, Grid, InputLabel, MenuItem, Select, Toolbar, Typography, useTheme } from '@mui/material';
+import Navbar from '../components/Navbar';
+import { FileManager, FileNavigator } from '@opuscapita/react-filemanager';
+import connectorNodeV1 from '@opuscapita/react-filemanager-connector-node-v1';
+import { useContext, useRef, useState } from 'react';
+import LogsDrawer from '../components/DrawerContent/LogsDrawer';
+import customDrawerStyles from '../utils/drawerStyles';
+import { ColorModeContext } from '../App';
+
+const drawerWidth = 240;
+const apiOptions = {
+ ...connectorNodeV1.apiOptions,
+ apiRoot: `https://demo.core.dev.opuscapita.com/filemanager/master`, // Or you local Server Node V1 installation.
+};
+
+const PipelineEditor = () => {
+ // States
+ const [isOpenLogs, setIsOpenLogs] = useState(false);
+ const [selectedFile, setSelectedFile] = useState(FILE_MANAGER_MOCK['1']);
+ const [locations, setLocations] = useState([]);
+
+ // Ref
+ const editorRef = useRef(null);
+
+ // Hooks
+ const theme = useTheme();
+ const colorMode = useContext(ColorModeContext);
+
+ // Functions
+ const handleThemeSelect = (e) => {
+ const color = e.target.value;
+ localStorage.setItem('theme', color);
+ colorMode.toggleColorMode();
+ };
+
+ const handleEditorOnMount = (editor) => {
+ editorRef.current = editor;
+
+ window.addEventListener('resize', () => {
+ editor.layout({
+ width: 'auto',
+ height: 'auto',
+ });
+ });
+ };
+
+ return (
+
+ theme.zIndex.drawer, background: (theme) => theme.palette.background.secondary, borderBottom: 1, borderColor: 'divider' }}>
+
+
+
+
+
+
+
+
+
+ Theme
+
+
+
+
+ Dev worker
+
+
+
+
+ Draft
+
+
+
+
+
+ setLocations(resourceLocation)}
+ onResourceItemDoubleClick={({ event, number, rowData }) => console.log(rowData)}
+ onResourceItemClick={({ event, number, rowData }) => setSelectedFile({ rowData, ...FILE_MANAGER_MOCK[rowData.id] })}
+ />
+
+
+
+
+
+
+
+
+
+
+
+ Pipeline permissions {'>'} Remove Logs {'>'} Clear the logs
+
+
+ /{locations.map((loc, idx) => `${idx !== 0 ? '/' : ''}${loc.name}`)} /{selectedFile && selectedFile.name}
+
+
+
+
+
+
+
+
+
+
+
+ }
+ label="Play"
+ sx={{ mr: 0, bgcolor: 'primary.main', color: '#fff', fontWeight: 600 }}
+ />
+
+
+
+
+
+
+
+
+
+ setIsOpenLogs(!isOpenLogs)} sx={customDrawerStyles}>
+
+
+
+ );
+};
+
+const PYTHON_CODE_EXAMPLE = `import banana
+
+
+ class Monkey:
+ # Bananas the monkey can eat
+ capacity = 10
+ def eat(self, n):
+ """Make the monkey eat n bananas!"""
+ self.capacity -= n * banana.size
+
+ def feeding_frenzy(self):
+ self.eat(9.25)
+ return "Yum yum"
+
+`;
+
+const FILE_MANAGER_MOCK = {
+ 1: {
+ language: 'python',
+ name: 'monkey.py',
+ content: PYTHON_CODE_EXAMPLE,
+ },
+ L2hlbGxvLXdvcmxkLmpz: {
+ language: 'javascript',
+ name: 'hello_world.js',
+ content: `
+ const message = 'Hello world';
+
+ console.log(message)
+ `,
+ },
+};
+
+export default PipelineEditor;
diff --git a/frontend/src/theme.js b/frontend/src/theme.js
index e829e6b16..507405048 100644
--- a/frontend/src/theme.js
+++ b/frontend/src/theme.js
@@ -51,6 +51,9 @@ const createCustomTheme = (mode) => ({
pipelineOnline: '#72B842',
pipelineOnlineText: '#2E6707',
},
+ editorPageBg: {
+ main: '#F4F6F9',
+ },
}
: {
success: {
@@ -96,6 +99,9 @@ const createCustomTheme = (mode) => ({
pipelineOnline: '#72B842',
pipelineOnlineText: '#72B842',
},
+ editorPageBg: {
+ main: 'rgba(14, 25, 40, 1)',
+ },
}),
},
breakpoints: {
@@ -125,6 +131,9 @@ const createCustomTheme = (mode) => ({
fontWeight: 900,
fontSize: '1.0625rem',
},
+ h4: {
+ fontSize: '1.25rem',
+ },
subtitle1: {
fontSize: '.75rem',
},