summaryrefslogtreecommitdiff
path: root/opendc-web/opendc-web-ui/src/redux/sagas
diff options
context:
space:
mode:
Diffstat (limited to 'opendc-web/opendc-web-ui/src/redux/sagas')
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/objects.js36
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/query.js41
-rw-r--r--opendc-web/opendc-web-ui/src/redux/sagas/topology.js48
3 files changed, 82 insertions, 43 deletions
diff --git a/opendc-web/opendc-web-ui/src/redux/sagas/objects.js b/opendc-web/opendc-web-ui/src/redux/sagas/objects.js
deleted file mode 100644
index 9b4f8094..00000000
--- a/opendc-web/opendc-web-ui/src/redux/sagas/objects.js
+++ /dev/null
@@ -1,36 +0,0 @@
-import { call, put, select, getContext } from 'redux-saga/effects'
-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 auth = yield getContext('auth')
-
- let topology = yield select((state) => state.objects.topology[id])
- if (!topology) {
- const newTopology = yield call(fetchTopology, auth, id)
- const { entities } = normalize(newTopology, Topology)
- yield put(storeTopology(entities))
- }
-
- return topology
-}
-
-export const updateTopologyOnServer = function* (id) {
- const topology = yield denormalizeTopology(id)
- const auth = yield getContext('auth')
- yield call(updateTopology, auth, topology)
-}
-
-/**
- * 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/query.js b/opendc-web/opendc-web-ui/src/redux/sagas/query.js
new file mode 100644
index 00000000..787006c7
--- /dev/null
+++ b/opendc-web/opendc-web-ui/src/redux/sagas/query.js
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2021 AtLarge Research
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+
+import { MutationObserver } from 'react-query'
+import { getContext, call } from 'redux-saga/effects'
+
+/**
+ * Fetch the query with the specified key.
+ */
+export function* fetchQuery(key, options) {
+ const queryClient = yield getContext('queryClient')
+ return yield call([queryClient, queryClient.fetchQuery], key, options)
+}
+
+/**
+ * Perform a mutation with the specified key.
+ */
+export function* mutate(key, object, options) {
+ const queryClient = yield getContext('queryClient')
+ const mutationObserver = new MutationObserver(queryClient, { mutationKey: key })
+ return yield call([mutationObserver, mutationObserver.mutate], object, options)
+}
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 a5a3be32..2d61643b 100644
--- a/opendc-web/opendc-web-ui/src/redux/sagas/topology.js
+++ b/opendc-web/opendc-web-ui/src/redux/sagas/topology.js
@@ -1,4 +1,6 @@
-import { call, put, select, getContext } from 'redux-saga/effects'
+import { normalize, denormalize } from 'normalizr'
+import { put, select } from 'redux-saga/effects'
+import { Topology } from '../../util/topology-schema'
import { goDownOneInteractionLevel } from '../actions/interaction-level'
import {
addIdToStoreObjectListProp,
@@ -6,6 +8,7 @@ import {
addToStore,
removeIdFromStoreObjectListProp,
} from '../actions/objects'
+import { storeTopology } from '../actions/topologies'
import {
cancelNewRoomConstructionSucceeded,
setCurrentTopology,
@@ -16,14 +19,15 @@ import {
DEFAULT_RACK_SLOT_CAPACITY,
MAX_NUM_UNITS_PER_MACHINE,
} from '../../components/topologies/map/MapConstants'
-import { fetchAndStoreTopology, denormalizeTopology, updateTopologyOnServer } from './objects'
import { uuid } from 'uuidv4'
-import { addTopology } from '../../api/topologies'
+import { fetchQuery, mutate } from './query'
+/**
+ * Fetches all topologies of the project with the specified identifier.
+ */
export function* fetchAndStoreAllTopologiesOfProject(projectId, setTopology = false) {
try {
- const queryClient = yield getContext('queryClient')
- const project = yield call(() => queryClient.fetchQuery(['projects', projectId]))
+ const project = yield fetchQuery(['projects', projectId])
for (const id of project.topologyIds) {
yield fetchAndStoreTopology(id)
@@ -37,6 +41,37 @@ export function* fetchAndStoreAllTopologiesOfProject(projectId, setTopology = fa
}
}
+/**
+ * Fetches and normalizes the topology with the specified identifier.
+ */
+export function* fetchAndStoreTopology(id) {
+ let topology = yield select((state) => state.objects.topology[id])
+ if (!topology) {
+ const newTopology = yield fetchQuery(['topologies', id])
+ const { entities } = normalize(newTopology, Topology)
+ yield put(storeTopology(entities))
+ }
+
+ return topology
+}
+
+/**
+ * Synchronize the topology with the specified identifier with the server.
+ */
+export function* updateTopologyOnServer(id) {
+ const topology = yield denormalizeTopology(id)
+ yield mutate('updateTopology', topology)
+}
+
+/**
+ * Denormalizes the topology representation in order to be stored on the server.
+ */
+export function* denormalizeTopology(id) {
+ const objects = yield select((state) => state.objects)
+ const topology = objects.topology[id]
+ return denormalize(topology, Topology, objects)
+}
+
export function* onAddTopology({ projectId, duplicateId, name }) {
try {
let topologyToBeCreated
@@ -48,8 +83,7 @@ export function* onAddTopology({ projectId, duplicateId, name }) {
topologyToBeCreated = { name, rooms: [] }
}
- const auth = yield getContext('auth')
- const topology = yield call(addTopology, auth, { ...topologyToBeCreated, projectId })
+ const topology = yield mutate('addTopology', { ...topologyToBeCreated, projectId })
yield fetchAndStoreTopology(topology._id)
yield put(setCurrentTopology(topology._id))
} catch (error) {