summaryrefslogtreecommitdiff
path: root/opendc-web/opendc-web-ui/src/redux
diff options
context:
space:
mode:
Diffstat (limited to 'opendc-web/opendc-web-ui/src/redux')
-rw-r--r--opendc-web/opendc-web-ui/src/redux/actions/portfolios.js41
-rw-r--r--opendc-web/opendc-web-ui/src/redux/actions/projects.js47
-rw-r--r--opendc-web/opendc-web-ui/src/redux/actions/scenarios.js43
-rw-r--r--opendc-web/opendc-web-ui/src/redux/actions/topologies.js11
-rw-r--r--opendc-web/opendc-web-ui/src/redux/actions/topology/building.js13
-rw-r--r--opendc-web/opendc-web-ui/src/redux/actions/topology/room.js2
-rw-r--r--opendc-web/opendc-web-ui/src/redux/middleware/viewport-adjustment.js6
-rw-r--r--opendc-web/opendc-web-ui/src/redux/reducers/construction-mode.js6
-rw-r--r--opendc-web/opendc-web-ui/src/redux/reducers/current-ids.js44
-rw-r--r--opendc-web/opendc-web-ui/src/redux/reducers/index.js7
-rw-r--r--opendc-web/opendc-web-ui/src/redux/reducers/interaction-level.js6
-rw-r--r--opendc-web/opendc-web-ui/src/redux/reducers/objects.js20
-rw-r--r--opendc-web/opendc-web-ui/src/redux/reducers/projects.js14
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/index.js26
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/objects.js238
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/portfolios.js136
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/prefabs.js11
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/projects.js44
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/scenarios.js69
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/topology.js126
20 files changed, 99 insertions, 811 deletions
diff --git a/opendc-web/opendc-web-ui/src/redux/actions/portfolios.js b/opendc-web/opendc-web-ui/src/redux/actions/portfolios.js
deleted file mode 100644
index d37886d8..00000000
--- a/opendc-web/opendc-web-ui/src/redux/actions/portfolios.js
+++ /dev/null
@@ -1,41 +0,0 @@
-export const ADD_PORTFOLIO = 'ADD_PORTFOLIO'
-export const UPDATE_PORTFOLIO = 'UPDATE_PORTFOLIO'
-export const DELETE_PORTFOLIO = 'DELETE_PORTFOLIO'
-export const OPEN_PORTFOLIO_SUCCEEDED = 'OPEN_PORTFOLIO_SUCCEEDED'
-export const SET_CURRENT_PORTFOLIO = 'SET_CURRENT_PORTFOLIO'
-
-export function addPortfolio(portfolio) {
- return {
- type: ADD_PORTFOLIO,
- portfolio,
- }
-}
-
-export function updatePortfolio(portfolio) {
- return {
- type: UPDATE_PORTFOLIO,
- portfolio,
- }
-}
-
-export function deletePortfolio(id) {
- return {
- type: DELETE_PORTFOLIO,
- id,
- }
-}
-
-export function openPortfolioSucceeded(projectId, portfolioId) {
- return {
- type: OPEN_PORTFOLIO_SUCCEEDED,
- projectId,
- portfolioId,
- }
-}
-
-export function setCurrentPortfolio(portfolioId) {
- return {
- type: SET_CURRENT_PORTFOLIO,
- portfolioId,
- }
-}
diff --git a/opendc-web/opendc-web-ui/src/redux/actions/projects.js b/opendc-web/opendc-web-ui/src/redux/actions/projects.js
index a6324c43..4fe6f6a8 100644
--- a/opendc-web/opendc-web-ui/src/redux/actions/projects.js
+++ b/opendc-web/opendc-web-ui/src/redux/actions/projects.js
@@ -1,52 +1,5 @@
-export const FETCH_PROJECTS = 'FETCH_PROJECTS'
-export const FETCH_PROJECTS_SUCCEEDED = 'FETCH_PROJECTS_SUCCEEDED'
-export const ADD_PROJECT = 'ADD_PROJECT'
-export const ADD_PROJECT_SUCCEEDED = 'ADD_PROJECT_SUCCEEDED'
-export const DELETE_PROJECT = 'DELETE_PROJECT'
-export const DELETE_PROJECT_SUCCEEDED = 'DELETE_PROJECT_SUCCEEDED'
export const OPEN_PROJECT_SUCCEEDED = 'OPEN_PROJECT_SUCCEEDED'
-export function fetchProjects() {
- return {
- type: FETCH_PROJECTS,
- }
-}
-
-export function fetchProjectsSucceeded(projects) {
- return {
- type: FETCH_PROJECTS_SUCCEEDED,
- projects,
- }
-}
-
-export function addProject(name) {
- return {
- type: ADD_PROJECT,
- name,
- }
-}
-
-export function addProjectSucceeded(project) {
- return {
- type: ADD_PROJECT_SUCCEEDED,
- project,
- }
-}
-
-export function deleteProject(id) {
- return {
- type: DELETE_PROJECT,
- id,
- }
-}
-
-export function deleteProjectSucceeded(id) {
- return {
- type: DELETE_PROJECT_SUCCEEDED,
- id,
- }
-}
-
export function openProjectSucceeded(id) {
return {
type: OPEN_PROJECT_SUCCEEDED,
diff --git a/opendc-web/opendc-web-ui/src/redux/actions/scenarios.js b/opendc-web/opendc-web-ui/src/redux/actions/scenarios.js
deleted file mode 100644
index c8a90762..00000000
--- a/opendc-web/opendc-web-ui/src/redux/actions/scenarios.js
+++ /dev/null
@@ -1,43 +0,0 @@
-export const ADD_SCENARIO = 'ADD_SCENARIO'
-export const UPDATE_SCENARIO = 'UPDATE_SCENARIO'
-export const DELETE_SCENARIO = 'DELETE_SCENARIO'
-export const OPEN_SCENARIO_SUCCEEDED = 'OPEN_SCENARIO_SUCCEEDED'
-export const SET_CURRENT_SCENARIO = 'SET_CURRENT_SCENARIO'
-
-export function addScenario(scenario) {
- return {
- type: ADD_SCENARIO,
- scenario,
- }
-}
-
-export function updateScenario(scenario) {
- return {
- type: UPDATE_SCENARIO,
- scenario,
- }
-}
-
-export function deleteScenario(id) {
- return {
- type: DELETE_SCENARIO,
- id,
- }
-}
-
-export function openScenarioSucceeded(projectId, portfolioId, scenarioId) {
- return {
- type: OPEN_SCENARIO_SUCCEEDED,
- projectId,
- portfolioId,
- scenarioId,
- }
-}
-
-export function setCurrentScenario(portfolioId, scenarioId) {
- return {
- type: SET_CURRENT_SCENARIO,
- portfolioId,
- scenarioId,
- }
-}
diff --git a/opendc-web/opendc-web-ui/src/redux/actions/topologies.js b/opendc-web/opendc-web-ui/src/redux/actions/topologies.js
index dcce3b7d..529e8663 100644
--- a/opendc-web/opendc-web-ui/src/redux/actions/topologies.js
+++ b/opendc-web/opendc-web-ui/src/redux/actions/topologies.js
@@ -1,17 +1,18 @@
export const ADD_TOPOLOGY = 'ADD_TOPOLOGY'
-export const DELETE_TOPOLOGY = 'DELETE_TOPOLOGY'
+export const STORE_TOPOLOGY = 'STORE_TOPOLOGY'
-export function addTopology(name, duplicateId) {
+export function addTopology(projectId, name, duplicateId) {
return {
type: ADD_TOPOLOGY,
+ projectId,
name,
duplicateId,
}
}
-export function deleteTopology(id) {
+export function storeTopology(entities) {
return {
- type: DELETE_TOPOLOGY,
- id,
+ type: STORE_TOPOLOGY,
+ entities,
}
}
diff --git a/opendc-web/opendc-web-ui/src/redux/actions/topology/building.js b/opendc-web/opendc-web-ui/src/redux/actions/topology/building.js
index 72deda6f..f1a7d569 100644
--- a/opendc-web/opendc-web-ui/src/redux/actions/topology/building.js
+++ b/opendc-web/opendc-web-ui/src/redux/actions/topology/building.js
@@ -32,7 +32,7 @@ export function startNewRoomConstructionSucceeded(roomId) {
export function finishNewRoomConstruction() {
return (dispatch, getState) => {
const { objects, construction } = getState()
- if (objects.room[construction.currentRoomInConstruction].tileIds.length === 0) {
+ if (objects.room[construction.currentRoomInConstruction].tiles.length === 0) {
dispatch(cancelNewRoomConstruction())
return
}
@@ -75,13 +75,10 @@ export function toggleTileAtLocation(positionX, positionY) {
return (dispatch, getState) => {
const { objects, construction } = getState()
- const tileIds = objects.room[construction.currentRoomInConstruction].tileIds
- for (let index in tileIds) {
- if (
- objects.tile[tileIds[index]].positionX === positionX &&
- objects.tile[tileIds[index]].positionY === positionY
- ) {
- dispatch(deleteTile(tileIds[index]))
+ const tileIds = objects.room[construction.currentRoomInConstruction].tiles
+ for (const tileId of tileIds) {
+ if (objects.tile[tileId].positionX === positionX && objects.tile[tileId].positionY === positionY) {
+ dispatch(deleteTile(tileId))
return
}
}
diff --git a/opendc-web/opendc-web-ui/src/redux/actions/topology/room.js b/opendc-web/opendc-web-ui/src/redux/actions/topology/room.js
index 61eea7fe..80ef7c5e 100644
--- a/opendc-web/opendc-web-ui/src/redux/actions/topology/room.js
+++ b/opendc-web/opendc-web-ui/src/redux/actions/topology/room.js
@@ -29,7 +29,7 @@ export function addRackToTile(positionX, positionY) {
return (dispatch, getState) => {
const { objects, interactionLevel } = getState()
const currentRoom = objects.room[interactionLevel.roomId]
- const tiles = currentRoom.tileIds.map((tileId) => objects.tile[tileId])
+ const tiles = currentRoom.tiles.map((tileId) => objects.tile[tileId])
const tile = findTileWithPosition(tiles, positionX, positionY)
if (tile !== null) {
diff --git a/opendc-web/opendc-web-ui/src/redux/middleware/viewport-adjustment.js b/opendc-web/opendc-web-ui/src/redux/middleware/viewport-adjustment.js
index 6b22eb80..c2fc5004 100644
--- a/opendc-web/opendc-web-ui/src/redux/middleware/viewport-adjustment.js
+++ b/opendc-web/opendc-web-ui/src/redux/middleware/viewport-adjustment.js
@@ -22,10 +22,10 @@ export const viewportAdjustmentMiddleware = (store) => (next) => (action) => {
mapDimensions = { width: action.width, height: action.height }
}
- if (topologyId !== '-1') {
- const roomIds = state.objects.topology[topologyId].roomIds
+ if (topologyId && topologyId !== '-1') {
+ const roomIds = state.objects.topology[topologyId].rooms
const rooms = roomIds.map((id) => Object.assign({}, state.objects.room[id]))
- rooms.forEach((room) => (room.tiles = room.tileIds.map((tileId) => state.objects.tile[tileId])))
+ rooms.forEach((room) => (room.tiles = room.tiles.map((tileId) => state.objects.tile[tileId])))
let hasNoTiles = true
for (let i in rooms) {
diff --git a/opendc-web/opendc-web-ui/src/redux/reducers/construction-mode.js b/opendc-web/opendc-web-ui/src/redux/reducers/construction-mode.js
index 257dddd2..5bac7fea 100644
--- a/opendc-web/opendc-web-ui/src/redux/reducers/construction-mode.js
+++ b/opendc-web/opendc-web-ui/src/redux/reducers/construction-mode.js
@@ -9,8 +9,6 @@ import {
START_ROOM_EDIT,
} from '../actions/topology/building'
import { DELETE_ROOM, START_RACK_CONSTRUCTION, STOP_RACK_CONSTRUCTION } from '../actions/topology/room'
-import { OPEN_PORTFOLIO_SUCCEEDED } from '../actions/portfolios'
-import { OPEN_SCENARIO_SUCCEEDED } from '../actions/scenarios'
export function currentRoomInConstruction(state = '-1', action) {
switch (action.type) {
@@ -20,8 +18,6 @@ export function currentRoomInConstruction(state = '-1', action) {
return action.roomId
case CANCEL_NEW_ROOM_CONSTRUCTION_SUCCEEDED:
case FINISH_NEW_ROOM_CONSTRUCTION:
- case OPEN_PORTFOLIO_SUCCEEDED:
- case OPEN_SCENARIO_SUCCEEDED:
case FINISH_ROOM_EDIT:
case SET_CURRENT_TOPOLOGY:
case DELETE_ROOM:
@@ -36,8 +32,6 @@ export function inRackConstructionMode(state = false, action) {
case START_RACK_CONSTRUCTION:
return true
case STOP_RACK_CONSTRUCTION:
- case OPEN_PORTFOLIO_SUCCEEDED:
- case OPEN_SCENARIO_SUCCEEDED:
case SET_CURRENT_TOPOLOGY:
case GO_DOWN_ONE_INTERACTION_LEVEL:
return false
diff --git a/opendc-web/opendc-web-ui/src/redux/reducers/current-ids.js b/opendc-web/opendc-web-ui/src/redux/reducers/current-ids.js
index 9b46aa60..c0baf567 100644
--- a/opendc-web/opendc-web-ui/src/redux/reducers/current-ids.js
+++ b/opendc-web/opendc-web-ui/src/redux/reducers/current-ids.js
@@ -1,7 +1,4 @@
-import { OPEN_PORTFOLIO_SUCCEEDED, SET_CURRENT_PORTFOLIO } from '../actions/portfolios'
-import { OPEN_PROJECT_SUCCEEDED } from '../actions/projects'
import { SET_CURRENT_TOPOLOGY } from '../actions/topology/building'
-import { OPEN_SCENARIO_SUCCEEDED, SET_CURRENT_SCENARIO } from '../actions/scenarios'
export function currentTopologyId(state = '-1', action) {
switch (action.type) {
@@ -11,44 +8,3 @@ export function currentTopologyId(state = '-1', action) {
return state
}
}
-
-export function currentProjectId(state = '-1', action) {
- switch (action.type) {
- case OPEN_PROJECT_SUCCEEDED:
- return action.id
- case OPEN_PORTFOLIO_SUCCEEDED:
- case OPEN_SCENARIO_SUCCEEDED:
- return action.projectId
- default:
- return state
- }
-}
-
-export function currentPortfolioId(state = '-1', action) {
- switch (action.type) {
- case OPEN_PORTFOLIO_SUCCEEDED:
- case SET_CURRENT_PORTFOLIO:
- case SET_CURRENT_SCENARIO:
- return action.portfolioId
- case OPEN_SCENARIO_SUCCEEDED:
- return action.portfolioId
- case OPEN_PROJECT_SUCCEEDED:
- case SET_CURRENT_TOPOLOGY:
- return '-1'
- default:
- return state
- }
-}
-export function currentScenarioId(state = '-1', action) {
- switch (action.type) {
- case OPEN_SCENARIO_SUCCEEDED:
- case SET_CURRENT_SCENARIO:
- return action.scenarioId
- case OPEN_PORTFOLIO_SUCCEEDED:
- case SET_CURRENT_TOPOLOGY:
- case OPEN_PROJECT_SUCCEEDED:
- return '-1'
- default:
- return state
- }
-}
diff --git a/opendc-web/opendc-web-ui/src/redux/reducers/index.js b/opendc-web/opendc-web-ui/src/redux/reducers/index.js
index b143d417..1b17a206 100644
--- a/opendc-web/opendc-web-ui/src/redux/reducers/index.js
+++ b/opendc-web/opendc-web-ui/src/redux/reducers/index.js
@@ -1,20 +1,15 @@
import { combineReducers } from 'redux'
import { construction } from './construction-mode'
-import { currentPortfolioId, currentProjectId, currentScenarioId, currentTopologyId } from './current-ids'
+import { currentTopologyId } from './current-ids'
import { interactionLevel } from './interaction-level'
import { map } from './map'
import { objects } from './objects'
-import { projects } from './projects'
const rootReducer = combineReducers({
objects,
- projects,
construction,
map,
- currentProjectId,
currentTopologyId,
- currentPortfolioId,
- currentScenarioId,
interactionLevel,
})
diff --git a/opendc-web/opendc-web-ui/src/redux/reducers/interaction-level.js b/opendc-web/opendc-web-ui/src/redux/reducers/interaction-level.js
index eafcb269..9f23949f 100644
--- a/opendc-web/opendc-web-ui/src/redux/reducers/interaction-level.js
+++ b/opendc-web/opendc-web-ui/src/redux/reducers/interaction-level.js
@@ -1,19 +1,13 @@
-import { OPEN_PORTFOLIO_SUCCEEDED } from '../actions/portfolios'
import {
GO_DOWN_ONE_INTERACTION_LEVEL,
GO_FROM_BUILDING_TO_ROOM,
GO_FROM_RACK_TO_MACHINE,
GO_FROM_ROOM_TO_RACK,
} from '../actions/interaction-level'
-import { OPEN_PROJECT_SUCCEEDED } from '../actions/projects'
import { SET_CURRENT_TOPOLOGY } from '../actions/topology/building'
-import { OPEN_SCENARIO_SUCCEEDED } from '../actions/scenarios'
export function interactionLevel(state = { mode: 'BUILDING' }, action) {
switch (action.type) {
- case OPEN_PORTFOLIO_SUCCEEDED:
- case OPEN_SCENARIO_SUCCEEDED:
- case OPEN_PROJECT_SUCCEEDED:
case SET_CURRENT_TOPOLOGY:
return {
mode: 'BUILDING',
diff --git a/opendc-web/opendc-web-ui/src/redux/reducers/objects.js b/opendc-web/opendc-web-ui/src/redux/reducers/objects.js
index a2483b43..11f6d353 100644
--- a/opendc-web/opendc-web-ui/src/redux/reducers/objects.js
+++ b/opendc-web/opendc-web-ui/src/redux/reducers/objects.js
@@ -6,11 +6,9 @@ import {
REMOVE_ID_FROM_STORE_OBJECT_LIST_PROP,
} from '../actions/objects'
import { CPU_UNITS, GPU_UNITS, MEMORY_UNITS, STORAGE_UNITS } from '../../util/unit-specifications'
+import { STORE_TOPOLOGY } from '../actions/topologies'
export const objects = combineReducers({
- project: object('project'),
- user: object('user'),
- authorization: objectWithId('authorization', (object) => [object.userId, object.projectId]),
cpu: object('cpu', CPU_UNITS),
gpu: object('gpu', GPU_UNITS),
memory: object('memory', MEMORY_UNITS),
@@ -20,10 +18,6 @@ export const objects = combineReducers({
tile: object('tile'),
room: object('room'),
topology: object('topology'),
- trace: object('trace'),
- scheduler: object('scheduler'),
- portfolio: object('portfolio'),
- scenario: object('scenario'),
prefab: object('prefab'),
})
@@ -33,18 +27,16 @@ function object(type, defaultState = {}) {
function objectWithId(type, getId, defaultState = {}) {
return (state = defaultState, action) => {
- if (action.objectType !== type) {
+ if (action.type === STORE_TOPOLOGY) {
+ return { ...state, ...action.entities[type] }
+ } else if (action.objectType !== type) {
return state
}
if (action.type === ADD_TO_STORE) {
- return Object.assign({}, state, {
- [getId(action.object)]: action.object,
- })
+ return { ...state, [getId(action.object)]: action.object }
} else if (action.type === ADD_PROP_TO_STORE_OBJECT) {
- return Object.assign({}, state, {
- [action.objectId]: Object.assign({}, state[action.objectId], action.propObject),
- })
+ return { ...state, [action.objectId]: { ...state[action.objectId], ...action.propObject } }
} else if (action.type === ADD_ID_TO_STORE_OBJECT_LIST_PROP) {
return Object.assign({}, state, {
[action.objectId]: Object.assign({}, state[action.objectId], {
diff --git a/opendc-web/opendc-web-ui/src/redux/reducers/projects.js b/opendc-web/opendc-web-ui/src/redux/reducers/projects.js
deleted file mode 100644
index a920e47f..00000000
--- a/opendc-web/opendc-web-ui/src/redux/reducers/projects.js
+++ /dev/null
@@ -1,14 +0,0 @@
-import { ADD_PROJECT_SUCCEEDED, DELETE_PROJECT_SUCCEEDED, FETCH_PROJECTS_SUCCEEDED } from '../actions/projects'
-
-export function projects(state = [], action) {
- switch (action.type) {
- case FETCH_PROJECTS_SUCCEEDED:
- return action.projects
- case ADD_PROJECT_SUCCEEDED:
- return [...state, action.project]
- case DELETE_PROJECT_SUCCEEDED:
- return state.filter((project) => project._id !== action.id)
- default:
- return state
- }
-}
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/index.js b/opendc-web/opendc-web-ui/src/redux/sagas/index.js
index a8f44843..318f0afb 100644
--- a/opendc-web/opendc-web-ui/src/redux/sagas/index.js
+++ b/opendc-web/opendc-web-ui/src/redux/sagas/index.js
@@ -1,6 +1,5 @@
import { takeEvery } from 'redux-saga/effects'
-import { ADD_PORTFOLIO, DELETE_PORTFOLIO, OPEN_PORTFOLIO_SUCCEEDED, UPDATE_PORTFOLIO } from '../actions/portfolios'
-import { ADD_PROJECT, DELETE_PROJECT, FETCH_PROJECTS, OPEN_PROJECT_SUCCEEDED } from '../actions/projects'
+import { OPEN_PROJECT_SUCCEEDED } from '../actions/projects'
import {
ADD_TILE,
CANCEL_NEW_ROOM_CONSTRUCTION,
@@ -10,8 +9,7 @@ import {
import { ADD_UNIT, DELETE_MACHINE, DELETE_UNIT } from '../actions/topology/machine'
import { ADD_MACHINE, DELETE_RACK, EDIT_RACK_NAME } from '../actions/topology/rack'
import { ADD_RACK_TO_TILE, DELETE_ROOM, EDIT_ROOM_NAME } from '../actions/topology/room'
-import { onAddPortfolio, onDeletePortfolio, onOpenPortfolioSucceeded, onUpdatePortfolio } from './portfolios'
-import { onFetchProjects, onOpenProjectSucceeded, onProjectAdd, onProjectDelete } from './projects'
+import { onOpenProjectSucceeded } from './projects'
import {
onAddMachine,
onAddRackToTile,
@@ -23,29 +21,19 @@ import {
onDeleteRack,
onDeleteRoom,
onDeleteTile,
- onDeleteTopology,
onDeleteUnit,
onEditRackName,
onEditRoomName,
onStartNewRoomConstruction,
} from './topology'
-import { ADD_TOPOLOGY, DELETE_TOPOLOGY } from '../actions/topologies'
-import { ADD_SCENARIO, DELETE_SCENARIO, OPEN_SCENARIO_SUCCEEDED, UPDATE_SCENARIO } from '../actions/scenarios'
-import { onAddScenario, onDeleteScenario, onOpenScenarioSucceeded, onUpdateScenario } from './scenarios'
+import { ADD_TOPOLOGY } from '../actions/topologies'
import { onAddPrefab } from './prefabs'
import { ADD_PREFAB } from '../actions/prefabs'
export default function* rootSaga() {
- yield takeEvery(FETCH_PROJECTS, onFetchProjects)
- yield takeEvery(ADD_PROJECT, onProjectAdd)
- yield takeEvery(DELETE_PROJECT, onProjectDelete)
-
yield takeEvery(OPEN_PROJECT_SUCCEEDED, onOpenProjectSucceeded)
- yield takeEvery(OPEN_PORTFOLIO_SUCCEEDED, onOpenPortfolioSucceeded)
- yield takeEvery(OPEN_SCENARIO_SUCCEEDED, onOpenScenarioSucceeded)
yield takeEvery(ADD_TOPOLOGY, onAddTopology)
- yield takeEvery(DELETE_TOPOLOGY, onDeleteTopology)
yield takeEvery(START_NEW_ROOM_CONSTRUCTION, onStartNewRoomConstruction)
yield takeEvery(CANCEL_NEW_ROOM_CONSTRUCTION, onCancelNewRoomConstruction)
yield takeEvery(ADD_TILE, onAddTile)
@@ -60,13 +48,5 @@ export default function* rootSaga() {
yield takeEvery(ADD_UNIT, onAddUnit)
yield takeEvery(DELETE_UNIT, onDeleteUnit)
- yield takeEvery(ADD_PORTFOLIO, onAddPortfolio)
- yield takeEvery(UPDATE_PORTFOLIO, onUpdatePortfolio)
- yield takeEvery(DELETE_PORTFOLIO, onDeletePortfolio)
-
- yield takeEvery(ADD_SCENARIO, onAddScenario)
- yield takeEvery(UPDATE_SCENARIO, onUpdateScenario)
- yield takeEvery(DELETE_SCENARIO, onDeleteScenario)
-
yield takeEvery(ADD_PREFAB, onAddPrefab)
}
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/objects.js b/opendc-web/opendc-web-ui/src/redux/sagas/objects.js
index e5fd092d..9b4f8094 100644
--- a/opendc-web/opendc-web-ui/src/redux/sagas/objects.js
+++ b/opendc-web/opendc-web-ui/src/redux/sagas/objects.js
@@ -1,234 +1,36 @@
import { call, put, select, getContext } from 'redux-saga/effects'
-import { addToStore } from '../actions/objects'
-import { getAllSchedulers } from '../../api/schedulers'
-import { getProject } from '../../api/projects'
-import { getAllTraces } from '../../api/traces'
-import { getTopology, updateTopology } from '../../api/topologies'
-import { uuid } from 'uuidv4'
-
-export const OBJECT_SELECTORS = {
- project: (state) => state.objects.project,
- user: (state) => state.objects.user,
- authorization: (state) => state.objects.authorization,
- portfolio: (state) => state.objects.portfolio,
- scenario: (state) => state.objects.scenario,
- cpu: (state) => state.objects.cpu,
- gpu: (state) => state.objects.gpu,
- memory: (state) => state.objects.memory,
- storage: (state) => state.objects.storage,
- machine: (state) => state.objects.machine,
- rack: (state) => state.objects.rack,
- tile: (state) => state.objects.tile,
- room: (state) => state.objects.room,
- topology: (state) => state.objects.topology,
-}
-
-function* fetchAndStoreObject(objectType, id, apiCall) {
- const objectStore = yield select(OBJECT_SELECTORS[objectType])
- let object = objectStore[id]
- if (!object) {
- object = yield apiCall
- yield put(addToStore(objectType, object))
- }
- return object
-}
-
-function* fetchAndStoreObjects(objectType, apiCall) {
- const objects = yield apiCall
- for (let object of objects) {
- yield put(addToStore(objectType, object))
- }
- return objects
-}
-
-export const fetchAndStoreProject = function* (id) {
- const auth = yield getContext('auth')
- return yield fetchAndStoreObject('project', id, call(getProject, auth, id))
-}
-
+import { fetchTopology, updateTopology } from '../../api/topologies'
+import { Topology } from '../../util/topology-schema'
+import { denormalize, normalize } from 'normalizr'
+import { storeTopology } from '../actions/topologies'
+
+/**
+ * Fetches and normalizes the topology with the specified identifier.
+ */
export const fetchAndStoreTopology = function* (id) {
- const topologyStore = yield select(OBJECT_SELECTORS['topology'])
- const roomStore = yield select(OBJECT_SELECTORS['room'])
- const tileStore = yield select(OBJECT_SELECTORS['tile'])
- const rackStore = yield select(OBJECT_SELECTORS['rack'])
- const machineStore = yield select(OBJECT_SELECTORS['machine'])
const auth = yield getContext('auth')
- let topology = topologyStore[id]
+ let topology = yield select((state) => state.objects.topology[id])
if (!topology) {
- const fullTopology = yield call(getTopology, auth, id)
-
- for (let roomIdx in fullTopology.rooms) {
- const fullRoom = fullTopology.rooms[roomIdx]
-
- generateIdIfNotPresent(fullRoom)
-
- if (!roomStore[fullRoom._id]) {
- for (let tileIdx in fullRoom.tiles) {
- const fullTile = fullRoom.tiles[tileIdx]
-
- generateIdIfNotPresent(fullTile)
-
- if (!tileStore[fullTile._id]) {
- if (fullTile.rack) {
- const fullRack = fullTile.rack
-
- generateIdIfNotPresent(fullRack)
-
- if (!rackStore[fullRack._id]) {
- for (let machineIdx in fullRack.machines) {
- const fullMachine = fullRack.machines[machineIdx]
-
- generateIdIfNotPresent(fullMachine)
-
- if (!machineStore[fullMachine._id]) {
- let machine = (({ _id, position, cpus, gpus, memories, storages }) => ({
- _id,
- rackId: fullRack._id,
- position,
- cpuIds: cpus.map((u) => u._id),
- gpuIds: gpus.map((u) => u._id),
- memoryIds: memories.map((u) => u._id),
- storageIds: storages.map((u) => u._id),
- }))(fullMachine)
- yield put(addToStore('machine', machine))
- }
- }
-
- const filledSlots = new Array(fullRack.capacity).fill(null)
- fullRack.machines.forEach(
- (machine) => (filledSlots[machine.position - 1] = machine._id)
- )
- let rack = (({ _id, name, capacity, powerCapacityW }) => ({
- _id,
- name,
- capacity,
- powerCapacityW,
- machineIds: filledSlots,
- }))(fullRack)
- yield put(addToStore('rack', rack))
- }
- }
-
- let tile = (({ _id, positionX, positionY, rack }) => ({
- _id,
- roomId: fullRoom._id,
- positionX,
- positionY,
- rackId: rack ? rack._id : undefined,
- }))(fullTile)
- yield put(addToStore('tile', tile))
- }
- }
-
- let room = (({ _id, name, tiles }) => ({ _id, name, tileIds: tiles.map((t) => t._id) }))(fullRoom)
- yield put(addToStore('room', room))
- }
- }
-
- topology = (({ _id, name, rooms }) => ({ _id, name, roomIds: rooms.map((r) => r._id) }))(fullTopology)
- yield put(addToStore('topology', topology))
-
- // TODO consider pushing the IDs
+ const newTopology = yield call(fetchTopology, auth, id)
+ const { entities } = normalize(newTopology, Topology)
+ yield put(storeTopology(entities))
}
return topology
}
-const generateIdIfNotPresent = (obj) => {
- if (!obj._id) {
- obj._id = uuid()
- }
-}
-
export const updateTopologyOnServer = function* (id) {
- const topology = yield getTopologyAsObject(id, true)
+ const topology = yield denormalizeTopology(id)
const auth = yield getContext('auth')
yield call(updateTopology, auth, topology)
}
-export const getTopologyAsObject = function* (id, keepIds) {
- const topologyStore = yield select(OBJECT_SELECTORS['topology'])
- const rooms = yield getAllRooms(topologyStore[id].roomIds, keepIds)
- return {
- _id: keepIds ? id : undefined,
- name: topologyStore[id].name,
- rooms: rooms,
- }
-}
-
-export const getAllRooms = function* (roomIds, keepIds) {
- const roomStore = yield select(OBJECT_SELECTORS['room'])
-
- let rooms = []
-
- for (let id of roomIds) {
- let tiles = yield getAllRoomTiles(roomStore[id], keepIds)
- rooms.push({
- _id: keepIds ? id : undefined,
- name: roomStore[id].name,
- tiles: tiles,
- })
- }
- return rooms
-}
-
-export const getAllRoomTiles = function* (roomStore, keepIds) {
- let tiles = []
-
- for (let id of roomStore.tileIds) {
- tiles.push(yield getTileById(id, keepIds))
- }
- return tiles
-}
-
-export const getTileById = function* (id, keepIds) {
- const tileStore = yield select(OBJECT_SELECTORS['tile'])
- return {
- _id: keepIds ? id : undefined,
- positionX: tileStore[id].positionX,
- positionY: tileStore[id].positionY,
- rack: !tileStore[id].rackId ? undefined : yield getRackById(tileStore[id].rackId, keepIds),
- }
-}
-
-export const getRackById = function* (id, keepIds) {
- const rackStore = yield select(OBJECT_SELECTORS['rack'])
- const machineStore = yield select(OBJECT_SELECTORS['machine'])
- const cpuStore = yield select(OBJECT_SELECTORS['cpu'])
- const gpuStore = yield select(OBJECT_SELECTORS['gpu'])
- const memoryStore = yield select(OBJECT_SELECTORS['memory'])
- const storageStore = yield select(OBJECT_SELECTORS['storage'])
-
- return {
- _id: keepIds ? rackStore[id]._id : undefined,
- name: rackStore[id].name,
- capacity: rackStore[id].capacity,
- powerCapacityW: rackStore[id].powerCapacityW,
- machines: rackStore[id].machineIds
- .filter((m) => m !== null)
- .map((machineId) => ({
- _id: keepIds ? machineId : undefined,
- position: machineStore[machineId].position,
- cpus: machineStore[machineId].cpuIds.map((id) => cpuStore[id]),
- gpus: machineStore[machineId].gpuIds.map((id) => gpuStore[id]),
- memories: machineStore[machineId].memoryIds.map((id) => memoryStore[id]),
- storages: machineStore[machineId].storageIds.map((id) => storageStore[id]),
- })),
- }
-}
-
-export const fetchAndStoreAllTraces = function* () {
- const auth = yield getContext('auth')
- return yield fetchAndStoreObjects('trace', call(getAllTraces, auth))
-}
-
-export const fetchAndStoreAllSchedulers = function* () {
- const auth = yield getContext('auth')
- const objects = yield call(getAllSchedulers, auth)
- for (let object of objects) {
- object._id = object.name
- yield put(addToStore('scheduler', object))
- }
- return objects
+/**
+ * Denormalizes the topology representation in order to be stored on the server.
+ */
+export const denormalizeTopology = function* (id) {
+ const objects = yield select((state) => state.objects)
+ const topology = objects.topology[id]
+ return denormalize(topology, Topology, objects)
}
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/portfolios.js b/opendc-web/opendc-web-ui/src/redux/sagas/portfolios.js
deleted file mode 100644
index 340cb490..00000000
--- a/opendc-web/opendc-web-ui/src/redux/sagas/portfolios.js
+++ /dev/null
@@ -1,136 +0,0 @@
-import { call, put, select, delay, getContext } from 'redux-saga/effects'
-import { addPropToStoreObject, addToStore } from '../actions/objects'
-import { addPortfolio, deletePortfolio, getPortfolio, updatePortfolio } from '../../api/portfolios'
-import { getProject } from '../../api/projects'
-import { fetchAndStoreAllSchedulers, fetchAndStoreAllTraces } from './objects'
-import { fetchAndStoreAllTopologiesOfProject } from './topology'
-import { getScenario } from '../../api/scenarios'
-
-export function* onOpenPortfolioSucceeded(action) {
- try {
- const auth = yield getContext('auth')
- const project = yield call(getProject, auth, action.projectId)
- yield put(addToStore('project', project))
- yield fetchAndStoreAllTopologiesOfProject(project._id)
- yield fetchPortfoliosOfProject()
- yield fetchAndStoreAllSchedulers()
- yield fetchAndStoreAllTraces()
-
- yield watchForPortfolioResults()
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* watchForPortfolioResults() {
- try {
- const currentPortfolioId = yield select((state) => state.currentPortfolioId)
- let unfinishedScenarios = yield getCurrentUnfinishedScenarios()
-
- while (unfinishedScenarios.length > 0) {
- yield delay(3000)
- yield fetchPortfolioWithScenarios(currentPortfolioId)
- unfinishedScenarios = yield getCurrentUnfinishedScenarios()
- }
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* getCurrentUnfinishedScenarios() {
- try {
- const currentPortfolioId = yield select((state) => state.currentPortfolioId)
- const scenarioIds = yield select((state) => state.objects.portfolio[currentPortfolioId].scenarioIds)
- const scenarioObjects = yield select((state) => state.objects.scenario)
- const scenarios = scenarioIds.map((s) => scenarioObjects[s])
- return scenarios.filter((s) => !s || s.simulation.state === 'QUEUED' || s.simulation.state === 'RUNNING')
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* fetchPortfoliosOfProject() {
- try {
- const currentProjectId = yield select((state) => state.currentProjectId)
- const currentProject = yield select((state) => state.objects.project[currentProjectId])
-
- yield fetchAndStoreAllSchedulers()
- yield fetchAndStoreAllTraces()
-
- for (let i in currentProject.portfolioIds) {
- yield fetchPortfolioWithScenarios(currentProject.portfolioIds[i])
- }
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* fetchPortfolioWithScenarios(portfolioId) {
- try {
- const auth = yield getContext('auth')
- const portfolio = yield call(getPortfolio, auth, portfolioId)
- yield put(addToStore('portfolio', portfolio))
-
- for (let i in portfolio.scenarioIds) {
- const scenario = yield call(getScenario, auth, portfolio.scenarioIds[i])
- yield put(addToStore('scenario', scenario))
- }
- return portfolio
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onAddPortfolio(action) {
- try {
- const currentProjectId = yield select((state) => state.currentProjectId)
- const auth = yield getContext('auth')
- const portfolio = yield call(
- addPortfolio,
- auth,
- currentProjectId,
- Object.assign({}, action.portfolio, {
- projectId: currentProjectId,
- scenarioIds: [],
- })
- )
- yield put(addToStore('portfolio', portfolio))
-
- const portfolioIds = yield select((state) => state.objects.project[currentProjectId].portfolioIds)
- yield put(
- addPropToStoreObject('project', currentProjectId, {
- portfolioIds: portfolioIds.concat([portfolio._id]),
- })
- )
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onUpdatePortfolio(action) {
- try {
- const auth = yield getContext('auth')
- const portfolio = yield call(updatePortfolio, auth, action.portfolio._id, action.portfolio)
- yield put(addToStore('portfolio', portfolio))
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onDeletePortfolio(action) {
- try {
- const auth = yield getContext('auth')
- yield call(deletePortfolio, auth, action.id)
-
- const currentProjectId = yield select((state) => state.currentProjectId)
- const portfolioIds = yield select((state) => state.objects.project[currentProjectId].portfolioIds)
-
- yield put(
- addPropToStoreObject('project', currentProjectId, {
- portfolioIds: portfolioIds.filter((id) => id !== action.id),
- })
- )
- } catch (error) {
- console.error(error)
- }
-}
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/prefabs.js b/opendc-web/opendc-web-ui/src/redux/sagas/prefabs.js
index ec679391..91b03bf6 100644
--- a/opendc-web/opendc-web-ui/src/redux/sagas/prefabs.js
+++ b/opendc-web/opendc-web-ui/src/redux/sagas/prefabs.js
@@ -1,14 +1,17 @@
import { call, put, select, getContext } from 'redux-saga/effects'
import { addToStore } from '../actions/objects'
import { addPrefab } from '../../api/prefabs'
-import { getRackById } from './objects'
+import { Rack } from '../../util/topology-schema'
+import { denormalize } from 'normalizr'
export function* onAddPrefab(action) {
try {
- const currentRackId = yield select((state) => state.objects.tile[state.interactionLevel.tileId].rackId)
- const currentRackJson = yield getRackById(currentRackId, false)
+ const interactionLevel = yield select((state) => state.interactionLevel)
+ const objects = yield select((state) => state.objects)
+ const rack = objects.rack[objects.tile[interactionLevel.tileId].rack]
+ const prefabRack = denormalize(rack, Rack, objects)
const auth = yield getContext('auth')
- const prefab = yield call(addPrefab, auth, { name: action.name, rack: currentRackJson })
+ const prefab = yield call(() => addPrefab(auth, { name: action.name, rack: prefabRack }))
yield put(addToStore('prefab', prefab))
} catch (error) {
console.error(error)
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/projects.js b/opendc-web/opendc-web-ui/src/redux/sagas/projects.js
index 506df6ed..5809d4d2 100644
--- a/opendc-web/opendc-web-ui/src/redux/sagas/projects.js
+++ b/opendc-web/opendc-web-ui/src/redux/sagas/projects.js
@@ -1,52 +1,8 @@
-import { call, put, getContext } from 'redux-saga/effects'
-import { addToStore } from '../actions/objects'
-import { addProjectSucceeded, deleteProjectSucceeded, fetchProjectsSucceeded } from '../actions/projects'
-import { addProject, deleteProject, getProject, getProjects } from '../../api/projects'
import { fetchAndStoreAllTopologiesOfProject } from './topology'
-import { fetchAndStoreAllSchedulers, fetchAndStoreAllTraces } from './objects'
-import { fetchPortfoliosOfProject } from './portfolios'
export function* onOpenProjectSucceeded(action) {
try {
- const auth = yield getContext('auth')
- const project = yield call(getProject, auth, action.id)
- yield put(addToStore('project', project))
-
yield fetchAndStoreAllTopologiesOfProject(action.id, true)
- yield fetchPortfoliosOfProject()
- yield fetchAndStoreAllSchedulers()
- yield fetchAndStoreAllTraces()
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onProjectAdd(action) {
- try {
- const auth = yield getContext('auth')
- const project = yield call(addProject, auth, { name: action.name })
- yield put(addToStore('project', project))
- yield put(addProjectSucceeded(project))
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onProjectDelete(action) {
- try {
- const auth = yield getContext('auth')
- yield call(deleteProject, auth, action.id)
- yield put(deleteProjectSucceeded(action.id))
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onFetchProjects(action) {
- try {
- const auth = yield getContext('auth')
- const projects = yield call(getProjects, auth)
- yield put(fetchProjectsSucceeded(projects))
} catch (error) {
console.error(error)
}
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/scenarios.js b/opendc-web/opendc-web-ui/src/redux/sagas/scenarios.js
deleted file mode 100644
index bdb7c45d..00000000
--- a/opendc-web/opendc-web-ui/src/redux/sagas/scenarios.js
+++ /dev/null
@@ -1,69 +0,0 @@
-import { call, put, select, getContext } from 'redux-saga/effects'
-import { addPropToStoreObject, addToStore } from '../actions/objects'
-import { getProject } from '../../api/projects'
-import { fetchAndStoreAllSchedulers, fetchAndStoreAllTraces } from './objects'
-import { fetchAndStoreAllTopologiesOfProject } from './topology'
-import { addScenario, deleteScenario, updateScenario } from '../../api/scenarios'
-import { fetchPortfolioWithScenarios, watchForPortfolioResults } from './portfolios'
-
-export function* onOpenScenarioSucceeded(action) {
- try {
- const auth = yield getContext('auth')
- const project = yield call(getProject, auth, action.projectId)
- yield put(addToStore('project', project))
- yield fetchAndStoreAllTopologiesOfProject(project._id)
- yield fetchAndStoreAllSchedulers()
- yield fetchAndStoreAllTraces()
- yield fetchPortfolioWithScenarios(action.portfolioId)
-
- // TODO Fetch scenario-specific metrics
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onAddScenario(action) {
- try {
- const auth = yield getContext('auth')
- const scenario = yield call(addScenario, auth, action.scenario.portfolioId, action.scenario)
- yield put(addToStore('scenario', scenario))
-
- const scenarioIds = yield select((state) => state.objects.portfolio[action.scenario.portfolioId].scenarioIds)
- yield put(
- addPropToStoreObject('portfolio', action.scenario.portfolioId, {
- scenarioIds: scenarioIds.concat([scenario._id]),
- })
- )
- yield watchForPortfolioResults()
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onUpdateScenario(action) {
- try {
- const auth = yield getContext('auth')
- const scenario = yield call(updateScenario, auth, action.scenario._id, action.scenario)
- yield put(addToStore('scenario', scenario))
- } catch (error) {
- console.error(error)
- }
-}
-
-export function* onDeleteScenario(action) {
- try {
- const auth = yield getContext('auth')
- yield call(deleteScenario, auth, action.id)
-
- const currentPortfolioId = yield select((state) => state.currentPortfolioId)
- const scenarioIds = yield select((state) => state.objects.portfolio[currentPortfolioId].scenarioIds)
-
- yield put(
- addPropToStoreObject('scenario', currentPortfolioId, {
- scenarioIds: scenarioIds.filter((id) => id !== action.id),
- })
- )
- } catch (error) {
- console.error(error)
- }
-}
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/topology.js b/opendc-web/opendc-web-ui/src/redux/sagas/topology.js
index e5fd3d39..5d9154fd 100644
--- a/opendc-web/opendc-web-ui/src/redux/sagas/topology.js
+++ b/opendc-web/opendc-web-ui/src/redux/sagas/topology.js
@@ -16,16 +16,17 @@ import {
DEFAULT_RACK_SLOT_CAPACITY,
MAX_NUM_UNITS_PER_MACHINE,
} from '../../components/app/map/MapConstants'
-import { fetchAndStoreTopology, getTopologyAsObject, updateTopologyOnServer } from './objects'
+import { fetchAndStoreTopology, denormalizeTopology, updateTopologyOnServer } from './objects'
import { uuid } from 'uuidv4'
-import { addTopology, deleteTopology } from '../../api/topologies'
+import { addTopology } from '../../api/topologies'
export function* fetchAndStoreAllTopologiesOfProject(projectId, setTopology = false) {
try {
- const project = yield select((state) => state.objects.project[projectId])
+ const queryClient = yield getContext('queryClient')
+ const project = yield call(() => queryClient.fetchQuery(['projects', projectId]))
- for (let i in project.topologyIds) {
- yield fetchAndStoreTopology(project.topologyIds[i])
+ for (const id of project.topologyIds) {
+ yield fetchAndStoreTopology(id)
}
if (setTopology) {
@@ -38,62 +39,26 @@ export function* fetchAndStoreAllTopologiesOfProject(projectId, setTopology = fa
export function* onAddTopology(action) {
try {
- const currentProjectId = yield select((state) => state.currentProjectId)
+ const { projectId, duplicateId, name } = action
let topologyToBeCreated
- if (action.duplicateId) {
- topologyToBeCreated = yield getTopologyAsObject(action.duplicateId, false)
- topologyToBeCreated = Object.assign({}, topologyToBeCreated, {
- name: action.name,
- })
+ if (duplicateId) {
+ topologyToBeCreated = yield denormalizeTopology(duplicateId)
+ topologyToBeCreated = { ...topologyToBeCreated, name }
+ delete topologyToBeCreated._id
} else {
topologyToBeCreated = { name: action.name, rooms: [] }
}
const auth = yield getContext('auth')
- const topology = yield call(
- addTopology,
- auth,
- Object.assign({}, topologyToBeCreated, {
- projectId: currentProjectId,
- })
- )
+ const topology = yield call(addTopology, auth, { ...topologyToBeCreated, projectId })
yield fetchAndStoreTopology(topology._id)
-
- const topologyIds = yield select((state) => state.objects.project[currentProjectId].topologyIds)
- yield put(
- addPropToStoreObject('project', currentProjectId, {
- topologyIds: topologyIds.concat([topology._id]),
- })
- )
yield put(setCurrentTopology(topology._id))
} catch (error) {
console.error(error)
}
}
-export function* onDeleteTopology(action) {
- try {
- const currentProjectId = yield select((state) => state.currentProjectId)
- const topologyIds = yield select((state) => state.objects.project[currentProjectId].topologyIds)
- const currentTopologyId = yield select((state) => state.currentTopologyId)
- if (currentTopologyId === action.id) {
- yield put(setCurrentTopology(topologyIds.filter((t) => t !== action.id)[0]))
- }
-
- const auth = yield getContext('auth')
- yield call(deleteTopology, auth, action.id)
-
- yield put(
- addPropToStoreObject('project', currentProjectId, {
- topologyIds: topologyIds.filter((id) => id !== action.id),
- })
- )
- } catch (error) {
- console.error(error)
- }
-}
-
export function* onStartNewRoomConstruction() {
try {
const topologyId = yield select((state) => state.currentTopologyId)
@@ -101,10 +66,10 @@ export function* onStartNewRoomConstruction() {
_id: uuid(),
name: 'Room',
topologyId,
- tileIds: [],
+ tiles: [],
}
yield put(addToStore('room', room))
- yield put(addIdToStoreObjectListProp('topology', topologyId, 'roomIds', room._id))
+ yield put(addIdToStoreObjectListProp('topology', topologyId, 'rooms', room._id))
yield updateTopologyOnServer(topologyId)
yield put(startNewRoomConstructionSucceeded(room._id))
} catch (error) {
@@ -116,7 +81,7 @@ export function* onCancelNewRoomConstruction() {
try {
const topologyId = yield select((state) => state.currentTopologyId)
const roomId = yield select((state) => state.construction.currentRoomInConstruction)
- yield put(removeIdFromStoreObjectListProp('topology', topologyId, 'roomIds', roomId))
+ yield put(removeIdFromStoreObjectListProp('topology', topologyId, 'rooms', roomId))
// TODO remove room from store, too
yield updateTopologyOnServer(topologyId)
yield put(cancelNewRoomConstructionSucceeded())
@@ -136,7 +101,7 @@ export function* onAddTile(action) {
positionY: action.positionY,
}
yield put(addToStore('tile', tile))
- yield put(addIdToStoreObjectListProp('room', roomId, 'tileIds', tile._id))
+ yield put(addIdToStoreObjectListProp('room', roomId, 'tiles', tile._id))
yield updateTopologyOnServer(topologyId)
} catch (error) {
console.error(error)
@@ -147,7 +112,7 @@ export function* onDeleteTile(action) {
try {
const topologyId = yield select((state) => state.currentTopologyId)
const roomId = yield select((state) => state.construction.currentRoomInConstruction)
- yield put(removeIdFromStoreObjectListProp('room', roomId, 'tileIds', action.tileId))
+ yield put(removeIdFromStoreObjectListProp('room', roomId, 'tiles', action.tileId))
yield updateTopologyOnServer(topologyId)
} catch (error) {
console.error(error)
@@ -172,7 +137,7 @@ export function* onDeleteRoom() {
const topologyId = yield select((state) => state.currentTopologyId)
const roomId = yield select((state) => state.interactionLevel.roomId)
yield put(goDownOneInteractionLevel())
- yield put(removeIdFromStoreObjectListProp('topology', topologyId, 'roomIds', roomId))
+ yield put(removeIdFromStoreObjectListProp('topology', topologyId, 'rooms', roomId))
yield updateTopologyOnServer(topologyId)
} catch (error) {
console.error(error)
@@ -182,7 +147,7 @@ export function* onDeleteRoom() {
export function* onEditRackName(action) {
try {
const topologyId = yield select((state) => state.currentTopologyId)
- const rackId = yield select((state) => state.objects.tile[state.interactionLevel.tileId].rackId)
+ const rackId = yield select((state) => state.objects.tile[state.interactionLevel.tileId].rack)
const rack = Object.assign({}, yield select((state) => state.objects.rack[rackId]))
rack.name = action.name
yield put(addPropToStoreObject('rack', rackId, { name: action.name }))
@@ -197,7 +162,7 @@ export function* onDeleteRack() {
const topologyId = yield select((state) => state.currentTopologyId)
const tileId = yield select((state) => state.interactionLevel.tileId)
yield put(goDownOneInteractionLevel())
- yield put(addPropToStoreObject('tile', tileId, { rackId: undefined }))
+ yield put(addPropToStoreObject('tile', tileId, { rack: undefined }))
yield updateTopologyOnServer(topologyId)
} catch (error) {
console.error(error)
@@ -212,10 +177,10 @@ export function* onAddRackToTile(action) {
name: 'Rack',
capacity: DEFAULT_RACK_SLOT_CAPACITY,
powerCapacityW: DEFAULT_RACK_POWER_CAPACITY,
+ machines: [],
}
- rack.machineIds = new Array(rack.capacity).fill(null)
yield put(addToStore('rack', rack))
- yield put(addPropToStoreObject('tile', action.tileId, { rackId: rack._id }))
+ yield put(addPropToStoreObject('tile', action.tileId, { rack: rack._id }))
yield updateTopologyOnServer(topologyId)
} catch (error) {
console.error(error)
@@ -225,23 +190,21 @@ export function* onAddRackToTile(action) {
export function* onAddMachine(action) {
try {
const topologyId = yield select((state) => state.currentTopologyId)
- const rackId = yield select((state) => state.objects.tile[state.interactionLevel.tileId].rackId)
+ const rackId = yield select((state) => state.objects.tile[state.interactionLevel.tileId].rack)
const rack = yield select((state) => state.objects.rack[rackId])
const machine = {
_id: uuid(),
- rackId,
position: action.position,
- cpuIds: [],
- gpuIds: [],
- memoryIds: [],
- storageIds: [],
+ cpus: [],
+ gpus: [],
+ memories: [],
+ storages: [],
}
yield put(addToStore('machine', machine))
- const machineIds = [...rack.machineIds]
- machineIds[machine.position - 1] = machine._id
- yield put(addPropToStoreObject('rack', rackId, { machineIds }))
+ const machineIds = [...rack.machines, machine._id]
+ yield put(addPropToStoreObject('rack', rackId, { machines: machineIds }))
yield updateTopologyOnServer(topologyId)
} catch (error) {
console.error(error)
@@ -253,35 +216,41 @@ export function* onDeleteMachine() {
const topologyId = yield select((state) => state.currentTopologyId)
const tileId = yield select((state) => state.interactionLevel.tileId)
const position = yield select((state) => state.interactionLevel.position)
- const rack = yield select((state) => state.objects.rack[state.objects.tile[tileId].rackId])
- const machineIds = [...rack.machineIds]
- machineIds[position - 1] = null
+ const rack = yield select((state) => state.objects.rack[state.objects.tile[tileId].rack])
yield put(goDownOneInteractionLevel())
- yield put(addPropToStoreObject('rack', rack._id, { machineIds }))
+ yield put(
+ addPropToStoreObject('rack', rack._id, { machines: rack.machines.filter((_, idx) => idx !== position - 1) })
+ )
yield updateTopologyOnServer(topologyId)
} catch (error) {
console.error(error)
}
}
+const unitMapping = {
+ cpu: 'cpus',
+ gpu: 'gpus',
+ memory: 'memories',
+ storage: 'storages',
+}
+
export function* onAddUnit(action) {
try {
const topologyId = yield select((state) => state.currentTopologyId)
const tileId = yield select((state) => state.interactionLevel.tileId)
const position = yield select((state) => state.interactionLevel.position)
const machine = yield select(
- (state) =>
- state.objects.machine[state.objects.rack[state.objects.tile[tileId].rackId].machineIds[position - 1]]
+ (state) => state.objects.machine[state.objects.rack[state.objects.tile[tileId].rack].machines[position - 1]]
)
- if (machine[action.unitType + 'Ids'].length >= MAX_NUM_UNITS_PER_MACHINE) {
+ if (machine[unitMapping[action.unitType]].length >= MAX_NUM_UNITS_PER_MACHINE) {
return
}
- const units = [...machine[action.unitType + 'Ids'], action.id]
+ const units = [...machine[unitMapping[action.unitType]], action.id]
yield put(
addPropToStoreObject('machine', machine._id, {
- [action.unitType + 'Ids']: units,
+ [unitMapping[action.unitType]]: units,
})
)
yield updateTopologyOnServer(topologyId)
@@ -296,15 +265,14 @@ export function* onDeleteUnit(action) {
const tileId = yield select((state) => state.interactionLevel.tileId)
const position = yield select((state) => state.interactionLevel.position)
const machine = yield select(
- (state) =>
- state.objects.machine[state.objects.rack[state.objects.tile[tileId].rackId].machineIds[position - 1]]
+ (state) => state.objects.machine[state.objects.rack[state.objects.tile[tileId].rack].machines[position - 1]]
)
- const unitIds = machine[action.unitType + 'Ids'].slice()
+ const unitIds = machine[unitMapping[action.unitType]].slice()
unitIds.splice(action.index, 1)
yield put(
addPropToStoreObject('machine', machine._id, {
- [action.unitType + 'Ids']: unitIds,
+ [unitMapping[action.unitType]]: unitIds,
})
)
yield updateTopologyOnServer(topologyId)