Skip to content

Commit

Permalink
#306 Layer UUIDs for Config API
Browse files Browse the repository at this point in the history
  • Loading branch information
tariqksoliman committed Jan 19, 2023
1 parent 9a6649e commit ad60330
Show file tree
Hide file tree
Showing 4 changed files with 47 additions and 54 deletions.
43 changes: 24 additions & 19 deletions API/Backend/Config/routes/configs.js
Original file line number Diff line number Diff line change
Expand Up @@ -296,7 +296,7 @@ function upsert(req, res, next, cb, info) {
} else configJSON = req.body.config;
}

populateUUIDs(configJSON);
const newlyAddedUUIDs = populateUUIDs(configJSON);
const validation = validate(configJSON);

if (!validation.valid) {
Expand Down Expand Up @@ -335,19 +335,22 @@ function upsert(req, res, next, cb, info) {
status: "success",
mission: created.mission,
version: created.version,
newlyAddedUUIDs: newlyAddedUUIDs,
});
else
res.send({
status: "success",
mission: created.mission,
version: created.version,
newlyAddedUUIDs: newlyAddedUUIDs,
});
openWebSocket(
req.body,
{
status: "success",
mission: created.mission,
version: created.version,
newlyAddedUUIDs: newlyAddedUUIDs,
},
info,
forceClientUpdate
Expand Down Expand Up @@ -606,7 +609,7 @@ function addLayer(req, res, next, cb, forceConfig, caller = "addLayer") {
const exampleBody = {
mission: "{mission_name}",
layer: {
name: "{new_unique_layer_name}",
name: "{new_layer_name}",
type: "header || vector || vectortile || query || model || tile || data",
"more...": "...",
},
Expand Down Expand Up @@ -717,13 +720,15 @@ function addLayer(req, res, next, cb, forceConfig, caller = "addLayer") {
message: `Added layer to the ${response.mission} mission. Configuration versioned ${response.version}.`,
mission: response.mission,
version: response.version,
newlyAddedUUIDs: response.newlyAddedUUIDs,
});
} else {
res.send({
status: "success",
message: `Added layer to the ${response.mission} mission. Configuration versioned ${response.version}.`,
mission: response.mission,
version: response.version,
newlyAddedUUIDs: response.newlyAddedUUIDs,
});
}
} else {
Expand Down Expand Up @@ -775,7 +780,7 @@ if (fullAccess)
router.post("/updateLayer", function (req, res, next) {
const exampleBody = {
mission: "{mission_name}",
layerName: "{existing_layer_name}",
layerUUID: "{existing_layer_uuid}",
layer: {
"...": "...",
},
Expand All @@ -796,10 +801,10 @@ if (fullAccess)
});
return;
}
if (req.body.layerName == null) {
if (req.body.layerUUID == null) {
res.send({
status: "failure",
message: `Required parameter 'layerName' is unset. (a layer.name is not sufficient)`,
message: `Required parameter 'layerUUID' is unset. (a layer.uuid is not sufficient)`,
example: exampleBody,
});
return;
Expand Down Expand Up @@ -832,7 +837,7 @@ if (fullAccess)
let placementIndex = req.body.placement?.index;

Utils.traverseLayers(config.layers, (layer, path, index) => {
if (layer.name === req.body.layerName) {
if (layer.uuid === req.body.layerUUID) {
existingLayer = JSON.parse(JSON.stringify(layer));
if (placementPath == null) placementPath = path;
if (placementIndex == null) placementIndex = index;
Expand All @@ -843,7 +848,7 @@ if (fullAccess)
if (existingLayer == null) {
res.send({
status: "failure",
message: `Layer ${req.body.layerName} not found. Cannot update.`,
message: `Layer ${req.body.layerUUID} not found. Cannot update.`,
});
return;
}
Expand Down Expand Up @@ -873,7 +878,7 @@ if (fullAccess)
if (resp.status === "success") {
res.send({
status: "success",
message: `Updated layer '${req.body.layerName}' in the ${resp.mission} mission. Configuration versioned ${resp.version}.`,
message: `Updated layer '${req.body.layerUUID}' in the ${resp.mission} mission. Configuration versioned ${resp.version}.`,
});
} else {
resp.message = `Update layer failed with: ${resp.message}`;
Expand All @@ -887,14 +892,14 @@ if (fullAccess)
} catch (err) {
logger(
"error",
`Failed to update layer: ${req.body.layerName}.`,
`Failed to update layer: ${req.body.layerUUID}.`,
req.originalUrl,
req,
err
);
res.send({
status: "failure",
message: `Failed to update layer: ${req.body.layerName}. Uncaught reason.`,
message: `Failed to update layer: ${req.body.layerUUID}. Uncaught reason.`,
});
}
}
Expand All @@ -905,7 +910,7 @@ if (fullAccess)
function removeLayer(req, res, next, cb) {
const exampleBody = {
mission: "{mission_name}",
layerName: "{existing_layer_name}",
layerUUID: "{existing_layer_uuid}",
"forceClientUpdate?": "{true}; default false",
};

Expand All @@ -917,10 +922,10 @@ function removeLayer(req, res, next, cb) {
});
return;
}
if (req.body.layerName == null) {
if (req.body.layerUUID == null) {
res.send({
status: "failure",
message: `Required parameter 'layerName' is unset.`,
message: `Required parameter 'layerUUID' is unset.`,
example: exampleBody,
});
return;
Expand All @@ -941,7 +946,7 @@ function removeLayer(req, res, next, cb) {
try {
let didRemove = false;
Utils.traverseLayers(config.layers, (layer, path, index) => {
if (layer.name === req.body.layerName) {
if (layer.uuid === req.body.layerUUID) {
didRemove = true;
return "remove";
}
Expand All @@ -962,24 +967,24 @@ function removeLayer(req, res, next, cb) {
if (resp.status === "success") {
res.send({
status: "success",
message: `Successfully removed layer '${req.body.layerName}'.`,
message: `Successfully removed layer '${req.body.layerUUID}'.`,
});
} else {
res.send({
status: "failure",
message: `Failed to remove layer '${req.body.layerName}': ${resp.message}`,
message: `Failed to remove layer '${req.body.layerUUID}': ${resp.message}`,
});
}
},
{
type: "removeLayer",
layerName: req.body.layerName,
layerName: req.body.layerUUID,
}
);
} else {
res.send({
status: "failure",
message: `Failed to remove layer '${req.body.layerName}'. Layer not found.`,
message: `Failed to remove layer '${req.body.layerUUID}'. Layer not found.`,
});
}
} catch (err) {}
Expand All @@ -992,7 +997,7 @@ if (fullAccess)
* /removeLayer
* body: {
"mission": "",
"layerName": ""
"layerUUID": ""
"forceClientUpdate?": true
}
*/
Expand Down
21 changes: 19 additions & 2 deletions API/Backend/Config/uuids.js
Original file line number Diff line number Diff line change
@@ -1,11 +1,28 @@
const Utils = require("../../utils.js");

const { v4: uuidv4 } = require("uuid");
const { v4: uuidv4, validate: uuidValidate } = require("uuid");

const populateUUIDs = (config) => {
const newlyAddedUUIDs = [];

Utils.traverseLayers(config.layers, (layer) => {
if (layer.uuid == null) layer.uuid = uuidv4();
if (layer.uuid == null) {
layer.uuid = uuidv4();
newlyAddedUUIDs.push({
name: layer.name,
uuid: layer.uuid,
});
} else if (!uuidValidate(layer.uuid)) {
const badUUID = layer.uuid;
layer.uuid = uuidv4();
newlyAddedUUIDs.push({
name: layer.name,
uuid: layer.uuid,
replacesBadUUID: badUUID,
});
}
});
return newlyAddedUUIDs;
};

module.exports = populateUUIDs;
29 changes: 0 additions & 29 deletions API/Backend/Config/validate.js
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,6 @@ const validateLayers = (config) => {
}
});

errs = errs.concat(hasDuplicateLayerNames(config));
errs = errs.concat(hasNonHeaderWithSublayers(config));

return errs;
Expand Down Expand Up @@ -291,34 +290,6 @@ const hasNonHeaderWithSublayers = (config) => {
return errs;
};

const hasDuplicateLayerNames = (config) => {
let allNames = [];

depthTraversal(config.layers, 0);

function depthTraversal(node, depth) {
for (var i = 0; i < node.length; i++) {
allNames.push(node[i].name);
//Add other feature information while we're at it
if (node[i].sublayers != null && node[i].sublayers.length > 0) {
depthTraversal(node[i].sublayers, depth + 1);
}
}
}

let unique = [];
const errs = [];
allNames.forEach((name) => {
if (!unique.includes(name)) unique.push(name);
else
errs.push(
err(`Found duplicate layer name: '${name}'`, ["layers[layer].name"])
);
});

return errs;
};

const fillInMissingFieldsWithDefaults = (layer) => {
if (layer.type != "header") {
layer.initialOpacity =
Expand Down
8 changes: 4 additions & 4 deletions docs/pages/APIs/Configure/Configure_REST_API.md
Original file line number Diff line number Diff line change
Expand Up @@ -132,15 +132,15 @@ Updates a single layer. Specified layer values are deep merged and overwrite exi
| Parameter | Type | Required | Default | Description |
| :-------------------: | :-------: | :------: | :-----: | :----------------------------------------------------------------------------------------------------------------: |
| **mission** | _string_ | true | N/A | Mission name |
| **layerName** | _string_ | true | N/A | Layer to update |
| **layerUUID** | _string_ | true | N/A | Layer to update |
| **layer** | _object_ | true | N/A | A partial layer configuration object. See browser console-network tab responses for examples. |
| **placement.path** | _string_ | false | '' | A path to a header in 'layers' to place the new layer. A simple path ('sublayers' are added). Defaults to no group |
| **placement.index** | _number_ | false | end | Index in 'layers' (or path) to place the new layer. Out of range placement indices are best fit. |
| **forceClientUpdate** | _boolean_ | false | false | Push the change out to clients. |

#### Example

`curl -X POST -H "Authorization:Bearer <token>" -H "Content-Type: application/json" -d '{"mission":"Test", "layerName":"name", "layer":{}}' http://localhost:8889/api/configure/updateLayer`
`curl -X POST -H "Authorization:Bearer <token>" -H "Content-Type: application/json" -d '{"mission":"Test", "layerUUID":"uuid", "layer":{}}' http://localhost:8889/api/configure/updateLayer`

---

Expand All @@ -151,12 +151,12 @@ Removes a single layer from the configuration object.
| Parameter | Type | Required | Default | Description |
| :-------------------: | :-------: | :------: | :-----: | :-----------------------------: |
| **mission** | _string_ | true | N/A | Mission name |
| **layerName** | _string_ | true | N/A | Layer to update |
| **layerUUID** | _string_ | true | N/A | Layer to update |
| **forceClientUpdate** | _boolean_ | false | false | Push the change out to clients. |

#### Example

`curl -X POST -H "Authorization:Bearer <token>" -H "Content-Type: application/json" -d '{"mission":"Test", "layerName":"name"}' http://localhost:8889/api/configure/removeLayer`
`curl -X POST -H "Authorization:Bearer <token>" -H "Content-Type: application/json" -d '{"mission":"Test", "layerUUID":"name"}' http://localhost:8889/api/configure/removeLayer`

---

Expand Down

0 comments on commit ad60330

Please sign in to comment.