source: Scheduling/trunk/cs/bsdx0200GUISourceCode/CGDocumentManager.cs@ 772

Last change on this file since 772 was 772, checked in by Sam Habiel, 14 years ago

Removal of Crystal Reports
Partial Rework of Clinic Patient List report
Other reports that used Crystal don't work yet.
Fixes for Strongly typed DataTables (change the RESOURCEID from uint to int) to support table merge from untyped table.
Support for command line arguments: /s= for server /p= for port /a= for access code /v= for verify code
Only the following combinations work: none; /s and /p; /s, /p, /a, /v

File size: 30.8 KB
Line 
1using System;
2using System.Windows.Forms;
3using System.Collections;
4using System.Data;
5using System.Text;
6using System.Diagnostics;
7using System.Net;
8using System.Net.Sockets;
9using System.Threading;
10using System.IO;
11using IndianHealthService.BMXNet;
12using System.Configuration;
13using Mono.Options;
14
15namespace IndianHealthService.ClinicalScheduling
16{
17 /// <summary>
18 /// Summary description for DocumentManager.
19 /// </summary>
20 public class CGDocumentManager : System.Windows.Forms.Form
21 {
22 #region Member Variables
23
24 private static CGDocumentManager _current;
25 private Hashtable _views = new Hashtable();
26 private Hashtable m_AVViews = new Hashtable();
27 private string m_sWindowText = "Clinical Scheduling"; //Default Window Text
28 private bool m_bSchedManager;
29 private bool m_bExitOK = true;
30 public string m_sHandle = "0";
31 private string m_AccessCode="";
32 private string m_VerifyCode="";
33 private string m_Server="";
34 private int m_Port=0;
35
36 //M Connection member variables
37 private DataSet m_dsGlobal = null;
38 private System.ComponentModel.IContainer components = null;
39 private BMXNetConnectInfo m_ConnectInfo = null;
40 private BMXNetConnectInfo.BMXNetEventDelegate CDocMgrEventDelegate;
41
42 #endregion
43
44 public CGDocumentManager()
45 {
46 InitializeComponent();
47 m_ConnectInfo = new BMXNetConnectInfo();
48 //m_ConnectInfo.bmxNetLib.StartLog(); //This line turns on logging of messages
49 m_bSchedManager = false;
50 CDocMgrEventDelegate = new BMXNetConnectInfo.BMXNetEventDelegate(CDocMgrEventHandler);
51 m_ConnectInfo.BMXNetEvent += CDocMgrEventDelegate;
52 m_ConnectInfo.EventPollingEnabled = false;
53 }
54
55 #region BMXNet Event Handler
56 private void CDocMgrEventHandler(Object obj, BMXNet.BMXNetEventArgs e)
57 {
58 if (e.BMXEvent == "BSDX CALL WORKSTATIONS")
59 {
60 string sParam = "";
61 string sDelim="~";
62 sParam += this.m_ConnectInfo.UserName + sDelim;
63 sParam += this.m_sHandle + sDelim;
64 sParam += Application.ProductVersion + sDelim;
65 sParam += this._views.Count.ToString();
66 _current.m_ConnectInfo.RaiseEvent("BSDX WORKSTATION REPORT", sParam, true);
67 }
68 if (e.BMXEvent == "BSDX ADMIN MESSAGE")
69 {
70 string sMsg = e.BMXParam;
71 ShowAdminMsgDelegate samd = new ShowAdminMsgDelegate(ShowAdminMsg);
72 this.Invoke(samd, new object [] {sMsg});
73 }
74 if (e.BMXEvent == "BSDX ADMIN SHUTDOWN")
75 {
76 string sMsg = e.BMXParam;
77 CloseAllDelegate cad = new CloseAllDelegate(CloseAll);
78 this.Invoke(cad, new object [] {sMsg});
79 }
80 }
81
82 delegate void ShowAdminMsgDelegate(string sMsg);
83
84 private void ShowAdminMsg(string sMsg)
85 {
86 MessageBox.Show(sMsg, "Message from Scheduling Administrator", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
87 }
88
89 #endregion BMXNet Event Handler
90
91 #region Properties
92
93 /// <summary>
94 /// Returns the document manager's BMXNetConnectInfo member
95 /// </summary>
96 public BMXNetConnectInfo ConnectInfo
97 {
98 get
99 {
100 return m_ConnectInfo;
101 }
102 }
103
104 /// <summary>
105 /// True if the current user holds the BSDXZMGR or XUPROGMODE keys in RPMS
106 /// </summary>
107 public bool ScheduleManager
108 {
109 get
110 {
111 return m_bSchedManager;
112 }
113 }
114
115 /// <summary>
116 /// Holds the user and division
117 /// </summary>
118 public string WindowText
119 {
120 get
121 {
122 return m_sWindowText;
123 }
124 }
125
126 /// <summary>
127 /// This dataset contains tables used by the entire application
128 /// </summary>
129 public DataSet GlobalDataSet
130 {
131 get
132 {
133 return m_dsGlobal;
134 }
135 set
136 {
137 m_dsGlobal = value;
138 }
139 }
140 //public BMXNetConnection ADOConnection
141 //{
142 // get
143 // {
144 // return m_ADOConnection;
145 // }
146 //}
147
148 /// <summary>
149 /// Returns the single CGDocumentManager object
150 /// </summary>
151 public static CGDocumentManager Current
152 {
153 get
154 {
155 return _current;
156 }
157 }
158
159 /// <summary>
160 /// Returns the list of currently opened documents
161 /// </summary>
162 public Hashtable Views
163 {
164 get
165 {
166 return _views;
167 }
168 }
169
170 /// <summary>
171 /// Returns the list of currently opened CGAVViews
172 /// </summary>
173 public Hashtable AvailabilityViews
174 {
175 get
176 {
177 return this.m_AVViews;
178 }
179 }
180
181
182 #endregion
183
184 #region Methods & Events
185 /// <summary>
186 /// Clean up any resources being used.
187 /// </summary>
188 protected override void Dispose( bool disposing )
189 {
190 if( disposing )
191 {
192 if (m_ConnectInfo != null)
193 {
194 m_ConnectInfo.EventPollingEnabled = false;
195 m_ConnectInfo.UnSubscribeEvent("BSDX SCHEDULE");
196 m_ConnectInfo.UnSubscribeEvent("BSDX CALL WORKSTATIONS");
197 m_ConnectInfo.CloseConnection();
198 }
199 if (components != null)
200 {
201 components.Dispose();
202 }
203 }
204 base.Dispose( disposing );
205 }
206
207
208 private void InitializeComponent()
209 {
210 //
211 // CGDocumentManager
212 //
213 this.AutoScaleBaseSize = new System.Drawing.Size(5, 13);
214 this.ClientSize = new System.Drawing.Size(292, 266);
215 this.Name = "CGDocumentManager";
216
217 }
218
219
220 private DSplash m_ds;
221 public void StartSplash()
222 {
223 m_ds = new DSplash();
224 m_ds.ShowDialog();
225 }
226
227 private void InitializeApp()
228 {
229 InitializeApp(false);
230 }
231
232 private void InitializeApp(bool bReLogin)
233 {
234 try
235 {
236 //Set M connection info
237 //Show a splash screen while initializing
238 m_ds = new DSplash();
239 m_ds.Show(this);
240 m_ds.SetStatus("Loading Configuration Settings...");
241 m_ds.Refresh();
242 this.Activate();
243 System.Configuration.ConfigurationManager.GetSection("appSettings");
244 m_ds.SetStatus("Connecting to VistA Server...");
245 m_ds.Refresh();
246 bool bRetry = true;
247 do
248 {
249 try
250 {
251 if (bReLogin == true)
252 {
253 //Prompt for Access and Verify codes
254 _current.m_ConnectInfo.LoadConnectInfo("", "");
255 }
256 else
257 {
258 if (m_Server != String.Empty && m_Port != 0 && m_AccessCode != String.Empty
259 && m_VerifyCode != String.Empty)
260 m_ConnectInfo.LoadConnectInfo(m_Server, m_Port, m_AccessCode, m_VerifyCode);
261
262 else if (m_Server != String.Empty && m_Port != 0)
263 m_ConnectInfo.LoadConnectInfo(m_Server, m_Port);
264
265 else
266 m_ConnectInfo.LoadConnectInfo();
267 }
268 bRetry = false;
269 }
270 catch (Exception ex)
271 {
272 m_ds.Close();
273 if (MessageBox.Show("Unable to connect to VistA. " + ex.Message , "Clinical Scheduling", MessageBoxButtons.RetryCancel) == DialogResult.Retry)
274 {
275 bRetry = true;
276 _current.m_ConnectInfo.ChangeServerInfo();
277 }
278 else
279 {
280 bRetry = false;
281 throw ex;
282 }
283 }
284 }while (bRetry == true);
285
286 //Create global dataset
287 _current.m_dsGlobal = new DataSet("GlobalDataSet");
288
289 //Version info
290 m_ds.SetStatus("Getting Version Info...");
291 m_ds.Refresh();
292 String sCmd = "BMX VERSION INFO^BSDX^";
293 this.m_ConnectInfo.RPMSDataTable(sCmd, "VersionInfo", m_dsGlobal);
294
295 //Keep the following commented code for future use:
296 //How to extract the version numbers:
297 //DataTable dtVersion = m_dsGlobal.Tables["VersionInfo"];
298 //Debug.Assert(dtVersion.Rows.Count == 1);
299 //DataRow rVersion = dtVersion.Rows[0];
300 //string sMajor = rVersion["MAJOR_VERSION"].ToString();
301 //string sMinor = rVersion["MINOR_VERSION"].ToString();
302 //string sBuild = rVersion["BUILD"].ToString();
303 //decimal fBuild = Convert.ToDecimal(sBuild);
304
305 //Set application context
306 m_ds.SetStatus("Setting Application Context to BSDXRPC...");
307 m_ds.Refresh();
308 m_ConnectInfo.AppContext = "BSDXRPC";
309
310 //Load global recordsets
311 m_ds.SetStatus("Loading VistA data tables...");
312 m_ds.Refresh();
313 if (_current.LoadGlobalRecordsets() == false)
314 {
315 MessageBox.Show("Unable to create VistA recordsets"); //TODO Improve this message
316 m_ds.Close();
317 return;
318 }
319
320 System.IntPtr pHandle = this.Handle;
321 System.IntPtr pConnHandle = this.ConnectInfo.Handle;
322 this.m_sHandle = pHandle.ToString();
323
324 _current.m_ConnectInfo.ReceiveTimeout = 30000; //30-second timeout
325
326#if DEBUG
327 _current.m_ConnectInfo.ReceiveTimeout = 600000; //longer timeout for debugging
328#endif
329 _current.m_ConnectInfo.SubscribeEvent("BSDX SCHEDULE");
330 _current.m_ConnectInfo.SubscribeEvent("BSDX CALL WORKSTATIONS");
331 _current.m_ConnectInfo.SubscribeEvent("BSDX ADMIN MESSAGE");
332 _current.m_ConnectInfo.SubscribeEvent("BSDX ADMIN SHUTDOWN");
333
334 _current.m_ConnectInfo.EventPollingInterval = 5000; //in milliseconds
335 _current.m_ConnectInfo.EventPollingEnabled = true;
336 _current.m_ConnectInfo.AutoFire = 12; //AutoFire every 12*5 seconds
337
338 m_ds.Close();
339 }
340 catch (Exception ex)
341 {
342 m_ds.Close();
343 Debug.Write(ex.Message);
344 MessageBox.Show(ex.Message + ex.StackTrace, "Clinical Scheduling Error -- Closing Application");
345 throw ex;
346 }
347 }
348
349 [STAThread()] static void Main(string[] args)
350 {
351 try
352 {
353 //Store the current manager
354 _current = new CGDocumentManager();
355
356 var opset = new OptionSet () {
357 { "s=", s => _current.m_Server = s },
358 { "p=", p => _current.m_Port = int.Parse(p) },
359 { "a=", a => _current.m_AccessCode = a },
360 { "v=", v => _current.m_VerifyCode = v }
361 };
362
363 opset.Parse(args);
364
365 try
366 {
367 _current.InitializeApp();
368 }
369 catch (Exception ex)
370 {
371 Debug.Write(ex.Message);
372 return;
373 }
374
375 //Create the first empty document
376 CGDocument doc = new CGDocument();
377 doc.DocManager = _current;
378 doc.OnNewDocument();
379 Application.DoEvents();
380
381 //Run the application
382 Application.Run();
383 }
384 catch (Exception ex)
385 {
386 Debug.Write(ex.Message);
387 MessageBox.Show(ex.Message + ex.StackTrace, "CGDocumentManager.Main(): Clinical Scheduling Error -- Closing Application");
388 return;
389 }
390 }
391
392 public void LoadAccessTypesTable()
393 {
394 string sCommandText = "SELECT * FROM BSDX_ACCESS_TYPE";
395 ConnectInfo.RPMSDataTable(sCommandText, "AccessTypes", m_dsGlobal);
396 Debug.Write("LoadGlobalRecordsets -- AccessTypes loaded\n");
397 }
398
399 public void LoadAccessGroupsTable()
400 {
401 string sCommandText = "SELECT * FROM BSDX_ACCESS_GROUP";
402 ConnectInfo.RPMSDataTable(sCommandText, "AccessGroup", m_dsGlobal);
403 Debug.Write("LoadGlobalRecordsets -- AccessGroups loaded\n");
404 }
405
406 public void LoadAccessGroupTypesTable()
407 {
408 string sCommandText = "BSDX GET ACCESS GROUP TYPES";
409 ConnectInfo.RPMSDataTable(sCommandText, "AccessGroupType", m_dsGlobal);
410 Debug.Write("LoadGlobalRecordsets -- AccessGroupTypes loaded\n");
411 }
412
413 public void LoadClinicSetupTable()
414 {
415 string sCommandText = "BSDX CLINIC SETUP";
416 ConnectInfo.RPMSDataTable(sCommandText, "ClinicSetupParameters", m_dsGlobal);
417 Debug.Write("LoadGlobalRecordsets -- ClinicSetupParameters loaded\n");
418 }
419
420 public void LoadBSDXResourcesTable()
421 {
422 string sCommandText = "BSDX RESOURCES^" + m_ConnectInfo.DUZ;
423 ConnectInfo.RPMSDataTable(sCommandText, "Resources", m_dsGlobal);
424 Debug.Write("LoadGlobalRecordsets -- Resources loaded\n");
425 }
426
427 public void LoadResourceGroupTable()
428 {
429 //ResourceGroup Table (Resource Groups by User)
430 //Table "ResourceGroup" contains all resource group names
431 //to which user has access
432 //Fields are: RESOURCE_GROUPID, RESOURCE_GROUP
433 string sCommandText = "BSDX RESOURCE GROUPS BY USER^" + m_ConnectInfo.DUZ;
434 ConnectInfo.RPMSDataTable(sCommandText, "ResourceGroup", m_dsGlobal);
435 Debug.Write("LoadGlobalRecordsets -- ResourceGroup loaded\n");
436 }
437
438 public void LoadGroupResourcesTable()
439 {
440 //Table "GroupResources" contains all active GROUP/RESOURCE combinations
441 //to which user has access based on entries in BSDX RESOURCE USER file
442 //If user has BSDXZMGR or XUPROGMODE keys, then ALL Group/Resource combinstions
443 //are returned.
444 //Fields are: RESOURCE_GROUPID, RESOURCE_GROUP, RESOURCE_GROUP_ITEMID, RESOURCE_NAME, RESOURCE_ID
445 string sCommandText = "BSDX GROUP RESOURCE^" + m_ConnectInfo.DUZ;
446 ConnectInfo.RPMSDataTable(sCommandText, "GroupResources", m_dsGlobal);
447 Debug.Write("LoadGlobalRecordsets -- GroupResources loaded\n");
448 }
449
450 public void LoadScheduleUserTable()
451 {
452 //Table "ScheduleUser" contains an entry for each user in File 200 (NEW PERSON)
453 //who possesses the BSDXZMENU security key.
454 string sCommandText = "BSDX SCHEDULE USER";
455 ConnectInfo.RPMSDataTable(sCommandText, "ScheduleUser", m_dsGlobal);
456 Debug.Write("LoadGlobalRecordsets -- ScheduleUser loaded\n");
457 }
458
459 public void LoadResourceUserTable()
460 {
461 //Table "ResourceUser" duplicates the BSDX RESOURCE USER File.
462 //NOTE: Column names are RESOURCEUSER_ID, RESOURCEID,
463 // OVERBOOK, MODIFY_SCHEDULE, USERID, USERID1
464 //string sCommandText = "SELECT BMXIEN RESOURCEUSER_ID, INTERNAL[RESOURCENAME] RESOURCEID, OVERBOOK, MODIFY_SCHEDULE, USERNAME USERID, INTERNAL[USERNAME] FROM BSDX_RESOURCE_USER";
465 LoadResourceUserTable(false);
466 }
467
468 public void LoadResourceUserTable(bool bAllUsers)
469 {
470 string sCommandText = "SELECT BMXIEN RESOURCEUSER_ID, RESOURCENAME, INTERNAL[RESOURCENAME] RESOURCEID, OVERBOOK, MODIFY_SCHEDULE, MODIFY_APPOINTMENTS, USERNAME, INTERNAL[USERNAME] USERID FROM BSDX_RESOURCE_USER";
471 ConnectInfo.RPMSDataTable(sCommandText, "ResourceUser", m_dsGlobal);
472 Debug.Write("LoadGlobalRecordsets -- ResourceUser loaded\n");
473 }
474
475 private bool LoadGlobalRecordsets()
476 {
477 //Schedule User Info
478 string sCommandText = "BSDX SCHEDULING USER INFO^" + m_ConnectInfo.DUZ;
479 DataTable dtUser = ConnectInfo.RPMSDataTable(sCommandText, "SchedulingUser", m_dsGlobal);
480
481 Debug.Assert(dtUser.Rows.Count == 1);
482 DataRow rUser = dtUser.Rows[0];
483 Object oUser = rUser["MANAGER"];
484 string sUser = oUser.ToString();
485 m_bSchedManager = (sUser == "YES")?true:false;
486
487 //AccessTypes
488 LoadAccessTypesTable();
489
490 //Build Primary Key for AccessTypes table
491 DataTable dtTypes = m_dsGlobal.Tables["AccessTypes"];
492 DataColumn dcKey = dtTypes.Columns["BMXIEN"];
493 DataColumn[] dcKeys = new DataColumn[1];
494 dcKeys[0] = dcKey;
495 dtTypes.PrimaryKey = dcKeys;
496
497 //AccessGroups
498 LoadAccessGroupsTable();
499
500 //Build Primary Key for AccessGroup table
501 DataTable dtGroups = m_dsGlobal.Tables["AccessGroup"];
502 dcKey = dtGroups.Columns["ACCESS_GROUP"];
503 dcKeys = new DataColumn[1];
504 dcKeys[0] = dcKey;
505 dtGroups.PrimaryKey = dcKeys;
506
507 //AccessGroupType
508 LoadAccessGroupTypesTable();
509
510 //Build Primary Key for AccessGroupType table
511 DataTable dtAGTypes = m_dsGlobal.Tables["AccessGroupType"];
512 DataColumn dcGTKey = dtAGTypes.Columns["ACCESS_GROUP_TYPEID"];
513 DataColumn[] dcGTKeys = new DataColumn[1];
514 dcGTKeys[0] = dcGTKey;
515 dtAGTypes.PrimaryKey = dcGTKeys;
516
517 //Build Data Relationship between AccessGroupType and AccessTypes tables
518 DataRelation dr = new DataRelation("AccessGroupType", //Relation Name
519 m_dsGlobal.Tables["AccessGroup"].Columns["BMXIEN"], //Parent
520 m_dsGlobal.Tables["AccessGroupType"].Columns["ACCESS_GROUP_ID"]); //Child
521 m_dsGlobal.Relations.Add(dr);
522
523 //ResourceGroup Table (Resource Groups by User)
524 LoadResourceGroupTable();
525
526 //Resources by user
527 LoadBSDXResourcesTable();
528
529 //Build Primary Key for Resources table
530 DataColumn[] dc = new DataColumn[1];
531 dc[0] = m_dsGlobal.Tables["Resources"].Columns["RESOURCEID"];
532 m_dsGlobal.Tables["Resources"].PrimaryKey = dc;
533
534 //GroupResources table
535 LoadGroupResourcesTable();
536
537 //Build Primary Key for ResourceGroup table
538 dc = new DataColumn[1];
539 dc[0] = m_dsGlobal.Tables["ResourceGroup"].Columns["RESOURCE_GROUP"];
540 m_dsGlobal.Tables["ResourceGroup"].PrimaryKey = dc;
541
542 //Build Data Relationships between ResourceGroup and GroupResources tables
543 dr = new DataRelation("GroupResource", //Relation Name
544 m_dsGlobal.Tables["ResourceGroup"].Columns["RESOURCE_GROUP"], //Parent
545 m_dsGlobal.Tables["GroupResources"].Columns["RESOURCE_GROUP"]); //Child
546 CGSchedLib.OutputArray(m_dsGlobal.Tables["GroupResources"], "GroupResources");
547 m_dsGlobal.Relations.Add(dr);
548
549 //HospitalLocation table
550 //cmd.CommandText = "SELECT BMXIEN 'HOSPITAL_LOCATION_ID', NAME 'HOSPITAL_LOCATION', DEFAULT_PROVIDER, STOP_CODE_NUMBER, INACTIVATE_DATE, REACTIVATE_DATE FROM HOSPITAL_LOCATION";
551 sCommandText = "BSDX HOSPITAL LOCATION";
552 ConnectInfo.RPMSDataTable(sCommandText, "HospitalLocation", m_dsGlobal);
553 Debug.Write("LoadGlobalRecordsets -- HospitalLocation loaded\n");
554
555 //Build Primary Key for HospitalLocation table
556 dc = new DataColumn[1];
557 DataTable dtTemp = m_dsGlobal.Tables["HospitalLocation"];
558 dc[0] = dtTemp.Columns["HOSPITAL_LOCATION_ID"];
559 m_dsGlobal.Tables["HospitalLocation"].PrimaryKey = dc;
560
561 LoadClinicSetupTable();
562
563 //Build Primary Key for ClinicSetupParameters table
564 dc = new DataColumn[1];
565 dtTemp = m_dsGlobal.Tables["ClinicSetupParameters"];
566 dc[0] = dtTemp.Columns["HOSPITAL_LOCATION_ID"];
567 m_dsGlobal.Tables["ClinicSetupParameters"].PrimaryKey = dc;
568
569 //Build Data Relationships between ClinicSetupParameters and HospitalLocation tables
570 dr = new DataRelation("HospitalLocationClinic", //Relation Name
571 m_dsGlobal.Tables["HospitalLocation"].Columns["HOSPITAL_LOCATION_ID"], //Parent
572 m_dsGlobal.Tables["ClinicSetupParameters"].Columns["HOSPITAL_LOCATION_ID"], false); //Child
573 m_dsGlobal.Relations.Add(dr);
574
575 dtTemp.Columns.Add("PROVIDER", System.Type.GetType("System.String"), "Parent.DEFAULT_PROVIDER");
576 dtTemp.Columns.Add("CLINIC_STOP", System.Type.GetType("System.String"), "Parent.STOP_CODE_NUMBER");
577 dtTemp.Columns.Add("INACTIVATE_DATE", System.Type.GetType("System.String"), "Parent.INACTIVATE_DATE");
578 dtTemp.Columns.Add("REACTIVATE_DATE", System.Type.GetType("System.String"), "Parent.REACTIVATE_DATE");
579
580 //Build Data Relationships between Resources and HospitalLocation tables
581 dr = new DataRelation("HospitalLocationResource", //Relation Name
582 m_dsGlobal.Tables["HospitalLocation"].Columns["HOSPITAL_LOCATION_ID"], //Parent
583 m_dsGlobal.Tables["Resources"].Columns["HOSPITAL_LOCATION_ID"], false); //Child
584 m_dsGlobal.Relations.Add(dr);
585
586 //Build ScheduleUser table
587 this.LoadScheduleUserTable();
588
589 //Build Primary Key for ScheduleUser table
590 dc = new DataColumn[1];
591 dtTemp = m_dsGlobal.Tables["ScheduleUser"];
592 dc[0] = dtTemp.Columns["USERID"];
593 m_dsGlobal.Tables["ScheduleUser"].PrimaryKey = dc;
594
595 //Build ResourceUser table
596 this.LoadResourceUserTable();
597
598 //Build Primary Key for ResourceUser table
599 dc = new DataColumn[1];
600 dtTemp = m_dsGlobal.Tables["ResourceUser"];
601 dc[0] = dtTemp.Columns["RESOURCEUSER_ID"];
602 m_dsGlobal.Tables["ResourceUser"].PrimaryKey = dc;
603
604 //Create relation between BSDX Resource and BSDX Resource User tables
605 dr = new DataRelation("ResourceUser", //Relation Name
606 m_dsGlobal.Tables["Resources"].Columns["RESOURCEID"], //Parent
607 m_dsGlobal.Tables["ResourceUser"].Columns["RESOURCEID"]); //Child
608 m_dsGlobal.Relations.Add(dr);
609
610 //Build active provider table
611 sCommandText = "SELECT BMXIEN, NAME FROM NEW_PERSON WHERE INACTIVE_DATE = '' AND INTERNAL[PROVIDER_CLASS] > 0";
612 ConnectInfo.RPMSDataTable(sCommandText, "Provider", m_dsGlobal);
613 Debug.Write("LoadGlobalRecordsets -- Provider loaded\n");
614
615 //Build the CLINIC_STOP table
616 // sCommandText = "SELECT BMXIEN, CODE, NAME FROM CLINIC_STOP"; //SMH
617 sCommandText = "SELECT BMXIEN, AMIS_REPORTING_STOP_CODE, NAME FROM CLINIC_STOP";
618 ConnectInfo.RPMSDataTable(sCommandText, "ClinicStop", m_dsGlobal);
619 Debug.Write("LoadGlobalRecordsets -- ClinicStop loaded\n");
620
621 //Build the HOLIDAY table
622 sCommandText = "SELECT NAME, DATE FROM HOLIDAY WHERE DATE > '" + DateTime.Today.ToShortDateString() + "'";
623 ConnectInfo.RPMSDataTable(sCommandText, "HOLIDAY", m_dsGlobal);
624
625 //Save the xml schema
626 //m_dsGlobal.WriteXmlSchema(@"..\..\csSchema20060526.xsd");
627
628 return true;
629 }
630
631 public void RegisterDocumentView(CGDocument doc, CGView view)
632 {
633 //Store the view in the list of views
634 this.Views.Add(view, doc);
635
636 //Hook into the view's 'closed' event
637 view.Closed += new EventHandler(ViewClosed);
638
639 //Hook into the view's mnuRPMSServer.Click event
640 view.mnuRPMSServer.Click += new EventHandler(mnuRPMSServer_Click);
641
642 //Hook into the view's mnuRPMSLogin.Click event
643 view.mnuRPMSLogin.Click += new EventHandler(mnuRPMSLogin_Click);
644
645 }
646
647 public void RegisterAVDocumentView(CGAVDocument doc, CGAVView view)
648 {
649 //Store the view in the list of views
650 this.AvailabilityViews.Add(view, doc);
651
652 //Hook into the view's 'closed' event
653 view.Closed += new EventHandler(AVViewClosed);
654 }
655
656 public CGAVView GetAVViewByResource(ArrayList sResourceArray)
657 {
658 if (sResourceArray == null)
659 return null;
660
661 bool bEqual = true;
662 foreach (CGAVView v in m_AVViews.Keys)
663 {
664 CGAVDocument d = v.Document;
665
666 bEqual = false;
667 if (d.Resources.Count == sResourceArray.Count)
668 {
669 bEqual = true;
670 for (int j = 0; j < sResourceArray.Count; j++)
671 {
672 if (sResourceArray.Contains(d.Resources[j]) == false)
673 {
674 bEqual = false;
675 break;
676 }
677 if (d.Resources.Contains(sResourceArray[j]) == false)
678 {
679 bEqual = false;
680 break;
681 }
682 }
683 if (bEqual == true)
684 return v;
685 }
686 }
687 return null;
688 }
689 /// <summary>
690 /// Return the first view having a resource array matching sResourceArray
691 /// </summary>
692 /// <param name="sResourceArray"></param>
693 /// <returns></returns>
694 public CGView GetViewByResource(ArrayList sResourceArray)
695 {
696 if (sResourceArray == null)
697 return null;
698
699 bool bEqual = true;
700 foreach (CGView v in _views.Keys)
701 {
702 CGDocument d = v.Document;
703
704 bEqual = false;
705 if (d.Resources.Count == sResourceArray.Count)
706 {
707 bEqual = true;
708 for (int j = 0; j < sResourceArray.Count; j++)
709 {
710 if (sResourceArray.Contains(d.Resources[j]) == false)
711 {
712 bEqual = false;
713 break;
714 }
715 if (d.Resources.Contains(sResourceArray[j]) == false)
716 {
717 bEqual = false;
718 break;
719 }
720 }
721 if (bEqual == true)
722 return v;
723 }
724 }
725 return null;
726 }
727
728 private void ViewClosed(object sender, EventArgs e)
729 {
730 //Remove the sender from our document list
731 Views.Remove(sender);
732
733 //If no documents left, then close RPMS connection & exit the application
734 if ((Views.Count == 0)&&(this.AvailabilityViews.Count == 0)&&(m_bExitOK == true))
735 {
736 m_ConnectInfo.EventPollingEnabled = false;
737 m_ConnectInfo.UnSubscribeEvent("BSDX SCHEDULE");
738 m_ConnectInfo.CloseConnection();
739 Application.Exit();
740 }
741 }
742
743 private void AVViewClosed(object sender, EventArgs e)
744 {
745 //Remove the sender from our document list
746 this.AvailabilityViews.Remove(sender);
747
748 //If no documents left, then close RPMS connection & exit the application
749 if ((Views.Count == 0)&&(this.AvailabilityViews.Count == 0)&&(m_bExitOK == true))
750 {
751 m_ConnectInfo.bmxNetLib.CloseConnection();
752 Application.Exit();
753 }
754 }
755
756 private void KeepAlive()
757 {
758 foreach (CGView v in _views.Keys)
759 {
760 CGDocument d = v.Document;
761 DateTime dNow = DateTime.Now;
762 DateTime dLast = d.LastRefreshed;
763 TimeSpan tsDiff = dNow - dLast;
764 if (tsDiff.Seconds > 180)
765 {
766 for (int j = 0; j < d.Resources.Count; j++)
767 {
768 v.RaiseRPMSEvent("SCHEDULE-" + d.Resources[j].ToString(), "");
769 }
770
771 break;
772 }
773 }
774 }
775
776 /// <summary>
777 /// Propogate availability updates to all sRresource's doc/views
778 /// </summary>
779 public void UpdateViews(string sResource, string sOldResource)
780 {
781 if (sResource == null)
782 return;
783 foreach (CGView v in _views.Keys)
784 {
785 CGDocument d = v.Document;
786 for (int j = 0; j < d.Resources.Count; j++)
787 {
788 if ((sResource == "") || (sResource == ((string) d.Resources[j])) || (sOldResource == ((string) d.Resources[j])))
789 {
790 d.RefreshDocument();
791 break;
792 }
793 }
794 v.UpdateTree();
795 }
796 }
797
798 /// <summary>
799 /// Propogate availability updates to all doc/views
800 /// </summary>
801 public void UpdateViews()
802 {
803 UpdateViews("","");
804 foreach (CGView v in _views.Keys)
805 {
806 v.UpdateTree();
807 }
808 }
809
810 /// <summary>
811 /// Calls each view associated with document Doc and closes it.
812 /// </summary>
813 public void CloseAllViews(CGDocument doc)
814 {
815 //iterate through all views and call update.
816 Hashtable h = CGDocumentManager.Current.Views;
817
818 CGDocument d;
819 int nTempCount = h.Count;
820 do
821 {
822 nTempCount = h.Count;
823 foreach (CGView v in h.Keys)
824 {
825 d = (CGDocument) h[v];
826 if (d == doc)
827 {
828 v.Close();
829 break;
830 }
831 }
832 } while ((h.Count > 0) && (nTempCount != h.Count));
833 }
834
835 /// <summary>
836 /// Calls each view associated with Availability Doc and closes it.
837 /// </summary>
838 public void CloseAllViews(CGAVDocument doc)
839 {
840 //iterate through all views and call update.
841 Hashtable h = CGDocumentManager.Current.AvailabilityViews;
842
843 CGAVDocument d;
844 int nTempCount = h.Count;
845 do
846 {
847 nTempCount = h.Count;
848 foreach (CGAVView v in h.Keys)
849 {
850 d = (CGAVDocument) h[v];
851 if (d == doc)
852 {
853 v.Close();
854 break;
855 }
856 }
857 } while ((h.Count > 0) && (nTempCount != h.Count));
858
859
860 }
861
862 private void mnuRPMSServer_Click(object sender, EventArgs e)
863 {
864 //Warn that changing servers will close all schedules
865 if (MessageBox.Show("Are you sure you want to close all schedules and connect to a different VistA server?", "Clinical Scheduling", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) != DialogResult.OK)
866 return;
867
868 //Reconnect to RPMS and recreate all global recordsets
869 try
870 {
871 m_bExitOK = false;
872 bool bRetry = true;
873 BMXNetConnectInfo tmpInfo;
874 do
875 {
876 tmpInfo = m_ConnectInfo;
877 try
878 {
879 tmpInfo.ChangeServerInfo();
880 bRetry = false;
881 }
882 catch (Exception ex)
883 {
884 if (ex.Message == "User cancelled.")
885 {
886 bRetry = false;
887 return;
888 }
889 if (MessageBox.Show("Unable to connect to VistA. " + ex.Message , "Clinical Scheduling", MessageBoxButtons.RetryCancel) == DialogResult.Retry)
890 {
891 bRetry = true;
892 }
893 else
894 {
895 bRetry = false;
896 return;
897 }
898 }
899 } while (bRetry == true);
900
901 CloseAll();
902 m_bExitOK = true;
903 m_ConnectInfo = tmpInfo;
904
905 this.InitializeApp();
906
907 //Create a new document
908 CGDocument doc = new CGDocument();
909 doc.DocManager = _current;
910 doc.OnNewDocument();
911
912 }
913 catch (Exception ex)
914 {
915 throw ex;
916 }
917
918 }
919
920 private void mnuRPMSLogin_Click(object sender, EventArgs e)
921 {
922 //Warn that changing login will close all schedules
923 if (MessageBox.Show("Are you sure you want to close all schedules and login to VistA?", "Clinical Scheduling", MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) != DialogResult.OK)
924 return;
925
926 //Reconnect to RPMS and recreate all global recordsets
927 try
928 {
929 m_bExitOK = false;
930 CloseAll();
931 m_bExitOK = true;
932 _current.m_ConnectInfo = new BMXNet.BMXNetConnectInfo();
933 this.InitializeApp(true);
934 //Create a new document
935 CGDocument doc = new CGDocument();
936 doc.DocManager = _current;
937 doc.OnNewDocument();
938 }
939 catch (Exception ex)
940 {
941 throw ex;
942 }
943
944 }
945
946 delegate void CloseAllDelegate(string sMsg);
947
948 private void CloseAll(string sMsg)
949 {
950 if (sMsg == "")
951 {
952 sMsg = "Scheduling System Shutting Down Immediately for Maintenance.";
953 }
954
955 MessageBox.Show(sMsg, "Clinical Scheduling Administrator -- System Shutdown Notification", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
956
957 CloseAll();
958 }
959
960 private void CloseAll()
961 {
962 //Close all documents, views and connections
963 Hashtable h = CGDocumentManager.Current.Views;
964 int nTempCount = h.Count;
965 do
966 {
967 nTempCount = h.Count;
968 foreach (CGView v in h.Keys)
969 {
970 v.Close();
971 break;
972 }
973 } while ((h.Count > 0) && (nTempCount != h.Count));
974
975 h = CGDocumentManager.Current.AvailabilityViews;
976 nTempCount = h.Count;
977 do
978 {
979 nTempCount = h.Count;
980 foreach (CGAVView v in h.Keys)
981 {
982 v.Close();
983 break;
984 }
985 } while ((h.Count > 0) && (nTempCount != h.Count));
986
987 }
988
989 delegate DataTable RPMSDataTableDelegate(string CommandString, string TableName);
990
991 public DataTable RPMSDataTable(string sSQL, string sTableName)
992 {
993 //Retrieves a recordset from RPMS
994 string sErrorMessage = "";
995 try
996 {
997 System.IntPtr pHandle = this.Handle;
998 DataTable dtOut;
999 RPMSDataTableDelegate rdtd = new RPMSDataTableDelegate(ConnectInfo.RPMSDataTable);
1000 dtOut = (DataTable) this.Invoke(rdtd, new object[] {sSQL, sTableName});
1001 return dtOut;
1002 }
1003 catch (Exception ex)
1004 {
1005 sErrorMessage = "CGDocumentManager.RPMSDataTable error: " + ex.Message;
1006 throw ex;
1007 }
1008 }
1009
1010 public void ChangeDivision(System.Windows.Forms.Form frmCaller)
1011 {
1012 this.ConnectInfo.ChangeDivision(frmCaller);
1013 foreach (CGView v in _views.Keys)
1014 {
1015 v.InitializeDocView(v.Document.DocName);
1016 v.Document.RefreshDocument();
1017 }
1018 }
1019
1020 public void ViewRefresh()
1021 {
1022 foreach (CGView v in _views.Keys)
1023 {
1024 try
1025 {
1026 v.Document.RefreshDocument();
1027 }
1028 catch (Exception ex)
1029 {
1030 Debug.Write("CGDocumentManager.ViewRefresh Exception: " + ex.Message + "\n");
1031 }
1032 finally
1033 {
1034 }
1035 }
1036 Debug.Write("DocManager refreshed all views.\n");
1037 }
1038
1039 #endregion Methods & Events
1040
1041 }
1042}
Note: See TracBrowser for help on using the repository browser.