source: trunk/autoquest-htmlmonitor/src/main/java/de/ugoe/cs/autoquest/htmlmonitor/HtmlGUIElementManager.java @ 1174

Last change on this file since 1174 was 1077, checked in by pharms, 11 years ago
  • prevented findbugs warnings
File size: 8.2 KB
Line 
1//   Copyright 2012 Georg-August-Universität Göttingen, Germany
2//
3//   Licensed under the Apache License, Version 2.0 (the "License");
4//   you may not use this file except in compliance with the License.
5//   You may obtain a copy of the License at
6//
7//       http://www.apache.org/licenses/LICENSE-2.0
8//
9//   Unless required by applicable law or agreed to in writing, software
10//   distributed under the License is distributed on an "AS IS" BASIS,
11//   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12//   See the License for the specific language governing permissions and
13//   limitations under the License.
14
15package de.ugoe.cs.autoquest.htmlmonitor;
16
17import java.io.UnsupportedEncodingException;
18import java.security.MessageDigest;
19import java.security.NoSuchAlgorithmException;
20import java.util.HashMap;
21import java.util.LinkedList;
22import java.util.List;
23import java.util.Map;
24
25import org.apache.commons.codec.binary.Base64;
26
27/**
28 * <p>
29 * This class is used to calculate unique ids for GUI elements and to reuse GUI element objects.
30 * For this it provides appropriate create methods. If there is already a GUI element for the
31 * given parameters, it is reused. Otherwise, a new one is instantiated with a unique id and
32 * returned.
33 * </p>
34 *
35 * @author Patrick Harms
36 */
37class HtmlGUIElementManager {
38
39    /**
40     * an internal map for GUI elements and their respective ids.
41     */
42    private Map<String, HtmlGUIElement> idMap = new HashMap<String, HtmlGUIElement>();
43   
44    /** */
45    private Map<String, List<HtmlPageElement>> domPathMap =
46          new HashMap<String, List<HtmlPageElement>>();
47   
48    /**
49     * <p>
50     * creates a new or reuses an existing GUI element representing a server
51     * </p>
52     *
53     * @param name the name of the server to represent (must not be null)
54     * @param port the port on the server via which the communication is done
55     *
56     * @return a new or reuses an existing GUI element representing a server
57     */
58    HtmlServer createHtmlServer(String name, int port) {
59        if (name == null) {
60            throw new IllegalArgumentException("name must not be null");
61        }
62       
63        String id = calculateId(name, Integer.toString(port));
64       
65        HtmlGUIElement server = idMap.get(id);
66       
67        if (server == null) {
68            server = new HtmlServer(id, name, port);
69            idMap.put(id, server);
70        }
71        else if (!(server instanceof HtmlServer)) {
72            throw new RuntimeException
73                ("id conflict: calculated the same id for two different GUI elements");
74        }
75       
76        return (HtmlServer) server;
77    }
78   
79    /**
80     * <p>
81     * creates a new or reuses an existing GUI element representing a document (web page)
82     * </p>
83     *
84     * @param server the server on which the document resides (must not be null)
85     * @param path   the path of the document on the web server (every following the server spec
86     *               in the URL, must not be null)
87     * @param query  the query part of the URL pointing to the document
88     * @param title  the title of the document if available
89     *
90     * @return a new or reuses an existing GUI element representing a document
91     */
92    HtmlDocument createHtmlDocument(HtmlServer server, String path, String query, String title) {
93        if (server == null) {
94            throw new IllegalArgumentException("server must not be null");
95        }
96        if (path == null) {
97            throw new IllegalArgumentException("path must not be null");
98        }
99
100        String id = calculateId(server.getId(), path, query, title);
101       
102        HtmlGUIElement document = idMap.get(id);
103
104        if (document == null) {
105            document = new HtmlDocument(id, server, path, query, title);
106            idMap.put(id, document);
107        }
108        else if (!(document instanceof HtmlDocument)) {
109            throw new RuntimeException
110                ("id conflict: calculated the same id for two different GUI elements");
111        }
112       
113        return (HtmlDocument) document;
114    }
115
116    /**
117     * <p>
118     * creates a new or reuses an existing GUI element representing an HTML tag in a document
119     * </p>
120     *
121     * @param document the document to which the HTML tag belongs (must not be null)
122     * @param parent   the parent tag, if any
123     * @param tagName  the name of the HTML tag (must not be null)
124     * @param htmlId   the document wide unique id of the tag, if available
125     * @param index    if no HTML id is present, the index of the tag regarding all children in
126     *                 the same parent having the same tag name.
127     *
128     * @return a new or reuses an existing GUI element representing an HTML tag
129     */
130    HtmlPageElement createHtmlPageElement(HtmlDocument    document,
131                                          HtmlPageElement parent,
132                                          String          tagName,
133                                          String          htmlId,
134                                          Integer         index)
135    {
136        if (document == null) {
137            throw new IllegalArgumentException("document must not be null");
138        }
139        if (tagName == null) {
140            throw new IllegalArgumentException("document must not be null");
141        }
142
143        String id = calculateId
144            (document.getId(), parent != null ? parent.getDOMPath() : null, tagName, htmlId,
145             index != null ? index.toString() : "-1");
146
147        HtmlGUIElement pageElement = idMap.get(id);
148
149        if (pageElement == null) {
150            pageElement = new HtmlPageElement(id, document, parent, tagName, htmlId, index);
151            idMap.put(id, pageElement);
152        }
153        else if (!(pageElement instanceof HtmlPageElement)) {
154            throw new RuntimeException
155                ("id conflict: calculated the same id for two different GUI elements");
156        }
157           
158        List<HtmlPageElement> candidates =
159            domPathMap.get(((HtmlPageElement) pageElement).getDOMPath());
160       
161        if (candidates == null) {
162            candidates = new LinkedList<HtmlPageElement>();
163            domPathMap.put(((HtmlPageElement) pageElement).getDOMPath(), candidates);
164        }
165       
166        if (!candidates.contains(pageElement)) {
167            candidates.add((HtmlPageElement) pageElement);
168        }
169
170        return (HtmlPageElement) pageElement;
171    }
172
173    /**
174     * <p>
175     * determines the HTML tag belonging to the given document and residing in the document at the
176     * location denoted by the path. The path must be equal to the return value of the
177     * {@link HtmlPageElement#getDOMPath()} method.
178     * </p>
179     *
180     * @param document the document to which the searched tag belongs
181     * @param domPath  the path through the DOM where the searched tag resists
182     *
183     * @return the appropriate HTML tag or null, if none is known
184     */
185    HtmlPageElement getPageElement(HtmlDocument document, String domPath) {
186        List<HtmlPageElement> candidates = domPathMap.get(domPath);
187       
188        if (candidates != null) {
189            for (HtmlPageElement candidate : candidates) {
190                if (document.equals(candidate.getDocument())) {
191                    return candidate;
192                }
193            }
194        }
195       
196        return null;
197    }
198
199    /**
200     * <p>
201     * calculates a unique id for the given string fragments using SHA-512 and Base64 encoding.
202     * </p>
203     *
204     * @param fragments strings to be used for calculating a unique id
205     *
206     * @return a Base64 encoded unique id for the provided fragments
207     */
208    private String calculateId(String... fragments) {
209        try {
210            MessageDigest md = MessageDigest.getInstance("SHA-512");
211           
212            for (String fragment : fragments) {
213                if (fragment != null) {
214                    md.update(fragment.getBytes("UTF-8"));
215                }
216            }
217           
218            return Base64.encodeBase64String(md.digest());
219        }
220        catch (UnsupportedEncodingException e) {
221            throw new IllegalStateException("Java VM does not support this code");
222        }
223        catch (NoSuchAlgorithmException e) {
224            throw new IllegalStateException("Java VM does not support this code");
225        }
226    }
227
228}
Note: See TracBrowser for help on using the repository browser.