ORWOR1 ; SLC/DCM - PKI RPC functions ;03/27/13 4:57pm
;;3.0;ORDER ENTRY/RESULTS REPORTING;**132,141,163,306,371,499**;Dec 17, 1997;Build 165
;
;
;
;
SIG(RET,ID,X1,X2,X3,X4,ORX5,X6,X7) ;Store the signature.
;ID = orifn;action
;X1 = Hash
;X2 = Length of the array
;X3 = Datafile (100)
;X4 = Provider DUZ
;ORX5 = Array for the sig
;X6 = CRLURL
;X7 = DFN
;
N ORHINFO,ORDINFO,OROUT,ORADD
;gets patient/user specific info used in hash on GUI
K ORDFDA
D HASHINFO^ORDEA(.ORHINFO,X7,X4,+ID) ;*499
;get order specific info used in hash on GUI
D ORDHINFO^ORDEA(.ORDINFO,+ID,X1,.ORHINFO)
;look for existing entries in 101.52
S ORADD=1
I $D(^ORPA(101.52,"B",+ID)) D
.N ORI S ORI=0 F S ORI=$O(^ORPA(101.52,"B",+ID,ORI)) Q:'ORI D
..;if existing entry is not one that originated from backdoor and it's hash matches the current hash set flag to not add new record
..I ($L($P($G(^ORPA(101.52,ORI,0)),U,2))=0),$P($G(^ORPA(101.52,ORI,0)),U,3)=X1 D
...S ORADD=0
...;keep record that this was called but matched for 60 days
...S ^XTMP("OR DUP ARCHIVE","HMATCH",+ID,ORI,$$NOW^XLFDT)=""
...S ^XTMP("OR DUP ARCHIVE",0)=$$FMADD^XLFDT($$NOW^XLFDT,60)_U_$$NOW^XLFDT
..;if existing entry is not one that originated from backdoor but it does not match the current hash delete it
..I ($L($P($G(^ORPA(101.52,ORI,0)),U,2))=0),$P($G(^ORPA(101.52,ORI,0)),U,3)'=X1 D
...;keep deleted archive entry in xtmp for 60 days
...M ^XTMP("OR DUP ARCHIVE","HUNMATCH",+ID,ORI,$$NOW^XLFDT)=^ORPA(101.52,ORI)
...S ^XTMP("OR DUP ARCHIVE",0)=$$FMADD^XLFDT($$NOW^XLFDT,60)_U_$$NOW^XLFDT
...N DA,DIK
...S DA=ORI,DIK="^ORPA(101.52," D ^DIK
..;if it is from backdoor then update that record with the hash and set flag to not add new record
..I $L($P($G(^ORPA(101.52,ORI,0)),U,2))>0 S $P(^ORPA(101.52,ORI,0),U,3)=X1 S ORADD=0
I ORADD D UPDATE^DIE("","ORDFDA","OROUT","ERROR") K ORDFDA
S Y1=$$STORESIG^XUSSPKI(X1,X2,.ORX5,X4,X3)
I +Y1>0 D
. S ORIFN=+ID,ACT=$P(ID,";",2)
. S $P(^OR(100,ORIFN,8,+ACT,2),"^",3)=X1
S RET=1
Q
CRLURL(RET,X1) ;Store the URL's
S RET=$$CRLURL^XUSSPKI(X1)
Q
VERIFY(RET,ORDER,DFN) ;Verify PKI Data
;DBIA #3750
;ORDER = ORIFN;ACTION - NOTE: if no ACTION then 1 (new order) is assumed
;Returned values: "1" if digital signature verifies
; "-1^error message" if DS fails during initial parameter checking
; "898020xx^message" if DS fails during verification
N ORIFN,ORACTION,HASH,DATE
K ^TMP("ORPKIDATA",$J)
I '$G(ORDER) S RET="-1^No order number passed" Q
I '$G(DFN) S RET="-1^No DFN passed" Q
S ORIFN=$P(ORDER,";"),ORACTION=$P(ORDER,";",2)
I 'ORACTION S ORACTION=1
I '$D(^OR(100,ORIFN,0)) S RET="-1^Invalid order number" Q
I DFN'=+$P(^OR(100,ORIFN,0),"^",2) S RET="-1^DFN does not match patient on order" Q
I '$D(^OR(100,ORIFN,8,ORACTION)) S RET="-1^Invalid order action passed" Q
S HASH=$P($G(^OR(100,ORIFN,8,ORACTION,2)),"^",3)
I '$L(HASH) S RET="-1^Order has no PKI Hash" Q
I '$O(^OR(100,ORIFN,8,ORACTION,.2,0)) S RET="-1^Order has no PKI Data" Q
S DATE=$P($G(^OR(100,ORIFN,8,ORACTION,.2,1,0)),"^")
I '$L(DATE) S RET="-1^No date associated with PKI Data" Q
S DATE=$$HL7TFM^XLFDT(DATE),I=0
F S I=$O(^OR(100,ORIFN,8,ORACTION,.2,I)) Q:'I S ^TMP("ORPKIDATA",$J,I)=^(I,0)
S RET=$$VERIFY^XUSSPKI(HASH,$NA(^TMP("ORPKIDATA",$J)),DATE)
I RET="OK" S RET=1 Q
I $E(RET,1,7)="-898020" S RET=$E(RET,2,99)
Q
CHKDIG(REQ,ORDER) ;Check if Digital Signature is required
N IFN,ACTION
S REQ=0,IFN=+ORDER,ACTION=$P(ORDER,";",2)
I +$P($G(^OR(100,+IFN,8,+ACTION,2)),U,5) S REQ=1
Q
GETDTEXT(TEXT,ORDER) ;Get External Text
N IFN,ACTION
S IFN=+ORDER,ACTION=$P(ORDER,";",2),I=0
F S I=$O(^OR(100,+IFN,8,+ACTION,.2,I)) Q:'I S TEXT(I)=^(I,0)
Q
GETDSIG(SIG,ORDER) ;Get Digital Signature
N IFN,ACTION
S SIG=0,IFN=+ORDER,ACTION=$P(ORDER,";",2)
I +$P($G(^OR(100,+IFN,8,+ACTION,2)),U,3) S SIG=$P(^(2),"^",3)
Q
GETDEA(Y,ORUSER) ;Get user DEA
S Y=$$DEA^XUSER(,$G(ORUSER))
Q
GETDSCH(Y,ORDER) ;Check if Drug Schedule
N IFN,ACTION
S IFN=+ORDER,ACTION=$P(ORDER,";",2)
S Y=$P($G(^OR(100,+IFN,8,+ACTION,2)),U,4)
Q
SETDTEXT(Y,ORDER,ORDEA,ORSIGNER) ;Set Digital Text data into file 100 & return the array
;ORDER = ORIFN;ACTION
;ORDEA = Schedule of Drug (2-5)
;ORSIGNER = DUZ of signer
N ORSET,IFN,ACT,I
S Y="-1^Digital Text failed to build",IFN=+ORDER,ACT=$P(ORDER,";",2)
I '$G(ORDEA) Q
I '$G(ORSIGNER) S ORSIGNER=DUZ
D DIGTEXT^ORCSAVE1(IFN,ORDEA,ORSIGNER)
S Y=0
I '$G(ORSET) Q
K ^OR(100,IFN,8,ACT,.2)
F I=1:1:ORSET S (Y(I),^OR(100,IFN,8,ACT,.2,I,0))=ORSET(I)
S ^OR(100,IFN,8,ACT,.2,0)="^^"_ORSET_"^"_ORSET_"^"_DT_"^",Y=ORSET
Q
GETDATA(Y,ORDER,DFN) ;Get PKI Data
;DBIA #3750
;On error: Y = -1^Error message
;Else: Y = 1^ Order # ^ Nature of order ^ Order Status ^ Date Signed
;Y(1) = Patient name ^ Street1 ^ Street2 ^ Street3 ^ City ^ State ^ Zip
;Y(2) = Drug name_strength_dosage form (Dispense drug) ^ Drug IEN (file 50) ^ Drug quantity prescribed ^ Schedule of medication ^ DEA Schedule
;Y(3) = Directions for use (SIG)
;Y(4) = Practitioner's name ^ DUZ ^ Practitioner's (DEA) registration number
;Y(5) = SiteName ^ SiteStreet1 ^ SiteStreet2 ^ SiteCity ^ SiteState ^ SiteZip
;Y(6) = Orderable Item ^ Orderable Item IEN (file 101.43)
N X0,X1,X2,X3,X4,X5,X6,ORNAT,ORSTAT
I '$D(^OR(100,+$G(ORDER),0)) S Y="-1^INVALID ORDER #" Q
I $G(DFN)'=+$P(^OR(100,ORDER,0),"^",2) S Y="-1^INVALID PATIENT ID" Q
I '$D(^OR(100,ORDER,8,1,.2,0)) S Y="-1^MISSING DIGITAL SIGNATURE TEXT" Q
S X0=$G(^OR(100,ORDER,8,1,0))
I $P($G(^OR(100,ORDER,8,1,0)),"^",4)'=7 S Y="-1^ORDER HAS NOT BEEN DIGITALLY SIGNED" Q
S X1=$G(^OR(100,ORDER,8,1,.2,1,0))
I DFN'=$P(X1,"^",4) S Y="-1^PKI PATIENT ID DOES NOT MATCH DFN" Q
S ORNAT=$P(X0,"^",12),ORSTAT=$P($G(^OR(100,ORDER,3)),"^",3)
I ORNAT S ORNAT=$P($G(^ORD(100.02,ORNAT,0)),"^")
I ORSTAT S ORSTAT=ORSTAT_";"_$P(^ORD(100.01,ORSTAT,0),"^")
S Y="1^"_ORDER_"^"_ORNAT_"^"_ORSTAT_"^"_$P(X0,"^",6)
S X2=$G(^OR(100,ORDER,8,1,.2,2,0)),X3=$G(^OR(100,ORDER,8,1,.2,3,0)),X4=$G(^OR(100,ORDER,8,1,.2,4,0)),X5=$G(^OR(100,ORDER,8,1,.2,5,0)),X6=$G(^OR(100,ORDER,8,1,.2,6,0))
S X3=$$VALUE^ORX8(ORDER,"DRUG",,"E")_"^"_$$VALUE^ORX8(ORDER,"DRUG",,"I")_"^"_$P(X3,"^",3,99)
S Y(1)=$P(X1,"^",2)_"^"_X2
S Y(2)=X3,Y(3)=X4,Y(4)=X5,Y(5)=X6
S Y(6)=$$VALUE^ORX8(ORDER,"ORDERABLE",,"E")_"^"_$$VALUE^ORX8(ORDER,"ORDERABLE",,"I")
Q
--- Routine Detail --- with STRUCTURED ROUTINE LISTING ---[H[J[2J[HORWOR1 6497 printed Oct 16, 2024@18:37:24 Page 2
ORWOR1 ; SLC/DCM - PKI RPC functions ;03/27/13 4:57pm
+1 ;;3.0;ORDER ENTRY/RESULTS REPORTING;**132,141,163,306,371,499**;Dec 17, 1997;Build 165
+2 ;
+3 ;
+4 ;
+5 ;
SIG(RET,ID,X1,X2,X3,X4,ORX5,X6,X7) ;Store the signature.
+1 ;ID = orifn;action
+2 ;X1 = Hash
+3 ;X2 = Length of the array
+4 ;X3 = Datafile (100)
+5 ;X4 = Provider DUZ
+6 ;ORX5 = Array for the sig
+7 ;X6 = CRLURL
+8 ;X7 = DFN
+9 ;
+10 NEW ORHINFO,ORDINFO,OROUT,ORADD
+11 ;gets patient/user specific info used in hash on GUI
+12 KILL ORDFDA
+13 ;*499
DO HASHINFO^ORDEA(.ORHINFO,X7,X4,+ID)
+14 ;get order specific info used in hash on GUI
+15 DO ORDHINFO^ORDEA(.ORDINFO,+ID,X1,.ORHINFO)
+16 ;look for existing entries in 101.52
+17 SET ORADD=1
+18 IF $DATA(^ORPA(101.52,"B",+ID))
Begin DoDot:1
+19 NEW ORI
SET ORI=0
FOR
SET ORI=$ORDER(^ORPA(101.52,"B",+ID,ORI))
if 'ORI
QUIT
Begin DoDot:2
+20 ;if existing entry is not one that originated from backdoor and it's hash matches the current hash set flag to not add new record
+21 IF ($LENGTH($PIECE($GET(^ORPA(101.52,ORI,0)),U,2))=0)
IF $PIECE($GET(^ORPA(101.52,ORI,0)),U,3)=X1
Begin DoDot:3
+22 SET ORADD=0
+23 ;keep record that this was called but matched for 60 days
+24 SET ^XTMP("OR DUP ARCHIVE","HMATCH",+ID,ORI,$$NOW^XLFDT)=""
+25 SET ^XTMP("OR DUP ARCHIVE",0)=$$FMADD^XLFDT($$NOW^XLFDT,60)_U_$$NOW^XLFDT
End DoDot:3
+26 ;if existing entry is not one that originated from backdoor but it does not match the current hash delete it
+27 IF ($LENGTH($PIECE($GET(^ORPA(101.52,ORI,0)),U,2))=0)
IF $PIECE($GET(^ORPA(101.52,ORI,0)),U,3)'=X1
Begin DoDot:3
+28 ;keep deleted archive entry in xtmp for 60 days
+29 MERGE ^XTMP("OR DUP ARCHIVE","HUNMATCH",+ID,ORI,$$NOW^XLFDT)=^ORPA(101.52,ORI)
+30 SET ^XTMP("OR DUP ARCHIVE",0)=$$FMADD^XLFDT($$NOW^XLFDT,60)_U_$$NOW^XLFDT
+31 NEW DA,DIK
+32 SET DA=ORI
SET DIK="^ORPA(101.52,"
DO ^DIK
End DoDot:3
+33 ;if it is from backdoor then update that record with the hash and set flag to not add new record
+34 IF $LENGTH($PIECE($GET(^ORPA(101.52,ORI,0)),U,2))>0
SET $PIECE(^ORPA(101.52,ORI,0),U,3)=X1
SET ORADD=0
End DoDot:2
End DoDot:1
+35 IF ORADD
DO UPDATE^DIE("","ORDFDA","OROUT","ERROR")
KILL ORDFDA
+36 SET Y1=$$STORESIG^XUSSPKI(X1,X2,.ORX5,X4,X3)
+37 IF +Y1>0
Begin DoDot:1
+38 SET ORIFN=+ID
SET ACT=$PIECE(ID,";",2)
+39 SET $PIECE(^OR(100,ORIFN,8,+ACT,2),"^",3)=X1
End DoDot:1
+40 SET RET=1
+41 QUIT
CRLURL(RET,X1) ;Store the URL's
+1 SET RET=$$CRLURL^XUSSPKI(X1)
+2 QUIT
VERIFY(RET,ORDER,DFN) ;Verify PKI Data
+1 ;DBIA #3750
+2 ;ORDER = ORIFN;ACTION - NOTE: if no ACTION then 1 (new order) is assumed
+3 ;Returned values: "1" if digital signature verifies
+4 ; "-1^error message" if DS fails during initial parameter checking
+5 ; "898020xx^message" if DS fails during verification
+6 NEW ORIFN,ORACTION,HASH,DATE
+7 KILL ^TMP("ORPKIDATA",$JOB)
+8 IF '$GET(ORDER)
SET RET="-1^No order number passed"
QUIT
+9 IF '$GET(DFN)
SET RET="-1^No DFN passed"
QUIT
+10 SET ORIFN=$PIECE(ORDER,";")
SET ORACTION=$PIECE(ORDER,";",2)
+11 IF 'ORACTION
SET ORACTION=1
+12 IF '$DATA(^OR(100,ORIFN,0))
SET RET="-1^Invalid order number"
QUIT
+13 IF DFN'=+$PIECE(^OR(100,ORIFN,0),"^",2)
SET RET="-1^DFN does not match patient on order"
QUIT
+14 IF '$DATA(^OR(100,ORIFN,8,ORACTION))
SET RET="-1^Invalid order action passed"
QUIT
+15 SET HASH=$PIECE($GET(^OR(100,ORIFN,8,ORACTION,2)),"^",3)
+16 IF '$LENGTH(HASH)
SET RET="-1^Order has no PKI Hash"
QUIT
+17 IF '$ORDER(^OR(100,ORIFN,8,ORACTION,.2,0))
SET RET="-1^Order has no PKI Data"
QUIT
+18 SET DATE=$PIECE($GET(^OR(100,ORIFN,8,ORACTION,.2,1,0)),"^")
+19 IF '$LENGTH(DATE)
SET RET="-1^No date associated with PKI Data"
QUIT
+20 SET DATE=$$HL7TFM^XLFDT(DATE)
SET I=0
+21 FOR
SET I=$ORDER(^OR(100,ORIFN,8,ORACTION,.2,I))
if 'I
QUIT
SET ^TMP("ORPKIDATA",$JOB,I)=^(I,0)
+22 SET RET=$$VERIFY^XUSSPKI(HASH,$NAME(^TMP("ORPKIDATA",$JOB)),DATE)
+23 IF RET="OK"
SET RET=1
QUIT
+24 IF $EXTRACT(RET,1,7)="-898020"
SET RET=$EXTRACT(RET,2,99)
+25 QUIT
CHKDIG(REQ,ORDER) ;Check if Digital Signature is required
+1 NEW IFN,ACTION
+2 SET REQ=0
SET IFN=+ORDER
SET ACTION=$PIECE(ORDER,";",2)
+3 IF +$PIECE($GET(^OR(100,+IFN,8,+ACTION,2)),U,5)
SET REQ=1
+4 QUIT
GETDTEXT(TEXT,ORDER) ;Get External Text
+1 NEW IFN,ACTION
+2 SET IFN=+ORDER
SET ACTION=$PIECE(ORDER,";",2)
SET I=0
+3 FOR
SET I=$ORDER(^OR(100,+IFN,8,+ACTION,.2,I))
if 'I
QUIT
SET TEXT(I)=^(I,0)
+4 QUIT
GETDSIG(SIG,ORDER) ;Get Digital Signature
+1 NEW IFN,ACTION
+2 SET SIG=0
SET IFN=+ORDER
SET ACTION=$PIECE(ORDER,";",2)
+3 IF +$PIECE($GET(^OR(100,+IFN,8,+ACTION,2)),U,3)
SET SIG=$PIECE(^(2),"^",3)
+4 QUIT
GETDEA(Y,ORUSER) ;Get user DEA
+1 SET Y=$$DEA^XUSER(,$GET(ORUSER))
+2 QUIT
GETDSCH(Y,ORDER) ;Check if Drug Schedule
+1 NEW IFN,ACTION
+2 SET IFN=+ORDER
SET ACTION=$PIECE(ORDER,";",2)
+3 SET Y=$PIECE($GET(^OR(100,+IFN,8,+ACTION,2)),U,4)
+4 QUIT
SETDTEXT(Y,ORDER,ORDEA,ORSIGNER) ;Set Digital Text data into file 100 & return the array
+1 ;ORDER = ORIFN;ACTION
+2 ;ORDEA = Schedule of Drug (2-5)
+3 ;ORSIGNER = DUZ of signer
+4 NEW ORSET,IFN,ACT,I
+5 SET Y="-1^Digital Text failed to build"
SET IFN=+ORDER
SET ACT=$PIECE(ORDER,";",2)
+6 IF '$GET(ORDEA)
QUIT
+7 IF '$GET(ORSIGNER)
SET ORSIGNER=DUZ
+8 DO DIGTEXT^ORCSAVE1(IFN,ORDEA,ORSIGNER)
+9 SET Y=0
+10 IF '$GET(ORSET)
QUIT
+11 KILL ^OR(100,IFN,8,ACT,.2)
+12 FOR I=1:1:ORSET
SET (Y(I),^OR(100,IFN,8,ACT,.2,I,0))=ORSET(I)
+13 SET ^OR(100,IFN,8,ACT,.2,0)="^^"_ORSET_"^"_ORSET_"^"_DT_"^"
SET Y=ORSET
+14 QUIT
GETDATA(Y,ORDER,DFN) ;Get PKI Data
+1 ;DBIA #3750
+2 ;On error: Y = -1^Error message
+3 ;Else: Y = 1^ Order # ^ Nature of order ^ Order Status ^ Date Signed
+4 ;Y(1) = Patient name ^ Street1 ^ Street2 ^ Street3 ^ City ^ State ^ Zip
+5 ;Y(2) = Drug name_strength_dosage form (Dispense drug) ^ Drug IEN (file 50) ^ Drug quantity prescribed ^ Schedule of medication ^ DEA Schedule
+6 ;Y(3) = Directions for use (SIG)
+7 ;Y(4) = Practitioner's name ^ DUZ ^ Practitioner's (DEA) registration number
+8 ;Y(5) = SiteName ^ SiteStreet1 ^ SiteStreet2 ^ SiteCity ^ SiteState ^ SiteZip
+9 ;Y(6) = Orderable Item ^ Orderable Item IEN (file 101.43)
+10 NEW X0,X1,X2,X3,X4,X5,X6,ORNAT,ORSTAT
+11 IF '$DATA(^OR(100,+$GET(ORDER),0))
SET Y="-1^INVALID ORDER #"
QUIT
+12 IF $GET(DFN)'=+$PIECE(^OR(100,ORDER,0),"^",2)
SET Y="-1^INVALID PATIENT ID"
QUIT
+13 IF '$DATA(^OR(100,ORDER,8,1,.2,0))
SET Y="-1^MISSING DIGITAL SIGNATURE TEXT"
QUIT
+14 SET X0=$GET(^OR(100,ORDER,8,1,0))
+15 IF $PIECE($GET(^OR(100,ORDER,8,1,0)),"^",4)'=7
SET Y="-1^ORDER HAS NOT BEEN DIGITALLY SIGNED"
QUIT
+16 SET X1=$GET(^OR(100,ORDER,8,1,.2,1,0))
+17 IF DFN'=$PIECE(X1,"^",4)
SET Y="-1^PKI PATIENT ID DOES NOT MATCH DFN"
QUIT
+18 SET ORNAT=$PIECE(X0,"^",12)
SET ORSTAT=$PIECE($GET(^OR(100,ORDER,3)),"^",3)
+19 IF ORNAT
SET ORNAT=$PIECE($GET(^ORD(100.02,ORNAT,0)),"^")
+20 IF ORSTAT
SET ORSTAT=ORSTAT_";"_$PIECE(^ORD(100.01,ORSTAT,0),"^")
+21 SET Y="1^"_ORDER_"^"_ORNAT_"^"_ORSTAT_"^"_$PIECE(X0,"^",6)
+22 SET X2=$GET(^OR(100,ORDER,8,1,.2,2,0))
SET X3=$GET(^OR(100,ORDER,8,1,.2,3,0))
SET X4=$GET(^OR(100,ORDER,8,1,.2,4,0))
SET X5=$GET(^OR(100,ORDER,8,1,.2,5,0))
SET X6=$GET(^OR(100,ORDER,8,1,.2,6,0))
+23 SET X3=$$VALUE^ORX8(ORDER,"DRUG",,"E")_"^"_$$VALUE^ORX8(ORDER,"DRUG",,"I")_"^"_$PIECE(X3,"^",3,99)
+24 SET Y(1)=$PIECE(X1,"^",2)_"^"_X2
+25 SET Y(2)=X3
SET Y(3)=X4
SET Y(4)=X5
SET Y(5)=X6
+26 SET Y(6)=$$VALUE^ORX8(ORDER,"ORDERABLE",,"E")_"^"_$$VALUE^ORX8(ORDER,"ORDERABLE",,"I")
+27 QUIT