Changeset 2926
- Timestamp:
- 05/22/13 16:13:37 (11 years ago)
- Location:
- SRUAggregator/trunk/src/main
- Files:
-
- 16 added
- 7 edited
- 10 copied
Legend:
- Unmodified
- Added
- Removed
-
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/app/Aggregator.java
r2738 r2926 41 41 import com.sun.jersey.api.client.config.ClientConfig; 42 42 import com.sun.jersey.api.client.config.DefaultClientConfig; 43 import eu.clarin.sru.fcs.aggregator.sparam2.Corpus2; 44 import eu.clarin.sru.fcs.aggregator.sparam2.Corpus2Renderer; 45 import eu.clarin.sru.fcs.aggregator.sparam2.CorpusTreeModel2; 43 46 import eu.clarin.weblicht.wlfxb.tc.api.GeoLongLatFormat; 44 47 import eu.clarin.weblicht.wlfxb.tc.api.Token; … … 46 49 import eu.clarin.weblicht.wlfxb.xb.WLData; 47 50 import javax.ws.rs.core.MediaType; 51 import org.zkoss.zul.Borderlayout; 52 import org.zkoss.zul.DefaultTreeNode; 53 import org.zkoss.zul.Div; 48 54 import org.zkoss.zul.Popup; 55 import org.zkoss.zul.Progressmeter; 49 56 50 57 /** … … 101 108 private CenterRegistry registry; 102 109 private boolean testingMode = false; 110 111 112 //TODO 113 @Wire 114 private Div aboutDiv; 115 @Wire 116 private Label aboutLabel; 117 @Wire 118 private Div soDiv; 119 private SearchOptions searchOptionsComposer; 120 @Wire 121 private Label soLabel; 122 @Wire 123 private Div srDiv; 124 private SearchResults searchResultsComposer; 125 @Wire 126 private Label srLabel; 127 @Wire 128 private Div helpDiv; 129 @Wire 130 private Label helpLabel; 131 132 133 @Wire 134 Progressmeter pMeter; 103 135 104 136 @Override … … 107 139 super.doAfterCompose(comp); 108 140 109 processParameters();110 111 languageSelect.setSelectedItem(anyLanguage);112 113 searchResultsController = new SearchResultsController(resultsBox, searchResultsProgress);114 // assign the search controller to desktop, so that it can be accessed to be shutdown when the desktop is destroyed115 Executions.getCurrent().getDesktop().setAttribute(searchResultsController.getClass().getSimpleName(), searchResultsController);116 // also add it to the list of actice controllers of the web application, so that they can be shutdown when the application stops117 Set<SearchResultsController> activeControllers = (Set<SearchResultsController>) Executions.getCurrent().getDesktop().getWebApp().getAttribute(WebAppListener.ACTIVE_SEARCH_CONTROLLERS);118 activeControllers.add(searchResultsController);119 120 registry = new CenterRegistry();121 registry.loadChildren(testingMode);122 CorpusTreeModel corporaModel = new CorpusTreeModel(registry);123 tree.setModel(corporaModel);124 tree.setItemRenderer(new CorpusTreeNodeRenderer());125 tree.setMultiple(true);141 // processParameters(); 142 // 143 // languageSelect.setSelectedItem(anyLanguage); 144 // 145 // searchResultsController = new SearchResultsController(resultsBox, searchResultsProgress); 146 // // assign the search controller to desktop, so that it can be accessed to be shutdown when the desktop is destroyed 147 // Executions.getCurrent().getDesktop().setAttribute(searchResultsController.getClass().getSimpleName(), searchResultsController); 148 // // also add it to the list of actice controllers of the web application, so that they can be shutdown when the application stops 149 // Set<SearchResultsController> activeControllers = (Set<SearchResultsController>) Executions.getCurrent().getDesktop().getWebApp().getAttribute(WebAppListener.ACTIVE_SEARCH_CONTROLLERS); 150 // activeControllers.add(searchResultsController); 151 // 152 // registry = new CenterRegistry(); 153 // registry.loadChildren(testingMode); 154 // CorpusTreeModel corporaModel = new CorpusTreeModel(registry); 155 // tree.setModel(corporaModel); 156 // tree.setItemRenderer(new CorpusTreeNodeRenderer()); 157 // tree.setMultiple(true); 126 158 127 159 128 160 //tempMap(); 129 161 162 searchOptionsComposer = (SearchOptions) soDiv.getChildren().get(0).getChildren().get(0).getAttribute("$" + SearchOptions.class.getSimpleName()); 163 searchResultsComposer = (SearchResults) srDiv.getChildren().get(0).getChildren().get(0).getAttribute("$" + SearchResults.class.getSimpleName()); 164 130 165 } 131 166 … … 158 193 @Listen("onClick = #searchButton") 159 194 public void onExecuteSearch(Event ev) { 160 int maxRecords = Integer.parseInt(maximumRecordsSelect.getValue()); 161 searchResultsController.executeSearch(tree.getSelectedItems(), maxRecords, searchString.getText(), version); 195 //searchResultsController.executeSearch(tree.getSelectedItems(), maxRecords, searchString.getText(), version); 196 Map<String,Set<Corpus2>> selectedCorpora = searchOptionsComposer.getSelectedCorpora(); 197 boolean emptyCorpora = true; 198 for (Set<Corpus2> corpora : selectedCorpora.values()) { 199 if (!corpora.isEmpty()) { 200 emptyCorpora = false; 201 break; 202 } 203 } 204 if (emptyCorpora) { 205 Messagebox.show("No corpora is selected. To perform the search, please select corus/corpora of interest by checking the corpora checkboxes.", "FCS", 0, Messagebox.INFORMATION); 206 } else if (searchString.getText().isEmpty()) { 207 Messagebox.show("No query is specified. To perform the search, please enter a keyword of interest in the search input field, e.g. Elefant, and press the 'Search' button.", "FCS", 0, Messagebox.INFORMATION); 208 } else { 209 int maxRecords = searchOptionsComposer.getMaxRecords(); 210 searchResultsComposer.executeSearch(selectedCorpora, maxRecords, searchString.getText(), pMeter); 211 onClickSearchResult(null); 212 } 162 213 } 163 214 … … 318 369 } 319 370 } 371 372 373 @Listen("onClick = #helpLabel") 374 public void onClickHelp(Event ev) { 375 this.helpDiv.setVisible(true); 376 this.helpLabel.setSclass("internalLinkSelected"); 377 this.aboutDiv.setVisible(false); 378 this.aboutLabel.setSclass("internalLink"); 379 this.soDiv.setVisible(false); 380 this.soLabel.setSclass("internalLink"); 381 this.srDiv.setVisible(false); 382 this.srLabel.setSclass("internalLink"); 383 } 384 385 @Listen("onClick = #aboutLabel") 386 public void onClickAbout(Event ev) { 387 this.aboutDiv.setVisible(true); 388 this.aboutLabel.setSclass("internalLinkSelected"); 389 this.helpDiv.setVisible(false); 390 this.helpLabel.setSclass("internalLink"); 391 this.soDiv.setVisible(false); 392 this.soLabel.setSclass("internalLink"); 393 this.srDiv.setVisible(false); 394 this.srLabel.setSclass("internalLink"); 395 } 396 397 @Listen("onClick = #soLabel") 398 public void onClickAdvSearch(Event ev) { 399 this.soDiv.setVisible(true); 400 this.soLabel.setSclass("internalLinkSelected"); 401 this.aboutDiv.setVisible(false); 402 this.aboutLabel.setSclass("internalLink"); 403 this.helpDiv.setVisible(false); 404 this.helpLabel.setSclass("internalLink"); 405 this.srDiv.setVisible(false); 406 this.srLabel.setSclass("internalLink"); 407 } 408 409 @Listen("onClick = #srLabel") 410 public void onClickSearchResult(Event ev) { 411 this.srDiv.setVisible(true); 412 this.srLabel.setSclass("internalLinkSelected"); 413 this.aboutDiv.setVisible(false); 414 this.aboutLabel.setSclass("internalLink"); 415 this.soDiv.setVisible(false); 416 this.soLabel.setSclass("internalLink"); 417 this.helpDiv.setVisible(false); 418 this.helpLabel.setSclass("internalLink"); 419 } 320 420 } -
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/app/SearchOptions.java
r2738 r2926 1 1 package eu.clarin.sru.fcs.aggregator.app; 2 2 3 import com.google.gson.Gson;4 import com.google.gson.reflect.TypeToken;5 import com.sun.jersey.api.client.Client;6 3 import eu.clarin.sru.client.SRUVersion; 7 4 import eu.clarin.sru.fcs.aggregator.data.CenterRegistry; 8 import eu.clarin.sru.fcs.aggregator.sparam.CorpusTreeModel; 5 import eu.clarin.sru.fcs.aggregator.data.Institution; 6 import eu.clarin.sru.fcs.aggregator.data.SearchResult; 9 7 import eu.clarin.sru.fcs.aggregator.sparam.CorpusTreeNodeRenderer; 10 import eu.clarin.sru.fcs.aggregator.sresult.SearchResultsController; 11 import java.lang.reflect.Type; 12 import java.util.ArrayList; 13 import java.util.LinkedHashMap; 8 import eu.clarin.sru.fcs.aggregator.sparam2.Corpus2; 9 import eu.clarin.sru.fcs.aggregator.sparam2.Corpus2Renderer; 10 import eu.clarin.sru.fcs.aggregator.sparam2.CorpusByInstitutionComparator; 11 import eu.clarin.sru.fcs.aggregator.sparam2.CorpusByInstitutionDComparator; 12 import eu.clarin.sru.fcs.aggregator.sparam2.CorpusByNameComparator; 13 import eu.clarin.sru.fcs.aggregator.sparam2.CorpusByNameDComparator; 14 import eu.clarin.sru.fcs.aggregator.sparam2.CorpusTreeModel2; 15 import eu.clarin.sru.fcs.aggregator.sparam2.Languages; 16 import java.util.HashMap; 17 import java.util.HashSet; 14 18 import java.util.List; 15 19 import java.util.Map; 16 20 import java.util.Set; 17 21 import java.util.logging.*; 18 import org.zkoss.util.media.AMedia;19 import org.zkoss.util.media.Media;20 22 import org.zkoss.zk.ui.Component; 21 23 import org.zkoss.zk.ui.Executions; … … 24 26 import org.zkoss.zk.ui.select.annotation.Listen; 25 27 import org.zkoss.zk.ui.select.annotation.Wire; 26 import org.zkoss.zul.Button;27 28 import org.zkoss.zul.Combobox; 28 29 import org.zkoss.zul.Comboitem; 29 import org.zkoss.zul.Groupbox; 30 import org.zkoss.zul.Iframe; 30 import org.zkoss.zul.DefaultTreeNode; 31 31 import org.zkoss.zul.Label; 32 import org.zkoss.zul.Menuitem;33 32 import org.zkoss.zul.Messagebox; 34 import org.zkoss.zul.Textbox;35 33 import org.zkoss.zul.Tree; 36 34 import org.zkoss.zul.Treechildren; 35 import org.zkoss.zul.Treecol; 37 36 import org.zkoss.zul.Treeitem; 38 import org.zkoss.zul.Window;39 37 import org.zkoss.zul.event.ZulEvents; 40 import com.sun.jersey.api.client.WebResource;41 import com.sun.jersey.api.client.config.ClientConfig;42 import com.sun.jersey.api.client.config.DefaultClientConfig;43 import eu.clarin.weblicht.wlfxb.tc.api.GeoLongLatFormat;44 import eu.clarin.weblicht.wlfxb.tc.api.Token;45 import eu.clarin.weblicht.wlfxb.tc.xb.TextCorpusStored;46 import eu.clarin.weblicht.wlfxb.xb.WLData;47 import javax.ws.rs.core.MediaType;48 import org.zkoss.zul.Popup;49 38 50 39 /** 51 * Main window of the Aggregator application.52 40 * 53 41 * @author Yana Panchenko 54 42 */ 55 public class Aggregatorextends SelectorComposer<Component> {43 public class SearchOptions extends SelectorComposer<Component> { 56 44 57 45 private static final Logger logger = Logger.getLogger(Aggregator.class.getName()); 58 // @Wire 59 // private Grid anzeigeGrid; 60 @Wire 61 private Textbox searchString; 46 62 47 @Wire 63 48 private Combobox languageSelect; 64 // @Wire65 // private Button searchButton;66 // @Wire67 // private Groupbox allCorpora;68 // @Wire69 // private Comboitem german;70 49 @Wire 71 50 private Comboitem anyLanguage; 72 51 @Wire 73 private Window resultsBox;74 // @Wire75 // private Button selectAll;76 // @Wire77 // private Button deselectAll;78 // @Wire79 // private Window mainWindow;80 @Wire81 52 private Combobox maximumRecordsSelect; 82 // @Wire83 // private Button addForeignEndpoint;84 @Wire85 Combobox foreignEndpointSelect;86 53 @Wire 87 54 private Tree tree; 88 @Wire 89 private Label searchResultsProgress; 90 @Wire 91 private Popup wspaceSigninpop; 92 @Wire 93 private Textbox wspaceUserName; 94 @Wire 95 private Textbox wspaceUserPwd; 96 private WebResource mapGenerator; 97 public static final String MAPS_SERVICE_URL = "http://weblicht.sfs.uni-tuebingen.de/rws/service-geolocationconsumer/resources/geoloc/"; 55 98 56 private Map<String, List<String>> xAggregationContext; 99 private SRUVersion version = SRUVersion.VERSION_1_2;100 private SearchResultsController searchResultsController;101 57 private CenterRegistry registry; 102 58 private boolean testingMode = false; 59 60 private Corpus2Renderer corpusRenderer; 61 62 private Languages languages; 63 103 64 104 65 @Override … … 106 67 107 68 super.doAfterCompose(comp); 108 109 processParameters(); 110 111 languageSelect.setSelectedItem(anyLanguage); 112 113 searchResultsController = new SearchResultsController(resultsBox, searchResultsProgress); 114 // assign the search controller to desktop, so that it can be accessed to be shutdown when the desktop is destroyed 115 Executions.getCurrent().getDesktop().setAttribute(searchResultsController.getClass().getSimpleName(), searchResultsController); 116 // also add it to the list of actice controllers of the web application, so that they can be shutdown when the application stops 117 Set<SearchResultsController> activeControllers = (Set<SearchResultsController>) Executions.getCurrent().getDesktop().getWebApp().getAttribute(WebAppListener.ACTIVE_SEARCH_CONTROLLERS); 118 activeControllers.add(searchResultsController); 119 69 70 languages = (Languages) Executions.getCurrent().getDesktop().getWebApp().getAttribute(WebAppListener.LANGUAGES); 71 120 72 registry = new CenterRegistry(); 121 registry.loadChildren(testingMode); 122 CorpusTreeModel corporaModel = new CorpusTreeModel(registry); 73 74 Corpus2 rootCorpus = new Corpus2(); 75 List<DefaultTreeNode<Corpus2>> rootChildren = Corpus2.initCorpusChildren(registry); 76 DefaultTreeNode<Corpus2> root = new DefaultTreeNode(rootCorpus, rootChildren); 77 CorpusTreeModel2 corporaModel = new CorpusTreeModel2(root); 78 79 corporaModel.setMultiple(true); 123 80 tree.setModel(corporaModel); 124 tree.setItemRenderer(new CorpusTreeNodeRenderer()); 125 tree.setMultiple(true); 126 127 128 //tempMap(); 129 81 corpusRenderer = new Corpus2Renderer(); 82 tree.setItemRenderer(corpusRenderer); 83 Treecol nameCol = (Treecol) tree.getTreecols().getFellow("nameCol"); 84 nameCol.setSortAscending(new CorpusByNameComparator()); 85 nameCol.setSortDescending(new CorpusByNameDComparator()); 86 Treecol instCol = (Treecol) tree.getTreecols().getFellow("instCol"); 87 instCol.setSortAscending(new CorpusByInstitutionComparator()); 88 instCol.setSortDescending(new CorpusByInstitutionDComparator()); 89 //tree.setSizedByContent(true); 90 loadLanguages(); 91 130 92 } 131 93 … … 137 99 @Listen(ZulEvents.ON_AFTER_RENDER + "=#tree") 138 100 public void onAfterRenderCorporaTree(Event ev) { 139 CorpusTreeNodeRenderer.selectEndpoints(this.tree, this.xAggregationContext);101 onSelectAll(null); 140 102 } 141 103 … … 144 106 Treechildren openTreeItems = tree.getTreechildren(); 145 107 for (Treeitem openItem : openTreeItems.getItems()) { 146 CorpusTreeNodeRenderer.selectItem(openItem);108 corpusRenderer.updateItem(openItem, true); 147 109 } 148 110 } … … 152 114 Treechildren openTreeItems = tree.getTreechildren(); 153 115 for (Treeitem openItem : openTreeItems.getItems()) { 154 CorpusTreeNodeRenderer.unselectItem(openItem); 155 } 156 } 157 158 @Listen("onClick = #searchButton") 159 public void onExecuteSearch(Event ev) { 160 int maxRecords = Integer.parseInt(maximumRecordsSelect.getValue()); 161 searchResultsController.executeSearch(tree.getSelectedItems(), maxRecords, searchString.getText(), version); 162 } 163 164 @Listen("onOK = #searchString") 165 public void onEnterSearchString(Event ev) { 166 onExecuteSearch(ev); 167 } 168 169 @Listen("onClick=#clearResults") 170 public void onClearResults(Event ev) { 171 resultsBox.getChildren().clear(); 172 } 173 174 @Listen("onClick=#showHelp") 175 public void onShowHelp(Event ev) { 176 resultsBox.getChildren().clear(); 177 Iframe help = new Iframe(); 178 help.setWidth("100%"); 179 help.setHeight("100%"); 180 help.setSrc("help.html"); 181 resultsBox.appendChild(help); 182 } 183 184 @Listen("onClick=#showAbout") 185 public void onShowAbout(Event ev) { 186 Messagebox.show("CLARIN-D Federated Content Search Aggregator\n\nVersion 0.0.1", "FCS", 0, Messagebox.INFORMATION); 187 188 } 189 190 @Listen("onClick=#exportResultsCSV") 191 public void onExportResultsCSV(Event ev) { 192 searchResultsController.exportCSV(); 193 } 194 195 @Listen("onClick=#exportResultsTCF") 196 public void onExportResultsTCF(Event ev) { 197 searchResultsController.exportTCF(); 198 } 199 200 @Listen("onClick=#exportResultsPWTCF") 201 public void onExportResultsPWTCF(Event ev) { 202 wspaceSigninpop.open(resultsBox, "top_center"); 203 } 204 205 @Listen("onClick=#wspaceSigninBtn") 206 public void onSignInExportResultsPWTCF(Event ev) { 207 String user = wspaceUserName.getValue(); 208 String pswd = wspaceUserPwd.getValue(); 209 if (user.isEmpty() || pswd.isEmpty()) { 210 Messagebox.show("Need user name and password!"); 211 } else { 212 wspaceUserPwd.setValue(""); 213 wspaceSigninpop.close(); 214 searchResultsController.exportPWTCF(user, pswd); 116 corpusRenderer.updateItem(openItem, false); 215 117 } 216 118 } 217 119 218 @Listen("onOK=#wspaceUserPwd") 219 public void onSignInExportResultsPWTCFPwdOK(Event ev) { 220 onSignInExportResultsPWTCF(ev); 120 public int getMaxRecords() { 121 return Integer.parseInt(maximumRecordsSelect.getValue()); 122 } 123 124 public Map<String,Set<Corpus2>> getSelectedCorpora() { 125 return corpusRenderer.getSelectedCorpora(); 126 } 127 128 129 130 // private void processParameters() { 131 // 132 // String[] paramValue; 133 // String contextJson = null; 134 // 135 // String[] paramsReceived = new String[4]; 136 // 137 // paramValue = Executions.getCurrent().getParameterMap().get("query"); 138 // if (paramValue != null) { 139 // searchString.setValue(paramValue[0].trim()); 140 // paramsReceived[0] = searchString.getValue(); 141 // } 142 // paramValue = Executions.getCurrent().getParameterMap().get("operation"); 143 // if (paramValue != null) { 144 // String operationString = paramValue[0].trim(); 145 // paramsReceived[1] = operationString; 146 // if (!operationString.equals("searchRetrieve")) { 147 // Messagebox.show("Not supported operation " + operationString, "FCS", 0, Messagebox.INFORMATION); 148 // } 149 // } 150 // paramValue = Executions.getCurrent().getParameterMap().get("version"); 151 // if (paramValue != null) { 152 // String versionString = paramValue[0].trim(); 153 // paramsReceived[2] = versionString; 154 // if (versionString.equals("1.2")) { 155 // version = SRUVersion.VERSION_1_2; 156 // } else if (versionString.equals("1.1")) { 157 // version = SRUVersion.VERSION_1_1; 158 // } else { 159 // Messagebox.show("SRU Version " + version + " not supported", "FCS", 0, Messagebox.INFORMATION); 160 // } 161 // } 162 // paramValue = Executions.getCurrent().getParameterMap().get("x-aggregation-context"); 163 // if (paramValue != null) { 164 // contextJson = paramValue[0].trim(); 165 // paramsReceived[3] = contextJson; 166 // } 167 // logger.log(Level.INFO, "Received parameters: query[{0}], operation[{1}], version[{2}], x-aggregation-context[{3}], ", paramsReceived); 168 // 169 // paramValue = Executions.getCurrent().getParameterMap().get("mode"); 170 // if (paramValue != null) { 171 // String mode = paramValue[0].trim(); 172 // if (mode.equals("testing")) { 173 // testingMode = true; 174 // } 175 // } 176 // 177 // if (contextJson != null) { 178 // Gson gson = new Gson(); 179 // Type mapType = new TypeToken<LinkedHashMap<String, ArrayList<String>>>() { 180 // }.getType(); 181 // try { 182 // this.xAggregationContext = gson.fromJson(contextJson, mapType); 183 // } catch (Exception ex) { 184 // logger.log(Level.SEVERE, "Error parsing JSON from x-aggregation-context: {0} {1}", new String[]{ex.getMessage(), contextJson}); 185 // Messagebox.show("Error in x-aggregation-context parameter", "FCS", 0, Messagebox.INFORMATION); 186 // } 187 // } 188 // 189 // } 190 191 private void loadLanguages() { 192 for (String code : this.languages.getCodes()) { 193 Comboitem item = this.languageSelect.appendItem(this.languages.nameForCode(code)); 194 item.setValue(code); 195 } 221 196 } 222 197 223 @Listen("onClick=#wspaceCancelBtn")224 public void onSignInPWCancel(Event ev) {225 wspaceUserPwd.setValue("");226 wspaceSigninpop.close();227 }228 229 230 @Listen("onClick=#addForeignEndpoint")231 public void onAddForeignEndpoint(Event ev) {232 registry.addForeignPoint(foreignEndpointSelect.getValue().split(";")[1], foreignEndpointSelect.getValue().split(";")[0]);233 }234 235 private void processParameters() {236 237 String[] paramValue;238 String contextJson = null;239 240 String[] paramsReceived = new String[4];241 242 paramValue = Executions.getCurrent().getParameterMap().get("query");243 if (paramValue != null) {244 searchString.setValue(paramValue[0].trim());245 paramsReceived[0] = searchString.getValue();246 }247 paramValue = Executions.getCurrent().getParameterMap().get("operation");248 if (paramValue != null) {249 String operationString = paramValue[0].trim();250 paramsReceived[1] = operationString;251 if (!operationString.equals("searchRetrieve")) {252 Messagebox.show("Not supported operation " + operationString, "FCS", 0, Messagebox.INFORMATION);253 }254 }255 paramValue = Executions.getCurrent().getParameterMap().get("version");256 if (paramValue != null) {257 String versionString = paramValue[0].trim();258 paramsReceived[2] = versionString;259 if (versionString.equals("1.2")) {260 version = SRUVersion.VERSION_1_2;261 } else if (versionString.equals("1.1")) {262 version = SRUVersion.VERSION_1_1;263 } else {264 Messagebox.show("SRU Version " + version + " not supported", "FCS", 0, Messagebox.INFORMATION);265 }266 }267 paramValue = Executions.getCurrent().getParameterMap().get("x-aggregation-context");268 if (paramValue != null) {269 contextJson = paramValue[0].trim();270 paramsReceived[3] = contextJson;271 }272 logger.log(Level.INFO, "Received parameters: query[{0}], operation[{1}], version[{2}], x-aggregation-context[{3}], ", paramsReceived);273 274 paramValue = Executions.getCurrent().getParameterMap().get("mode");275 if (paramValue != null) {276 String mode = paramValue[0].trim();277 if (mode.equals("testing")) {278 testingMode = true;279 }280 }281 282 if (contextJson != null) {283 Gson gson = new Gson();284 Type mapType = new TypeToken<LinkedHashMap<String, ArrayList<String>>>() {285 }.getType();286 try {287 this.xAggregationContext = gson.fromJson(contextJson, mapType);288 } catch (Exception ex) {289 logger.log(Level.SEVERE, "Error parsing JSON from x-aggregation-context: {0} {1}", new String[]{ex.getMessage(), contextJson});290 Messagebox.show("Error in x-aggregation-context parameter", "FCS", 0, Messagebox.INFORMATION);291 }292 }293 294 }295 296 private void tempMap() {297 ClientConfig config = new DefaultClientConfig();298 Client client = Client.create(config);299 mapGenerator = client.resource(MAPS_SERVICE_URL);300 TextCorpusStored tc = new TextCorpusStored("en");301 Token t1 = tc.createTokensLayer().addToken("Virginia");302 List<Token> s1 = new ArrayList<Token>();303 s1.add(t1);304 tc.createSentencesLayer().addSentence(s1);305 tc.createGeoLayer("unknown", GeoLongLatFormat.DegDec);306 //tc.getGeoLayer().addPoint("138.56027", "-34.6663", 15.0, null, null, null, t1);307 WLData data = new WLData(tc);308 309 Iframe resultsPic = (Iframe) resultsBox.getFellow("resultsPic");310 311 try {312 String output = mapGenerator.path("3").accept(MediaType.TEXT_HTML).type("text/tcf+xml").post(String.class, data);313 Media media = new AMedia("map-" + 4 + ".html", null, "text/html", output);314 resultsPic.setContent(media);315 } catch (Exception e) {316 Logger.getLogger(Aggregator.class.getName()).log(Level.SEVERE, "ERROR accessing the maps generator service", e);317 Messagebox.show("ERROR accessing the maps generator service \n" + e.getMessage(), "FCS", 0, Messagebox.INFORMATION);318 }319 }320 198 } -
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/app/SearchResults.java
r2738 r2926 6 6 import eu.clarin.sru.client.SRUVersion; 7 7 import eu.clarin.sru.fcs.aggregator.data.CenterRegistry; 8 import eu.clarin.sru.fcs.aggregator.sparam.CorpusTreeModel;9 import eu.clarin.sru.fcs.aggregator.sparam.CorpusTreeNodeRenderer;10 import eu.clarin.sru.fcs.aggregator.sresult.SearchResultsController;11 8 import java.lang.reflect.Type; 12 9 import java.util.ArrayList; … … 41 38 import com.sun.jersey.api.client.config.ClientConfig; 42 39 import com.sun.jersey.api.client.config.DefaultClientConfig; 40 import eu.clarin.sru.client.SRUClientException; 41 import eu.clarin.sru.client.SRURecord; 42 import eu.clarin.sru.client.SRUSearchRetrieveRequest; 43 import eu.clarin.sru.client.SRUSearchRetrieveResponse; 44 import eu.clarin.sru.client.SRUThreadedClient; 45 import eu.clarin.sru.client.fcs.ClarinFCSRecordData; 46 import eu.clarin.sru.fcs.aggregator.sparam2.SearchResult2; 47 import eu.clarin.sru.fcs.aggregator.sparam2.Corpus2; 48 import eu.clarin.sru.fcs.aggregator.sparam2.Corpus2Renderer; 49 import eu.clarin.sru.fcs.aggregator.sparam2.CorpusTreeModel2; 50 import eu.clarin.sru.fcs.aggregator.sparam2.Languages; 51 import eu.clarin.sru.fcs.aggregator.sparam2.SearchResult2; 52 import eu.clarin.sru.fcs.aggregator.sparam2.SearchResultRecordRenderer2; 53 import eu.clarin.sru.fcs.aggregator.sresult.SearchResultRecordRenderer; 54 import eu.clarin.sru.fcs.aggregator.sresult.SearchResultsController; 55 import eu.clarin.sru.fcs.aggregator.util.SRUCQLsearchRetrieve; 43 56 import eu.clarin.weblicht.wlfxb.tc.api.GeoLongLatFormat; 44 57 import eu.clarin.weblicht.wlfxb.tc.api.Token; 45 58 import eu.clarin.weblicht.wlfxb.tc.xb.TextCorpusStored; 46 59 import eu.clarin.weblicht.wlfxb.xb.WLData; 60 import java.util.concurrent.Future; 47 61 import javax.ws.rs.core.MediaType; 62 import org.zkoss.zk.ui.event.EventListener; 63 import org.zkoss.zul.Borderlayout; 64 import org.zkoss.zul.Column; 65 import org.zkoss.zul.Columns; 66 import org.zkoss.zul.DefaultTreeNode; 67 import org.zkoss.zul.Div; 68 import org.zkoss.zul.Grid; 69 import org.zkoss.zul.ListModel; 48 70 import org.zkoss.zul.Popup; 71 import org.zkoss.zul.Progressmeter; 72 import org.zkoss.zul.SimpleListModel; 49 73 50 74 /** 51 * Main window of the Aggregator application.52 75 * 53 76 * @author Yana Panchenko 54 77 */ 55 public class Aggregatorextends SelectorComposer<Component> {78 public class SearchResults extends SelectorComposer<Component> { 56 79 57 80 private static final Logger logger = Logger.getLogger(Aggregator.class.getName()); … … 98 121 private Map<String, List<String>> xAggregationContext; 99 122 private SRUVersion version = SRUVersion.VERSION_1_2; 100 private SearchResultsController searchResultsController;101 123 private CenterRegistry registry; 102 124 private boolean testingMode = false; 125 126 private SRUThreadedClient searchClient; 127 128 private List<SearchResult2> resultsUnprocessed; 129 private List<SearchResult2> resultsProcessed; 130 private UpdateResultsThread resultsThread; 131 private int currentRequestId = 0; 132 133 134 private Progressmeter progress; 135 136 103 137 104 138 @Override … … 106 140 107 141 super.doAfterCompose(comp); 108 109 processParameters(); 110 111 languageSelect.setSelectedItem(anyLanguage); 112 113 searchResultsController = new SearchResultsController(resultsBox, searchResultsProgress); 114 // assign the search controller to desktop, so that it can be accessed to be shutdown when the desktop is destroyed 115 Executions.getCurrent().getDesktop().setAttribute(searchResultsController.getClass().getSimpleName(), searchResultsController); 116 // also add it to the list of actice controllers of the web application, so that they can be shutdown when the application stops 117 Set<SearchResultsController> activeControllers = (Set<SearchResultsController>) Executions.getCurrent().getDesktop().getWebApp().getAttribute(WebAppListener.ACTIVE_SEARCH_CONTROLLERS); 118 activeControllers.add(searchResultsController); 119 120 registry = new CenterRegistry(); 121 registry.loadChildren(testingMode); 122 CorpusTreeModel corporaModel = new CorpusTreeModel(registry); 123 tree.setModel(corporaModel); 124 tree.setItemRenderer(new CorpusTreeNodeRenderer()); 125 tree.setMultiple(true); 142 143 Executions.getCurrent().getDesktop().enableServerPush(true); 144 searchClient = (SRUThreadedClient) Executions.getCurrent().getDesktop().getWebApp().getAttribute(WebAppListener.SHARED_SRU_CLIENT); 145 146 147 // processParameters(); 148 // 149 // languageSelect.setSelectedItem(anyLanguage); 150 // 151 // searchResultsController = new SearchResultsController(resultsBox, searchResultsProgress); 152 // // assign the search controller to desktop, so that it can be accessed to be shutdown when the desktop is destroyed 153 // Executions.getCurrent().getDesktop().setAttribute(searchResultsController.getClass().getSimpleName(), searchResultsController); 154 // // also add it to the list of actice controllers of the web application, so that they can be shutdown when the application stops 155 // Set<SearchResultsController> activeControllers = (Set<SearchResultsController>) Executions.getCurrent().getDesktop().getWebApp().getAttribute(WebAppListener.ACTIVE_SEARCH_CONTROLLERS); 156 // activeControllers.add(searchResultsController); 157 // 158 // registry = new CenterRegistry(); 159 // registry.loadChildren(testingMode); 160 // CorpusTreeModel corporaModel = new CorpusTreeModel(registry); 161 // tree.setModel(corporaModel); 162 // tree.setItemRenderer(new CorpusTreeNodeRenderer()); 163 // tree.setMultiple(true); 126 164 127 165 128 166 //tempMap(); 129 167 168 130 169 } 131 170 … … 135 174 } 136 175 137 @Listen(ZulEvents.ON_AFTER_RENDER + "=#tree") 138 public void onAfterRenderCorporaTree(Event ev) { 139 CorpusTreeNodeRenderer.selectEndpoints(this.tree, this.xAggregationContext); 140 } 141 142 @Listen("onClick = #selectAll") 143 public void onSelectAll(Event ev) { 144 Treechildren openTreeItems = tree.getTreechildren(); 145 for (Treeitem openItem : openTreeItems.getItems()) { 146 CorpusTreeNodeRenderer.selectItem(openItem); 147 } 148 } 149 150 @Listen("onClick = #deselectAll") 151 public void onDeselectAll(Event ev) { 152 Treechildren openTreeItems = tree.getTreechildren(); 153 for (Treeitem openItem : openTreeItems.getItems()) { 154 CorpusTreeNodeRenderer.unselectItem(openItem); 155 } 156 } 157 158 @Listen("onClick = #searchButton") 159 public void onExecuteSearch(Event ev) { 160 int maxRecords = Integer.parseInt(maximumRecordsSelect.getValue()); 161 searchResultsController.executeSearch(tree.getSelectedItems(), maxRecords, searchString.getText(), version); 162 } 163 164 @Listen("onOK = #searchString") 165 public void onEnterSearchString(Event ev) { 166 onExecuteSearch(ev); 167 } 176 // @Listen(ZulEvents.ON_AFTER_RENDER + "=#tree") 177 // public void onAfterRenderCorporaTree(Event ev) { 178 // Corpus2Renderer.selectEndpoints(this.tree, this.xAggregationContext); 179 // } 180 // 181 // @Listen("onClick = #selectAll") 182 // public void onSelectAll(Event ev) { 183 // Treechildren openTreeItems = tree.getTreechildren(); 184 // for (Treeitem openItem : openTreeItems.getItems()) { 185 // Corpus2Renderer.selectItem(openItem); 186 // } 187 // } 188 // 189 // @Listen("onClick = #deselectAll") 190 // public void onDeselectAll(Event ev) { 191 // Treechildren openTreeItems = tree.getTreechildren(); 192 // for (Treeitem openItem : openTreeItems.getItems()) { 193 // Corpus2Renderer.unselectItem(openItem); 194 // } 195 // } 168 196 169 197 @Listen("onClick=#clearResults") … … 172 200 } 173 201 174 @Listen("onClick=#showHelp") 175 public void onShowHelp(Event ev) { 176 resultsBox.getChildren().clear(); 177 Iframe help = new Iframe(); 178 help.setWidth("100%"); 179 help.setHeight("100%"); 180 help.setSrc("help.html"); 181 resultsBox.appendChild(help); 182 } 183 184 @Listen("onClick=#showAbout") 185 public void onShowAbout(Event ev) { 186 Messagebox.show("CLARIN-D Federated Content Search Aggregator\n\nVersion 0.0.1", "FCS", 0, Messagebox.INFORMATION); 187 188 } 189 190 @Listen("onClick=#exportResultsCSV") 191 public void onExportResultsCSV(Event ev) { 192 searchResultsController.exportCSV(); 193 } 194 195 @Listen("onClick=#exportResultsTCF") 196 public void onExportResultsTCF(Event ev) { 197 searchResultsController.exportTCF(); 198 } 199 200 @Listen("onClick=#exportResultsPWTCF") 201 public void onExportResultsPWTCF(Event ev) { 202 wspaceSigninpop.open(resultsBox, "top_center"); 203 } 204 205 @Listen("onClick=#wspaceSigninBtn") 206 public void onSignInExportResultsPWTCF(Event ev) { 207 String user = wspaceUserName.getValue(); 208 String pswd = wspaceUserPwd.getValue(); 209 if (user.isEmpty() || pswd.isEmpty()) { 210 Messagebox.show("Need user name and password!"); 211 } else { 212 wspaceUserPwd.setValue(""); 213 wspaceSigninpop.close(); 214 searchResultsController.exportPWTCF(user, pswd); 215 } 216 } 217 218 @Listen("onOK=#wspaceUserPwd") 219 public void onSignInExportResultsPWTCFPwdOK(Event ev) { 220 onSignInExportResultsPWTCF(ev); 221 } 222 223 @Listen("onClick=#wspaceCancelBtn") 224 public void onSignInPWCancel(Event ev) { 225 wspaceUserPwd.setValue(""); 226 wspaceSigninpop.close(); 227 } 228 229 230 @Listen("onClick=#addForeignEndpoint") 231 public void onAddForeignEndpoint(Event ev) { 232 registry.addForeignPoint(foreignEndpointSelect.getValue().split(";")[1], foreignEndpointSelect.getValue().split(";")[0]); 233 } 202 // @Listen("onClick=#exportResultsCSV") 203 // public void onExportResultsCSV(Event ev) { 204 // searchResultsController.exportCSV(); 205 // } 206 // 207 // @Listen("onClick=#exportResultsTCF") 208 // public void onExportResultsTCF(Event ev) { 209 // searchResultsController.exportTCF(); 210 // } 211 // 212 // @Listen("onClick=#exportResultsPWTCF") 213 // public void onExportResultsPWTCF(Event ev) { 214 // wspaceSigninpop.open(resultsBox, "top_center"); 215 // } 216 // 217 // @Listen("onClick=#wspaceSigninBtn") 218 // public void onSignInExportResultsPWTCF(Event ev) { 219 // String user = wspaceUserName.getValue(); 220 // String pswd = wspaceUserPwd.getValue(); 221 // if (user.isEmpty() || pswd.isEmpty()) { 222 // Messagebox.show("Need user name and password!"); 223 // } else { 224 // wspaceUserPwd.setValue(""); 225 // wspaceSigninpop.close(); 226 // searchResultsController.exportPWTCF(user, pswd); 227 // } 228 // } 229 // 230 // @Listen("onOK=#wspaceUserPwd") 231 // public void onSignInExportResultsPWTCFPwdOK(Event ev) { 232 // onSignInExportResultsPWTCF(ev); 233 // } 234 // 235 // @Listen("onClick=#wspaceCancelBtn") 236 // public void onSignInPWCancel(Event ev) { 237 // wspaceUserPwd.setValue(""); 238 // wspaceSigninpop.close(); 239 // } 240 234 241 235 242 private void processParameters() { … … 294 301 } 295 302 296 private void tempMap() { 297 ClientConfig config = new DefaultClientConfig(); 298 Client client = Client.create(config); 299 mapGenerator = client.resource(MAPS_SERVICE_URL); 300 TextCorpusStored tc = new TextCorpusStored("en"); 301 Token t1 = tc.createTokensLayer().addToken("Virginia"); 302 List<Token> s1 = new ArrayList<Token>(); 303 s1.add(t1); 304 tc.createSentencesLayer().addSentence(s1); 305 tc.createGeoLayer("unknown", GeoLongLatFormat.DegDec); 306 //tc.getGeoLayer().addPoint("138.56027", "-34.6663", 15.0, null, null, null, t1); 307 WLData data = new WLData(tc); 308 309 Iframe resultsPic = (Iframe) resultsBox.getFellow("resultsPic"); 310 303 304 void executeSearch(Map<String, Set<Corpus2>> selectedCorpora, int maxRecords, String searchString, Progressmeter pMeter) { 305 306 this.progress = pMeter; 307 this.progress.setValue(0); 308 this.progress.setVisible(true); 309 310 // terminate previous search requests and corresponding response processing 311 terminateProcessingRequestsAndResponses(); 312 313 // update current search request id 314 currentRequestId++; 315 316 // clear are where results are to be displayed 317 resultsBox.getChildren().clear(); 318 319 // empty storage for unprocessed processed lists with recordsData 320 resultsProcessed = new ArrayList<SearchResult2>(); 321 resultsUnprocessed = new ArrayList<SearchResult2>(); 322 323 // finally, send search requests to all the selected by user 324 // endpoints/corpora and process the responses 325 for (String endpointUrl : selectedCorpora.keySet()) { 326 for (Corpus2 corpus : selectedCorpora.get(endpointUrl)) { 327 resultsUnprocessed.add(executeSearch(corpus, maxRecords, searchString)); 328 } 329 } 330 331 processResponses(); 332 333 } 334 335 private SearchResult2 executeSearch(Corpus2 corpus, int maxRecords, String searchString) { 336 SearchResult2 resultsItem = new SearchResult2(corpus); 337 logger.log(Level.FINE, "Executing search for {0} query={1} maxRecords={2}", 338 new Object[]{corpus.toString(), searchString, maxRecords}); 339 SRUSearchRetrieveRequest searchRequest = new SRUSearchRetrieveRequest(corpus.getEndpointUrl()); 340 searchRequest.setVersion(version); 341 searchRequest.setMaximumRecords(maxRecords); 342 searchRequest.setRecordSchema(ClarinFCSRecordData.RECORD_SCHEMA); 343 searchString = searchString.replace(" ", "%20"); 344 searchRequest.setQuery("%22" + searchString + "%22"); 345 if (resultsItem.hasCorpusHandler()) { 346 searchRequest.setExtraRequestData(SRUCQLsearchRetrieve.CORPUS_HANDLE_PARAMETER, resultsItem.getCorpus().getHandle()); 347 } 311 348 try { 312 String output = mapGenerator.path("3").accept(MediaType.TEXT_HTML).type("text/tcf+xml").post(String.class, data); 313 Media media = new AMedia("map-" + 4 + ".html", null, "text/html", output); 314 resultsPic.setContent(media); 315 } catch (Exception e) { 316 Logger.getLogger(Aggregator.class.getName()).log(Level.SEVERE, "ERROR accessing the maps generator service", e); 317 Messagebox.show("ERROR accessing the maps generator service \n" + e.getMessage(), "FCS", 0, Messagebox.INFORMATION); 318 } 349 Future<SRUSearchRetrieveResponse> futureResponse = searchClient.searchRetrieve(searchRequest); 350 resultsItem.setFutureResponse(futureResponse); 351 } catch (SRUClientException ex) { 352 logger.log(Level.SEVERE, "SearchRetrieve failed for {0} {1} {2}", 353 new String[]{corpus.getEndpointUrl(), ex.getClass().getName(), ex.getMessage()}); 354 } 355 return resultsItem; 356 } 357 358 public void shutdown() { 359 terminateProcessingRequestsAndResponses(); 360 } 361 362 private void terminateProcessingRequestsAndResponses() { 363 364 if (resultsThread != null) { 365 resultsThread.interrupt(); 366 try { 367 resultsThread.join(); 368 } catch (InterruptedException ex) { 369 Logger.getLogger(SearchResults.class.getName()).log(Level.SEVERE, null, ex); 370 } 371 } 372 373 Logger.getLogger(SearchResults.class.getName()).log(Level.INFO, "Search terminated"); 374 } 375 376 private void processResponses() { 377 resultsThread = new SearchResults.UpdateResultsThread(); 378 resultsThread.start(); 379 } 380 381 382 private class UpdateResultsThread extends Thread { 383 384 @Override 385 public void run() { 386 while (!resultsUnprocessed.isEmpty() && !Thread.currentThread().isInterrupted()) { 387 388 SearchResult2 resultsItem = resultsUnprocessed.remove(0); 389 if (!resultsItem.isWaitingForResponse()) { 390 resultsItem.consumeResponse(); 391 Executions.schedule(resultsBox.getDesktop(), new SearchResults.ResponseListener(resultsItem, currentRequestId), new Event("onDummy")); 392 // this alternative to Executions.schedule() - sinchronious update - 393 // doesn't work: if interrupted here (exception thrown), then 394 // the current thread seems to already get controll of the desktop, 395 // but never gets it back and desktop (page) hangs.... 396 ////Obtain the control of UI 397 //Executions.activate(resultsArea.getDesktop()); 398 //try { 399 // updateResultsArea(); 400 //} finally { 401 // //SDeactivate to return the control of UI back 402 // Executions.deactivate(resultsArea.getDesktop()); 403 //} 404 resultsProcessed.add(resultsItem); 405 //System.out.println("RECORDS ITEM ADDED"); 406 407 } else { 408 resultsUnprocessed.add(resultsItem); 409 } 410 } 411 412 if (Thread.currentThread().isInterrupted()) { 413 for (SearchResult2 resultsItem : resultsUnprocessed) { 414 resultsItem.cancelWaitingForResponse(); 415 } 416 } 417 418 } 419 } 420 421 private class ResponseListener implements EventListener { 422 423 int requestId; 424 SearchResult2 resultsItem; 425 426 public ResponseListener(SearchResult2 resultsItem, int requestId) { 427 this.resultsItem = resultsItem; 428 this.requestId = requestId; 429 } 430 431 @Override 432 public void onEvent(Event event) { 433 434 // create groupbox with search results item 435 Groupbox groupbox = createRecordsGroup(resultsItem); 436 437 // appand this search result only if it 438 // is a result of the current request 439 if (requestId == currentRequestId) { 440 resultsBox.appendChild(groupbox); 441 } 442 443 // if in the meanwhile there was a new request 444 // this search result is outdated, detach it: 445 if (requestId != currentRequestId) { 446 groupbox.detach(); 447 } 448 449 if (resultsUnprocessed.isEmpty()) { 450 progress.setValue(0); 451 progress.setVisible(false); 452 } else { 453 progress.setValue(100 * resultsProcessed.size() / (resultsUnprocessed.size() + resultsProcessed.size() + 1)); 454 } 455 456 } 457 } 458 459 private Groupbox createRecordsGroup(SearchResult2 resultsItem) { 460 461 Groupbox recordsGroup = new Groupbox(); 462 463 // style the box 464 recordsGroup.setMold("3d"); 465 recordsGroup.setSclass("ccsLightBlue"); 466 recordsGroup.setContentStyle("border:0;"); 467 recordsGroup.setStyle("margin:10px;10px;10px;10px;"); 468 recordsGroup.setClosable(true); 469 //recordsGroup.setOpen(false); 470 471 // create title 472 StringBuilder sb = new StringBuilder(); 473 sb.append(resultsItem.getCorpus().getInstitution().getName()); 474 sb.append(" "); 475 sb.append(resultsItem.getCorpus().getEndpointUrl()); 476 if (resultsItem.hasCorpusHandler()) { 477 if (resultsItem.getCorpus().getDisplayName() != null) { 478 sb.append(" "); 479 sb.append(resultsItem.getCorpus().getDisplayName()); 480 } 481 if (sb.append(resultsItem.getCorpus().getHandle()) != null) { 482 sb.append(" "); 483 sb.append(resultsItem.getCorpus().getHandle()); 484 } 485 } 486 recordsGroup.setTitle(sb.toString()); 487 488 // populate it with records grid or failure message 489 if (resultsItem.getResponse() == null) { // there was an error in response 490 recordsGroup.appendChild(new Label("Sorry, the search failed!")); 491 } else if (resultsItem.getResponse().hasRecords()) { // the response was fine and there >=1 records 492 Grid grid = new Grid(); 493 // grid.setWidth("100%"); 494 // grid.setMold("paging"); 495 // grid.setPageSize(10); 496 Columns columns = new Columns(); 497 Column c; 498 c = new Column(); 499 //c.setLabel("Left"); 500 columns.appendChild(c); 501 //c.setHflex("2"); 502 c = new Column(); 503 //c.setLabel("Hit"); 504 c.setHflex("min"); 505 //c.setHflex("1"); 506 columns.appendChild(c); 507 c = new Column(); 508 //c.setHflex("2"); 509 //c.setLabel("Right"); 510 columns.appendChild(c); 511 grid.appendChild(columns); 512 513 List<SRURecord> sruRecords = resultsItem.getResponse().getRecords(); 514 ListModel lmodel = new SimpleListModel(sruRecords); 515 grid.setModel(lmodel); 516 grid.setRowRenderer(new SearchResultRecordRenderer2(resultsItem)); 517 recordsGroup.appendChild(grid); 518 } else { // the response was fine, but there are no records 519 recordsGroup.appendChild(new Label("Sorry, there were no results!")); 520 } 521 522 return recordsGroup; 319 523 } 320 524 } -
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/app/WebAppListener.java
r2527 r2926 4 4 import eu.clarin.sru.client.SRUThreadedClient; 5 5 import eu.clarin.sru.client.fcs.ClarinFCSRecordParser; 6 import eu.clarin.sru.fcs.aggregator.sparam2.Languages; 6 7 import eu.clarin.sru.fcs.aggregator.sresult.SearchResultsController; 7 8 import java.util.HashSet; … … 21 22 public static String ACTIVE_SEARCH_CONTROLLERS = "ACTIVE_SEARCH_CONTROLLERS"; 22 23 public static String SHARED_SRU_CLIENT = "SHARED_SRU_CLIENT"; 24 public static String LANGUAGES = "LANG"; 25 23 26 private static final Logger logger = Logger.getLogger(WebAppListener.class.getName()); 24 27 … … 41 44 logger.log(Level.SEVERE, "SRU Client Parser registration failed", e); 42 45 } 46 47 Languages languages = new Languages(); 48 webapp.setAttribute(LANGUAGES, languages); 43 49 } 44 50 -
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/sparam/CorpusTreeModel.java
r2820 r2926 6 6 package eu.clarin.sru.fcs.aggregator.sparam; 7 7 8 import eu.clarin.sru.fcs.aggregator.sparam.CorpusTreeNode; 8 9 import org.zkoss.zul.AbstractTreeModel; 9 10 import org.zkoss.zul.ext.TreeSelectableModel; -
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/sparam2/SearchResult2.java
r2820 r2926 3 3 * and open the template in the editor. 4 4 */ 5 package eu.clarin.sru.fcs.aggregator. data;5 package eu.clarin.sru.fcs.aggregator.sparam2; 6 6 7 7 import eu.clarin.sru.client.SRUSearchRetrieveResponse; … … 20 20 * @author Yana Panchenko 21 21 */ 22 public class SearchResult {22 public class SearchResult2 { 23 23 24 private Endpoint endpoint;25 private Corpus corpus;24 //private Endpoint endpoint; 25 private Corpus2 corpus; 26 26 private Future<SRUSearchRetrieveResponse> futureResponse; 27 27 private SRUSearchRetrieveResponse response; 28 28 private List<DataViewKWIC> dataKWIC = new ArrayList<DataViewKWIC>(); 29 29 30 private static final Logger logger = Logger.getLogger(SearchResult .class.getName());30 private static final Logger logger = Logger.getLogger(SearchResult2.class.getName()); 31 31 32 32 public List<DataViewKWIC> getDataKWIC() { … … 39 39 40 40 41 public SearchResult(Object nodeData) { 42 if (nodeData instanceof Endpoint) { 43 endpoint = (Endpoint) nodeData; 44 } else { 45 corpus = (Corpus) nodeData; 46 endpoint = corpus.getEndpoint(); 47 } 41 public SearchResult2(Corpus2 corpus) { 42 this.corpus = corpus; 48 43 } 49 44 50 public Endpoint getEndpoint() { 51 return endpoint; 52 } 53 54 public Corpus getCorpus() { 45 public Corpus2 getCorpus() { 55 46 return corpus; 56 47 } … … 69 60 70 61 public boolean hasCorpusHandler() { 71 if (corpus != null && corpus.get Value() != null) {62 if (corpus != null && corpus.getHandle() != null) { 72 63 return true; 73 64 } … … 97 88 } catch (Exception ex) { 98 89 logger.log(Level.SEVERE, "Error consuming response from {0} {1} {2} {3}", 99 new Object[]{ endpoint.getUrl(), corpus, ex.getClass().getName(), ex.getMessage()});90 new Object[]{corpus.getEndpointUrl(), corpus, ex.getClass().getName(), ex.getMessage()}); 100 91 } 101 92 } -
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/sparam2/SearchResultRecordRenderer2.java
r2527 r2926 1 package eu.clarin.sru.fcs.aggregator.s result;1 package eu.clarin.sru.fcs.aggregator.sparam2; 2 2 3 3 import eu.clarin.sru.client.SRURecord; … … 7 7 import eu.clarin.sru.client.fcs.DataViewKWIC; 8 8 import eu.clarin.sru.client.fcs.Resource; 9 import eu.clarin.sru.fcs.aggregator. data.SearchResult;9 import eu.clarin.sru.fcs.aggregator.sparam2.SearchResult2; 10 10 import java.util.ArrayList; 11 11 import java.util.List; … … 22 22 * @author Yana Panchenko 23 23 */ 24 public class SearchResultRecordRenderer implements RowRenderer {24 public class SearchResultRecordRenderer2 implements RowRenderer { 25 25 26 private SearchResult searchResult;26 private SearchResult2 searchResult; 27 27 28 private static final Logger logger = Logger.getLogger(SearchResultRecordRenderer .class.getName());28 private static final Logger logger = Logger.getLogger(SearchResultRecordRenderer2.class.getName()); 29 29 30 public SearchResultRecordRenderer (SearchResultsearchResult) {30 public SearchResultRecordRenderer2(SearchResult2 searchResult) { 31 31 this.searchResult = searchResult; 32 32 } -
SRUAggregator/trunk/src/main/java/eu/clarin/sru/fcs/aggregator/sresult/SearchResultsController.java
r2821 r2926 146 146 searchRequest.setMaximumRecords(maxRecords); 147 147 searchRequest.setRecordSchema(ClarinFCSRecordData.RECORD_SCHEMA); 148 searchRequest.setQuery(searchString); 148 searchString = searchString.replace(" ", "%20"); 149 searchRequest.setQuery("%22" + searchString + "%22"); 149 150 if (resultsItem.hasCorpusHandler()) { 150 151 searchRequest.setExtraRequestData(SRUCQLsearchRetrieve.CORPUS_HANDLE_PARAMETER, resultsItem.getCorpus().getValue()); -
SRUAggregator/trunk/src/main/webapp/about.zul
r2508 r2926 1 <!-- 2 To change this template, choose Tools | Templates 3 and open the template in the editor. 4 --> 5 <!DOCTYPE html> 6 <html> 7 <head> 8 <title></title> 9 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 10 </head> 11 <body> 12 <h3>Welcome to the CLARIN-D Federated Content Search!</h3> 13 </body> 14 </html> 1 <vlayout> 2 <div align="center"> 3 <image src="karte.png" width="400px"/> 4 </div> 5 <div align="center"> 6 <include src="about-fcs.html" width="600px" /> 7 </div> 8 </vlayout> -
SRUAggregator/trunk/src/main/webapp/clarind.css
r2502 r2926 65 65 word-wrap: break-word; 66 66 } 67 68 69 .internalLinkSelected { 70 color:#801418; 71 text-decoration:none; 72 cursor:pointer; 73 margin:15px; 74 font-size:larger; 75 } 76 77 .internalLink { 78 color:#0C4F66; 79 text-decoration:underline; 80 cursor:pointer; 81 margin:15px; 82 font-size:larger; 83 } -
SRUAggregator/trunk/src/main/webapp/help.html
r2450 r2926 10 10 </head> 11 11 <body> 12 <h3>Welcome to the CLARIN-D Federated Content Search!</h3> 12 <h3>Welcome to the CLARIN-D Federated Content Search</h3> 13 <p>CLARIN-D Federated Content Search makes European linguistic resources accessable via the common interface. 14 Currently, 9 centers in Germany and Netherland make more than 20 resources available to the lingustic researches, 15 and this number is growing.</p> 16 <p>To perform simple keyword search in all available resources, 17 go to the search field at the top of the page and click 'search' or press the 'Enter' button.</p> 18 <p>To select specific resources based on their name or language and to specify number of search results 19 to be returned, click on the 'Advanced search' link.</p> 20 <p>To save the search result, ...</p> 21 <p>Feedback....</p> 13 22 </body> 14 23 </html> -
SRUAggregator/trunk/src/main/webapp/help.zul
r2508 r2926 1 <!-- 2 To change this template, choose Tools | Templates 3 and open the template in the editor. 4 --> 5 <!DOCTYPE html> 6 <html> 7 <head> 8 <title></title> 9 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 10 </head> 11 <body> 12 <h3>Welcome to the CLARIN-D Federated Content Search!</h3> 13 </body> 14 </html> 1 <vlayout> 2 <div align="center"> 3 <include src="help-fcs.html" width="600px"/> 4 </div> 5 </vlayout> -
SRUAggregator/trunk/src/main/webapp/index-old.zul
r2738 r2926 7 7 <borderlayout sclass="complex-layout"> 8 8 <!-- Kopf --> 9 <north height="65px" style="border-width:0px 0px 1px 0px;"> 10 <image src="clarindLogo.png"/> 9 <north height="120px" style="border-width:0px 0px 1px 0px;"> 10 <!--<image src="clarindLogo.png"/>--> 11 12 <vlayout> 13 <div align="center"> 14 <image src="clarindLogo.png"/> 15 <hlayout > 16 <textbox id="searchString" value="Elefant" focus="true" 17 style="font-size:16px;margin:5px 0px 5px 10px;color:#0e4071;border: 1px solid #801418;width:468px;"/> 18 19 <button id="searchButton" label="Search" image="buttonSearch.png" 20 sclass="ccsDarkBlue" style="margin:5px 10px 5px 0px;"/> 21 </hlayout> 22 </div> 23 </vlayout> 11 24 </north> 12 25 13 26 <!-- Linke Sidebar --> 14 <west autoscroll="true" splittable="true" title=" " size=" 25%" border="0"27 <west autoscroll="true" splittable="true" title=" " size="40%" border="0" 15 28 collapsible="true"> 16 29 17 30 <borderlayout sclass="complex-layout"> 18 31 <north style="border-width:0px 0px 0px 0px;"> 32 <!-- 19 33 <hlayout 20 34 style="margin-top:20px;margin-bottom:10px;margin-left:auto;margin-right:auto;width:95%;-moz-border-radius:3px;-webkit-border-radius:3px;border-radius:3px;"> … … 25 39 sclass="ccsDarkBlue" style="margin:5px 10px 5px 0px;"/> 26 40 </hlayout> 41 --> 27 42 </north> 28 43 <center margins="0,0,0,0" autoscroll="true" border="0"> -
SRUAggregator/trunk/src/main/webapp/index.zul
r2738 r2926 6 6 7 7 <borderlayout sclass="complex-layout"> 8 <!-- Kopf --> 9 <north height="65px" style="border-width:0px 0px 1px 0px;"> 10 <image src="clarindLogo.png"/> 8 9 <north height="160px" style="border-width:0px 0px 0px 0px;"> 10 <!--<image src="clarindLogo.png"/>--> 11 12 <vlayout> 13 <div align="center"> 14 <image src="clarindLogo.png"/> 15 <hlayout > 16 <textbox id="searchString" value="Elefant" focus="true" 17 style="font-size:16px;margin:5px 0px 5px 10px;color:#0e4071;border: 1px solid #801418;width:468px;"/> 18 19 <button id="searchButton" label="Search" image="buttonSearch.png" 20 sclass="ccsDarkBlue" style="margin:5px 10px 5px 0px;"/> 21 </hlayout> 22 <hlayout> 23 <label id="aboutLabel" sclass="internalLinkSelected">About</label> 24 <label id="soLabel" sclass="internalLink">Search options</label> 25 <label id="srLabel" sclass="internalLink">Search results</label> 26 <label id="helpLabel" sclass="internalLink">Help</label> 27 </hlayout> 28 <separator height="20px"></separator> 29 <progressmeter visible="false" id="pMeter" value="0" width="300px" /> 30 </div> 31 </vlayout> 11 32 </north> 12 33 13 <!-- Linke Sidebar -->14 <west autoscroll="true" splittable="true" title=" " size="25%" border="0"15 collapsible="true">16 17 <borderlayout sclass="complex-layout">18 <north style="border-width:0px 0px 0px 0px;">19 <hlayout20 style="margin-top:20px;margin-bottom:10px;margin-left:auto;margin-right:auto;width:95%;-moz-border-radius:3px;-webkit-border-radius:3px;border-radius:3px;">21 <textbox hflex="1" id="searchString" value="Elefant" focus="true"22 style="font-size:16px;margin:5px 0px 5px 10px;color:#0e4071;border: 1px solid #801418;"/>23 24 <button id="searchButton" label="Search" image="buttonSearch.png"25 sclass="ccsDarkBlue" style="margin:5px 10px 5px 0px;"/>26 </hlayout>27 </north>28 <center margins="0,0,0,0" autoscroll="true" border="0">29 <panel>30 <panelchildren31 style="margin-top:10px;margin-left:10px;margin-right:10px;border:0;overflow:auto;">32 33 <groupbox mold="3d" id="allCorpora" sclass="ccsLightBlue"34 contentStyle="border:0" title="Corpora">35 <!--<caption label="Corpora" style="border:0;"/>-->36 37 <div style="text-align:right;">38 <button id="selectAll" label="Select All"39 image="buttonSelectAll.png" sclass="ccsDarkBlue"/>40 <button id="deselectAll" label="Deselect All"41 image="buttonDeselectAll.png" sclass="ccsDarkBlue"/>42 </div>43 44 <tree id="tree" style="margin-top:2px;"> </tree>45 </groupbox>46 47 <separator/>48 <separator/>49 50 <groupbox mold="3d" id="nHits" sclass="ccsLightBlue"51 contentStyle="border:0" open="false">52 <caption label="Maximum hits" style="border:0;"/>53 <combobox id="maximumRecordsSelect" width="100%" value="10"54 style="margin-top:7px;margin-bottom:7px;">55 <comboitem label="10" id="maximumHits10"/>56 <comboitem label="20" id="maximumHits20"/>57 <comboitem label="30" id="maximumHits30"/>58 </combobox>59 </groupbox>60 61 <separator/>62 <separator/>63 64 <groupbox mold="3d" id="sLang" sclass="ccsLightBlue"65 contentStyle="border:0" open="false">66 <caption label="Language" style="border:0;"/>67 <div style="margin-top:7px;margin-bottom:7px;">68 <combobox id="languageSelect" width="100%">69 <comboitem label="Any Language" id="anyLanguage"/>70 <comboitem label="German" id="german"/>71 <comboitem label="English" id="english"/>72 <comboitem label="Dutch" id="dutch"/>73 <comboitem label="-More to come-"/>74 </combobox>75 <div style="margin-top:2px;text-align:right;">76 <button id="addLangButton" label="Add"77 image="buttonSelectAll.png" sclass="ccsDarkBlue"/>78 <button id="removeLangButton" label="Remove"79 image="buttonDeselectAll.png" sclass="ccsDarkBlue"/>80 </div>81 </div>82 </groupbox>83 84 <separator/>85 <separator/>86 87 <groupbox mold="3d" id="sTiers" sclass="ccsLightBlue"88 contentStyle="border:0" open="false">89 <caption label="Tier types" style="border:0;"/>90 <div style="margin-top:7px;margin-bottom:7px;">91 <combobox id="tiersSelect" width="100%" value="words">92 <comboitem label="full text"/>93 <comboitem label="words"/>94 </combobox>95 <div style="margin-top:2px;text-align:right;">96 <button id="addTierButton" label="Add"97 image="buttonSelectAll.png" sclass="ccsDarkBlue"/>98 <button id="removeTierButton" label="Remove"99 image="buttonDeselectAll.png" sclass="ccsDarkBlue"/>100 </div>101 </div>102 </groupbox>103 104 105 <!--106 <separator/>107 <separator/>108 109 <groupbox mold="3d" id="gbForeignEndpoints" sclass="ccsLightBlue"110 contentStyle="border:0" open="false">111 <caption label="Foreign Endpoints" style="border:0;"/>112 <div style="margin-top:7px;margin-bottom:7px;">113 <combobox id="foreignEndpointSelect" width="100%"114 value="Select an endpoint">115 <comboitem116 label="Mimore;http://www.meertens.knaw.nl/mimore/srucql/"/>117 <comboitem118 label="INL;http://gysseling.corpus.taalbanknederlands.inl.nl/cqlwebapp/cql"/>119 <comboitem label="DANS;http://srucql.dans.knaw.nl"/>120 <comboitem121 label="ICLTT;http://corpus3.aac.ac.at/ddconsru"/>122 <comboitem label="UPF;http://gilmere.upf.edu/pais_sru"/>123 </combobox>124 <div style="margin-top:2px;">125 <button id="addFepButton" label="Add"126 image="buttonSelectAll.png" sclass="ccsDarkBlue"/>127 <button id="removeFepButton" label="Remove"128 image="buttonDeselectAll.png" sclass="ccsDarkBlue"/>129 </div>130 </div>131 </groupbox>132 -->133 <separator/>134 </panelchildren>135 </panel>136 </center>137 </borderlayout>138 </west>139 140 <!-- Mittlerer Bereich-->141 34 <center margins="0,5,0,0" autoscroll="true" border="0"> 142 <borderlayout sclass="complex-layout"> 143 <north style="border-width:0px 0px 1px 0px;"> 144 <menubar id="menubar" width="100%" style="margin-top:2px;border:0;"> 145 <menu label="Actions" image="buttonActions.png"> 146 <menupopup> 147 <menuitem label="Clear Results" id="clearResults" 148 image="buttonDelete.png"/> 149 <menuitem label="Export Results to CSV" id="exportResultsCSV" 150 image="buttonExport.png"/> 151 <menuitem label="Export Results to TCF" id="exportResultsTCF" 152 image="buttonExport.png"/> 153 <menuitem label="Export Results as TCF to personal workspace" id="exportResultsPWTCF" 154 image="buttonExport.png"/> 155 </menupopup> 156 </menu> 157 <menu label="Help" image="buttonHelp.png"> 158 <menupopup> 159 <menuitem label="Show Help" id="showHelp" image="buttonHelp.png"/> 160 <menuitem label="About" id="showAbout" 161 image="buttonShowAbout.png"/> 162 </menupopup> 163 </menu> 164 </menubar> 165 </north> 166 <center margins="0,5,0,0" autoscroll="true" border="0" > 167 <panel> 168 <panelchildren id="resultsPanel" > 169 <window id="resultsBox" style="overflow:auto;"> 170 <iframe id="resultsPic" src="help.html" width="80%" height="80%"/> 171 </window> 172 <label value=" " id="searchResultsProgress" style="border-width:0px;margin-left:5px;"/> 173 </panelchildren> 174 </panel> 175 </center> 176 </borderlayout> 35 <div> 36 <div id="aboutDiv"><include src="about.zul"/></div> 37 <div id="soDiv" visible="false"><include src="searchOptions.zul"/></div> 38 <div id="srDiv" visible="false"><include src="searchResults.zul"/></div> 39 <div id="helpDiv" visible="false"><include src="help.zul"/></div> 40 </div> 41 177 42 </center> 178 43 -
SRUAggregator/trunk/src/main/webapp/searchOptions.zul
r2508 r2926 1 <!-- 2 To change this template, choose Tools | Templates 3 and open the template in the editor. 4 --> 5 <!DOCTYPE html> 6 <html> 7 <head> 8 <title></title> 9 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 10 </head> 11 <body> 12 <h3>Welcome to the CLARIN-D Federated Content Search!</h3> 13 </body> 14 </html> 1 <panel apply="eu.clarin.sru.fcs.aggregator.app.SearchOptions"> 2 <panelchildren 3 style="margin-top:10px;margin-left:10px;margin-right:10px;border:0;overflow:auto;"> 4 5 <groupbox mold="3d" id="allCorpora" sclass="ccsLightBlue" 6 contentStyle="border:0" title="Corpora"> 7 <!--<caption label="Corpora" style="border:0;"/>--> 8 9 <div style="text-align:right;"> 10 <button id="selectAll" label="Select All" 11 image="buttonSelectAll.png" sclass="ccsDarkBlue"/> 12 <button id="deselectAll" label="Deselect All" 13 image="buttonDeselectAll.png" sclass="ccsDarkBlue"/> 14 </div> 15 16 <tree id="tree" style="margin-top:2px;"> 17 <treecols sizable="true"> 18 <treecol id="nameCol" label="Resource" style="margin-left:100px;" sort="auto"/> 19 <treecol label="" hflex="min"/> 20 <treecol label="Language" hflex="min" /> 21 <treecol id="instCol" label="Institution" hflex="min" sort="auto"/> 22 <treecol label="Description" /> 23 </treecols> 24 </tree> 25 </groupbox> 26 27 <separator/> 28 <separator/> 29 30 <groupbox mold="3d" id="nHits" sclass="ccsLightBlue" 31 contentStyle="border:0" open="false"> 32 <caption label="Maximum hits" style="border:0;"/> 33 <combobox id="maximumRecordsSelect" width="100%" value="10" 34 style="margin-top:7px;margin-bottom:7px;"> 35 <comboitem label="10" id="maximumHits10"/> 36 <comboitem label="20" id="maximumHits20"/> 37 <comboitem label="30" id="maximumHits30"/> 38 </combobox> 39 </groupbox> 40 41 <separator/> 42 <separator/> 43 44 <groupbox mold="3d" id="sLang" sclass="ccsLightBlue" 45 contentStyle="border:0" open="false"> 46 <caption label="Language" style="border:0;"/> 47 <div style="margin-top:7px;margin-bottom:7px;"> 48 <combobox id="languageSelect" width="100%"> 49 <comboitem label="Any Language" id="anyLanguage"/> 50 </combobox> 51 <div style="margin-top:2px;text-align:right;"> 52 <button id="addLangButton" label="Add" 53 image="buttonSelectAll.png" sclass="ccsDarkBlue"/> 54 <button id="removeLangButton" label="Remove" 55 image="buttonDeselectAll.png" sclass="ccsDarkBlue"/> 56 </div> 57 </div> 58 </groupbox> 59 60 <separator/> 61 <separator/> 62 63 <groupbox mold="3d" id="sTiers" sclass="ccsLightBlue" 64 contentStyle="border:0" open="false"> 65 <caption label="Tier types" style="border:0;"/> 66 <div style="margin-top:7px;margin-bottom:7px;"> 67 <combobox id="tiersSelect" width="100%" value="words"> 68 <comboitem label="full text"/> 69 <comboitem label="words"/> 70 </combobox> 71 <div style="margin-top:2px;text-align:right;"> 72 <button id="addTierButton" label="Add" 73 image="buttonSelectAll.png" sclass="ccsDarkBlue"/> 74 <button id="removeTierButton" label="Remove" 75 image="buttonDeselectAll.png" sclass="ccsDarkBlue"/> 76 </div> 77 </div> 78 </groupbox> 79 80 81 82 <separator/> 83 </panelchildren> 84 </panel> -
SRUAggregator/trunk/src/main/webapp/searchResults.zul
r2508 r2926 1 <!-- 2 To change this template, choose Tools | Templates 3 and open the template in the editor. 4 --> 5 <!DOCTYPE html> 6 <html> 7 <head> 8 <title></title> 9 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 10 </head> 11 <body> 12 <h3>Welcome to the CLARIN-D Federated Content Search!</h3> 13 </body> 14 </html> 1 <vlayout apply="eu.clarin.sru.fcs.aggregator.app.SearchResults"> 2 3 <menubar id="menubar" width="100%" style="margin-top:2px;border:0;"> 4 <menu label="Actions" image="buttonActions.png"> 5 <menupopup> 6 <menuitem label="Clear Results" id="clearResults" 7 image="buttonDelete.png"/> 8 <menuitem label="Export Results to CSV" id="exportResultsCSV" 9 image="buttonExport.png"/> 10 <menuitem label="Export Results to TCF" id="exportResultsTCF" 11 image="buttonExport.png"/> 12 <menuitem label="Export Results as TCF to personal workspace" id="exportResultsPWTCF" 13 image="buttonExport.png"/> 14 </menupopup> 15 </menu> 16 <menu label="Help" image="buttonHelp.png"> 17 <menupopup> 18 <menuitem label="Show Help" id="showHelp" image="buttonHelp.png"/> 19 <menuitem label="About" id="showAbout" 20 image="buttonShowAbout.png"/> 21 </menupopup> 22 </menu> 23 </menubar> 24 25 <panel> 26 <panelchildren id="resultsPanel" > 27 <window id="resultsBox" style="overflow:auto;"> 28 <div style="margin:30px;">To get the results, please enter a keyword into the search fieled above, e.g. Elephant, and press the search button.</div> 29 </window> 30 <label value=" " id="searchResultsProgress" style="border-width:0px;margin-left:5px;"/> 31 </panelchildren> 32 </panel> 33 </vlayout> -
SRUAggregator/trunk/src/main/webapp/tree-test.zul
r2508 r2926 1 < !--2 To change this template, choose Tools | Templates 3 and open the template in the editor. 4 --> 5 <!DOCTYPE html>6 <html>7 <head>8 <title></title>9 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">10 </head>11 <body>12 <h3>Welcome to the CLARIN-D Federated Content Search!</h3>13 </body>14 </ html>1 <?xml version="1.0" encoding="utf-8"?> 2 <?page title="CLARIN-D Federated Content Search"?> 3 <zk> 4 <window contentStyle="background:white;" height="100%" 5 apply="eu.clarin.sru.fcs.aggregator.app.Treetest"> 6 <vlayout> 7 <div align="center"> 8 test1 9 </div> 10 <div align="center"> 11 test2 12 </div> 13 </vlayout> 14 </window>
Note: See TracChangeset
for help on using the changeset viewer.