Produced by Araxis Merge on 10/3/2017 11:16:05 AM Central Daylight Time. See www.araxis.com for information about Merge. This report uses XHTML and CSS2, and is best viewed with a modern standards-compliant browser. For optimum results when printing this report, use landscape orientation and enable printing of background images and colours in your browser.
| # | Location | File | Last Modified |
|---|---|---|---|
| 1 | ehmp.zip\ehmp\ehmp\product\production\vx-sync\tools\solr | check-solr.js | Mon Aug 28 20:41:42 2017 UTC |
| 2 | ehmp.zip\ehmp\ehmp\product\production\vx-sync\tools\solr | check-solr.js | Mon Oct 2 20:07:29 2017 UTC |
| Description | Between Files 1 and 2 |
|
|---|---|---|
| Text Blocks | Lines | |
| Unchanged | 2 | 756 |
| Changed | 1 | 2 |
| Inserted | 0 | 0 |
| Removed | 0 | 0 |
| Whitespace | |
|---|---|
| Character case | Differences in character case are significant |
| Line endings | Differences in line endings (CR and LF characters) are ignored |
| CR/LF characters | Not shown in the comparison detail |
No regular expressions were active.
| 1 | 'use stric t'; | |
| 2 | ||
| 3 | require('. ./../env-s etup'); | |
| 4 | ||
| 5 | var _ = re quire('und erscore'); | |
| 6 | var async = require( 'async'); | |
| 7 | var yargs = require( 'yargs'); | |
| 8 | var fs = r equire('fs '); | |
| 9 | var errorU til = requ ire(global .VX_UTILS + 'error') ; | |
| 10 | ||
| 11 | var config = require (global.VX _ROOT + 'w orker-conf ig'); | |
| 12 | var JdsCli ent = requ ire(global .VX_SUBSYS TEMS + 'jd s/jds-clie nt'); | |
| 13 | var solrSm artClient = require( 'solr-smar t-client') ; | |
| 14 | ||
| 15 | var log = require('b unyan').cr eateLogger ({ | |
| 16 | name: 'check-sol r', | |
| 17 | level: 'info' | |
| 18 | }); | |
| 19 | ||
| 20 | //TODO: Re place jds/ solr clien t creation with poll er-utils b uildEnviro nment | |
| 21 | var jdsCli ent = new JdsClient( log, log, config); | |
| 22 | var solr = solrSmart Client.ini tClient(co nfig.solrC lient.core , config.s olrClient. zooKeeperC onnection, log); | |
| 23 | ||
| 24 | var argv = parseOpti ons(log); | |
| 25 | ||
| 26 | var option Config = _ .clone(con fig.syncRe questApi); | |
| 27 | ||
| 28 | //Default to using V M sync end point | |
| 29 | if (!argv. local && ! argv.l) { | |
| 30 | optionConf ig.host = ' IP '; | |
| 31 | } | |
| 32 | log.debug( 'Using syn c endpoint location: ', option Config.hos t); | |
| 33 | ||
| 34 | log.info(' check-solr : Starting process.. .'); | |
| 35 | ||
| 36 | // http:// ip:port/so lr/vpr/sel ect?q=*&fq =pid:(9E7A ;100826+OR +C877;1008 26+OR+HDR; 5000000327 V828570)&w t=json&fl= uid,pid,do main | |
| 37 | function b uildSolrSe archUrl(co mpletedPid s) { | |
| 38 | var pi dJoin = co mpletedPid s.join('+O R+'); | |
| 39 | //Use very large number fo r rows, mo re than co uld concei vably be r eturned, s o that all data is r eturned on a single call | |
| 40 | var ur l = 'q=*&f q=pid:(' + pidJoin + ')&wt=jso n&fl=uid,p id,domain& rows=10000 00000'; | |
| 41 | return url; | |
| 42 | } | |
| 43 | ||
| 44 | ||
| 45 | getListOfP atients(lo g, argv, f unction(er r, patient s) { | |
| 46 | if (er r) { | |
| 47 | lo g.error(er r); | |
| 48 | lo g.error('s olr-check: Error enc ountered g etting lis t of patie nts.'); | |
| 49 | re turn; | |
| 50 | } | |
| 51 | ||
| 52 | //in a bsence of support fo r Set unti l node v0. 12, use a collection with name d properti es/keys, n ull value, will coll ect the ke ys at the end | |
| 53 | var al lPids = [] ; | |
| 54 | ||
| 55 | log.in fo('Using patient si mple statu s to deter mine uniqu e Pids to process... '); | |
| 56 | ||
| 57 | async. eachSeries (patients, function( patient, u niquePidCa llback){ | |
| 58 | // query simp le status | |
| 59 | va r path = ' /sync/comb inedstat/' + patient ; | |
| 60 | lo g.info('Pr ocessing f ind patien t result ' + patient ); | |
| 61 | ||
| 62 | jd sClient.ex ecute(path , null, 'G ET', {}, f unction (e rr, respon se, result ) { | |
| 63 | if (err) { | |
| 64 | log. error('Err or queryin g JDS: ' + path); | |
| 65 | log. error(err) ; | |
| 66 | retu rn; | |
| 67 | } | |
| 68 | ||
| 69 | var site s = result .sites; | |
| 70 | log.info ('Simple J DS status for pid ' + patient) ; | |
| 71 | log.info (sites); | |
| 72 | ||
| 73 | _.each(s ites, func tion(site) { | |
| 74 | log. info('Site pid: ' + site.pid); | |
| 75 | allP ids.push(s ite.pid); | |
| 76 | }); | |
| 77 | uniquePi dCallback( null); | |
| 78 | }) ; | |
| 79 | }, | |
| 80 | functi on(err){ | |
| 81 | if (err){ | |
| 82 | log.erro r('Error e ncountered eachSerie s within p atients'); | |
| 83 | process. exit(); | |
| 84 | } | |
| 85 | el se{ | |
| 86 | log.debu g('async.e achSeries patients c omplete... '); | |
| 87 | //write results | |
| 88 | ||
| 89 | //now ge t unique s et | |
| 90 | var uniq uePids = _ .uniq(allP ids); | |
| 91 | log.info ('uniquePi ds: '); | |
| 92 | log.info (uniquePid s); | |
| 93 | ||
| 94 | log.info ('Unique P ids determ ined'); | |
| 95 | processP atients(lo g, uniqueP ids); | |
| 96 | ||
| 97 | } | |
| 98 | }); | |
| 99 | ||
| 100 | //quer y jds deta iled statu s | |
| 101 | functi on process Patients(l ogger, pat ients) { | |
| 102 | ||
| 103 | ||
| 104 | lo gger.debug ('processP atients'); | |
| 105 | lo gger.debug ('input pa tients:'); | |
| 106 | lo gger.debug (patients) ; | |
| 107 | ||
| 108 | va r patientT asksInfo = _.map(pat ients, fun ction(pati ent){ | |
| 109 | var task Info = {pi d: patient , | |
| 110 | quer yComplete: false, | |
| 111 | data Missing: f alse}; | |
| 112 | return t askInfo; | |
| 113 | }) ; | |
| 114 | ||
| 115 | ||
| 116 | as ync.eachSe ries(patie ntTasksInf o, functio n(patientT ask, eachP atientCall back){ | |
| 117 | ||
| 118 | var pati ent = pati entTask.pi d; | |
| 119 | var path = '/statu s/' + pati ent + '?de tailed=tru e'; | |
| 120 | ||
| 121 | jdsClien t.execute( path, null , 'GET', { }, functio n (err, re sponse, re sult) { | |
| 122 | if ( err) { | |
| 123 | logger.err or('Error querying J DS: ' + pa th); | |
| 124 | logger.err or(err); | |
| 125 | return eac hPatientCa llback(err ); | |
| 126 | } | |
| 127 | ||
| 128 | if ( result.com pletedStam p === unde fined){ | |
| 129 | //No compl etedStamp, so no sol r records expected | |
| 130 | logger.deb ug('Patien t ' + pati ent + ' St atus missi ng complet edStamp.') ; | |
| 131 | return eac hPatientCa llback(nul l, patient ); | |
| 132 | } | |
| 133 | ||
| 134 | logg er.trace(' sourceMeta Stamp'); | |
| 135 | var sourceMeta Stamp = re sult.compl etedStamp. sourceMeta Stamp; | |
| 136 | logg er.trace(s ourceMetaS tamp); | |
| 137 | ||
| 138 | var completedP ids = []; | |
| 139 | var completedS ourceKeys = _.keys(s ourceMetaS tamp); | |
| 140 | ||
| 141 | ||
| 142 | //TO DO: change reference s to "faci lity" with "source" to be in l ine with v x-sync ter minology | |
| 143 | //ga ther all t he complet ed Pids | |
| 144 | comp letedSourc eKeys.forE ach(functi on(complet edSource){ | |
| 145 | //get the pid | |
| 146 | var source Data = sou rceMetaSta mp[complet edSource]; | |
| 147 | var pid = sourceData .pid; | |
| 148 | //save the pid | |
| 149 | completedP ids.push(p id); | |
| 150 | }); | |
| 151 | ||
| 152 | //fo r each fac ility defi ned in sou rceMetaSta mp | |
| 153 | asyn c.eachSeri es(complet edSourceKe ys, functi on(complet edSource, eachFacili tyCallback ){ | |
| 154 | ||
| 155 | //If the f acility is n't for th e specific pid we're working u nder, skip it... | |
| 156 | var patien tPidSource = patient .split(';' )[0]; | |
| 157 | if (comple tedSource !== patien tPidSource ){ | |
| 158 | logger .debug('Sk ipping Fac ility ' + completedS ource + ' did not ma tch patien t ' + pati ent); | |
| 159 | return eachFacil ityCallbac k(null); | |
| 160 | } | |
| 161 | / /get the p id | |
| 162 | var source Data = sou rceMetaSta mp[complet edSource]; | |
| 163 | var pid = sourceData .pid; | |
| 164 | ||
| 165 | logger.inf o('process ing pid ' + pid); | |
| 166 | ||
| 167 | var domain MetaStamp = sourceDa ta.domainM etaStamp; | |
| 168 | var facili tyDomainKe ys = _.key s(domainMe taStamp); | |
| 169 | var patien tSourceEve ntUids = [ ]; //hol d all foun d event ui ds | |
| 170 | ||
| 171 | _.each(fac ilityDomai nKeys, fun ction(faci lityDomain Key){ | |
| 172 | if (is SolrDomain (facilityD omainKey)) { | |
| 173 | lo g.debug('c hecking do main ' + f acilityDom ainKey); | |
| 174 | va r eventMet aStamp = d omainMetaS tamp[facil ityDomainK ey].eventM etaStamp; | |
| 175 | ||
| 176 | va r eventUid s = _.keys (eventMeta Stamp); | |
| 177 | ||
| 178 | // check stor ed value f or each ev entuid bef ore adding it | |
| 179 | ev entUids.fo rEach(func tion(event Uid){ | |
| 180 | var even tData = ev entMetaSta mp[eventUi d]; | |
| 181 | if (even tData.stor ed === tru e){ | |
| 182 | pati entSourceE ventUids = patientSo urceEventU ids.concat (eventUid) ; | |
| 183 | } | |
| 184 | }) ; | |
| 185 | } | |
| 186 | }); | |
| 187 | ||
| 188 | logger.deb ug('Finish ed eachSer ies on fac ilityDomai nKeys'); | |
| 189 | ||
| 190 | //all pids and event uids have been save d | |
| 191 | //now quer y solr | |
| 192 | ||
| 193 | //search w ith just t he current facility pid | |
| 194 | var url = buildSolrS earchUrl([ pid]); | |
| 195 | logger.deb ug('Queryi ng Solr wi th query: ' + url); | |
| 196 | // "docs": [ | |
| 197 | // { | |
| 198 | // "uid": "u rn:va:alle rgy:9E7A:3 :751", | |
| 199 | // "pid": "9 E7A;3", | |
| 200 | // "domain": "allergy" | |
| 201 | // }, | |
| 202 | // { | |
| 203 | // "uid": "u rn:va:alle rgy:9E7A:3 :874", | |
| 204 | // "pid": "9 E7A;3", | |
| 205 | // "domain": "allergy" | |
| 206 | // }, | |
| 207 | // | |
| 208 | ||
| 209 | solr.searc h(url, fun ction(err, result){ | |
| 210 | if (er r){ | |
| 211 | lo gger.error ('Error on solr.sear ch'); | |
| 212 | lo gger.error (err); | |
| 213 | ||
| 214 | re turn eachF acilityCal lback(err) ; | |
| 215 | } | |
| 216 | ||
| 217 | logger .trace('ev al solr se arch resul t'); | |
| 218 | logger .trace(res ult); | |
| 219 | ||
| 220 | logger .debug('ex ecution of solr quer y: ' + url + ', numF ound: ' + result.res ponse.numF ound); | |
| 221 | patien tTask.quer yComplete = true; | |
| 222 | ||
| 223 | var do cs = resul t.response .docs; | |
| 224 | ||
| 225 | patien tTask.data Missing = !(_.every( patientSou rceEventUi ds, functi on(eventUi d) { | |
| 226 | va r matching Docs = _.f indWhere(d ocs, {uid: eventUid} ); | |
| 227 | if (matching Docs === u ndefined) { | |
| 228 | logger.i nfo('Unabl e to find record ' + eventUid + ' in Sol r'); | |
| 229 | return f alse; | |
| 230 | } | |
| 231 | re turn true; | |
| 232 | })); | |
| 233 | ||
| 234 | eachFa cilityCall back(null) ; | |
| 235 | }); | |
| 236 | }, | |
| 237 | func tion(err){ | |
| 238 | if (err) { | |
| 239 | logger .error('Er ror eachSe ries on co mpletedFac ilityKeys' ); | |
| 240 | logger .error(err ); | |
| 241 | return eachPatie ntCallback (err); | |
| 242 | } | |
| 243 | else{ | |
| 244 | logger .debug('Fi nished eac hSeries on completed FacilityKe ys'); | |
| 245 | return eachPatie ntCallback (null); | |
| 246 | } | |
| 247 | }); //end eac hSeries on completed FacilityKe ys | |
| 248 | ||
| 249 | }); //e nd jds exe cute statu s | |
| 250 | }, | |
| 251 | //series callback patientTas ksInfo | |
| 252 | function (err){ | |
| 253 | if ( err){ | |
| 254 | logger.err or('Error encountere d eachSeri es within processPat ients'); | |
| 255 | process.ex it(); | |
| 256 | } | |
| 257 | else { | |
| 258 | log.debug( 'processPa tients com plete...') ; | |
| 259 | //write re sults | |
| 260 | ||
| 261 | writeOutpu tFile(log, patientTa sksInfo, f unction(){ | |
| 262 | proces s.exit(); | |
| 263 | }); | |
| 264 | } | |
| 265 | }); //en d eachSeri es patient TasksInfo | |
| 266 | } | |
| 267 | ||
| 268 | // pro cessPatien ts(patient s); | |
| 269 | }); | |
| 270 | ||
| 271 | //takes co llection o f {pid, da taMissing} | |
| 272 | function w riteOutput File(logge r, results , writeOut putFileCal lback) { | |
| 273 | var fi leContents = ''; | |
| 274 | result s.forEach( function ( patientInf o) { | |
| 275 | if (patientI nfo.dataMi ssing) { | |
| 276 | logger.d ebug('addi ng ' + pat ientInfo.p id + ' to results'); | |
| 277 | fileCont ents += pa tientInfo. pid + '\n' ; | |
| 278 | } | |
| 279 | }); | |
| 280 | ||
| 281 | //writ e results to file | |
| 282 | fs.wri teFile('/t mp/check-s olr-result s.txt', fi leContents , function (err){ | |
| 283 | if (err) { | |
| 284 | logger.d ebug('err: ' + err); | |
| 285 | } | |
| 286 | lo gger.debug ('File wri tten'); | |
| 287 | ||
| 288 | wr iteOutputF ileCallbac k(err); | |
| 289 | }); | |
| 290 | } | |
| 291 | ||
| 292 | ||
| 293 | ||
| 294 | var solrDo mains = [ | |
| 295 | 'aller gy', | |
| 296 | 'appoi ntment', | |
| 297 | 'consu lt', | |
| 298 | 'cpt', | |
| 299 | 'docum ent', | |
| 300 | 'facto r', | |
| 301 | 'image ', | |
| 302 | 'immun ization', | |
| 303 | 'lab', | |
| 304 | 'med', | |
| 305 | 'order ', | |
| 306 | 'pov', | |
| 307 | 'probl em', | |
| 308 | 'proce dure', | |
| 309 | 'surge ry', | |
| 310 | 'visit ', | |
| 311 | 'vital ', | |
| 312 | 'vlerd ocument' | |
| 313 | ]; | |
| 314 | ||
| 315 | function i sSolrDomai n(key){ | |
| 316 | return _.contain s(solrDoma ins, key); | |
| 317 | } | |
| 318 | ||
| 319 | function p arseOption s(logger) { | |
| 320 | var ar gv = yargs | |
| 321 | .c heck(funct ion(args) { | |
| 322 | if ((!ar gs.s && !a rgs.e)) { | |
| 323 | logg er.error(' Invalid ar guments. S ee usage.' ); | |
| 324 | retu rn false; | |
| 325 | } | |
| 326 | return t rue; | |
| 327 | }) | |
| 328 | .o ption('s', { | |
| 329 | alias: ' startdate' , | |
| 330 | describe : 'Sync St art date ( according to JDS)', | |
| 331 | type: 's tring' | |
| 332 | }) | |
| 333 | .o ption('e', { | |
| 334 | alias: ' enddate', | |
| 335 | describe : 'Sync En d date (ac cording to JDS)', | |
| 336 | type: 's tring' | |
| 337 | }) | |
| 338 | .u sage('Usag e: ./check -solr.sh - startdate <string> - enddate <s tring>') | |
| 339 | .a rgv; | |
| 340 | ||
| 341 | return argv; | |
| 342 | } | |
| 343 | ||
| 344 | function g etListOfPa tients(log ger, argv, callback) { | |
| 345 | ||
| 346 | logger .trace('ge tListOfPat ients(): e ntering me thod...'); | |
| 347 | //quer y jds by a rgument da tes | |
| 348 | queryJ dsPatients BySyncDate Range(logg er, argv.s tartdate, argv.endda te, functi on(err, re sponse, re sult){ | |
| 349 | lo gger.debug ('queryJds PatientsBy SyncDateRa nge callba ck'); | |
| 350 | if (err){ | |
| 351 | logger.d ebug('erro r' + err); | |
| 352 | callback (err, null ); | |
| 353 | } | |
| 354 | ||
| 355 | // var body = val(resu lt, 'body' ); | |
| 356 | lo gger.info( 'getListOf Patients ( initial JD S query) t otalItems: ' + resul t.data.tot alItems); | |
| 357 | ||
| 358 | va r pidArray = _.map(r esult.data .items, 'p id'); | |
| 359 | ca llback(nul l, pidArra y); | |
| 360 | }); | |
| 361 | ||
| 362 | } | |
| 363 | ||
| 364 | function q ueryJdsPat ientsBySyn cDateRange (logger, s tartdate, enddate, c allback) { | |
| 365 | logger .debug('so lr-check.q uerySyncsf orDateRang e() %s %s' , startdat e, enddate ); | |
| 366 | ||
| 367 | if (_. isEmpty(st artdate)) { | |
| 368 | lo gger.error ('solr-che ck.querySy ncsforDate Range() No startdate passed in '); | |
| 369 | re turn setTi meout(call back, 0, e rrorUtil.c reateFatal ('No start date passe d in')); | |
| 370 | } | |
| 371 | if (_. isEmpty(en ddate)) { | |
| 372 | lo gger.error ('solr-che ck.querySy ncsforDate Range() No enddate p assed in') ; | |
| 373 | re turn setTi meout(call back, 0, e rrorUtil.c reateFatal ('No endda te passed in')); | |
| 374 | } | |
| 375 | ||
| 376 | // var path = '/ vpr/' + pi d; | |
| 377 | var pa th = '/vpr /all/find/ patient?fi lter=dgt(s tampTime,' + startda te + '),dl t(stampTim e,' + endd ate + ')'; | |
| 378 | jdsCli ent.execut e(path, nu ll, 'GET', {}, callb ack); | |
| 379 | } |
Araxis Merge (but not the data content of this report) is Copyright © 1993-2016 Araxis Ltd (www.araxis.com). All rights reserved.