1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 package complex.dispatches;
28 
29 // __________ Imports __________
30 
31 // structs, const, ...
32 import com.sun.star.beans.PropertyValue;
33 
34 // exceptions
35 import com.sun.star.frame.DispatchDescriptor;
36 import com.sun.star.frame.XDispatch;
37 import com.sun.star.frame.XDispatchProvider;
38 import com.sun.star.frame.XDispatchProviderInterceptor;
39 import com.sun.star.frame.XInterceptorInfo;
40 import com.sun.star.frame.XStatusListener;
41 
42 // interfaces
43 
44 
45 // helper
46 import com.sun.star.util.URL;
47 
48 // others
49 //import java.lang.*;
50 
51 // __________ Implementation __________
52 
53 /**
54  * implements a configurable interceptor for dispatch events.
55  */
56 public class Interceptor implements XDispatchProvider,
57                                     XDispatch,
58                                     XDispatchProviderInterceptor,
59                                     XInterceptorInfo
60 {
61     // ____________________
62 
63     /** contains the list of interception URL schema's (wildcards are allowed there!)
64         supported by this interceptor. It can be set from outside.
65         If no external URLs are set, the default "*" is used instead.
66         That would have the same effect as if this implementation would not support the
67         interface XInterceptorInfo !
68      */
69     private String[] m_lURLs4InterceptionInfo = null;
70 
71     // ____________________
72 
73     /** These URL's will be blocked by this interceptor.
74         Can be set from outside. Every queryDispatch() for these
75         set of URL's will be answered with an empty dispatch object!
76         If no external URLs are set the default "*" is used instead.
77         So every incoming URL will be blocked .-)
78      */
79     private String[] m_lURLs4Blocking = null;
80 
81     // ____________________
82 
83     /** Every dispatch interceptor knows it's master and slave interceptor
84         of the dispatch chain. These values must be stupid handled .-)
85         They have to be set and reset in case the right interface methods are called.
86         Nothing more. It's not allowed to dispose() it.
87         The slave can be used inside queryDispatch() to forward requests,
88         which are not handled by this interceptor instance.
89      */
90     private XDispatchProvider m_xSlave  = null;
91     private XDispatchProvider m_xMaster = null;
92 
93     // ____________________
94 
95     /** counts calls of setSlave...().
96         So the outside API test can use this value to know if this interceptor
97         was realy added to the interceptor chain of OOo.
98      */
99     private int m_nRegistrationCount = 0;
100 
101     // ____________________
102 
103     /** indicates if this interceptor object is currently part of the interceptor
104         chain of OOo. Only true if a valid slave or master dispatch is set on this
105         instance.
106      */
107     private boolean m_bIsRegistered = false;
108 
109 
110     // ____________________
111 
112     /** ctor
113      *  It's initialize an object of this class with default values.
114      */
115     public Interceptor()
116     {
117     }
118 
119     // ____________________
120 
121     /** XInterceptorInfo */
122     public synchronized String[] getInterceptedURLs()
123     {
124         return impl_getURLs4InterceptionInfo();
125     }
126 
127     // ____________________
128 
129     /** XDispatchProviderInterceptor */
130     public synchronized XDispatchProvider getSlaveDispatchProvider()
131     {
132         System.out.println("Interceptor.getSlaveDispatchProvider() called");
133         return m_xSlave;
134     }
135 
136     // ____________________
137 
138     /** XDispatchProviderInterceptor */
139     public synchronized XDispatchProvider getMasterDispatchProvider()
140     {
141         System.out.println("Interceptor.getMasterDispatchProvider() called");
142         return m_xMaster;
143     }
144 
145     // ____________________
146 
147     /** XDispatchProviderInterceptor */
148     public synchronized void setSlaveDispatchProvider(XDispatchProvider xSlave)
149     {
150         System.out.println("Interceptor.setSlaveDispatchProvider("+xSlave+") called");
151 
152         if (xSlave != null)
153         {
154             ++m_nRegistrationCount;
155             m_bIsRegistered = true;
156         }
157         else
158         {
159             m_bIsRegistered = false;
160         }
161 
162         m_xSlave = xSlave;
163     }
164 
165     // ____________________
166 
167     /** XDispatchProviderInterceptor */
168     public synchronized void setMasterDispatchProvider(XDispatchProvider xMaster)
169     {
170         System.out.println("Interceptor.setMasterDispatchProvider("+xMaster+") called");
171         m_xMaster = xMaster;
172     }
173 
174     // ____________________
175 
176     /** XDispatchProvider
177      */
178     public synchronized XDispatch queryDispatch(URL aURL            ,
179                                                                    String                sTargetFrameName,
180                                                                    int                   nSearchFlags    )
181     {
182         System.out.println("Interceptor.queryDispatch('"+aURL.Complete+"', '"+sTargetFrameName+"', "+nSearchFlags+") called");
183 
184         if (impl_isBlockedURL(aURL.Complete))
185         {
186             System.out.println("Interceptor.queryDispatch(): URL blocked => returns NULL");
187             return null;
188         }
189 
190         if (m_xSlave != null)
191         {
192             System.out.println("Interceptor.queryDispatch(): ask slave ...");
193             return m_xSlave.queryDispatch(aURL, sTargetFrameName, nSearchFlags);
194         }
195 
196         System.out.println("Interceptor.queryDispatch(): no idea => returns this");
197         return this;
198     }
199 
200     // ____________________
201 
202     /** XDispatchProvider
203      */
204     public XDispatch[] queryDispatches(DispatchDescriptor[] lRequests)
205     {
206         int i = 0;
207         int c = lRequests.length;
208 
209         XDispatch[] lResults = new XDispatch[c];
210         for (i=0; i<c; ++i)
211         {
212             lResults[i] = queryDispatch(lRequests[i].FeatureURL ,
213                                         lRequests[i].FrameName  ,
214                                         lRequests[i].SearchFlags);
215         }
216 
217         return lResults;
218     }
219 
220     // ____________________
221 
222     /** XDispatch
223      */
224     public synchronized void dispatch(URL              aURL      ,
225                                       PropertyValue[] lArguments)
226     {
227         System.out.println("Interceptor.dispatch('"+aURL.Complete+"') called");
228     }
229 
230     // ____________________
231 
232     /** XDispatch
233      */
234     public synchronized void addStatusListener(XStatusListener xListener,
235                                                com.sun.star.util.URL              aURL     )
236     {
237         System.out.println("Interceptor.addStatusListener(..., '"+aURL.Complete+"') called");
238     }
239 
240     // ____________________
241 
242     /** XDispatch
243      */
244     public synchronized void removeStatusListener(XStatusListener xListener,
245                                                   com.sun.star.util.URL              aURL     )
246     {
247         System.out.println("Interceptor.removeStatusListener(..., '"+aURL.Complete+"') called");
248     }
249 
250     // ____________________
251 
252     public synchronized int getRegistrationCount()
253     {
254         return m_nRegistrationCount;
255     }
256 
257     // ____________________
258 
259     public synchronized boolean isRegistered()
260     {
261         return m_bIsRegistered;
262     }
263 
264     // ____________________
265 
266     /** set a new list of URL's, which should be used on registration time
267         (that's why it's neccessary to call this impl-method before the interceptor
268         is used at the OOo API!) to optimize the interception chain.
269      */
270     public synchronized void setURLs4InterceptionInfo(String[] lURLs)
271     {
272         m_lURLs4InterceptionInfo = lURLs;
273     }
274 
275     // ____________________
276 
277     /** set a new list of URL's, which should be blocked by this interceptor.
278         (that's why it's neccessary to call this impl-method before the interceptor
279         is used at the OOo API!)
280      */
281     public synchronized void setURLs4URLs4Blocking(String[] lURLs)
282     {
283         m_lURLs4Blocking = lURLs;
284     }
285 
286     // ____________________
287 
288     /** must be used internal to access the member m_lURLs4InterceptionInfo
289         - threadsafe
290         - and to make sure it's initialized on demand
291      */
292     private synchronized String[] impl_getURLs4InterceptionInfo()
293     {
294         if (m_lURLs4InterceptionInfo == null)
295         {
296             m_lURLs4InterceptionInfo    = new String[1];
297             m_lURLs4InterceptionInfo[0] = "*";
298         }
299 
300         return m_lURLs4InterceptionInfo;
301     }
302 
303     // ____________________
304 
305     /** must be used internal to access the member m_lURLs4Blocking
306         - threadsafe
307         - and to make sure it's initialized on demand
308      */
309     private synchronized String[] impl_getURLs4Blocking()
310     {
311         if (m_lURLs4Blocking == null)
312         {
313             m_lURLs4Blocking    = new String[1];
314             m_lURLs4Blocking[0] = "*";
315         }
316 
317         return m_lURLs4Blocking;
318     }
319 
320     // ____________________
321     private boolean impl_isBlockedURL(String sURL)
322     {
323         String[] lBlockedURLs = impl_getURLs4Blocking();
324         int      i            = 0;
325         int      c            = lBlockedURLs.length;
326 
327         for (i=0; i<c; ++i)
328         {
329             if (impl_match(sURL, lBlockedURLs[i]))
330             {
331                 return true;
332             }
333         }
334 
335         return false;
336     }
337 
338     // ____________________
339 
340     private boolean impl_match(String sVal1, String sVal2)
341     {
342         // TODO implement wildcard match
343         return (sVal1.equals(sVal2));
344     }
345 }
346