View Javadoc
1   package ca.uhn.hl7v2.testpanel.controller;
2   
3   import static org.apache.commons.lang.StringUtils.*;
4   
5   import java.io.File;
6   import java.io.FileWriter;
7   import java.io.IOException;
8   import java.net.MalformedURLException;
9   import java.net.URL;
10  
11  import javax.swing.JFileChooser;
12  import javax.swing.JOptionPane;
13  
14  import org.apache.commons.lang.StringUtils;
15  import org.slf4j.Logger;
16  import org.slf4j.LoggerFactory;
17  
18  import ca.uhn.hl7v2.concurrent.DefaultExecutorService;
19  import ca.uhn.hl7v2.conf.ProfileException;
20  import ca.uhn.hl7v2.testpanel.model.conf.ExportedProfileGroupFile;
21  import ca.uhn.hl7v2.testpanel.model.conf.ProfileFileList;
22  import ca.uhn.hl7v2.testpanel.model.conf.ProfileGroup;
23  import ca.uhn.hl7v2.testpanel.model.conf.ProfileProxy;
24  import ca.uhn.hl7v2.testpanel.model.conf.TableFile;
25  import ca.uhn.hl7v2.testpanel.model.conf.TableFileList;
26  import ca.uhn.hl7v2.testpanel.ui.conf.ConformanceEditorPanel;
27  import ca.uhn.hl7v2.testpanel.ui.conf.ImportProfileGroupDialog;
28  import ca.uhn.hl7v2.testpanel.ui.conf.ProfileGroupNameDialog;
29  import ca.uhn.hl7v2.testpanel.util.AllFileFilter;
30  import ca.uhn.hl7v2.testpanel.util.ExtensionFilter;
31  import ca.uhn.hl7v2.testpanel.util.IOkCancelCallback;
32  
33  public class ConformanceEditorController {
34  
35  	private static final Logger ourLog = LoggerFactory.getLogger(ConformanceEditorController.class);
36  
37  	private JFileChooser myAddProfileFileChooser;
38  	private JFileChooser myAddTableFileChooser;
39  	private Controller myParentController;
40  
41  	private ConformanceEditorPanel myView;
42  
43  	public ConformanceEditorController(Controller theParentController) {
44  		myParentController = theParentController;
45  		myView = new ConformanceEditorPanel(this);
46  	}
47  
48  	public void addProfile(ProfileGroup theProfileGroup) {
49  		if (myAddProfileFileChooser == null) {
50  			myAddProfileFileChooser = new JFileChooser(Prefs.getInstance().getOpenPathConformanceProfile());
51  			myAddProfileFileChooser.setDialogTitle("Choose an HL7 Conformance Profile");
52  
53  			createFileSelectionExtentionFolder(myAddProfileFileChooser);
54  		}
55  
56  		int result = myAddProfileFileChooser.showDialog(myView.getFrame(), "Open");
57  		if (result == JFileChooser.APPROVE_OPTION) {
58  
59  			File chosenFile = myAddProfileFileChooser.getSelectedFile();
60  			try {
61  				ProfileProxy profile = ProfileProxy.loadFromFile(chosenFile);
62  				theProfileGroup.addProfile(profile);
63  				myParentController.getProfileFileList().updatePrefs();
64  			} catch (IOException e) {
65  				ourLog.error("Failed to load profile", e);
66  				myParentController.showDialogError("Failed to load profile: " + e.getMessage());
67  			} catch (ProfileException e) {
68  				ourLog.error("Failed to load profile", e);
69  				myParentController.showDialogError("Failed to load profile: " + e.getMessage());
70  			}
71  
72  		}
73  
74  	}
75  
76  	public static void createFileSelectionExtentionFolder(JFileChooser theChooser) {
77  		theChooser.addChoosableFileFilter(new ExtensionFilter("XML Files", new String[] { ".xml" }));
78  		theChooser.addChoosableFileFilter(new AllFileFilter());
79  	}
80  
81  	public void addTableFile() {
82  		if (myAddTableFileChooser == null) {
83  			myAddTableFileChooser = new JFileChooser(Prefs.getDefaultTableFileDirectory());
84  			createFileSelectionExtentionFolder(myAddTableFileChooser);
85  		}
86  
87  		int outcome = myAddTableFileChooser.showDialog(myView.getFrame(), "Create");
88  		if (outcome == JFileChooser.APPROVE_OPTION) {
89  
90  			File chosenFile = myAddTableFileChooser.getSelectedFile();
91  			if (chosenFile.exists()) {
92  				myParentController.getTableFileList().openFile(chosenFile);
93  			} else {
94  				myParentController.getTableFileList().addNewFile(chosenFile);
95  			}
96  
97  		}
98  
99  	}
100 
101 	public void closeFile(TableFile theSelectedFileOrTable) {
102 		myParentController.getTableFileList().removeTableFile(theSelectedFileOrTable);
103 		myParentController.getProfileFileList().updatePrefs();
104 	}
105 
106 	public void closeProfileGroup(ProfileGroup theSel) {
107 		if (showDialogYesNo("Are you sure you want to close this Profile Group?") == JOptionPane.YES_OPTION) {
108 			getProfileFileList().removeProfileGroup(theSel);
109 			myParentController.getProfileFileList().updatePrefs();
110 		}
111 	}
112 
113 	public void exportProfileGroup(ProfileGroup theSelectedProfileGroupOrFile) {
114 		String directory = Prefs.getInstance().getExportProfileGroupDirectory();
115 		JFileChooser chooser = new JFileChooser(new File(directory));
116 		chooser.setName("Export Profile Group to file...");
117 		int value = chooser.showDialog(myView.getFrame(), "Export");
118 		if (value == JFileChooser.APPROVE_OPTION) {
119 			File file = chooser.getSelectedFile();
120 			if (file.isDirectory()) {
121 				myParentController.showDialogError("Must enter a file to save to");
122 				return;
123 			}
124 
125 			if (file.exists()) {
126 				if (JOptionPane.YES_OPTION != myParentController.showDialogYesNo("File exists, overwrite it: " + file.getName())) {
127 					return;
128 				}
129 			}
130 
131 			Prefs.getInstance().setExportProfileGroupDirectory(file.getParent());
132 
133 			try {
134 
135 				ExportedProfileGroupFile exported = new  ExportedProfileGroupFile(theSelectedProfileGroupOrFile, getTableFileList());
136 				FileWriter w = new FileWriter(file, false);
137 				w.append(exported.exportConfigToXm());
138 				w.close();
139 
140 				myParentController.showDialogInfo("Exported conformance group to file:\n" + file.getName());
141 
142 			} catch (IOException e) {
143 				ourLog.error("Failed to export profile", e);
144 				myParentController.showDialogError("Failed to export profile: " + e.getMessage());
145 			}
146 		}
147 	}
148 
149 	public ProfileFileList getProfileFileList() {
150 		return myParentController.getProfileFileList();
151 	}
152 
153 	public TableFileList getTableFileList() {
154 		return myParentController.getTableFileList();
155 	}
156 
157 	public void importProfileGroup() {
158 		ImportProfileGroupDialog dialog = new ImportProfileGroupDialog();
159 		dialog.setVisible(true);
160 
161 		URL importUrl;
162 		if (dialog.getUrlString() != null) {
163 			importUrl = dialog.getUrlString();
164 		} else if (dialog.getFileString() != null) {
165 			try {
166 				File file = dialog.getFileString();
167 				Prefs.getInstance().setImportProfileGroupDirectory(file.getParentFile());
168 				importUrl = file.toURI().toURL();
169 			} catch (MalformedURLException e) {
170 				myParentController.showDialogError(e.getMessage());
171 				return;
172 			}
173 		} else {
174 			ourLog.info("Aborting because neither a file nor a URL were selected");
175 			return;
176 		}
177 
178 		ExportedProfileGroupFile file = ExportedProfileGroupFile.loadFromUrl(importUrl);
179 		if (file == null || file.getProfileGroup() == null || isBlank(file.getProfileGroup().getId())) {
180 			myParentController.showDialogError("File does not appear to hold an exported profile group:\n" + importUrl.toString());
181 			return;
182 		}
183 
184 		try {
185 			file.hydrate();
186 		} catch (Exception e) {
187 			ourLog.error("Failed to hydrate exported profile group", e);
188 			myParentController.showDialogError("Experienced an error importing profile group file:\n" + importUrl.toString() + "\nMessage: " + e.getMessage());
189 			return;
190 		}
191 
192 		String profileId = file.getProfileGroup().getId();
193 		if (getProfileFileList().getProfile(profileId) != null) {
194 			int overwrite = JOptionPane.showOptionDialog(null, "It appears that this profile group already exists. Do you want to overwrite it? Select no to add as a new profile group instead of overwriting.", "Overwrite?", JOptionPane.YES_NO_CANCEL_OPTION,
195 					JOptionPane.QUESTION_MESSAGE, null, null, JOptionPane.YES_OPTION);
196 			if (overwrite == JOptionPane.CANCEL_OPTION) {
197 				return;
198 			} else if (overwrite == JOptionPane.NO_OPTION) {
199 				file.renumberEverything();
200 			}
201 		}
202 
203 		file.getProfileGroup().setSourceUrl(importUrl.toString());
204 
205 		for (TableFile next : file.getTableFiles()) {
206 			getTableFileList().importFile(next);
207 		}
208 
209 		getProfileFileList().importFile(file.getProfileGroup());
210 
211 	}
212 
213 	public void markFileForSaving(final TableFile theTableFile) {
214 		theTableFile.setUnsaved(true);
215 
216 		// TODO: this is a pretty messy way of doing this
217 		DefaultExecutorService.getDefaultService().execute(new Runnable() {
218 
219 			public void run() {
220 				synchronized (ConformanceEditorController.this) {
221 					if (theTableFile.isUnsaved()) {
222 						try {
223 							Thread.sleep(5000);
224 						} catch (InterruptedException e) {
225 							// ignore
226 						}
227 
228 						try {
229 							ourLog.info("Saving table file: {}", theTableFile.getFileName().getAbsolutePath());
230 							theTableFile.flushToFile();
231 							theTableFile.setUnsaved(false);
232 						} catch (IOException e) {
233 							ourLog.error("Failed to save table file " + theTableFile.getFileName().getAbsolutePath(), e);
234 						}
235 
236 					}
237 				}
238 			}
239 		});
240 	}
241 
242 	public void newProfileGroup() {
243 
244 		IOkCancelCallback<String> callback = new IOkCancelCallback<String>() {
245 
246 			public void cancel(String theArg) {
247 				// ignore
248 			}
249 
250 			public void ok(String theArg) {
251 				if (StringUtils.isBlank(theArg)) {
252 					return;
253 				}
254 
255 				myParentController.getProfileFileList().newProfileGroup(theArg);
256 				myParentController.getProfileFileList().updatePrefs();
257 			}
258 		};
259 
260 		ProfileGroupNameDialog dialog = new ProfileGroupNameDialog();
261 		dialog.setName("New Profile Group");
262 		dialog.setCallback(callback);
263 		dialog.start();
264 
265 	}
266 
267 	public void renameProfileGroup(final ProfileGroup theSel) {
268 		IOkCancelCallback<String> callback = new IOkCancelCallback<String>() {
269 
270 			public void cancel(String theArg) {
271 				// ignore
272 			}
273 
274 			public void ok(String theArg) {
275 				if (StringUtils.isBlank(theArg)) {
276 					return;
277 				}
278 
279 				theSel.setName(theArg);
280 				myParentController.getProfileFileList().updatePrefs();
281 			}
282 		};
283 
284 		ProfileGroupNameDialog dialog = new ProfileGroupNameDialog();
285 		dialog.setCallback(callback);
286 		dialog.setName(theSel.getName());
287 		dialog.start();
288 	}
289 
290 	public void show() {
291 		myView.show();
292 	}
293 
294 	public int showDialogYesNo(String message) {
295 		return JOptionPane.showConfirmDialog(myView.getFrame(), message, Controller.DIALOG_TITLE, JOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE);
296 	}
297 
298 }