-
+
Status of Query: ${status.query.queryName}
-
Last Updated: ${status.updated | dateTime}
+
Last Updated: ${status.updated | dateTime}
+
Waiting on response from network...
-
+
- Query results are shown below
- **************************************************************************
+ Query results are shown below:
+
\ No newline at end of file
diff --git a/shrine-webclient/src/main/js/client/js-shrine/src/views/query-status/query-status.js b/shrine-webclient/src/main/js/client/js-shrine/src/views/query-status/query-status.js
index c3e81f832..000d566e7 100644
--- a/shrine-webclient/src/main/js/client/js-shrine/src/views/query-status/query-status.js
+++ b/shrine-webclient/src/main/js/client/js-shrine/src/views/query-status/query-status.js
@@ -1,33 +1,33 @@
-import {EventAggregator} from 'aurelia-event-aggregator';
-import {notifications, commands} from 'common/shrine.messages';
-import {QueryStatusModel} from 'common/query-status.model';
-export class QueryStatus {
- static inject = [EventAggregator, notifications, commands, QueryStatusModel];
- constructor(evtAgg, notifications, commands, queryStatus) {
- const initialState = () => ({query: {queryName: null, updated: null, complete: false}, nodes: null});
+import { QueryStatusModel } from 'services/query-status.model';
+import { PubSub } from 'services/pub-sub'
+export class QueryStatus extends PubSub {
+ static inject = [QueryStatusModel];
+ constructor(queryStatus, ...rest) {
+ super(...rest);
+ const initialState = () => ({ query: { queryName: null, updated: null, complete: false }, nodes: null });
this.status = initialState();
- // -- publishers --
- const publishFetchNetworkId = n => evtAgg.publish(commands.shrine.fetchNetworkId, n);
- const publishFetchQuery = id => evtAgg.publish(commands.shrine.fetchQuery, id);
// -- subscribers -- //
- evtAgg.subscribe(notifications.i2b2.queryStarted, (n) => {
+ this.subscribe(this.notifications.i2b2.queryStarted, (n) => {
// -- @todo: centralize the logic, investigate adding a new "status" every time -- //
this.status.query.queryName = n;
- publishFetchNetworkId(n)
});
- evtAgg.subscribe(notifications.shrine.networkIdReceived, id => publishFetchQuery(id));
- evtAgg.subscribe(notifications.shrine.queryReceived, data => {
+ this.subscribe(this.notifications.i2b2.networkIdReceived, id => this.publish(this.commands.shrine.fetchQuery, id));
+ this.subscribe(this.notifications.shrine.queryReceived, data => {
// -- @todo: centralize the logic, investigate adding a new "status" every time -- //
- this.status.query = {...this.status.query, ...data.query};
+ this.status.query = { ...this.status.query, ...data.query };
this.status.nodes = data.nodes;
this.status.updated = Number(new Date());
const complete = data.query.complete;
const networkId = data.query.networkId;
- if(!complete) {
- publishFetchQuery(networkId)
+ if (!complete) {
+ window.setTimeout(() => publishFetchQuery(networkId), 10000);
}
});
- // -- testing only -- //
- evtAgg.publish(notifications.i2b2.queryStarted, '@queryqueryName');
+
+ const isDevEnv = document.location.href.includes('http://localhost:8000/');
+ if (isDevEnv) {
+ this.publish(this.notifications.i2b2.queryStarted, "started query");
+ this.publish(this.notifications.i2b2.networkIdReceived, 1);
+ }
}
}
\ No newline at end of file
diff --git a/shrine-webclient/src/main/js/server/data/query-result.js b/shrine-webclient/src/main/js/server/data/query-result.js
new file mode 100644
index 000000000..80cd4fccc
--- /dev/null
+++ b/shrine-webclient/src/main/js/server/data/query-result.js
@@ -0,0 +1,217 @@
+module.exports = {
+ "results": [
+ {
+ "count": 1185,
+ "networkQueryId": 2421519216383772200,
+ "statusMessage": "FINISHED",
+ "changeDate": 1501001608958,
+ "instanceId": 221,
+ "resultId": 367,
+ "status": "FINISHED",
+ "resultType": {
+ "isBreakdown": false,
+ "name": "PATIENT_COUNT_XML",
+ "id": 4,
+ "i2b2Options": {
+ "description": "Number of patients",
+ "displayType": "CATNUM"
+ }
+ },
+ "adapterNode": "shrine-dev1",
+ "breakdowns": [
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Race Patient Breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_RACE_COUNT_XML",
+ },
+ "results": [
+ { changeDate: 1502294526455, value: -1, dataKey: "Other" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Asian Pacific Islander" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Middle Eastern" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Not recorded" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Eskimo" },
+ { changeDate: 1502294526455, value: -1, dataKey: "American Indian" },
+ { changeDate: 1502294526455, value: 80, dataKey: "White" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Native American" },
+ { changeDate: 1502294526455, value: 370, dataKey: "Black" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Multiracial" },
+ { changeDate: 1502294526455, value: 170, dataKey: "Hispanic" },
+ { changeDate: 1502294526455, value: 95, dataKey: "Indian" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Aleutian" },
+ { changeDate: 1502294526455, value: 105, dataKey: "Asian" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Oriental" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Navajo" }
+ ]
+ },
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Age patient breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_AGE_COUNT_XML",
+ },
+ results: [
+ { changeDate: 1502294526455, value: 290, dataKey: " 18-34 years old" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Not recorded" },
+ { changeDate: 1502294526455, value: 80, dataKey: " 45-54 years old" },
+ { changeDate: 1502294526455, value: -1, dataKey: " 0-9 years old" },
+ { changeDate: 1502294526455, value: 235, dataKey: " 35-44 years old" },
+ { changeDate: 1502294526455, value: 45, dataKey: " 75-84 years old" },
+ { changeDate: 1502294526455, value: 35, dataKey: ">= 85 years old" },
+ { changeDate: 1502294526455, value: 65, dataKey: " 65-74 years old" },
+ { changeDate: 1502294526455, value: 150, dataKey: ">= 65 years old" },
+ { changeDate: 1502294526455, value: -1, dataKey: " 10-17 years old" },
+ { changeDate: 1502294526455, value: 45, dataKey: " 55-64 years old" }
+ ]
+ },
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Gender patient breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_COUNT_COUNT_XML",
+ },
+ results: [
+ { changeDate: 1502294526455, value: 1180, dataKey: "Female" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Male" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Unknown" }
+ ]
+ },
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Vital Status patient breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_VITALSTATS_COUNT_XML",
+ },
+ results: [
+ { changeDate: 1502294526455, value: 25, dataKey: "Deceased" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Deferred" },
+ { changeDate: 1502294526455, value: 1155, dataKey: "Living" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Not recorded" }
+ ]
+ }
+ ]
+ },
+ {
+ "count": 1795,
+ "networkQueryId": 2421519216383772200,
+ "statusMessage": "FINISHED",
+ "changeDate": 1501001608966,
+ "instanceId": 174,
+ "resultId": 320,
+ "status": "FINISHED",
+ "resultType": {
+ "isBreakdown": false,
+ "name": "PATIENT_COUNT_XML",
+ "id": 4,
+ "i2b2Options": {
+ "description": "Number of patients",
+ "displayType": "CATNUM"
+ }
+ },
+ "adapterNode": "shrine-dev2",
+ "breakdowns": [
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Race Patient Breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_RACE_COUNT_XML",
+ },
+ "results": [
+ { changeDate: 1502294526455, value: -1, dataKey: "Other" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Asian Pacific Islander" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Middle Eastern" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Not recorded" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Eskimo" },
+ { changeDate: 1502294526455, value: -1, dataKey: "American Indian" },
+ { changeDate: 1502294526455, value: 80, dataKey: "White" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Native American" },
+ { changeDate: 1502294526455, value: 370, dataKey: "Black" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Multiracial" },
+ { changeDate: 1502294526455, value: 170, dataKey: "Hispanic" },
+ { changeDate: 1502294526455, value: 95, dataKey: "Indian" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Aleutian" },
+ { changeDate: 1502294526455, value: 105, dataKey: "Asian" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Oriental" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Navajo" }
+ ]
+ },
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Age patient breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_AGE_COUNT_XML",
+ },
+ results: [
+ { changeDate: 1502294526455, value: 290, dataKey: " 18-34 years old" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Not recorded" },
+ { changeDate: 1502294526455, value: 80, dataKey: " 45-54 years old" },
+ { changeDate: 1502294526455, value: -1, dataKey: " 0-9 years old" },
+ { changeDate: 1502294526455, value: 235, dataKey: " 35-44 years old" },
+ { changeDate: 1502294526455, value: 45, dataKey: " 75-84 years old" },
+ { changeDate: 1502294526455, value: 35, dataKey: ">= 85 years old" },
+ { changeDate: 1502294526455, value: 65, dataKey: " 65-74 years old" },
+ { changeDate: 1502294526455, value: 150, dataKey: ">= 65 years old" },
+ { changeDate: 1502294526455, value: -1, dataKey: " 10-17 years old" },
+ { changeDate: 1502294526455, value: 45, dataKey: " 55-64 years old" }
+ ]
+ },
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Gender patient breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_COUNT_COUNT_XML",
+ },
+ results: [
+ { changeDate: 1502294526455, value: 1180, dataKey: "Female" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Male" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Unknown" }
+ ]
+ },
+ {
+ resultType: {
+ i2b2Options: {
+ description: "Vital Status patient breakdown",
+ displayType: "CATNUM"
+ },
+ isBreakdown: true,
+ name: "PATIENT_VITALSTATS_COUNT_XML",
+ },
+ results: [
+ { changeDate: 1502294526455, value: 25, dataKey: "Deceased" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Deferred" },
+ { changeDate: 1502294526455, value: 1155, dataKey: "Living" },
+ { changeDate: 1502294526455, value: -1, dataKey: "Not recorded" }
+ ]
+ }
+ ]
+ }
+ ],
+ "query": {
+ "queryName": "Female@12:53:25",
+ "changeDate": 1501001607335,
+ "networkId": "2421519216383772161",
+ "queryXml": "
SHRINE180000i2b2demoshrineSessionKey:HUTBEZkgsz9XyADXjDEO24215192163837721613Test dev1 approved4PATIENT_COUNT_XMLfalseNumber of patientsCATNUMFemale@12:53:25\\\\SHRINE\\SHRINE\\Demographics\\Gender\\Female\\",
+ "dateCreated": 1501001607334
+ }
+};
\ No newline at end of file
diff --git a/shrine-webclient/src/main/js/server/pm-mock.js b/shrine-webclient/src/main/js/server/pm-mock.js
index 82801766b..c45f92dc2 100644
--- a/shrine-webclient/src/main/js/server/pm-mock.js
+++ b/shrine-webclient/src/main/js/server/pm-mock.js
@@ -1,115 +1,113 @@
/*
This is a first stab at a i2b2 pm-mock
@todo: refactor/cleanup this module.
*/
var express = require('express');
var cors = require('cors');
var bodyParser = require('body-parser');
require('body-parser-xml')(bodyParser);
var app = express();
var bodyParser = require('body-parser');
var port = process.env.PORT || 6443;
var router = express.Router();
var fs = require('fs');
var isAuthorized = false;
function start(dir) {
app.use(bodyParser.urlencoded({ extended: true }));
app.use(bodyParser.json());
app.use(bodyParser.xml({
limit: '1GB', // Reject payload bigger than 1 MB
xmlParseOptions: {
normalize: true, // Trim whitespace inside text nodes
normalizeTags: true, // Transform tags to lowercase
explicitArray: false // Only put nodes in array if >1
}
}));
app.use(cors());
app.use('/', router);
app.listen(port);
console.log('I2B2SERVER Mock Server started on port: ' + port);
// -- routes --//
router.post('/shrine-proxy/request', function (req, res) {
var requestType = parseRequest(req);
var fileName = getFilename(requestType);
var xml = fs.readFileSync('./' + dir+ '/i2b2-xml/' + fileName);
res.header('Content-Type', 'text/xml').send(xml);
});
router.get('/shrine-metadata/data', function(req, res) {
res.json('steward@steward.com');
});
router.get('/shrine-metadata/qep/queryResultsTable', (req, res) => {
//todo: cleanup.
const service = require('./data/async-queries');
const url = require('url');
const query = url.parse(req.url, true).query;
const result = service.getQueryResults(query.skip, query.limit);
res.json(result);
})
}
-router.get('/shrine-metadata/qep/queryResults', (req, res) => {
- const service = require('./data/async-queries');
- const url = require('url');
- const data = url.parse(req.url, true).query;
- const result = service.getQueryStatus(data.networkId);
- setTimeout(() => res.json(result), 5000);
+router.get('/shrine-metadata/qep/queryResult/:id', (req, res) => {
+ const result= require('./data/query-result');
+ const TIMEOUT = 5000;
+ setTimeout(() => res.json(result), TIMEOUT);
});
router.get('/shrine-metadata/qep/networkId', (req, res) => {
const service = require('./data/async-queries');
const url = require('url');
const data = url.parse(req.url, true).query;
const result = service.getNetworkId(data.queryName);
res.json(result);
});
/*
Any request with an XML payload will be parsed and a JavaScript requestect produced on req.body
corresponding to the request payload.
This is messy refactor.
*/
function parseRequest(request) {
request = request.body;
var requestTypes = ['i2b2:request', 'ns2:request', 'ns3:request', 'ns6:request'];
var requestType = requestTypes.find(t => request[t] !== undefined);
request = (request[requestType] && request[requestType].message_body) ?
request[requestType].message_body : null;
return parseBodyRequest(request);
}
function parseBodyRequest(request) {
var bodyTypes = ['pm:get_user_configuration', 'ns4:get_categories', 'ns4:get_schemes', 'ns7:sheriff_header', 'ns4:psmheader'];
var bodyType = bodyTypes.find(t => request[t] !== undefined);
if (bodyType == 'ns4:psmheader') {
bodyType = request['ns4:psmheader'].request_type;
}
return bodyType;
}
function getFilename(value) {
let fileMap = {
'pm:get_user_configuration': 'getUserAuth.xml',
'ns4:get_categories': 'GetCategories.xml',
'ns4:get_schemes': 'GetSchemes.xml',
'ns7:sheriff_header': 'getUserAuth.xml',
'CRC_QRY_getResultType': 'getQRY_getResultType.xml',
'CRC_QRY_getQueryMasterList_fromUserId': 'getQueryMasterList_fromUserId.xml'
};
return fileMap[value];
}
module.exports = {start: start};
\ No newline at end of file