UI WIP
This commit is contained in:
parent
04bfa594cd
commit
843acfaa89
@ -28,15 +28,6 @@ function App() {
|
||||
});
|
||||
|
||||
|
||||
const testButton = () => {
|
||||
client?.publish({
|
||||
"destination": "/app/items",
|
||||
"body": "Potato"
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
|
||||
useEffect(() => {
|
||||
// Kjør din funksjon her når komponenten lastes inn for første gang
|
||||
// Sjekk om cursor er null
|
||||
@ -56,16 +47,26 @@ function App() {
|
||||
return (
|
||||
<ThemeProvider theme={theme}>
|
||||
<CssBaseline />
|
||||
<BrowserRouter>
|
||||
<Box sx={{ marginTop: "70px", minHeight: "50vh", width: "100%", display: "block", overflow: "hidden" }}>
|
||||
<button onClick={testButton}>Click me</button>
|
||||
<Routes>
|
||||
<Route path='/files' element={<ExplorePage />} />
|
||||
<Route path='/' element={<LaunchPage />} />
|
||||
</Routes>
|
||||
</Box>
|
||||
<Footer />
|
||||
</BrowserRouter>
|
||||
<Box sx={{
|
||||
height: 70,
|
||||
backgroundColor: theme.palette.action.selected
|
||||
}}>
|
||||
</Box>
|
||||
<Box sx={{
|
||||
display: "block",
|
||||
maxHeight: window.screen.height - 70,
|
||||
height: window.screen.height - 70,
|
||||
width: "100vw",
|
||||
maxWidth: "100vw"
|
||||
}}>
|
||||
<BrowserRouter>
|
||||
<Routes>
|
||||
<Route path='/files' element={<ExplorePage />} />
|
||||
<Route path='/' element={<LaunchPage />} />
|
||||
</Routes>
|
||||
<Footer />
|
||||
</BrowserRouter>
|
||||
</Box>
|
||||
</ThemeProvider>
|
||||
);
|
||||
}
|
||||
|
||||
22
UI/web/src/app/features/UxTc.tsx
Normal file
22
UI/web/src/app/features/UxTc.tsx
Normal file
@ -0,0 +1,22 @@
|
||||
import { Typography } from "@mui/material";
|
||||
|
||||
|
||||
export function UnixTimestamp({ timestamp }: { timestamp?: number }) {
|
||||
if (!timestamp) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const date = new Date(timestamp);
|
||||
const day = date.getDate();
|
||||
const month = date.toLocaleString('default', { month: 'short' });
|
||||
const year = date.getFullYear();
|
||||
const hours = date.getHours().toString().padStart(2, '0');
|
||||
const minutes = date.getMinutes().toString().padStart(2, '0');
|
||||
return (
|
||||
<>
|
||||
<Typography variant='body1'>
|
||||
{day}.{month}.{year} {hours}.{minutes}
|
||||
</Typography>
|
||||
</>
|
||||
)
|
||||
}
|
||||
133
UI/web/src/app/features/table.tsx
Normal file
133
UI/web/src/app/features/table.tsx
Normal file
@ -0,0 +1,133 @@
|
||||
import { useEffect, useState } from "react";
|
||||
import { useSelector } from "react-redux";
|
||||
import { RootState } from "../store";
|
||||
import IconArrowUp from '@mui/icons-material/ArrowUpward';
|
||||
import IconArrowDown from '@mui/icons-material/ArrowDownward';
|
||||
import { Table, TableHead, TableRow, TableCell, TableBody, Typography, Box, useTheme, TableContainer } from "@mui/material";
|
||||
|
||||
export interface TablePropetyConfig {
|
||||
label: string
|
||||
accessor: string
|
||||
}
|
||||
|
||||
export interface TableCellCustomizer<T> {
|
||||
(accessor: string, data: T): JSX.Element | null
|
||||
}
|
||||
|
||||
type NullableTableRowActionEvents<T> = TableRowActionEvents<T> | null;
|
||||
export interface TableRowActionEvents<T> {
|
||||
click: (row: T) => void;
|
||||
doubleClick: (row: T) => void;
|
||||
contextMenu: (row: T) => void;
|
||||
}
|
||||
|
||||
|
||||
export default function SimpleTable<T>({ items, columns, customizer, onRowClickedEvent }: { items: Array<T>, columns: Array<TablePropetyConfig>, customizer?: TableCellCustomizer<T>, onRowClickedEvent?: TableRowActionEvents<T> }) {
|
||||
const muiTheme = useTheme();
|
||||
|
||||
const [contextMenuVisible, setContextMenuVisible] = useState(false);
|
||||
const [contextMenuPosition, setContextMenuPosition] = useState({ top: 0, left: 0 });
|
||||
|
||||
const [order, setOrder] = useState<'asc' | 'desc'>('asc');
|
||||
const [orderBy, setOrderBy] = useState<string>('');
|
||||
const [selectedRow, setSelectedRow] = useState<T | null>(null);
|
||||
|
||||
const tableRowSingleClicked = (row: T | null) => {
|
||||
setSelectedRow(row);
|
||||
if (row && onRowClickedEvent) {
|
||||
onRowClickedEvent.click(row);
|
||||
}
|
||||
}
|
||||
const tableRowDoubleClicked = (row: T | null) => {
|
||||
setSelectedRow(row);
|
||||
if (row && onRowClickedEvent) {
|
||||
onRowClickedEvent.doubleClick(row);
|
||||
}
|
||||
}
|
||||
|
||||
const handleSort = (property: string) => {
|
||||
const isAsc = orderBy === property && order === 'asc';
|
||||
setOrder(isAsc ? 'desc' : 'asc');
|
||||
setOrderBy(property);
|
||||
};
|
||||
|
||||
const compareValues = (a: any, b: any, orderBy: string) => {
|
||||
if (typeof a[orderBy] === 'string') {
|
||||
return a[orderBy].localeCompare(b[orderBy]);
|
||||
} else if (typeof a[orderBy] === 'number') {
|
||||
return a[orderBy] - b[orderBy];
|
||||
}
|
||||
return 0;
|
||||
};
|
||||
|
||||
const sortedData = items.slice().sort((a, b) => {
|
||||
if (order === 'asc') {
|
||||
return compareValues(a, b, orderBy);
|
||||
} else {
|
||||
return compareValues(b, a, orderBy);
|
||||
}
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
handleSort(columns[0].accessor)
|
||||
}, [])
|
||||
|
||||
|
||||
return (
|
||||
<Box sx={{
|
||||
display: "flex",
|
||||
flexDirection: "column", // Bruk column-fleksretning
|
||||
height: "100%",
|
||||
overflow: "hidden"
|
||||
}}>
|
||||
<TableContainer sx={{
|
||||
flex: 1,
|
||||
overflowY: "auto",
|
||||
position: "relative", // Legg til denne linjen for å justere layout
|
||||
maxHeight: "100%" // Legg til denne linjen for å begrense høyden
|
||||
}}>
|
||||
<Table>
|
||||
<TableHead sx={{
|
||||
position: "sticky",
|
||||
top: 0,
|
||||
backgroundColor: muiTheme.palette.background.paper,
|
||||
}}>
|
||||
<TableRow>
|
||||
{columns.map((column) => (
|
||||
<TableCell key={column.accessor} onClick={() => handleSort(column.accessor)} sx={{ cursor: "pointer" }}>
|
||||
<Box display="flex">
|
||||
{orderBy === column.accessor ?
|
||||
(order === "asc" ? (<IconArrowDown />) : (<IconArrowUp />)) : (
|
||||
<IconArrowDown sx={{ color: "transparent" }} />
|
||||
)
|
||||
}
|
||||
<Typography>{column.label}</Typography>
|
||||
</Box>
|
||||
</TableCell>
|
||||
))}
|
||||
</TableRow>
|
||||
</TableHead>
|
||||
<TableBody sx={{
|
||||
overflowY: "scroll"
|
||||
}}>
|
||||
{sortedData?.map((row: T, rowIndex: number) => (
|
||||
<TableRow key={rowIndex}
|
||||
onClick={() => tableRowSingleClicked(row)}
|
||||
onDoubleClick={() => tableRowDoubleClicked(row)}
|
||||
style={{ cursor: "pointer", backgroundColor: selectedRow === row ? muiTheme.palette.action.selected : '' }}
|
||||
>
|
||||
{columns.map((column) => (
|
||||
<TableCell key={column.accessor}>
|
||||
{customizer && customizer(column.accessor, row) !== null
|
||||
? customizer(column.accessor, row)
|
||||
: <Typography variant='body1'>{(row as any)[column.accessor]}</Typography>}
|
||||
</TableCell>
|
||||
))}
|
||||
</TableRow>
|
||||
))}
|
||||
</TableBody>
|
||||
</Table>
|
||||
</TableContainer>
|
||||
</Box>
|
||||
)
|
||||
}
|
||||
180
UI/web/src/app/page/ExplorePage.tsx
Normal file
180
UI/web/src/app/page/ExplorePage.tsx
Normal file
@ -0,0 +1,180 @@
|
||||
import { useEffect } from 'react';
|
||||
import { UnixTimestamp } from '../features/UxTc';
|
||||
import { Box, Button, Typography, useTheme } from '@mui/material';
|
||||
import { useDispatch, useSelector } from 'react-redux';
|
||||
import { RootState } from '../store';
|
||||
import SimpleTable, { TableCellCustomizer, TablePropetyConfig, TableRowActionEvents } from '../features/table';
|
||||
import { useStompClient } from 'react-stomp-hooks';
|
||||
import { useWsSubscription } from '../ws/subscriptions';
|
||||
import { updateItems } from '../store/explorer-slice';
|
||||
import FolderIcon from '@mui/icons-material/Folder';
|
||||
import IconForward from '@mui/icons-material/ArrowForwardIosRounded';
|
||||
import IconHome from '@mui/icons-material/Home';
|
||||
import { ExplorerItem, ExplorerCursor, ExplorerItemType } from '../../types';
|
||||
|
||||
|
||||
const createTableCell: TableCellCustomizer<ExplorerItem> = (accessor, data) => {
|
||||
switch (accessor) {
|
||||
case "created": {
|
||||
if (typeof data[accessor] === "number") {
|
||||
const timestampObject = { timestamp: data[accessor] as number }; // Opprett et objekt med riktig struktur
|
||||
return UnixTimestamp(timestampObject);
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
case "extension": {
|
||||
if (data[accessor] === null) {
|
||||
return <FolderIcon sx={{ margin: 1 }} />
|
||||
} else {
|
||||
return <Typography>{data[accessor]}</Typography>
|
||||
}
|
||||
}
|
||||
default: return null;
|
||||
}
|
||||
};
|
||||
|
||||
const columns: Array<TablePropetyConfig> = [
|
||||
{ label: "Name", accessor: "name" },
|
||||
{ label: "Format", accessor: "extension" },
|
||||
{ label: "Created", accessor: "created" },
|
||||
];
|
||||
|
||||
|
||||
|
||||
function getPartFor(path: string, index: number): string | null {
|
||||
if (path.match(/\//)) {
|
||||
return path.split(/\//, index + 1).join("/");
|
||||
} else if (path.match(/\\/)) {
|
||||
return path.split(/\\/, index + 1).join("\\");
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
function getSegmentedNaviagatablePath(navigateTo: (path: string | null) => void, path: string | null): JSX.Element {
|
||||
console.log(path);
|
||||
const parts: Array<string> = path?.split(/\\|\//).map((value: string, index: number) => value.replaceAll(":", "")) ?? [];
|
||||
const segments = parts.map((name: string, index: number) => {
|
||||
return (
|
||||
<Box key={index} sx={{
|
||||
display: "flex",
|
||||
flexDirection: "row",
|
||||
alignItems: "center"
|
||||
}}>
|
||||
<Button sx={{
|
||||
borderRadius: 5
|
||||
}} onClick={() => navigateTo(getPartFor(path!, index))}>
|
||||
<Typography>{name}</Typography>
|
||||
</Button>
|
||||
{index < parts.length - 1 && <IconForward fontSize="small" />}
|
||||
</Box>
|
||||
)
|
||||
});
|
||||
|
||||
|
||||
console.log(parts)
|
||||
return (
|
||||
<Box display="flex">
|
||||
{segments}
|
||||
</Box>
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
export default function ExplorePage() {
|
||||
const muiTheme = useTheme();
|
||||
const dispatch = useDispatch();
|
||||
const client = useStompClient();
|
||||
const cursor = useSelector((state: RootState) => state.explorer)
|
||||
|
||||
const navigateTo = (path: string | null) => {
|
||||
console.log(path)
|
||||
if (path) {
|
||||
client?.publish({
|
||||
destination: "/app/explorer/navigate",
|
||||
body: path
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
const onItemSelectedEvent: TableRowActionEvents<ExplorerItem> = {
|
||||
click: (row: ExplorerItem) => null,
|
||||
doubleClick: (row: ExplorerItem) => {
|
||||
console.log(row);
|
||||
if (row.type === "FOLDER") {
|
||||
navigateTo(row.path);
|
||||
}
|
||||
},
|
||||
contextMenu: (row: ExplorerItem) => null
|
||||
}
|
||||
|
||||
const onHomeClick = () => {
|
||||
client?.publish({
|
||||
destination: "/app/explorer/home"
|
||||
})
|
||||
}
|
||||
|
||||
useWsSubscription<ExplorerCursor>("/topic/explorer/go", (response) => {
|
||||
dispatch(updateItems(response))
|
||||
});
|
||||
|
||||
|
||||
useEffect(() => {
|
||||
if (cursor)
|
||||
|
||||
|
||||
// Kjør din funksjon her når komponenten lastes inn for første gang
|
||||
// Sjekk om cursor er null
|
||||
if (cursor.path === null && client !== null) {
|
||||
console.log(cursor)
|
||||
// Kjør din funksjon her når cursor er null og client ikke er null
|
||||
client?.publish({
|
||||
destination: "/app/explorer/home"
|
||||
});
|
||||
|
||||
// Alternativt, du kan dispatche en Redux handling her
|
||||
// dispatch(fetchDataAction()); // Eksempel på å dispatche en handling
|
||||
}
|
||||
}, [cursor, client, dispatch]);
|
||||
|
||||
|
||||
return (
|
||||
<Box display="block">
|
||||
<Box sx={{
|
||||
height: 50,
|
||||
width: "100%",
|
||||
maxHeight: "100%",
|
||||
overflow: "hidden",
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
justifyContent: "flex-start",
|
||||
backgroundColor: muiTheme.palette.background.paper
|
||||
}}>
|
||||
<Box sx={{
|
||||
display: "flex",
|
||||
}}>
|
||||
<Button onClick={onHomeClick} sx={{
|
||||
borderRadius: 5
|
||||
}}>
|
||||
<IconHome />
|
||||
</Button>
|
||||
<Box sx={{
|
||||
borderRadius: 5,
|
||||
backgroundColor: muiTheme.palette.divider
|
||||
}}>
|
||||
{getSegmentedNaviagatablePath(navigateTo, cursor?.path)}
|
||||
</Box>
|
||||
</Box>
|
||||
</Box>
|
||||
<Box sx={{
|
||||
display: "block",
|
||||
height: "calc(100% - 120px)",
|
||||
overflow: "hidden",
|
||||
position: "absolute",
|
||||
width: "100%"
|
||||
}}>
|
||||
<SimpleTable items={cursor?.items ?? []} columns={columns} customizer={createTableCell} onRowClickedEvent={onItemSelectedEvent} />
|
||||
</Box>
|
||||
</Box>
|
||||
)
|
||||
}
|
||||
75
UI/web/src/app/page/LaunchPage.tsx
Normal file
75
UI/web/src/app/page/LaunchPage.tsx
Normal file
@ -0,0 +1,75 @@
|
||||
import { useDispatch, useSelector } from "react-redux";
|
||||
import SimpleTable, { TableCellCustomizer, TablePropetyConfig } from "../features/table"
|
||||
import { RootState } from "../store";
|
||||
import { useEffect } from "react";
|
||||
import { useStompClient } from "react-stomp-hooks";
|
||||
import { Box, Button, useTheme } from "@mui/material";
|
||||
import IconRefresh from '@mui/icons-material/Refresh'
|
||||
|
||||
|
||||
const columns: Array<TablePropetyConfig> = [
|
||||
{ label: "Title", accessor: "givenTitle" },
|
||||
{ label: "Type", accessor: "determinedType" },
|
||||
{ label: "Collection", accessor: "givenCollection" },
|
||||
{ label: "Encoded", accessor: "eventEncoded" }
|
||||
];
|
||||
|
||||
|
||||
|
||||
export default function LaunchPage() {
|
||||
const dispatch = useDispatch();
|
||||
const muiTheme = useTheme();
|
||||
const client = useStompClient();
|
||||
const simpleList = useSelector((state: RootState) => state.kafkaComposedFlat)
|
||||
useEffect(() => {
|
||||
if (simpleList.items.filter((item) => item.encodingTimeLeft !== null).length > 0) {
|
||||
columns.push({
|
||||
label: "Completion",
|
||||
accessor: "encodingTimeLeft"
|
||||
})
|
||||
}
|
||||
}, [simpleList, dispatch])
|
||||
|
||||
const onRefresh = () => {
|
||||
client?.publish({
|
||||
"destination": "/app/items",
|
||||
"body": "Potato"
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
return (
|
||||
<Box display="block">
|
||||
<Box sx={{
|
||||
height: 50,
|
||||
width: "100%",
|
||||
maxHeight: "100%",
|
||||
overflow: "hidden",
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
justifyContent: "flex-start",
|
||||
backgroundColor: muiTheme.palette.background.paper
|
||||
}}>
|
||||
<Box sx={{
|
||||
display: "flex",
|
||||
}}>
|
||||
<Button onClick={onRefresh} sx={{
|
||||
borderRadius: 5
|
||||
}}>
|
||||
<IconRefresh />
|
||||
</Button>
|
||||
</Box>
|
||||
</Box>
|
||||
<Box sx={{
|
||||
display: "block",
|
||||
height: "calc(100% - 120px)",
|
||||
overflow: "hidden",
|
||||
position: "absolute",
|
||||
width: "100%"
|
||||
}}>
|
||||
<SimpleTable items={simpleList.items} columns={columns} />
|
||||
|
||||
</Box>
|
||||
</Box>
|
||||
)
|
||||
}
|
||||
22
UI/web/src/app/store/composed-slice.ts
Normal file
22
UI/web/src/app/store/composed-slice.ts
Normal file
@ -0,0 +1,22 @@
|
||||
import { PayloadAction, createSlice } from "@reduxjs/toolkit"
|
||||
|
||||
interface ComposedState {
|
||||
items: Array<EventDataObject>
|
||||
}
|
||||
|
||||
const initialState: ComposedState = {
|
||||
items: []
|
||||
}
|
||||
|
||||
const composedSlice = createSlice({
|
||||
name: "Composed",
|
||||
initialState,
|
||||
reducers: {
|
||||
updateItems(state, action: PayloadAction<Array<EventDataObject>>) {
|
||||
state.items = action.payload
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
export const { updateItems } = composedSlice.actions;
|
||||
export default composedSlice.reducer;
|
||||
29
UI/web/src/app/store/explorer-slice.ts
Normal file
29
UI/web/src/app/store/explorer-slice.ts
Normal file
@ -0,0 +1,29 @@
|
||||
import { PayloadAction, createSlice } from "@reduxjs/toolkit"
|
||||
import { ExplorerItem, ExplorerCursor } from "../../types"
|
||||
|
||||
interface ExplorerState {
|
||||
name: string | null
|
||||
path: string | null
|
||||
items: Array<ExplorerItem>
|
||||
}
|
||||
|
||||
const initialState: ExplorerState = {
|
||||
name: null,
|
||||
path: null,
|
||||
items: []
|
||||
}
|
||||
|
||||
const composedSlice = createSlice({
|
||||
name: "Explorer",
|
||||
initialState,
|
||||
reducers: {
|
||||
updateItems(state, action: PayloadAction<ExplorerCursor>) {
|
||||
state.items = action.payload.items;
|
||||
state.name = action.payload.name;
|
||||
state.path = action.payload.path
|
||||
},
|
||||
}
|
||||
})
|
||||
|
||||
export const { updateItems } = composedSlice.actions;
|
||||
export default composedSlice.reducer;
|
||||
22
UI/web/src/app/store/kafka-items-flat-slice.ts
Normal file
22
UI/web/src/app/store/kafka-items-flat-slice.ts
Normal file
@ -0,0 +1,22 @@
|
||||
import { PayloadAction, createSlice } from "@reduxjs/toolkit"
|
||||
|
||||
interface ComposedState {
|
||||
items: Array<SimpleEventDataObject>
|
||||
}
|
||||
|
||||
const initialState: ComposedState = {
|
||||
items: []
|
||||
}
|
||||
|
||||
const kafkaComposedFlat = createSlice({
|
||||
name: "Composed",
|
||||
initialState,
|
||||
reducers: {
|
||||
simpleEventsUpdate(state, action: PayloadAction<Array<SimpleEventDataObject>>) {
|
||||
state.items = action.payload
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
export const { simpleEventsUpdate } = kafkaComposedFlat.actions;
|
||||
export default kafkaComposedFlat.reducer;
|
||||
@ -6,6 +6,8 @@ body {
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
overflow: hidden;
|
||||
max-height: 100vh;
|
||||
height: 100vh;
|
||||
}
|
||||
|
||||
code {
|
||||
|
||||
16
UI/web/src/theme.d.ts
vendored
Normal file
16
UI/web/src/theme.d.ts
vendored
Normal file
@ -0,0 +1,16 @@
|
||||
import { Theme, ThemeOptions } from '@mui/material/styles';
|
||||
|
||||
declare module '@mui/material/styles' {
|
||||
interface CustomTheme extends Theme {
|
||||
status: {
|
||||
danger: string;
|
||||
};
|
||||
}
|
||||
// allow configuration using `createTheme`
|
||||
interface CustomThemeOptions extends ThemeOptions {
|
||||
status?: {
|
||||
danger?: string;
|
||||
};
|
||||
}
|
||||
export function createTheme(options?: CustomThemeOptions): CustomTheme;
|
||||
}
|
||||
23
UI/web/src/theme.ts
Normal file
23
UI/web/src/theme.ts
Normal file
@ -0,0 +1,23 @@
|
||||
import { createTheme } from '@mui/material/styles';
|
||||
|
||||
export const theme = createTheme({
|
||||
palette: {
|
||||
mode: "dark",
|
||||
primary: {
|
||||
main: '#8800da',
|
||||
},
|
||||
secondary: {
|
||||
main: '#004dbb',
|
||||
},
|
||||
background: {
|
||||
default: '#181818',
|
||||
paper: '#080808',
|
||||
},
|
||||
divider: '#000000',
|
||||
action: {
|
||||
selected: "rgb(67 0 107)"
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
export default theme;
|
||||
74
UI/web/src/types.d.ts
vendored
Normal file
74
UI/web/src/types.d.ts
vendored
Normal file
@ -0,0 +1,74 @@
|
||||
import { type } from "os";
|
||||
|
||||
|
||||
interface ExplorerCursor {
|
||||
name: string
|
||||
path: string
|
||||
items: Array<ExplorerItem>
|
||||
}
|
||||
|
||||
|
||||
type ExplorerItemType = "FILE" | "FOLDER";
|
||||
|
||||
interface ExplorerItem {
|
||||
path: string;
|
||||
name: string;
|
||||
extension: string|null;
|
||||
created: number,
|
||||
type: ExplorerItemType
|
||||
}
|
||||
|
||||
|
||||
interface EventDataObject {
|
||||
id: string;
|
||||
details: Details
|
||||
encode: Encode
|
||||
io: IO
|
||||
events: Array<string>
|
||||
}
|
||||
|
||||
interface Details {
|
||||
title: string;
|
||||
file: string;
|
||||
sanitizedName: string
|
||||
collection: string|null
|
||||
}
|
||||
|
||||
interface Metadata {
|
||||
source: string
|
||||
}
|
||||
|
||||
interface Encode {
|
||||
state: string;
|
||||
progress: number = 0
|
||||
}
|
||||
|
||||
interface IO {
|
||||
inputFile: string;
|
||||
outputFile: string;
|
||||
}
|
||||
|
||||
|
||||
enum SimpleEventDataState {
|
||||
NA,
|
||||
QUEUED,
|
||||
STARTED,
|
||||
ENDED,
|
||||
FAILED,
|
||||
}
|
||||
|
||||
interface SimpleEventDataObject {
|
||||
id: string;
|
||||
name?: string | null;
|
||||
path?: string | null;
|
||||
givenTitle?: string | null;
|
||||
givenSanitizedName?: string | null;
|
||||
givenCollection?: string | null;
|
||||
determinedType?: string | null;
|
||||
eventEncoded: SimpleEventDataState;
|
||||
eventExtracted: SimpleEventDataState;
|
||||
eventConverted: SimpleEventDataState;
|
||||
eventCollected: SimpleEventDataState;
|
||||
encodingProgress?: number | null;
|
||||
encodingTimeLeft?: number | null;
|
||||
}
|
||||
Loading…
Reference in New Issue
Block a user