]> git.argeo.org Git - gpl/argeo-slc.git/blob - rcp/org.argeo.cms.ui.rcp/src/org/argeo/cms/ui/rcp/CmsRcpApp.java
[maven-release-plugin] prepare for next development iteration
[gpl/argeo-slc.git] / rcp / org.argeo.cms.ui.rcp / src / org / argeo / cms / ui / rcp / CmsRcpApp.java
1 package org.argeo.cms.ui.rcp;
2
3 import java.io.IOException;
4 import java.io.InputStream;
5 import java.security.PrivilegedAction;
6 import java.util.HashMap;
7 import java.util.Map;
8 import java.util.UUID;
9
10 import javax.security.auth.Subject;
11 import javax.security.auth.login.LoginContext;
12 import javax.security.auth.login.LoginException;
13
14 import org.apache.commons.logging.Log;
15 import org.apache.commons.logging.LogFactory;
16 import org.argeo.api.NodeConstants;
17 import org.argeo.cms.ui.CmsApp;
18 import org.argeo.cms.ui.CmsImageManager;
19 import org.argeo.cms.ui.CmsTheme;
20 import org.argeo.cms.ui.CmsView;
21 import org.argeo.cms.ui.UxContext;
22 import org.argeo.cms.ui.util.CmsUiUtils;
23 import org.eclipse.e4.ui.css.core.engine.CSSEngine;
24 import org.eclipse.e4.ui.css.core.engine.CSSErrorHandler;
25 import org.eclipse.e4.ui.css.swt.engine.CSSSWTEngineImpl;
26 import org.eclipse.swt.layout.GridLayout;
27 import org.eclipse.swt.widgets.Composite;
28 import org.eclipse.swt.widgets.Display;
29 import org.eclipse.swt.widgets.Shell;
30 import org.osgi.service.event.Event;
31 import org.osgi.service.event.EventAdmin;
32
33 /** Runs a {@link CmsApp} as an SWT desktop application. */
34 @SuppressWarnings("restriction")
35 public class CmsRcpApp implements CmsView {
36 private final static Log log = LogFactory.getLog(CmsRcpApp.class);
37
38 private Display display;
39 private Shell shell;
40 private CmsApp cmsApp;
41 private CmsUiThread uiThread;
42
43 // CMS View
44 private String uid;
45 private LoginContext loginContext;
46
47 private EventAdmin eventAdmin;
48
49 private CSSEngine cssEngine;
50
51 public CmsRcpApp() {
52 uid = UUID.randomUUID().toString();
53 }
54
55 public void init(Map<String, String> properties) {
56 try {
57 Thread.sleep(5000);
58 } catch (InterruptedException e) {
59 // silent
60 }
61 uiThread = new CmsUiThread();
62 uiThread.start();
63
64 }
65
66 public void destroy(Map<String, String> properties) {
67 if (!shell.isDisposed())
68 shell.dispose();
69 try {
70 uiThread.join();
71 } catch (InterruptedException e) {
72 // silent
73 } finally {
74 uiThread = null;
75 }
76 }
77
78 class CmsUiThread extends Thread {
79
80 public CmsUiThread() {
81 super("CMS UI");
82 }
83
84 @Override
85 public void run() {
86 display = new Display();
87 shell = new Shell(display);
88 shell.setText("Argeo CMS");
89 Composite parent = shell;
90 parent.setLayout(new GridLayout());
91 CmsView.registerCmsView(shell, CmsRcpApp.this);
92
93 // Subject subject = new Subject();
94 // CmsLoginShell loginShell = new CmsLoginShell(CmsRcpApp.this);
95 // loginShell.setSubject(subject);
96 try {
97 // try pre-auth
98 // loginContext = new LoginContext(NodeConstants.LOGIN_CONTEXT_USER, subject, loginShell);
99 loginContext = new LoginContext(NodeConstants.LOGIN_CONTEXT_SINGLE_USER);
100 loginContext.login();
101 } catch (LoginException e) {
102 throw new IllegalStateException("Could not log in.", e);
103 // loginShell.createUi();
104 // loginShell.open();
105 //
106 // while (!loginShell.getShell().isDisposed()) {
107 // if (!display.readAndDispatch())
108 // display.sleep();
109 // }
110 }
111
112 Subject.doAs(loginContext.getSubject(), (PrivilegedAction<Void>) () -> {
113 Composite ui = cmsApp.initUi(parent);
114 // ui.setData(CmsApp.UI_NAME_PROPERTY, uiName);
115 ui.setLayoutData(CmsUiUtils.fillAll());
116
117 // Styling
118 CmsTheme theme = CmsTheme.getCmsTheme(ui);
119 if (theme != null) {
120 cssEngine = new CSSSWTEngineImpl(display);
121 for (String path : theme.getSwtCssPaths()) {
122 try (InputStream in = theme.loadPath(path)) {
123 cssEngine.parseStyleSheet(in);
124 } catch (IOException e) {
125 throw new IllegalStateException("Cannot load stylesheet " + path, e);
126 }
127 }
128 cssEngine.setErrorHandler(new CSSErrorHandler() {
129 public void error(Exception e) {
130 log.error("SWT styling error: ", e);
131 }
132 });
133 applyStyles(shell);
134 }
135 shell.layout(true, true);
136
137 shell.open();
138 while (!shell.isDisposed()) {
139 if (!display.readAndDispatch())
140 display.sleep();
141 }
142 display.dispose();
143 return null;
144 });
145 }
146
147 }
148
149 /*
150 * CMS VIEW
151 */
152
153 @Override
154 public String getUid() {
155 return uid;
156 }
157
158 @Override
159 public UxContext getUxContext() {
160 throw new UnsupportedOperationException();
161 }
162
163 @Override
164 public void navigateTo(String state) {
165 throw new UnsupportedOperationException();
166 }
167
168 @Override
169 public void authChange(LoginContext loginContext) {
170 }
171
172 @Override
173 public void logout() {
174 if (loginContext != null)
175 try {
176 loginContext.logout();
177 } catch (LoginException e) {
178 log.error("Cannot log out", e);
179 }
180 }
181
182 @Override
183 public void exception(Throwable e) {
184 log.error("Unexpected exception in CMS RCP", e);
185 }
186
187 @Override
188 public CmsImageManager getImageManager() {
189 throw new UnsupportedOperationException();
190 }
191
192 @Override
193 public boolean isAnonymous() {
194 return false;
195 }
196
197 @Override
198 public void applyStyles(Object node) {
199 if (cssEngine != null)
200 cssEngine.applyStyles(node, true);
201 }
202
203 @Override
204 public void sendEvent(String topic, Map<String, Object> properties) {
205 if (properties == null)
206 properties = new HashMap<>();
207 if (properties.containsKey(CMS_VIEW_UID_PROPERTY) && !properties.get(CMS_VIEW_UID_PROPERTY).equals(uid))
208 throw new IllegalArgumentException("Property " + CMS_VIEW_UID_PROPERTY + " is set to another CMS view uid ("
209 + properties.get(CMS_VIEW_UID_PROPERTY) + ") then " + uid);
210 properties.put(CMS_VIEW_UID_PROPERTY, uid);
211 eventAdmin.sendEvent(new Event(topic, properties));
212 }
213
214 public <T> T doAs(PrivilegedAction<T> action) {
215 return Subject.doAs(getSubject(), action);
216 }
217
218 protected Subject getSubject() {
219 return loginContext.getSubject();
220 }
221
222 /*
223 * DEPENDENCY INJECTION
224 */
225 public void setCmsApp(CmsApp cmsApp) {
226 this.cmsApp = cmsApp;
227 }
228
229 public void setEventAdmin(EventAdmin eventAdmin) {
230 this.eventAdmin = eventAdmin;
231 }
232
233 }