Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
// listen for events to track cache rate and errors
cacher.on("hit", function (key) {
console.log("Using Cached response for: " + key)
});
cacher.on("miss", function (key) {
console.log("No cached response for: " + key + ". Generating.")
});
cacher.on("error", function (key) {
console.log("Error with cache. " + err)
});
//Show specific GP operation
//Cacher will use in-memory cache for 1 day.
app.all('/services/custom/custom_operation', cacher.cache('days', 1), flow.define(function (req, res) {
//app.all('/services/custom/custom_operation', flow.define(function (req, res) {
this.args = {};
this.req = req;
this.res = res;
//Grab POST or QueryString args depending on type
if (req.method.toLowerCase() == "post") {
//If a post, then arguments will be members of the this.req.body property
this.args = req.body;
} else if (req.method.toLowerCase() == "get") {
//If request is a get, then args will be members of the this.req.query property
this.args = req.query;
}
if (JSON.stringify(this.args) != '{}') {
shortid = require('shortid');
var operation = {};
/* METADATA */
operation.name = "GetThemeFeaturesByID";
operation.description = "Gets theme-based features and properties based on GADM ID and level.";
operation.inputs = {};
operation.outputImage = false;
operation.inputs["ids"] = {}; //comma separated list of ids
operation.inputs["theme"] = {}; //string - theme name
operation.Query = "SELECT ST_AsGeoJSON(geom) as geom, theme_count, level FROM vw_theme_{{theme}}_gadm WHERE stack_guid IN ({{ids}})";
operation.execute = flow.define(
function (args, callback) {
this.args = args;
this.callback = callback;
//Step 1
//Generate UniqueID for this Task
operation.id = shortid.generate();
//See if inputs are set. Incoming arguments should contain the same properties as the input parameters.
if (operation.isInputValid(args) === true) {
operation.inputs["ids"] = args.ids;
operation.inputs["theme"] = args.theme.toLowerCase();
//need to wrap ids in single quotes
//Execute the query
var query;
var operation = {};
/* METADATA */
operation.name = "GetAggregatedThemeFeaturesByID";
operation.description = "Gets theme-based features and properties based on GADM ID and level.";
operation.inputs = {};
operation.outputImage = false;
operation.inputs["ids"] = {}; //comma separated list of ids
operation.inputs["theme"] = {}; //string - theme name
operation.inputs["gadm_level"] = {}; //string - gadm_level (0 -5)
operation.Query = "SELECT sum(count{{gadm_level}}) as project_count, guid{{gadm_level}} as guid, ST_ASGeoJSON(geom{{gadm_level}}) FROM sf_aggregated_gadm_{{theme}}_counts WHERE guid{{gadm_level}} IN ({{ids}}) GROUP BY guid{{gadm_level}}, geom{{gadm_level}}";
operation.execute = flow.define(
function (args, callback) {
this.args = args;
this.callback = callback;
//Step 1
//Generate UniqueID for this Task
operation.id = shortid.generate();
//See if inputs are set. Incoming arguments should contain the same properties as the input parameters.
if (operation.isInputValid(args) === true) {
operation.inputs["ids"] = args.ids;
operation.inputs["theme"] = args.theme.toLowerCase();
operation.inputs["gadm_level"] = args.gadm_level.toLowerCase();
//need to wrap ids in single quotes
//Execute the query
/* METADATA */
operation.name = "GetBreadCrumbsWithThemeCountsByID";
operation.description = "Gets full stack for breadcrumbs (including theme counts at each level) based on GADM ID and level.";
operation.inputs = {};
operation.outputImage = false;
operation.inputs["ids"] = {}; //comma separated list of ids
operation.inputs["theme"] = {}; //string - theme name
operation.inputs["gadm_level"] = {}; //string - gadm_level (0 -5)
//operation.Query = "SELECT sum(count{{gadm_level}}) as project_count, guid{{gadm_level}} as guid, ST_ASGeoJSON(geom{{gadm_level}}) as geom FROM sf_aggregated_gadm_{{theme}}_counts WHERE guid{{gadm_level}} IN ({{ids}}) GROUP BY guid{{gadm_level}}, geom{{gadm_level}}";
//SELECT guid2, name2, guid1, name1, guid0, name0, guidarc, namearc, guidarc FROM gadmrollup WHERE guid2 IN ('ca4f7dd8-3023-4e18-b644-13449e14b4b3')
operation.execute = flow.define(
function (args, callback) {
this.args = args;
this.callback = callback;
//Step 1
//Generate UniqueID for this Task
operation.id = shortid.generate();
//See if inputs are set. Incoming arguments should contain the same properties as the input parameters.
if (operation.isInputValid(args) === true) {
operation.inputs["ids"] = args.ids;
operation.inputs["theme"] = args.theme.toLowerCase();
operation.inputs["gadm_level"] = args.gadm_level.toLowerCase();
//need to wrap ids in single quotes
//Execute the query
function fetchTableNames(cb) {
var queryStr = "SELECT * FROM pg_tables;";
query(queryStr, function(err, rows) {
var tables = {};
rows.forEach(function(row){
tables[row.tablename] = true;
});
cb(tables);
});
}
/*
Wrap insertRows in a Flow. Each step is dependant upon the previous.
*/
var insertRows = flow.define(
function(queryTable, rows, queryStr, cb) {
this.queryTable = queryTable;
this.rows = rows;
this.queryStr = queryStr;
this.cb = cb;
//Get an array of proper field names
this.fields = getTableFieldNamesFromQuery(this.queryStr);
//Get table names from postgres
fetchTableNames(this);
},function (tables) { //TODO: Only look up table names once. Move this out of here.
// See if a query table exists.
"inner join (SELECT ST_Union(ST_transform( ST_BUFFER( ST_transform(geom, {srid}), {buffer_distance}), 4326 )) as geom " +
"FROM {country}_cicos " +
"WHERE {where_clause} " +
") b on " +
"st_intersects(a.geom, b.geom) " +
"GROUP BY a.landuse, a.name, a.total; " +
"CREATE INDEX _gptemp_gix ON _gptemp USING GIST (geom); " +
"END$$; " +
"SELECT SUM((_st_summarystats(ST_Clip(rast,_gptemp.geom, true), 1, true, 1)).sum) as sum, _gptemp.landuse, _gptemp.name, _gptemp.total, ST_AsGeoJSON(_gptemp.geom) as geom " +
"FROM {country}_population_raster, _gptemp " +
"WHERE ST_Intersects(_gptemp.geom,rast) " +
"GROUP BY _gptemp.landuse, _gptemp.geom, _gptemp.name, _gptemp.total; ";
operation.execute = flow.define(
function (args, callback) {
this.args = args;
this.callback = callback;
//Step 1
//Generate UniqueID for this GP Task
operation.id = shortid.generate();
//See if inputs are set. Incoming arguments should contain the same properties as the input parameters.
if (operation.isInputValid(args) === true) {
operation.inputs["where_clause"] = args.where_clause;
operation.inputs["buffer_distance"] = args.buffer_distance;
operation.inputs["country_code"] = args.country_code.toUpperCase();
//Take the point and buffer it in PostGIS
var query = { text: operation.Query.replace("{where_clause}", operation.inputs["where_clause"]).replace("{buffer_distance}", operation.inputs["buffer_distance"]).split("{country}").join(countries[operation.inputs["country_code"]].name).replace("{srid}", countries[operation.inputs["country_code"]].srid), values: [] };
"ST_UNION(st_intersection(a.geom,b.geom)) as geom " +
"from {country}_district_landuse a " +
"inner join (SELECT ST_Union(ST_transform( ST_BUFFER( ST_transform(ST_GeomFromGeoJson('{geojson}'), {srid}), {buffer_distance}), 4326 )) as geom " +
") b on " +
"st_intersects(a.geom, b.geom) " +
"GROUP BY a.landuse, a.name, a.total; " +
"CREATE INDEX \"_gptemp{gpid}_gix\" ON \"_gptemp{gpid}\" USING GIST (geom); " +
"END$$; " +
"SELECT SUM((_st_summarystats(ST_Clip(rast,c.geom, true), 1, true, 1)).sum) as sum, c.landuse, c.name, c.total, ST_AsGeoJSON(c.geom) as geom " +
"FROM {country}_population_raster, \"_gptemp{gpid}\" c " +
"WHERE ST_Intersects(c.geom,rast) " +
"GROUP BY c.landuse, c.geom, c.name, c.total; ";
operation.execute = flow.define(
function (args, callback) {
this.args = args;
this.callback = callback;
//Step 1
//Generate UniqueID for this GP Task
operation.id = shortid.generate();
//See if inputs are set. Incoming arguments should contain the same properties as the input parameters.
if (operation.isInputValid(args) === true) {
operation.inputs["geojson"] = args.geojson;
operation.inputs["buffer_distance"] = args.buffer_distance;
operation.inputs["country_code"] = args.country_code.toUpperCase();
//Take the point and buffer it in PostGIS
var query = { text: operation.Query.replace("{geojson}", operation.inputs["geojson"]).split("{gpid}").join(operation.id).replace("{buffer_distance}", operation.inputs["buffer_distance"]).split("{country}").join(countries[operation.inputs["country_code"]].name).replace("{srid}", countries[operation.inputs["country_code"]].srid), values: [] };
exports.createCachedFolder = function (table) {
var folder = './public/cached_nodetiles/' + table;
//create a folder for this table in public/cached_nodetiles if it doesn't exist
fs.exists(folder, function (exists) {
if (exists === false) {
//make it
console.log("Didn't find cache folder. Tyring to make folder: " + folder);
fs.mkdir(folder, function () {
console.log("Made " + folder);
});
//Synch
}
});
}
//Create a static renderer that will always use the default styling
exports.createPGTileRenderer = flow.define(function (app, table, geom_field, epsgSRID, cartoFile) {
this.app = app;
this.table = table;
this.epsg = epsgSRID;
var name;
var stylepath = __dirname + '/cartocss/';
var fullpath = "";
//Set the path to the style file
if (cartoFile) {
//Passed in
fullpath = stylepath + cartoFile;
} else {
//default
fullpath = stylepath + table + styleExtension;
fs.exists(folder, function (exists) {
if (exists === false) {
//make it
console.log("Didn't find cache folder. Tyring to make folder: " + folder);
fs.mkdir(folder, function () {
console.log("Made " + folder);
});
//Synch
}
});
};
//Create a renderer that will accept dynamic GeoJSON Objects and styling and bring back a single image to fit the map's extent.
exports.createGeoJSONQueryRenderer = flow.define(function (app, geoJSON, epsgSRID, cartoFile, id, callback) {
this.app = app;
this.geoJSON = geoJSON;
//this.geom_field = geom_field;
this.epsg = epsgSRID;
var _self = this;
var dynamicURL = '/services/GeoJSONQueryMap/' + id;
//Create Route for this table - TODO: Figure out how/when to kill this endpoint
this.app.all(dynamicURL, function (req, res) {
//Check for correct args
//Needs: width (px), height (px), bbox (xmin, ymax, xmax, ymin), where, optional styling
var args = {};
if (gp && gp.names) {
for ( i = 0; i < gp.names.length; i++) {
args.opslist.push({
name : gp.names[i],
link : "geoprocessing_operation?name=" + gp.names[i]
});
}
}
//Render HTML page with results at bottom
common.respond(req, res, args);
});
//Show specific GP operation
app.all('/services/geoprocessing/geoprocessing_operation', flow.define(function(req, res) {
this.args = {};
this.req = req;
this.res = res;
//Grab POST or QueryString args depending on type
if (req.method.toLowerCase() == "post") {
//If a post, then arguments will be members of the this.req.body property
this.args = req.body;
//Add in req.files if present
if(req.files) this.args.files = req.files;
} else if (req.method.toLowerCase() == "get") {
//If request is a get, then args will be members of the this.req.query property
this.args = req.query;
}
if (JSON.stringify(this.args) != '{}') {